Understanding multiplier in auto layout to use relative positioning

十年热恋 提交于 2019-11-28 16:42:55

There are a couple ways to do this. In the simplest case, you've already almost got it: if you want the horizontal boundaries to be at 10% and 90%, then you need to specify both constraints with respect to the trailing edge of the superview -- so Subview.Trailing locks to Superview.Trailing with a multiplier of 0.9, as you say, but then Subview.Leading also locks to Superview.Trailing, just with a multiplier of 0.1:

(and similarly for top / bottom)

On the other hand, the case you mention at the end is a little more complicated: "specifying a label's top should lie 10% beneath another label's bottom." For that you probably won't be able to use fixed percentage insets like the previous case. Instead, you can create an invisible spacer view between them: add a constraint with Spacer.Height = 0.1 * Superview.Height and then attach it between the two labels. (You can also handle the previous case with these spacer views, but for that case it isn't really necessary.)

In my opinion, "You can't have a negative multiplier I don't think, and I don't believe a value greater than 1 does anything when constant is 0" exposed your comprehending deviation.

The rule underneath the hood is just a linear equation:

FirstItem.Attribute1 = (SecondItem.Attribute2 * Multiplier) + Constant

All measured in points. As you see, multiplier(a property of NSLayoutConstraint) is not the multiplier of constant. Follow the equation, what you don't understand will be clear.

As to your specific example, @Archaeopterasa presented a great solution, another is shown below:

Based on the fact you know how to do bottom and trailing, I suppose you've done these two. Then add another two constraints, the effect will be what you want:

At last, if you want to specify a label's top lie 10% beneath another label's bottom, it seems that you cannot implement it without writing a line of code. You have to use code to set the constant of the NSLayoutConstraint object connecting the FirstItem and the SecondItem after the superview's height is known in runtime.

Firstly, control drag from one label to the other and choose "Vertical Spacing".(Or you can do this in other ways)

Secondly, a referencing outlet is needed:

@IBOutlet weak var tenPercentOfSuperview: NSLayoutConstraint!

Then, do this in a appropriate place(for example, in viewDidLoad())

let heightOfSuperview = self.view.bounds.height
tenPercentOfSuperview.constant = heightOfSuperview * 0.1

Everything is OK now.

If you want to know more about this topic, Apple's document is recommended:https://developer.apple.com/library/ios/recipes/xcode_help-IB_auto_layout/chapters/EditingConstraintAttributesintheAttributesInspector.html

Here's the

INCREDIBLY SIMPLE

way to do it.

Just add 'helper' or "measure' views:

The 'calculation helper' views are yellow in the example.

The general technique is so simple and obvious - it doesn't need any explantion, you can get it from the image.

It's one of those "elephant in the room" things they "don't teach you about" in iOS. But it is used constantly in all layouts.

(Indeed, Apple should have made a special UIView subclass "measures" for exactly this purpose - and indeed, many large teams do just that, with the obvious features.)

Notice icon #1 is centered on the right end of the "View 1/4" helper view.

Notice icon #3 is centered on the left end of the "View 3/4" helper view.

You're done, have a Chardonnay.

Conveniently, in the helper views, just set the multiplier to anything you want, depending on the feel wanted. It's incredibly easy to then change those in your code, use IBInspectable, animate, and so on and on...

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!