NSLayoutConstraints code to center the view and maintain its aspect ratio

I would like my subview to be a 16: 9 rectangle centered at the top of the add-in. In other words, I would like to:

  • be as wide as the add-in, but not more than 400 pixels (the user interface can rotate in landscape orientation),
  • center horizontally, if it is narrower than supervision,
  • It has a top attached to it from top to top, and
  • change the height to maintain a 16: 9 aspect ratio.

This code almost does this, except it is difficult for me to comply with horizontal restrictions, rather than overloading or holding back ...

- (void)viewDidLoad { [super viewDidLoad]; // Do any additional setup after loading the view. UIView *contentView = [[UIView alloc] init]; contentView.backgroundColor = [UIColor redColor]; [self.view addSubview:contentView]; contentView.translatesAutoresizingMaskIntoConstraints = NO; NSDictionary *views = NSDictionaryOfVariableBindings(contentView); NSMutableArray *constraints = [NSMutableArray array]; // this layout string is more like 'wishful coding'. I don't see why it wouldn't work // but clearly this one is the problem [constraints addObjectsFromArray:[NSLayoutConstraint constraintsWithVisualFormat:@"H:|-(>=0)-[contentView(<=400)-(>=0)-]" options:0 metrics:0 views:views]]; // this centering constraint below almost does the job, but doesn't give me a way // to specify width, changing the one above to just @"H:[contentView(<=400)]" // doesn't work either [constraints addObject: [NSLayoutConstraint constraintWithItem:contentView attribute:NSLayoutAttributeCenterY relatedBy:NSLayoutRelationEqual toItem:self.view attribute:NSLayoutAttributeCenterY multiplier:1.f constant:0.f]]; // 9:16 works fine, I think [constraints addObject: [NSLayoutConstraint constraintWithItem:contentView attribute:NSLayoutAttributeHeight relatedBy:NSLayoutRelationEqual toItem:contentView attribute:NSLayoutAttributeWidth multiplier:9.0/16.0 constant:0.0]]; // pin the tops works fine, I think [constraints addObjectsFromArray: [NSLayoutConstraint constraintsWithVisualFormat:@"V:|-0-[contentView]" options:0 metrics:0 views:views]]; [self.view addConstraints:constraints]; } 
+6
source share
2 answers

If you want to center the red square horizontally, then you want to equate them to "CenterX", not CenterY. Thus, the restriction should look like this:

 [NSLayoutConstraint constraintWithItem:contentView attribute:NSLayoutAttributeCenterX relatedBy:NSLayoutRelationEqual toItem:self.view attribute:NSLayoutAttributeCenterX multiplier:1.f constant:0.f]]; 

Then, with the first restrictions, the restrictions that you have there are ambiguous, since there is more than one way to satisfy the field >=0 on each side and <=400 in width. It would be best to say exactly what you said in your question, namely: you need a width that should be <= 400, and you would , like , field 0, if possible.

So something like this:

 [NSLayoutConstraint constraintsWithVisualFormat:@"H:|-( 0@900 )-[contentView(<=400)]-( 0@900 )-|" options:0 metrics:0 views:views]]; 

I believe you want what you want?

+14
source

Sometimes, I think, there is one more solution, I copied my solution here.

If you want horizontal alignment, just use it [parentView addConstraint:[NSLayoutConstraint constraintWithItem:subView attribute:NSLayoutAttributeCenterX relatedBy:NSLayoutRelationEqual toItem:parentView attribute:NSLayoutAttributeCenterX multiplier:1 constant:0]];

If you want vertical alignment, just use it [parentView addConstraint:[NSLayoutConstraint constraintWithItem:subView attribute:NSLayoutAttributeCenterY relatedBy:NSLayoutRelationEqual toItem:parentView attribute:NSLayoutAttributeCenterY multiplier:1 constant:0]];

And this solution works for me, I hope that I pass it on to someone else.

0
source

Source: https://habr.com/ru/post/951686/


All Articles