Как обновить ограничения на основе пользовательского ввода - PullRequest
0 голосов
/ 29 марта 2019

У меня есть вид контроллера представления с 3 секциями столбца (по умолчанию это ноги, aView, bView и cView). Пользователь может переключать его между 2 и 3 в меню настроек, которое отображается модально на том же экране.

Я пытаюсь сделать так, чтобы столбцы занимали одинаковое пространство на экране, поэтому, когда есть 3 столбца, каждый из них занимает примерно 1/3 ширины (игнорируя заполнение), а когда их 2, они каждый занимает примерно 1/2.

Мой текущий метод заключается в установке некоторых ограничений, которые всегда активны, а затем для тех, которые меняются в зависимости от количества столбцов, с помощью оператора if. Я пробовал некоторые варианты layoutIfNeeded(), removeConstraints и другие, но не совсем уверен, как их реализовать.

Для пояснения по коду xView - это представление столбца, которое содержит xTitle и xTextView. Также есть mainButton над текстовыми представлениями и button1 под текстовыми представлениями. Все это существует в настройках contentView и scrollView.


let sidePadding: CGFloat = 15


func placeViews() { // run in viewWillAppear

        let alwaysConstraints = [
            aView.topAnchor.constraint(equalTo: mainButton.bottomAnchor, constant: 25),
            aView.leftAnchor.constraint(equalTo: contentView.leftAnchor, constant: sidePadding),
            aView.rightAnchor.constraint(equalTo: bView.leftAnchor),
            bView.topAnchor.constraint(equalTo: aView.topAnchor),
            bView.bottomAnchor.constraint(equalTo: aView.bottomAnchor),
            aTitle.topAnchor.constraint(equalTo: aView.topAnchor),
            bTitle.topAnchor.constraint(equalTo: aTitle.topAnchor),
            aTitle.centerXAnchor.constraint(equalTo: aView.centerXAnchor),
            bTitle.centerXAnchor.constraint(equalTo: bView.centerXAnchor),
            aTextView.topAnchor.constraint(equalTo: aTitle.bottomAnchor, constant: 25),
            bTextView.topAnchor.constraint(equalTo: aTextView.topAnchor),
            aTextView.bottomAnchor.constraint(equalTo: aView.bottomAnchor),
            bTextView.bottomAnchor.constraint(equalTo: aTextView.bottomAnchor),
            aTextView.centerXAnchor.constraint(equalTo: aView.centerXAnchor),
            bTextView.centerXAnchor.constraint(equalTo: bView.centerXAnchor),
            aTextView.widthAnchor.constraint(equalTo: aView.widthAnchor),
            bTextView.widthAnchor.constraint(equalTo: bView.widthAnchor),
            bView.widthAnchor.constraint(equalTo: aView.widthAnchor),

            // Restrict buttons to leg views
            button1.heightAnchor.constraint(equalToConstant: buttonHeight),
            button1.leftAnchor.constraint(equalTo: contentView.leftAnchor, constant: 20),
            button1.rightAnchor.constraint(equalTo: contentView.rightAnchor, constant: -20),
            button1.topAnchor.constraint(equalTo: aView.bottomAnchor, constant: 40),

            // Restrict button to bottom
            button1.bottomAnchor.constraint(equalTo: contentView.bottomAnchor, constant: -20)
        ]




        let twoLegConstraints = [
            aView.widthAnchor.constraint(equalToConstant: (view.frame.width - (sidePadding * 2) / 2)),
            bView.rightAnchor.constraint(equalTo: contentView.rightAnchor, constant: -sidePadding),
        ]

        let threeLegConstraints = [
            aView.widthAnchor.constraint(equalToConstant: (view.frame.width - (sidePadding * 2)) / 3),
            bView.rightAnchor.constraint(equalTo: cView.leftAnchor),
            cView.rightAnchor.constraint(equalTo: contentView.rightAnchor, constant: -sidePadding),
            cView.topAnchor.constraint(equalTo: aView.topAnchor),
            cView.bottomAnchor.constraint(equalTo: aView.bottomAnchor),
            cTitle.topAnchor.constraint(equalTo: aTitle.topAnchor),
            cTitle.centerXAnchor.constraint(equalTo: cView.centerXAnchor),
            cTextView.topAnchor.constraint(equalTo: aTextView.topAnchor),
            cTextView.bottomAnchor.constraint(equalTo: aTextView.bottomAnchor),
            cTextView.centerXAnchor.constraint(equalTo: cView.centerXAnchor),
            cTextView.widthAnchor.constraint(equalTo: cView.widthAnchor),
            cView.widthAnchor.constraint(equalTo: aView.widthAnchor),
        ]





        NSLayoutConstraint.activate(alwaysConstraints)

        if legs == 2 {
            cView.isHidden = true
            NSLayoutConstraint.activate(twoLegConstraints)
        } else if legs == 3 {
            cView.isHidden = false
            NSLayoutConstraint.activate(threeLegConstraints)
        }
    }

На данный момент экран начинается с 3 по умолчанию, и он работает отлично (каждый ~ 1/3 ширины экрана). Затем пользователь может переключить его на 2, и он снова отлично работает (каждый ~ 1/2 ширины экрана). Затем переключение обратно на 3, первые два не меняются вообще, а третий столбец появляется в правом краю экрана.

1 Ответ

1 голос
/ 29 марта 2019

Используйте представление стека с distribution = .fillEqually. Он позаботится о макете и ограничениях автоматически, когда вы установите свойство isHidden любого из ваших представлений.

...