我有一个带有两个约束的UILabel。我激活了一个约束,而另一个则禁用了。我有一个禁用第一个约束并激活第二个约束的按钮。然后,当第二次点击时,禁用第二约束并重新激活第一约束。第一次点击此按钮将按预期工作。 UILabel(包括受其约束的所有其他UILabel)将移动到另一个位置。但是,点击按钮将其移回时,布局会中断。 UILabel移至几乎以前的位置,但受其约束的所有其他UILabel保持原样,并且不会移回其原始位置。
这是处理激活约束的功能。
- (void)tapOnce:(UIGestureRecognizer *)gesture
{
if (_constraintLabelOne.isActive) {
[_constraintLabelOne setActive:NO];
[_constraintLabelTwo setActive:YES];
} else {
[_constraintLabelTwo setActive:NO];
[_constraintLabelOne setActive:YES];
}
[self layoutIfNeeded];
}
约束看起来像这样。
_constraintLabelOne = [NSLayoutConstraint constraintWithItem:myLabel
attribute:NSLayoutAttributeTop
relatedBy:NSLayoutRelationEqual
toItem:topView
attribute:NSLayoutAttributeBottom
multiplier:1.0
constant:6];
_constraintLabelTwo = [NSLayoutConstraint constraintWithItem:myLabel
attribute:NSLayoutAttributeTop
relatedBy:NSLayoutRelationEqual
toItem:topView
attribute:NSLayoutAttributeBottom
multiplier:1.0
constant:20];
第一次调用myLabel
之后,其他约束为tapOnce
的标签将停留在第二位置。在myLabel
约束更新之后,为什么他们不回到初始位置?
我在屏幕快照中附有当前行为的图形。蓝色框代表topView
。洋红色框代表myLabel
。第一个屏幕是在调用tapOnce
之前。中间屏幕是在调用tapOnce
一次之后。两次调用tapOnce
后,屏幕将显示在右侧。
答案 0 :(得分:0)
我这样做的方式是将约束之一的priority
设置得较低,这样它是“可选的”,例如UILayoutPriorityDefaultHigh
,甚至更高,例如999。
然后您可以同时激活两个约束,并且优先考虑所需的约束。
要进行设置,请为默认状态设置所需的约束,并为按钮按下状态设置可选的约束。
您可以先激活两个约束,然后在按下按钮时,只需禁用(设置constraint.active = NO
)所需的约束,另一个约束优先。再次按下按钮时,只需重新启用所需的约束即可。
答案 1 :(得分:0)
我知道了。发生的事情是UILabel的高度没有受到限制,因此当停用第二个约束并重新激活第一个约束时,高度会自动增加(请参见下图)。要解决此问题,我必须手动限制所有视图项的高度。如果有人有更好的解决方案,请发布它,因为我不希望手动为每个项目设置高度,因为这可能会导致布局在其他设备上中断。
更新
感谢siburb指出了UI元素的Content Hugging Priority
属性。我问题的根源在于未设置此属性,这允许我的UILabel的高度扩展。解决方案是将此属性设置为750或更高的值。
[myLabel setContentHuggingPriority:750 forAxis:UILayoutConstraintAxisVertical];