• AutoLayout


    随着iPhone设备出现了不同的尺寸,iOS6.0以后storyboard和xib文件新增了一个Use Auto Layout选项,用来实现自动布局。当你勾选上这个选项,以前传统的布局方式将不能正常工作。一旦使用了自动布局,就要忘记 Frame 的概念!

    要判断UIView是否可以使用自动布局,可以使用如下方法:

    if ([self.view respondsToSelector:@selector(addConstraints:)])
    {
        //自动布局
    }
    else
    {
        //传统布局
    }

    可以通过-layoutIfNeeded和-setNeedsUpdateConstraints两个方法来刷新约束的改变,使UIView重新布局。layoutIfNeeded是调整布局,也就是view的位置,一般是对subviews作用。setNeedsDisplay涉及到redraw,也就是重绘,一般都是对receiver作用。

    layoutIfNeeded

    使用此方法强制立即进行layout,从当前view开始,此方法会遍历整个view层次(包括superviews)请求layout。因此,调用此方法会强制整个view层次布局。

    setNeedsUpdateConstraints

    当一个自定义view的某个属性发生改变,并且可能影响到constraint时,需要调用此方法去标记constraints需要在未来的某个点更新,系统然后调用updateConstraints.

    添加约束一般要遵循下面的规则:

    • 对于两个同层级view之间的约束关系,添加到他们的父view上:

    • 对于两个不同层级view之间的约束关系,添加到他们最近的共同父view上:

    • 对于有层次关系的两个view之间的约束关系,添加到层次较高的父view上:

     

    下面的例子演示了通过设定控件边界距离,从而确定控件尺寸:

    UIButton *button = [UIButton buttonWithType:UIButtonTypeRoundedRect];
    [button setTitle:@"测试按钮" forState:UIControlStateNormal];
    [button sizeToFit];
    [button setBackgroundColor:[UIColor yellowColor]];
    button.translatesAutoresizingMaskIntoConstraints = NO;
    [self.view addSubview:button];
    
    NSLayoutConstraint *constraint;
    
    //上边距
    constraint = [NSLayoutConstraint
                  constraintWithItem:button
                  attribute:NSLayoutAttributeTop
                  relatedBy:NSLayoutRelationEqual
                  toItem:self.view
                  attribute:NSLayoutAttributeTop
                  multiplier:1.0f
                  constant:50.0f];
    [self.view addConstraint:constraint];
    
    //左边距
    constraint = [NSLayoutConstraint
                  constraintWithItem:button
                  attribute:NSLayoutAttributeLeading
                  relatedBy:NSLayoutRelationEqual
                  toItem:self.view
                  attribute:NSLayoutAttributeLeading
                  multiplier:1.0f
                  constant:100.0f];
    [self.view addConstraint:constraint];
    
    //右边距
    constraint = [NSLayoutConstraint
                  constraintWithItem:button
                  attribute:NSLayoutAttributeTrailing
                  relatedBy:NSLayoutRelationEqual
                  toItem:self.view
                  attribute:NSLayoutAttributeTrailing
                  multiplier:1.0f
                  constant:-100.0f];
    [self.view addConstraint:constraint];
    
    //下边距
    constraint = [NSLayoutConstraint
                  constraintWithItem:button
                  attribute:NSLayoutAttributeBottom
                  relatedBy:NSLayoutRelationEqual
                  toItem:self.view
                  attribute:NSLayoutAttributeBottom
                  multiplier:1.0f
                  constant:-350.0f];
    [self.view addConstraint:constraint];

    下面的例子设定了控件在父容器中水平垂直居中:

    UIButton *button = [UIButton buttonWithType:UIButtonTypeRoundedRect];
    [button setTitle:@"测试按钮" forState:UIControlStateNormal];
    [button sizeToFit];
    [button setBackgroundColor:[UIColor yellowColor]];
    button.translatesAutoresizingMaskIntoConstraints = NO;
    [self.view addSubview:button];
    
    NSLayoutConstraint *constraint;
    
    //水平居中
    constraint = [NSLayoutConstraint
                  constraintWithItem:button
                  attribute:NSLayoutAttributeCenterX
                  relatedBy:NSLayoutRelationEqual
                  toItem:self.view
                  attribute:NSLayoutAttributeCenterX
                  multiplier:1.0f
                  constant:0.0f];
    [self.view addConstraint:constraint];
    
    //垂直居中
    constraint = [NSLayoutConstraint
                  constraintWithItem:button
                  attribute:NSLayoutAttributeCenterY
                  relatedBy:NSLayoutRelationEqual
                  toItem:self.view
                  attribute:NSLayoutAttributeCenterY
                  multiplier:1.0f
                  constant:0.0f];
    [self.view addConstraint:constraint];

    下面的例子直接设定了控件的尺寸:

    UIButton *button = [UIButton buttonWithType:UIButtonTypeRoundedRect];
    [button setTitle:@"测试按钮" forState:UIControlStateNormal];
    [button sizeToFit];
    [button setBackgroundColor:[UIColor yellowColor]];
    button.translatesAutoresizingMaskIntoConstraints = NO;
    [self.view addSubview:button];
    
    NSLayoutConstraint *constraint;
    
    //设置宽度
    constraint = [NSLayoutConstraint constraintWithItem:button attribute:NSLayoutAttributeWidth relatedBy:NSLayoutRelationEqual toItem:nil attribute:NSLayoutAttributeNotAnAttribute multiplier:1.0f constant:130.0f];
    [self.view addConstraint:constraint];
    
    //设置高度
    constraint = [NSLayoutConstraint constraintWithItem:button attribute:NSLayoutAttributeHeight relatedBy:NSLayoutRelationEqual toItem:nil attribute:NSLayoutAttributeNotAnAttribute multiplier:1.0f constant:70.0f];
    [self.view addConstraint:constraint];

    除了上面添加约束的方法,还有一种全新的方法:Visual Format Language(可视格式语言),这种语言是对视觉描述的一种抽象。基本用法如下:

    UIButton *buttonA = [UIButton buttonWithType:UIButtonTypeRoundedRect];
    [buttonA setTitle:@"AAA" forState:UIControlStateNormal];
    [buttonA sizeToFit];
    [buttonA setBackgroundColor:[UIColor yellowColor]];
    buttonA.translatesAutoresizingMaskIntoConstraints = NO;
    [self.view addSubview:buttonA];
    
    UIButton *buttonB = [UIButton buttonWithType:UIButtonTypeRoundedRect];
    [buttonB setTitle:@"BBB" forState:UIControlStateNormal];
    [buttonB sizeToFit];
    [buttonB setBackgroundColor:[UIColor yellowColor]];
    buttonB.translatesAutoresizingMaskIntoConstraints = NO;
    [self.view addSubview:buttonB];
    
    
    NSMutableArray *array = [NSMutableArray array];
    
    //水平方向布局(从左向右)
    [array addObjectsFromArray:[NSLayoutConstraint
                                constraintsWithVisualFormat:@"|-60-[buttonA(==90)]-30-[buttonB]"
                                options:NSLayoutFormatDirectionLeadingToTrailing
                                metrics:nil
                                views:NSDictionaryOfVariableBindings(buttonA,buttonB)]];
    
    //垂直方向布局(从上向下)
    [array addObjectsFromArray:[NSLayoutConstraint
                                constraintsWithVisualFormat:@"V:|-100-[buttonB]-50-[buttonA]"
                                options:NSLayoutFormatDirectionLeadingToTrailing
                                metrics:nil
                                views:NSDictionaryOfVariableBindings(buttonA,buttonB)]];
    
    [self.view addConstraints:array];

    constraintsWithVisualFormat方法的最后一个参数views需要提供一个字典,用来指明可视化字符串里出现控件名所对应的控件:

    NSDictionary *viewsDictionary = NSDictionaryOfVariableBindings(buttonA,buttonB);
    
    for(NSString *key in viewsDictionary)
    {
        NSLog(@"key:%@, value:%@",key,viewsDictionary[key]);
    }
    //key:buttonA, value:<UIButton: 0x8dc5850; frame = (0 0; 30 30); opaque = NO; layer = <CALayer: 0x8dc7270>>
    //key:buttonB, value:<UIButton: 0x8dc8a90; frame = (0 0; 32 30); opaque = NO; layer = <CALayer: 0x8dc8b80>>

    下面是两个具有代表性的语句示例:

    @"|-50-[buttonA(80@100)]-[buttonB(90@200)]-50-|"

    这条语句的含义是:“左右边距都为50,中间有两个按钮,相隔缺省宽度,一个控件宽度为80,约束优先级为100;另一个控件宽度为90,约束优先级为200”。实际运行后,发现buttonB的控件宽度为90,而buttonA的宽度为自适应宽度,并不是80像素;这是因为buttonB的约束优先级200大于buttonA的约束优先级,所以优先生效。可以把buttonA的优先级改的比buttonB大,就可以看到完全相反的结果。

     

    @"V:[buttonA(80)]-20-[buttonB(==buttonA)]"

    这条语句的含义是:“垂直方向有一个高度为80的buttonA,然后间隔20有一个和buttonA同样高度的buttonB”

    P.s. NSLayoutAttributeLeft/NSLayoutAttributeRight 和 NSLayoutAttributeLeading/NSLayoutAttributeTrailing的区别是left/right永远是指左右,而leading/trailing在某些从右至左习惯的地区会变成,leading是右边,trailing是左边。

     

  • 相关阅读:
    GC原理---垃圾收集算法
    GC原理---对象可达判断
    散列算法和哈希表结构
    桶排序
    Spring事务梳理
    AQS
    重入锁
    CAS
    研究一下phpspider
    用php写爬虫去爬数据
  • 原文地址:https://www.cnblogs.com/CoderWayne/p/3935453.html
Copyright © 2020-2023  润新知