Swift UI: 在iOS 13上,UIHostingController.view不适合内容视图大小。

6

iOS 13 iOS 14

我希望根据通信结果更新Swift UI视图。 但是在iOS 13上,UIHostingController.view与rootView大小不匹配。 当我尝试使用下面的示例代码时,同样的事情发生了。 我想将自适应大小的SwiftUI View添加到UIStackView中,但是由于这个问题,SwiftUI View会重叠在前一个和后一个视图上。 我该如何避免这个问题?

class ViewController: UIViewController {

    override func viewDidLoad() {
        super.viewDidLoad()
        
        let object = SampleObject()
        let sampleView = SampleView(object: object)
        let hosting = UIHostingController(rootView: sampleView)
        hosting.view.backgroundColor = UIColor.green
        addChild(hosting)
        view.addSubview(hosting.view)
        hosting.view.translatesAutoresizingMaskIntoConstraints = false
        hosting.view.leadingAnchor.constraint(equalTo: view.leadingAnchor).isActive = true
        hosting.view.trailingAnchor.constraint(equalTo: view.trailingAnchor).isActive = true
        hosting.view.topAnchor.constraint(equalTo: view.topAnchor).isActive = true
        hosting.didMove(toParent: self)
        
        DispatchQueue.main.asyncAfter(deadline: .now() + 1.0) {
            object.test()
        }
    }
}


struct SampleView: View {
    @ObservedObject var object: SampleObject
    
    var body: some View {
        VStack {
            Text("test1").background(Color.blue)
            Text("test2").background(Color.red)
            if object.state.isVisibleText {
                Text("test2").background(Color.gray)
            }
        }
        .padding(32)
        .background(Color.yellow)
    }
}


final class SampleObject: ObservableObject {
    struct ViewState {
        var isVisibleText: Bool = false
    }
    
    @Published private(set) var state = ViewState()
    
    func test() {
        state.isVisibleText = true
    }
}

如果将子视图添加到UIStackView中,如下所示,在iOS13中Swift UI View的高度将不会改变。 enter image description here iOS13(不正确) enter image description here iOS14(正确) enter image description here
2个回答

4

您尚未设置底部锚点,请添加此行。

hosting.view.bottomAnchor.constraint(equalTo: view.bottomAnchor).isActive = true

另一种简单的方法是将框架设置为承载控制器视图并删除限制。

class ViewController: UIViewController {

    override func viewDidLoad() {
        super.viewDidLoad()
        
        let object = SampleObject()
        let sampleView = SampleView(object: object)
        let hosting = UIHostingController(rootView: sampleView)
        hosting.view.frame = UIScreen.main.bounds //<---here
        hosting.view.backgroundColor = UIColor.green
        addChild(hosting)
        view.addSubview(hosting.view)
        hosting.didMove(toParent: self)
        
        DispatchQueue.main.asyncAfter(deadline: .now() + 1.0) {
            object.test()
        }
    }
}

1
通过这种解决方法,屏幕大小和Swift UI视图大小将相同。但是我希望Swift UI视图的大小是自适应的。 - 野瀬田 裕樹
你能添加一个你想要的图片吗? - Raja Kishan
我想让它看起来像附加的iOS 14图片。https://i.stack.imgur.com/Q2SUq.jpg - 野瀬田 裕樹
我添加了描述和屏幕截图,请检查。 - 野瀬田 裕樹
@RajaKishan 是完全正确的 - 你必须添加顶部 + 底部 + 左侧 + 右侧的约束。 - Murlakatam
显示剩余3条评论

1

仅适用于iOS 13

尝试以下操作:

每次视图大小更改时,调用此函数:

sampleView.view.removeFromSuperview()
let sampleView = SampleView(object: object)
let hosting = UIHostingController(rootView: sampleView)
view.addArrangedSubview(hosting.view)

1
是的,我没有提到,但我已经用那种方式修复了它。 - 野瀬田 裕樹

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接