两个视图,一个在纵向上并排排列在横向上,使用布局约束
假设我有两个文本视图。 在肖像模式下,我想这些在另一个&在横向模式下,我想这些是并排的
是否有可能使用自动布局在故事板中使用布局约束? 如果是,那么如何? 如果没有,那么实现这一目标的其他更好的解决scheme是什么?
ios6是我的目标版本
以下是你如何在代码中去解决这个问题。
基本上你需要:
a)在UIViewController
updateViewConstraints
中为给定方向configuration合适的NSLayoutConstraint
。
b)当界面旋转时调用[self.view setNeedsUpdateConstraints]
。
下面是一个ViewController的实现和UIView与辅助方法的类别。
@interface ConstraintsViewController () @property (nonatomic, weak) IBOutlet UIView *upperOrLeftView, *lowerOrRightView; @end @implementation ConstraintsViewController -(void)willRotateToInterfaceOrientation:(UIInterfaceOrientation)toInterfaceOrientation duration:(NSTimeInterval)duration { [super willAnimateRotationToInterfaceOrientation:toInterfaceOrientation duration:duration]; [self.view setNeedsUpdateConstraints]; } -(void)updateViewConstraints { [super updateViewConstraints]; [self.view removeConstraintsRelatingToItems:@[self.upperOrLeftView,self.lowerOrRightView]]; if(UIInterfaceOrientationIsPortrait(self.interfaceOrientation)) { [self.view constrainSubview:self.upperOrLeftView usingEdgeInsets:UIEdgeInsetsMake(0, 0, -1, 0)]; [self.view constrainSubview:self.lowerOrRightView usingEdgeInsets:UIEdgeInsetsMake(-1, 0, 0, 0)]; [self.view constrainSubviewsTopToBottom:@[self.upperOrLeftView, self.lowerOrRightView]]; } else { [self.view constrainSubview:self.upperOrLeftView usingEdgeInsets:UIEdgeInsetsMake(0, 0, 0, -1)]; [self.view constrainSubview:self.lowerOrRightView usingEdgeInsets:UIEdgeInsetsMake(0, -1, 0, 0)]; [self.view constrainSubviewsLeftToRight:@[self.upperOrLeftView, self.lowerOrRightView]]; } } @end
把它放在UIView + Constraints.h中
@interface UIView (Constraints) -(void)removeConstraintsRelatingToItems:(NSArray*)items; -(void)constrainSubview:(UIView*)subview usingEdgeInsets:(UIEdgeInsets)insets; -(void)constrainSubviewsLeftToRight:(NSArray*)subviews; -(void)constrainSubviewsTopToBottom:(NSArray*)subviews; @end
这是UIView + Constraints.m
@implementation UIView (Constraints) -(void)removeConstraintsRelatingToItems:(NSArray *)items { for(NSLayoutConstraint *constraint in self.constraints) { if([items containsObject:constraint.firstItem] || [items containsObject:constraint.secondItem]) { [self removeConstraint:constraint]; } } } /** Set up constraints to flow the subviews from top to bottom and with equal heights */ -(void)constrainSubviewsTopToBottom:(NSArray*)subviews { if(subviews.count > 1) { UIView *anchorView = subviews[0]; for(int i = 1; i < subviews.count; i++) { UIView *view = subviews[i]; NSLayoutConstraint *heightConstraint = [NSLayoutConstraint constraintWithItem:anchorView attribute:NSLayoutAttributeHeight relatedBy:NSLayoutRelationEqual toItem:view attribute:NSLayoutAttributeHeight multiplier:1.0 constant:0.0]; NSLayoutConstraint *edgesConstraint = [NSLayoutConstraint constraintWithItem:anchorView attribute:NSLayoutAttributeBottom relatedBy:NSLayoutRelationEqual toItem:view attribute:NSLayoutAttributeTop multiplier:1.0 constant:0.0]; [self addConstraints:@[heightConstraint, edgesConstraint]]; anchorView = view; } } } /** Set up constraints to flow the subviews from left to right and with equal widths */ -(void)constrainSubviewsLeftToRight:(NSArray*)subviews { if(subviews.count > 1) { UIView *anchorView = subviews[0]; for(int i = 1; i < subviews.count; i++) { UIView *view = subviews[i]; NSLayoutConstraint *widthConstraint = [NSLayoutConstraint constraintWithItem:anchorView attribute:NSLayoutAttributeWidth relatedBy:NSLayoutRelationEqual toItem:view attribute:NSLayoutAttributeWidth multiplier:1.0 constant:0.0]; NSLayoutConstraint *edgesConstraint = [NSLayoutConstraint constraintWithItem:anchorView attribute:NSLayoutAttributeRight relatedBy:NSLayoutRelationEqual toItem:view attribute:NSLayoutAttributeLeft multiplier:1.0 constant:0.0]; [self addConstraints:@[widthConstraint, edgesConstraint]]; anchorView = view; } } } /** Set up constraints to anchor the various edges of the subview to it's superview (this view) using the provided insets. Any inset set to < 0.0 means that edge is ignored; */ -(void)constrainSubview:(UIView*)subview usingEdgeInsets:(UIEdgeInsets)insets { if(insets.top >= 0.0) { [self addConstraint:[NSLayoutConstraint constraintWithItem:subview attribute:NSLayoutAttributeTop relatedBy:NSLayoutRelationEqual toItem:self attribute:NSLayoutAttributeTop multiplier:1.0 constant:insets.top]]; } if(insets.right >= 0.0) { [self addConstraint:[NSLayoutConstraint constraintWithItem:subview attribute:NSLayoutAttributeRight relatedBy:NSLayoutRelationEqual toItem:self attribute:NSLayoutAttributeRight multiplier:1.0 constant:-insets.right]]; } if(insets.bottom >= 0.0) { [self addConstraint:[NSLayoutConstraint constraintWithItem:subview attribute:NSLayoutAttributeBottom relatedBy:NSLayoutRelationEqual toItem:self attribute:NSLayoutAttributeBottom multiplier:1.0 constant:-insets.bottom]]; } if(insets.left >= 0.0) { [self addConstraint:[NSLayoutConstraint constraintWithItem:subview attribute:NSLayoutAttributeLeft relatedBy:NSLayoutRelationEqual toItem:self attribute:NSLayoutAttributeLeft multiplier:1.0 constant:insets.left]]; } } @end
在我看来,以多个方向布置viewController视图的最佳方法是为每个方向创buildless量的视图。 在这里我find了这个:
“当你添加一个视图控制器到故事板时,它带有一个视图,调用这个容器视图,在容器视图中添加两个视图:纵向视图和横向视图,适当地设置纵向视图和横向视图的尺寸使用尺寸检查器,根据需要为应用程序添加button,更多视图,标签或其他内容,然后当方向改变时隐藏一个视图并显示另一个视图。
您只能通过使用Interface Builder来实现此类行为。 您需要设置一些不同优先级的约束。
在这里看到我更详细的答案。 还有一个截屏video和一个我创build的示例应用程序的链接。
- MvvmCross:如何在iPhone上的iOS 7中强制MvxViewController的特定方向
- 可可豆荚入门
- 在iPhone模拟器上使用UIImagePickerController
- 删除UICollectionView中的最后一个单元格会导致崩溃
- testing更新时的TestFlight警报:您已经安装了此应用程序
- 在tableview中使用timer会在任何滚动或表重新加载后重新创建计时器
- 如何检查iOS中是否存在方法systemFontOfSize(fontSize:weight :)
- 如何检测和超链接/提及/标签在UILabel点击?
- UINavigationBar和后退button的自定义