iOS開發之Auto Layout入門

來源:互聯網
上載者:User

iOS開發之Auto Layout入門

隨著iPhone6與iOS8的臨近,適配的問題講更加複雜,最近學習了一下Auto Layout的使用,與大家分享。


什麼是Auto Layout?

Auto Layout是iOS6發布後引入的一個全新的布局特性,其目的是彌補以往Autoresizing在布局方面的不足之處,以及未來面對更多尺寸適配時介面布局可以更好的適應。


為什麼要用Auto Layout?

Autolayout能解決不同螢幕(iPhone4,iPhone5,iPad...)之間的適配問題。

在iPhone4時代開發人員只需要適配一種螢幕尺寸,相比與Android陣營的相對布局,iOS開發人員們最長用的做法是使用絕對布局,座標和大小隻要寫死就ok了。隨後iPhone5出了,對於兩種螢幕尺寸,就需要考慮一個新的問題,螢幕適配。蘋果其實很早就考慮到了這一點Autoresizing技術,誠然Autoresizing有所不足,蘋果在iOS6發布後引入了Autolayout特性,適應更廣泛情境下的布局需求。當然了iPhone5由於和iPhone4在螢幕寬度上一致,即便不用上這些技術適配起來也不麻煩(筆者再之前也只用到了Autoresizing),不過在iPhone6即將推出,即將面臨更複雜的螢幕適配時,Auto Layout能協助我們很好地解決這個問題,此外也能解決橫屏豎屏切換,iPad的適配問題。

下面是本文案例代碼在橫豎屏切換下的效果:



如何使用Auto Layout?

Auto Layout的基本概念

Auto Layout的核心是約束(constraint),通過對view的約束(view的大小,view與view之間的關係)使得view能夠自己計算出尺寸和座標。

Visual Format Language,在Auto Layout中使用的形象描述約束的一種語言規則。

Auto Layout的使用還是比較複雜的,一開始用可能會感覺雲裡霧裡的,用的多了習慣VFL的寫法之後就會感覺到它的方便了。


在代碼中使用Auto Layout

- (void)viewDidLoad{    [super viewDidLoad];        self.view.backgroundColor = [UIColor greenColor];    UIView *viewTopLeft = [[UIView alloc] init];    UIView *viewTopRight = [[UIView alloc] init];    UIView *viewBottom = [[UIView alloc] init];    [viewTopLeft setBackgroundColor:[UIColor blueColor]];    [viewTopRight setBackgroundColor:[UIColor redColor]];    [viewBottom setBackgroundColor:[UIColor blackColor]];        //添加約束之前必須講view添加到superview裡    [self.view addSubview:viewTopRight];    [self.view addSubview:viewTopLeft];    [self.view addSubview:viewBottom];        //對於要使用Auto Layout的控制項需要關閉Autoresizing    [viewTopLeft setTranslatesAutoresizingMaskIntoConstraints:NO];    [viewTopRight setTranslatesAutoresizingMaskIntoConstraints:NO];    [viewBottom setTranslatesAutoresizingMaskIntoConstraints:NO];        //使用VFL#if 1        //dict和metrics相當於vfl中的名稱與對象和數值的映射    NSDictionary *dict = NSDictionaryOfVariableBindings(viewTopLeft, viewTopRight, viewBottom);    //相當於這麼寫 NSDictionary *dict = @[@"viewTopLeft":viewTopLeft, @"viewTopRight":viewTopRight, @"viewBottom",viewBottom];不一定名稱要與對象名一致    NSDictionary *metrics = @{@"pad":@10};        //水平關係(H:,可省略如vfl1),"|"相當與superview,"-"是串連符,表示兩者間的間距也可以沒有表示無間距    //轉化正自然語言的描述就是:superview的左邊界間隔pad距離是viewTopLeft(寬度與viewTopRight相等)再間隔預設距離是viewTopRight再間隔10的距離是superview的右邊界。    NSString *vfl0 = @"H:|-pad-[viewTopLeft(==viewTopRight)]-[viewTopRight]-10-|";    NSString *vfl1 = @"|[viewBottom]|";        //垂直關係(V:)    NSString *vfl2 = @"V:|-[viewTopLeft(==viewBottom)]-[viewBottom]-pad-|";    NSString *vfl3 = @"V:|-[viewTopRight]-[viewBottom]-pad-|";        [self.view addConstraints:[NSLayoutConstraint constraintsWithVisualFormat:vfl0 options:0 metrics:metrics views:dict]];    [self.view addConstraints:[NSLayoutConstraint constraintsWithVisualFormat:vfl1 options:0 metrics:metrics views:dict]];    [self.view addConstraints:[NSLayoutConstraint constraintsWithVisualFormat:vfl2 options:0 metrics:metrics views:dict]];    [self.view addConstraints:[NSLayoutConstraint constraintsWithVisualFormat:vfl3 options:0 metrics:metrics views:dict]];        //不使用VFL#else    //viewTopLeft的leading與其superview的leading(左側)對齊    [self.view addConstraint:[NSLayoutConstraint constraintWithItem:self.view attribute:NSLayoutAttributeLeading relatedBy:NSLayoutRelationEqual toItem:viewTopLeft attribute:NSLayoutAttributeLeading multiplier:1 constant:-10]];        //viewTopLeft的top與其superview的top對齊    [self.view addConstraint:[NSLayoutConstraint constraintWithItem:self.view attribute:NSLayoutAttributeTop relatedBy:NSLayoutRelationEqual toItem:viewTopLeft attribute:NSLayoutAttributeTop multiplier:1 constant:-10]];        //viewTopRight的top與viewTopLeft的top對齊    [self.view addConstraint:[NSLayoutConstraint constraintWithItem:viewTopRight attribute:NSLayoutAttributeTop relatedBy:NSLayoutRelationEqual toItem:viewTopLeft attribute:NSLayoutAttributeTop multiplier:1 constant:0]];        //viewTopRight的leading與viewTopLeft的trailing(右側)對齊    [self.view addConstraint:[NSLayoutConstraint constraintWithItem:viewTopRight attribute:NSLayoutAttributeLeading relatedBy:NSLayoutRelationEqual toItem:viewTopLeft attribute:NSLayoutAttributeTrailing multiplier:1 constant:10]];        //viewTopRight的trailing與其superview的右側對其    [self.view addConstraint:[NSLayoutConstraint constraintWithItem:viewTopRight attribute:NSLayoutAttributeTrailing relatedBy:NSLayoutRelationEqual toItem:self.view attribute:NSLayoutAttributeTrailing multiplier:1 constant:-10]];        //viewTopRight的寬與viewTopLeft寬相等    [self.view addConstraint:[NSLayoutConstraint constraintWithItem:viewTopRight attribute:NSLayoutAttributeWidth relatedBy:NSLayoutRelationEqual toItem:viewTopLeft attribute:NSLayoutAttributeWidth multiplier:1 constant:0]];        //viewTopRight的高與viewTopLeft高相等    [self.view addConstraint:[NSLayoutConstraint constraintWithItem:viewTopLeft attribute:NSLayoutAttributeHeight relatedBy:NSLayoutRelationEqual toItem:viewTopRight attribute:NSLayoutAttributeHeight multiplier:1 constant:0]];        //viewBottom的top與viewTopRight的bottom對齊    [self.view addConstraint:[NSLayoutConstraint constraintWithItem:viewBottom attribute:NSLayoutAttributeTop relatedBy:NSLayoutRelationEqual toItem:viewTopRight attribute:NSLayoutAttributeBottom multiplier:1 constant:10]];        //viewBottom的bottom與superview的bottom對齊    [self.view addConstraint:[NSLayoutConstraint constraintWithItem:viewBottom attribute:NSLayoutAttributeBottom relatedBy:NSLayoutRelationEqual toItem:self.view attribute:NSLayoutAttributeBottom multiplier:1 constant:-10]];        //viewBottom的leading與viewTopLeft的leading對齊    [self.view addConstraint:[NSLayoutConstraint constraintWithItem:viewBottom attribute:NSLayoutAttributeLeading relatedBy:NSLayoutRelationEqual toItem:viewTopLeft attribute:NSLayoutAttributeLeading multiplier:1 constant:0]];        //viewBottom的高與viewTopLeft的高相等    [self.view addConstraint:[NSLayoutConstraint constraintWithItem:viewBottom attribute:NSLayoutAttributeHeight relatedBy:NSLayoutRelationEqual toItem:viewTopLeft attribute:NSLayoutAttributeHeight multiplier:1 constant:0]];        //viewBottom的寬與其superview的高相等    [self.view addConstraint:[NSLayoutConstraint constraintWithItem:viewBottom attribute:NSLayoutAttributeWidth relatedBy:NSLayoutRelationEqual toItem:self.view attribute:NSLayoutAttributeWidth multiplier:1 constant:-20]];    #endif        //更新約束    [self.view setNeedsUpdateConstraints];    [self.view updateConstraintsIfNeeded];}

注意點:

1.約束必須有給定的size然後通過約束計算出各個view的size和位置,上面self.view的size是給定的,如果superview的size不固定則必須給定某個subview的size才能通過約束計算出其他的。

2.兩個view之間的約束應該放在他們superview上,如果一個view是superview只要放在superview的那個上就行了。

2.約束的設計最好不要衝突,雖然可以設定優先權,但是容易出問題。

3.VFL方式的設定view的size時只有相等,小等或大等3種關係,沒法像使用方法產生約束那樣可以設定兩個view的比例,所以在具體的應用中還是要兩者結合起來使用。


在xib中使用Auto Layout

感覺在xib中使用autolayout還沒有用代碼來的方便,原理與代碼上相同,這裡就不多做描述了。


參考資料

Auto Layout Guide

ios8來了,螢幕更大,準備好使用 iOS Auto Layout了嗎?

Autolayout及VFL經驗分享



聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.