上篇文章说的tableViewCell
的问题,其实不是,是我VFL
的语法写错了,下面请看下这段代码:
//设置autoLayout
NSDictionary *viewsDictionary = @{@"titleLabel":self.titleLabel, @"subLabel":self.subLabel, @"bgScrollView":self.bgScrollView};
//约束1 横向 Horizontal
[self.contentView addConstraints:
[NSLayoutConstraint constraintsWithVisualFormat:@"H:|-10-[titleLabel]|"
options:0
metrics:nil
views:viewsDictionary]];
[self.contentView addConstraints:
[NSLayoutConstraint constraintsWithVisualFormat:@"H:|-10-[subLabel]|"
options:0
metrics:nil
views:viewsDictionary]];
[self.contentView addConstraints:
[NSLayoutConstraint constraintsWithVisualFormat:@"H:|[bgScrollView]|"
options:0
metrics:nil
views:viewsDictionary]];
//约束2 纵向 Vertical
NSString *formatV = @"V:|-2-[titleLabel(28)]-[subLabel(15)]-4-[bgScrollView]|";
[self.contentView addConstraints:
[NSLayoutConstraint constraintsWithVisualFormat:formatV
options:0
metrics:nil
views:viewsDictionary]];
第一句代码是和
NSDictionary *viewsDictionary = NSDictionaryOfVariableBindings(view);
一样的,但是用NSDictionary *viewsDictionary = NSDictionaryOfVariableBindings(view);
会有括号里面传属性crash的问题,原因就是self.
。
解释下代码实现的效果
titleLabel
距离父视图左边10
点,右边和父视图对齐。
subLabel
距离父视图左边10
点,右边和父视图对齐。
bgScrollView
和父视图等宽。
titleLabel
距离父视图上边2
点高度为28
,下边和subLabel
上边对齐,subLabel
高度为15
,和bgScrollView
距离4
点,bgScrollView
和父视图下边对齐。
这段代码看起来没有问题,但是会报错。
Unable to simultaneously satisfy constraints.
Probably at least one of the constraints in the following list is one you don't want. Try this: (1) look at each constraint and try to figure out which you don't expect; (2) find the code that added the unwanted constraint or constraints and fix it. (Note: If you're seeing NSAutoresizingMaskLayoutConstraints that you don't understand, refer to the documentation for the UIView property translatesAutoresizingMaskIntoConstraints)
(
"<NSLayoutConstraint:0x7ff2ec18d060 V:|-(2)-[UILabel:0x7ff2ec1b9d10'\U4e94\U9053\U53e3\U5546\U5708'] (Names: '|':UITableViewCellContentView:0x7ff2ec192230 )>",
"<NSLayoutConstraint:0x7ff2ec19f560 V:[UILabel:0x7ff2ec1b9d10'\U4e94\U9053\U53e3\U5546\U5708'(28)]>",
"<NSLayoutConstraint:0x7ff2ec19f5b0 V:[UILabel:0x7ff2ec1b9d10'\U4e94\U9053\U53e3\U5546\U5708']-(NSSpace(8))-[UILabel:0x7ff2ec191cb0'\U534e\U6e05\U5609\U56ed | \U84dd\U65d7\U8425 | \U9038\U6210\U4e1c\U82d1\n']>",
"<NSLayoutConstraint:0x7ff2ec19f600 V:[UILabel:0x7ff2ec191cb0'\U534e\U6e05\U5609\U56ed | \U84dd\U65d7\U8425 | \U9038\U6210\U4e1c\U82d1\n'(15)]>",
"<NSLayoutConstraint:0x7ff2ec19f650 V:[UILabel:0x7ff2ec191cb0'\U534e\U6e05\U5609\U56ed | \U84dd\U65d7\U8425 | \U9038\U6210\U4e1c\U82d1\n']-(4)-[UIScrollView:0x7ff2ec19e6e0]>",
"<NSLayoutConstraint:0x7ff2ec19f6a0 V:[UIScrollView:0x7ff2ec19e6e0]-(0)-| (Names: '|':UITableViewCellContentView:0x7ff2ec192230 )>",
"<NSLayoutConstraint:0x7ff2e9f02660 'UIView-Encapsulated-Layout-Height' V:[UITableViewCellContentView:0x7ff2ec192230(49.5)]>"
)
Will attempt to recover by breaking constraint
<NSLayoutConstraint:0x7ff2ec19f5b0 V:[UILabel:0x7ff2ec1b9d10'xxxxx']-(NSSpace(8))-[UILabel:0x7ff2ec191cb0'xxxxx | xxxxx | xxxxx
']>
Make a symbolic breakpoint at UIViewAlertForUnsatisfiableConstraints to catch this in the debugger.
The methods in the UIConstraintBasedLayoutDebugging category on UIView listed in <UIKit/UIView.h> may also be helpful.
错误是这样的:
没有办法同时满足所有约束.
下面列出的约束中,至少有一个是你不想要的.试着这么做:(1)查看每个约束,然后想明白哪个你不需要(2)找到你不想添加约束的代码,修改下.
Unable to simultaneously satisfy constraints.
Probably at least one of the constraints in the following list is one you don't want. Try this: (1) look at each constraint and try to figure out which you don't expect; (2) find the code that added the unwanted constraint or constraints and fix it. (Note: If you're seeing NSAutoresizingMaskLayoutConstraints that you don't understand, refer to the documentation for the UIView property translatesAutoresizingMaskIntoConstraints)
是这一个约束冲突了:
"<NSLayoutConstraint:0x7ff2e9f02660 'UIView-Encapsulated-Layout-Height' V:[UITableViewCellContentView:0x7ff2ec192230(49.5)]>"
UITableViewCellContentView
压缩的高度冲突了?
最后找到了@"V:|-2-[titleLabel(28)]-[subLabel(15)]-4-[bgScrollView]|"
这里。
原因在于[titleLabel(28)]-[subLabel(15)]
中间的-
,起初我认为的-10-
这样才会有效果,单独的-
相当于-0-
,这样错了。
-
在[titleLabel(28)]-[subLabel(15)]
是默认8
点距离,相当于-8-
,在|-[titleLabel]-|
,默认10
点距离,相当于|-10-[titleLabel]-10-|
。有资料说是20
点,但我自己试的是10
点,不过这不是问题。以后用每次都会加上-8-
或者|-10-[titleLabel]-10-|
,这样也好维护。
上面的代码改成[titleLabel(28)][subLabel(15)]
就解决问题了,原因是本身的约束已经满足确定位置的条件,bgScrollView
和下边对齐,但是再加上-
,就多出8
点高度,这样就冲突了。
或者我这样写 @"V:|-2-[titleLabel(28)]-[subLabel(15)]-4-[bgScrollView(213)]"
也不会报错,但是UI的位置会因为-
不正确。
所以写VFL
之前一定要充分学习研究VFL
语法,比如scrollview
、label
、imageView
就需要注意点,这样可以避免很多不必要的问题。
当然一开始写VFL
一般都会遇到各种奇葩问题的,重要的是不能慌不能急,尝试各种解决方法,尤其>=
、<=
、@
用起来效果会很好,也能避免很多问题。
比如:|-10-[view(40)]|
,这样写会有问题吗?有的,view
距离父视图左边10
点,宽度40
,和父视图右边对齐。这样一看就冲突了,设置了左边距和宽度,再设置右边距为0
就冲突了。
可以这么写|-10-[view(40)]
或者|-10-[view(40)]->=0-|
或者|-10-[view]|
。