Подтвердить что ты не робот

IOS - Позиционирование UIView в центре наблюдения с использованием Auto Layout программно

Как программно установить UIView в центр его просмотра с помощью Auto Layout?

UIButton* viewObj = [UIButton buttonWithType:UIButtonTypeRoundedRect];
[viewObj setTranslatesAutoresizingMaskIntoConstraints:NO];
[viewObj setBackgroundColor:[UIColor greenColor]];
[self.view addSubview:viewObj];

NSLayoutConstraint* cn = [NSLayoutConstraint constraintWithItem:viewObj
                                                      attribute:NSLayoutAttributeCenterX
                                                      relatedBy:NSLayoutRelationEqual
                                                         toItem:self.view
                                                      attribute:NSLayoutAttributeCenterX 
                                                     multiplier:1.0
                                                       constant:0];
[self.view addConstraint:cn];
cn = [NSLayoutConstraint constraintWithItem:viewObj 
                                  attribute:NSLayoutAttributeCenterY
                                  relatedBy:NSLayoutRelationEqual 
                                     toItem:self.view
                                  attribute:NSLayoutAttributeCenterY
                                 multiplier:1.0
                                   constant:0];
[self.view addConstraint:cn];

Этот код работает для меня для UIButton, но мне не удается заменить первую строку чем-то, что работает для UIView.

Я пробовал

UIView* viewObj = [UIView alloc] initWithFrame:CGRectZero];

но представление не отображается в симуляторе.

Любые предложения?

Спасибо!

4b9b3361

Ответ 1

Поскольку вы задали этот вопрос в контексте использования автоматического макета, здесь проблема заключается в том, что UIButton имеет собственный размер (передается через метод intrinsicContentSize), который предоставляет автоматическую компоновку информацию о ширине и высоте, но UIView обычно делает не. Поэтому вам нужно добавить дополнительные ограничения, связанные с шириной и высотой.

Если вы хотите, чтобы ваш UIView был установленным размером (скажем, 200x200), вы могли бы добавить следующие строки:

cn = [NSLayoutConstraint constraintWithItem:viewObj 
                                  attribute:NSLayoutAttributeHeight
                                  relatedBy:NSLayoutRelationEqual 
                                     toItem:nil
                                  attribute:NSLayoutAttributeNotAnAttribute 
                                 multiplier:1
                                   constant:200];
[viewObj addConstraint:cn];

cn = [NSLayoutConstraint constraintWithItem:viewObj
                                  attribute:NSLayoutAttributeWidth
                                  relatedBy:NSLayoutRelationEqual
                                     toItem:nil
                                  attribute:NSLayoutAttributeNotAnAttribute 
                                 multiplier:1 
                                   constant:200];
[viewObj addConstraint: cn];

Обратите внимание, что аргумент toItem: nil, а второй атрибут NSLayoutAttributeNotAnAttribute, потому что вы не указываете ширину и высоту относительно чего-либо еще. Если вы хотите, чтобы высота и ширина подвыбора были относительно надзора (скажем, 0,5), вы могли бы сделать это:

cn = [NSLayoutConstraint constraintWithItem:viewObj
                                  attribute:NSLayoutAttributeHeight
                                  relatedBy:NSLayoutRelationEqual
                                     toItem:self.view
                                  attribute:NSLayoutAttributeHeight 
                                 multiplier:0.5 
                                   constant:0];
[self.view addConstraint:cn];
cn = [NSLayoutConstraint constraintWithItem:viewObj
                                  attribute:NSLayoutAttributeWidth
                                  relatedBy:NSLayoutRelationEqual
                                     toItem:self.view
                                  attribute:NSLayoutAttributeWidth
                                 multiplier:0.5
                                   constant:0];
[self.view addConstraint: cn];

Ответ 2

UIButton, UIImageView, UIlabel и UITextField могут автоматически устанавливать свой размер в соответствии с их свойствами содержимого. Ширина и высота a UIImageView задаются символом UIImage, который может содержать. Размер a UIlabel будет зависеть от его текста. Ширина и высота UIButton определяются заголовком и изображением, которое у него есть (вы можете узнать больше об этом с помощью Внутренний размер содержимого).

Следовательно, если вы хотите центрировать UIButton, a UIlabel, a UITextField или UIImageView внутри UIView с автоматическим макетом, почти во всех случаях вам не нужно создавать ограничения для их ширины и высоты. Вам просто нужно установить для них горизонтальные и вертикальные ограничения.

Однако при автоматической компоновке UIView, у которой нет подзаголовков, не может полагаться ни на что, чтобы установить свой размер, если вы не предоставите ему какие-либо произвольные ограничения ширины и высоты. И в соответствии с вашими потребностями вы можете решить это тремя способами.


Стиль чистого макета

Здесь мы устанавливаем ширину и высоту нашего UIView непосредственно в качестве ограничений макета:

override func viewDidLoad() {
    super.viewDidLoad()

    let newView = UIView()
    newView.backgroundColor = .redColor()
    newView.translatesAutoresizingMaskIntoConstraints = false
    view.addSubview(newView)

    // Auto layout code using anchors (iOS9+)
    let horizontalConstraint = newView.centerXAnchor.constraintEqualToAnchor(view.centerXAnchor)
    let verticalConstraint = newView.centerYAnchor.constraintEqualToAnchor(view.centerYAnchor)
    let widthConstraint = newView.widthAnchor.constraintEqualToAnchor(nil, constant: 100)
    let heightConstraint = newView.heightAnchor.constraintEqualToAnchor(nil, constant: 100)
    NSLayoutConstraint.activateConstraints([horizontalConstraint, verticalConstraint, widthConstraint, heightConstraint])
}

Стиль маскировки авторезистировки

Здесь мы инициализируем наш UIView с его шириной и высотой, делаем его центр и его центр супервизора равными и создаем несколько масок авторезистировки. Затем мы просим UIKit перевести эти авторезистирующие маски в автоматические ограничения макета:

override func viewDidLoad() {
    super.viewDidLoad()

    let newView = UIView(frame: CGRect(x: 0.0, y: 0.0, width: 100.0, height: 100.0))
    newView.backgroundColor = .redColor()

    newView.center = CGPointMake(view.bounds.midX, view.bounds.midY)
    newView.autoresizingMask = [.FlexibleLeftMargin, .FlexibleRightMargin, .FlexibleTopMargin, .FlexibleBottomMargin]

    newView.translatesAutoresizingMaskIntoConstraints = true // default is true
    view.addSubview(newView)
}

Стиль подкласса

Здесь мы создаем подкласс UIView и переопределяем его метод intrinsicContentSize() (объявление), чтобы он возвращал желаемый размер:

import UIKit

class CustomView: UIView {
    override func intrinsicContentSize() -> CGSize {
        return CGSize(width: 100, height: 100)
    }
}

class ViewController: UIViewController {

    override func viewDidLoad() {
        super.viewDidLoad()

        let newView = CustomView()
        newView.backgroundColor = .redColor()
        newView.translatesAutoresizingMaskIntoConstraints = false
        view.addSubview(newView)

        let horizontalConstraint = NSLayoutConstraint(item: newView,
            attribute: .CenterX,
            relatedBy: .Equal,
            toItem: view,
            attribute: .CenterX,
            multiplier: 1,
            constant: 0)
        view.addConstraint(horizontalConstraint)
        let verticalConstraint = NSLayoutConstraint(item: newView,
            attribute: .CenterY,
            relatedBy: .Equal,
            toItem: view,
            attribute: .CenterY,
            multiplier: 1,
            constant: 0)
        view.addConstraint(verticalConstraint)
    }

}