Swift - 以编程方式更改约束

时间:2017-08-24 03:26:04

标签: swift uicollectionview constraints

我正在尝试展示' &安培; '隐藏'通过以编程方式操纵约束的集合视图。

我的应用程序是用代码编写的,没有使用故事板或@IBOutlets。

第一次按下按钮时,集合视图会按预期正确显示。

第二次按下按钮时,集合视图就会停留在原位并且不会隐藏。

openMenu代码中的print语句确认正在调用每个约束块。即:我收到控制台消息,以便打开'并且'关闭'。

我没有创建集合视图的问题,只是以编程方式设置约束不会关闭菜单。

我的代码如下......

override func viewDidLoad() {
    super.viewDidLoad()

    navigationController?.isNavigationBarHidden = false

    view.backgroundColor = .white

    view.addSubview(bgImageView)

    view.addSubview(myListCV)
}

lazy var myListCV: UICollectionView = {

    let myListLayout = UICollectionViewFlowLayout()
    myListLayout.itemSize = CGSize(width: 200, height: 40)
    myListLayout.minimumLineSpacing = 1
    myListLayout.sectionHeadersPinToVisibleBounds = true

    let myListView = UICollectionView(frame: .zero, collectionViewLayout: myListLayout)
    myListView.translatesAutoresizingMaskIntoConstraints = false
    myListView.delegate = self
    myListView.dataSource = self

    myListView.bounces = false
    myListView.alwaysBounceVertical = false
    myListView.showsVerticalScrollIndicator = true
    myListView.backgroundColor = UIColor(r: 203, g: 203, b: 203)

    return myListView
}()

var menuShowing = false

func openMenu() {

    if (menuShowing) {
        print("closed")
        myListCV.leftAnchor.constraint(equalTo: view.rightAnchor).isActive = true
        myListCV.topAnchor.constraint(equalTo: view.topAnchor, constant: 64).isActive = true
        myListCV.rightAnchor.constraint(equalTo: view.rightAnchor).isActive = true
        myListCV.bottomAnchor.constraint(equalTo: view.bottomAnchor).isActive = true

    } else {
        print("open")
        myListCV.leftAnchor.constraint(equalTo: view.rightAnchor, constant: -200).isActive = true
        myListCV.topAnchor.constraint(equalTo: view.topAnchor, constant: 64).isActive = true
        myListCV.rightAnchor.constraint(equalTo: view.rightAnchor).isActive = true
        myListCV.bottomAnchor.constraint(equalTo: view.bottomAnchor).isActive = true
    }

    menuShowing = !menuShowing
}

1 个答案:

答案 0 :(得分:1)

上述代码的问题在于,每次用户打开或关闭该部分时,您都会不断设置约束,因此,根据用户执行此操作的次数,您最终将获得数百个限制条件。不需要。

您应该做的是设置默认状态的约束,我假设在此实例中已关闭,并存储您希望在属性中更改的约束。然后,您只需调整此约束的常量即可显示/隐藏菜单。

e.g。

private var myListCVLeftConstraint: NSLayoutConstraint?

override func viewDidLoad() {
    super.viewDidLoad()

    navigationController?.isNavigationBarHidden = false

    view.backgroundColor = .white

    view.addSubview(bgImageView)

    self.configMyListCV()
}

lazy var myListCV: UICollectionView = {

    let myListLayout = UICollectionViewFlowLayout()
    myListLayout.itemSize = CGSize(width: 200, height: 40)
    myListLayout.minimumLineSpacing = 1
    myListLayout.sectionHeadersPinToVisibleBounds = true

    let myListView = UICollectionView(frame: .zero, collectionViewLayout: myListLayout)
    myListView.translatesAutoresizingMaskIntoConstraints = false
    myListView.delegate = self
    myListView.dataSource = self

    myListView.bounces = false
    myListView.alwaysBounceVertical = false
    myListView.showsVerticalScrollIndicator = true
    myListView.backgroundColor = UIColor(r: 203, g: 203, b: 203)

    return myListView
}()

var menuShowing = false

private func configMyListCV() -> Void {

    view.addSubview(myListCV)

    self.myListCV.topAnchor.constraint(equalTo: view.topAnchor, constant: 64).isActive = true
    self.myListCV.rightAnchor.constraint(equalTo: view.rightAnchor).isActive = true
    self.myListCV.bottomAnchor.constraint(equalTo: view.bottomAnchor).isActive = true

    self.myListCVLeftConstraint = myListCV.leftAnchor.constraint(equalTo: view.rightAnchor)
    self.myListCVLeftConstraint.isActive = true
}

func openMenu() {

    if (menuShowing) {

        self.myListCVLeftConstraint?.constant = 0.0

    } else {

        self.myListCVLeftConstraint?.constant = -200.0

    }

    menuShowing = !menuShowing
}

这适用于这个简单的用户案例;但是如果你将来做更深入的任何事情,我建议在视图上设置多个约束,并根据需要简单地禁用/启用所需的约束。