代码之家  ›  专栏  ›  技术社区  ›  kiwisip

iOS 11 UIStackView按比例填充分布会导致奇怪的视图加载动画

  •  6
  • kiwisip  · 技术社区  · 7 年前

    如果我设置:

    stackView.distributon = .fillProportionally 
    

    然后在iOS 11上,当加载包含这个堆栈视图的视图时,我得到了一个非常奇怪的动画(所有子视图——不仅仅是堆栈视图——都从屏幕的顶部或底部飞出)。在较低的iOS版本上,一切正常。如果我将堆栈视图的分布设置为任何其他值,那么一切都很好。

    3 回复  |  直到 7 年前
        1
  •  12
  •   Matt Cline    7 年前

    我想我找到了一个固定电话 self.view.layoutIfNeeded() animations

    import UIKit
    
    class ViewController: UIViewController {
    
        var showB = true
    
        weak var viewB: UIView!
    
        override func viewDidLoad() {
            super.viewDidLoad()
    
            let viewA = UIView()
            viewA.backgroundColor = UIColor.green
    
            let toggleViewBButtonAnimated = UIButton(frame: CGRect(x: 50, y: 150, width: 200, height: 40))
            toggleViewBButtonAnimated.backgroundColor = UIColor.cyan
            toggleViewBButtonAnimated.setTitle("Toggle B (animated)", for: .normal)
            viewA.addSubview(toggleViewBButtonAnimated)
            toggleViewBButtonAnimated.addTarget(self, action: #selector(toggleBButtonTappedAnimated), for: .touchUpInside)
    
    
            let viewB = UIView()
            viewB.backgroundColor = UIColor.orange
            let viewBHeightConstraint = viewB.heightAnchor.constraint(equalToConstant: 200)
            viewBHeightConstraint.priority = 999
            viewBHeightConstraint.isActive = true
            self.viewB = viewB
    
    
            let stackView = UIStackView(arrangedSubviews: [viewA, viewB])
            stackView.axis = .vertical
            stackView.alignment = .fill
            stackView.distribution = .fill
            stackView.translatesAutoresizingMaskIntoConstraints = false
    
            self.view.addSubview(stackView)
    
            stackView.topAnchor.constraint(equalTo: self.view.topAnchor).isActive = true
            stackView.bottomAnchor.constraint(equalTo: self.view.bottomAnchor).isActive = true
            stackView.leadingAnchor.constraint(equalTo: self.view.leadingAnchor).isActive = true
            stackView.trailingAnchor.constraint(equalTo: self.view.trailingAnchor).isActive = true
        }
    
        @IBAction func toggleBButtonTappedAnimated() {
            self.showB = !self.showB
            UIView.animate(withDuration: 0.3,
                           animations: { self.viewB.isHidden = !self.showB; self.view.layoutIfNeeded() }
            )
        }
    }
    

    该控制器设置 UIStackView 它有两个垂直视图,一个绿色的(a)和一个橙色的(B)。点击按钮隐藏/取消隐藏视图B。

    动画 然后,当显示视图B时,它会从屏幕顶部飞入。(当视图B被隐藏时,它会正常隐藏-从屏幕底部向下移动。)

    块,视图B按预期显示-它从屏幕底部出现。

    感谢@g3rv4的回答,为我指明了这个方向!

        2
  •  2
  •   AlexD Cameron Ketcham    7 年前

    对我来说,问题是iOS 11中引入的行为回归,与UIStackView分布类型无关。我尝试了两种基于代码的解决方案,但都没有成功:首先,在容器层次结构上调用layoutifneed;其次,(如另一个类似问题的答案所示)调整视图的内容模式。

        3
  •  1
  •   Sean Howard    7 年前

    今天早上,我在使用转基因种子时遇到了同样的问题。我最终使用了 UIView.performWithoutAnimation { 阻止执行任何操作 UIStackView