UIStackView隐藏/取消隐藏ArrangeSubView问题

时间:2018-05-19 10:51:16

标签: ios swift uiview uistackview

我隐藏并取消隐藏dropDownView(UIView由textfield和button组成),基于Segment控件中的Segment。以下是视图层次结构: -

enter image description here

以下是隐藏/取消隐藏dropDownView的代码: -

 private func animateView(view: UIStackView, toHidden hidden: Bool) {
    UIView.animate(withDuration: 0.25) 
    {
    let firstView = view.arrangedSubviews[0]
    firstView.isHidden = hidden
    }
    }
func segmentValueChanged(_ sender: UISegmentedControl) {
        let segmentSelected = segmentControl.selectedSegmentIndex
        switch segmentSelected {
        case 0:
            animateView(view: mainStackView, toHidden: true)
        case 1:
         animateView(view: mainStackView, toHidden: true)
        case 2:
            animateView(view: mainStackView, toHidden: true)
        case 3:
           animateView(view: mainStackView, toHidden: false)
        default:
            break
        }
    }

我遇到的问题是在更改段超过10-15次后,上述代码停止工作,DropDown View与段控制重叠,我不知道为什么。任何帮助理解这个问题都表示赞赏。

我也已经尝试过了  的 1。 setNeedsLayout,
 2. setNeedsDisplay和
 3.将dropDownView的高度约束优先级降低到999     1000

4 个答案:

答案 0 :(得分:1)

似乎在 completionClosure 中的附加设置 isHidden 修复了该问题(Swift 5 语法):

private func animateView(view: UIStackView, toHidden hidden: Bool) {
    let firstView = view.arrangedSubviews[0]
    UIView.animate(withDuration: 0.25) {
        firstView.isHidden = hidden
        view.layoutIfNeeded()
    } completion {
        firstView.isHidden = hidden
    }
}

答案 1 :(得分:0)

尝试不使用animate函数,因为stackView应该为隐藏和取消隐藏设置动画。添加对隐藏状态的检查,并在必要时进行更改:

func segmentValueChanged(_ sender: UISegmentedControl) {
    let segmentSelected = segmentControl.selectedSegmentIndex
    let dropDown = mainStackView.arrangedSubviews.first!

    switch segmentSelected {
        case 0, 1, 2:
            if !dropDown.isHidden {
                dropDown.isHidden = true
            }
        case 3:
            if dropDown.isHidden {
                dropDown.isHidden = false
            }
        default:
            break
    }

}

答案 2 :(得分:0)

请尝试下面这个。希望能解决你的问题。

private func animateView(view: UIStackView, toHidden hidden: Bool) {
    let firstView = view.arrangedSubviews[0]
    UIView.animate(withDuration: 0.25) {
        firstView.isHidden = hidden
        view.layoutIfNeeded()
    }
}

答案 3 :(得分:0)

以下是我实施的解决方案似乎有效: -

private func animateView(view: UIStackView, toHidden hidden: Bool) {
        if !hidden
        {
          mainStackView.insertArrangedSubview(view, at: 0)
          view.isHidden = true
          UIView.animate(withDuration: 0.25, animations: {
            view.isHidden = false
          })
        } else {
            let firstView = mainStackView.arrangedSubviews[0]
            UIView.animate(withDuration: 0.25, animations: {
                if firstView == view {
                    firstView.isHidden = true
                }
            }, completion: { [weak self] _ in
                if firstView == view {
                    self?.mainStackView.removeArrangedSubview(firstView)
                    firstView.removeFromSuperview()
                }
            })
        }
    }

以编程方式创建DropDown视图(而不是在故事板中创建)并在每次完成时删除它。我没有将这个答案标记为正确的解决方法。我想了解为什么故事板dropDownView在10-15次尝试后失败。