[英]Animating UIView inside of a UIScrollView with autolayout constraints
[英]UIView not obeying autolayout constraints in UIScrollView
我将UIView添加到UIScrollView
并对其进行约束,使其填充水平空间,除了一些边距。 我的视觉约束看起来像这样:
@"|-16-[theLineView]-16-|"
我已将视图设置为一个像素高,因此它将显示为一条线,并将其放在两个文本标签之间:
@"V:[someOtherStuff]-[aTextLabel]-[theLineView]-[anotherLabel]"
但是,我发现线条的宽度只扩展到它上面/下面最长标签的宽度。
为什么会这样?
PS我已阅读此http://developer.apple.com/library/ios/#technotes/tn2154/_index.html
码
以下是来自测试项目的整个视图控制器代码,该测试项目在iPad上显示此问题。
- (void)viewDidLoad
{[super viewDidLoad];
self.scrollView = [[UIScrollView alloc] init];
self.scrollView.translatesAutoresizingMaskIntoConstraints = NO;
self.scrollView.backgroundColor = [UIColor greenColor];
[self.view addSubview:self.scrollView];
[self.view addConstraints:[NSLayoutConstraint constraintsWithVisualFormat:@"|[scrollView]|"
options:0
metrics:0
views:@{@"scrollView":self.scrollView}]];
[self.view addConstraints:[NSLayoutConstraint constraintsWithVisualFormat:@"V:|[scrollView]|"
options:0
metrics:0
views:@{@"scrollView":self.scrollView}]];
self.line1 = [[UIView alloc] init];
self.line2 = [[UIView alloc] init];
self.label1 = [[UILabel alloc] init];
self.label2 = [[UILabel alloc] init];
self.label3 = [[UILabel alloc] init];
for (UILabel *label in @[self.label1, self.label2, self.label3])
{
label.text = @"I am a label and I am long enough that I can be multiline on an iphone but single on ipad";
}
for (UIView *view in @[self.line1, self.line2, self.label1, self.label2, self.label3])
{
view.translatesAutoresizingMaskIntoConstraints = NO;
view.backgroundColor = [UIColor redColor];
[self.scrollView addSubview:view];
}
//horizontal layout - all views/labels should fill the horizontal space expect for margin
for (UIView *view in @[self.line1, self.line2, self.label1, self.label2, self.label3])
{
NSArray *constraints = [NSLayoutConstraint constraintsWithVisualFormat:@"|-16-[view]-16-|"
options:0
metrics:0
views:@{@"view":view}];
[self.scrollView addConstraints:constraints];
}
//vertical layout - stack em up
[self.scrollView addConstraints:[NSLayoutConstraint constraintsWithVisualFormat:@"V:|-[lab1]-[line1(==1)]-[lab2]-[line2(==1)]-[lab3]-|"
options:0
metrics:0
views:@{@"lab1":self.label1, @"line1":self.line1, @"lab2":self.label2, @"line2":self.line2, @"lab3":self.label3}]];
}
UIScrollView会自动缩小以适应其中的视图。 你需要在某个地方设置宽度。
推荐策略:
如果在interface-builder中执行此操作(可能),则每次触摸该场景中的某些内容时都需要重新检查约束。 通过触摸我的意思是“选择”不仅“修改”。
找到了一个适用于您的用例的工作解决方案。 看到这里 。
扩大Patric Schenke答案的第4位; 因为scrollView
的内容大小是流动的,将内部视图固定到其边缘只是不能用于确定视图的宽度。 你的左侧引脚会工作,但两者都不会。 根据下一级容器计算视图宽度是可行的方法。 只要你的self.scrollView
被固定到它的容器(我称之为containerView
),这行代码将完成你想要的。 将此行添加到for
循环中以获得水平约束:
// Pin view's width to match the scrollView container's width
// -32 constant offset for margins
[containerView addConstraint:
[NSLayoutConstraint constraintWithItem:view
attribute:NSLayoutAttributeWidth
relatedBy:NSLayoutRelationEqual
toItem:containerView
attribute:NSLayoutAttributeWidth
multiplier:1.0f
constant:-32]];
我找到了一种简单的基于约束的方法来实现这一点(我没有测试过这个解决方案的脆弱程度):
...@"H:|-16-[view]-16-|"... // (your original constraint)
[self.scrollView addConstraint:
[NSLayoutConstraint constraintWithItem:view
attribute:NSLayoutAttributeCenterX
relatedBy:NSLayoutRelationEqual
toItem:self.scrollView
attribute:NSLayoutAttributeCenterX
multiplier:1.0f
constant:0.0f]];
这将view
一直延伸到view
的另一侧。 这可能不适合水平滚动的内容,但应垂直工作。
我意识到这是一年多以后的事了,但是对于单维滚动用例来说比patric.schenke的答案(这是好的和更强大的)更简单。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.