gpt4 book ai didi

uikit - 如何将不在根层次结构中的 SwiftUI View 呈现为 UIImage?

转载 作者:行者123 更新时间:2023-12-03 15:01:25 27 4
gpt4 key购买 nike

假设我有一个简单的 SwiftUI View ,它不是像这样的 ContentView:

struct Test: View {        
var body: some View {
VStack {
Text("Test 1")
Text("Test 2")
}
}
}

如何将此 View 呈现为 UIImage?

我研究了解决方案,例如:
extension UIView {
func asImage() -> UIImage {
let renderer = UIGraphicsImageRenderer(bounds: bounds)
return renderer.image { rendererContext in
layer.render(in: rendererContext.cgContext)
}
}
}

但似乎这样的解决方案只适用于 UIView,而不适用于 SwiftUI View 。

最佳答案

这是对我有用的方法,因为我需要将图像与其他图像放在一起时的大小完全相同。希望对其他人有帮助。
演示:上面的分隔线是 SwiftUI 渲染的,下面是图像(在边框中显示大小)
enter image description here

extension View {
func asImage() -> UIImage {
let controller = UIHostingController(rootView: self)

// locate far out of screen
controller.view.frame = CGRect(x: 0, y: CGFloat(Int.max), width: 1, height: 1)
UIApplication.shared.windows.first!.rootViewController?.view.addSubview(controller.view)

let size = controller.sizeThatFits(in: UIScreen.main.bounds.size)
controller.view.bounds = CGRect(origin: .zero, size: size)
controller.view.sizeToFit()

let image = controller.view.asImage()
controller.view.removeFromSuperview()
return image
}
}

extension UIView {
func asImage() -> UIImage {
let renderer = UIGraphicsImageRenderer(bounds: bounds)
return renderer.image { rendererContext in
// [!!] Uncomment to clip resulting image
// rendererContext.cgContext.addPath(
// UIBezierPath(roundedRect: bounds, cornerRadius: 20).cgPath)
// rendererContext.cgContext.clip()

// As commented by @MaxIsom below in some cases might be needed
// to make this asynchronously, so uncomment below DispatchQueue
// if you'd same met crash
// DispatchQueue.main.async {
layer.render(in: rendererContext.cgContext)
// }
}
}
}


// TESTING
struct TestableView: View {
var body: some View {
VStack {
Text("Test 1")
Text("Test 2")
}
}
}

struct TestBackgroundRendering: View {
var body: some View {
VStack {
TestableView()
Divider()
Image(uiImage: render())
.border(Color.black)
}
}

private func render() -> UIImage {
TestableView().asImage()
}
}

struct TestBackgroundRendering_Previews: PreviewProvider {
static var previews: some View {
TestBackgroundRendering()
}
}

关于uikit - 如何将不在根层次结构中的 SwiftUI View 呈现为 UIImage?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/59330805/

27 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com