標籤:
AutoLayout不管是在StoryBorad還是在xib中都相對來說比較簡單,VFL(Visual fromat language)可視化語言基本上用到的比較少,在xCode4時候自動布局的概念還沒有,直接使用VFL會很方便,可視化語言依賴於oc運行時建立對應的約束,如果IBOutlet發生改變有的時候會造成莫名其妙的Bug。xCode5之後可視化語言用到的情境相對較少,但是作為一個工作的輔助還是可以稍微瞭解下。
基礎知識
在StotyBoard中添加一個標籤一個按鈕,不適用自動布局,簡單的控制它們之間的水平距離為80,如所示:
視圖中添加約束:
NSLayoutConstraint *labelContraint=[NSLayoutConstraint constraintWithItem:self.changeButton attribute:NSLayoutAttributeLeft relatedBy:NSLayoutRelationEqual toItem:self.descriptionLabel attribute:NSLayoutAttributeRight multiplier:1.0 constant:60]; [self.view addConstraint:labelContraint];
這個只是視圖約束的一種方式,下面這種方式才是本文的主角:
//使用可視化語言添加約束 NSDictionary *viewDictionary=NSDictionaryOfVariableBindings(_descriptionLabel,_changeButton); NSArray *visualConstraint=[NSLayoutConstraint constraintsWithVisualFormat:@"[_descriptionLabel]-60-[_changeButton]" options:0 metrics:nil views:viewDictionary]; [self.view addConstraints:visualConstraint];
這裡面用到的constraintsWithVisualFormat方法,具體參數說明如下:
format:參數是vfl語句,語句的基本元素下面會詳細解釋一下;
opts:枚舉參數,預設寫0;
metrics:字典,當在format中使用了動態資料,會根據字典去匹配,接下來會具體有例子;
views:字典,傳入需要用到的視圖集合;
具體format需要參考一下運算式的意思:
水平方向 H:
垂直方向 V:
Views [需要定義的視圖]
SuperView |
關係 >=,==,<=
間隙 -
視圖內部約束 ()
Demo實戰
通過VFL控制手動添加的標籤的位置,具體效果如下:
代碼實現如下:
UILabel *link=[[UILabel alloc]init]; [email protected]"http://www.cnblogs.com/xiaofeixiang"; link.translatesAutoresizingMaskIntoConstraints=NO; [link setBackgroundColor:[UIColor greenColor]]; [self.view addSubview:link]; NSArray *horizontal=[NSLayoutConstraint constraintsWithVisualFormat:@"H:|-40-[link]-20-|" options:0 metrics:nil views:NSDictionaryOfVariableBindings(link)]; NSArray *vertical=[NSLayoutConstraint constraintsWithVisualFormat:@"V:[_descriptionLabel]-100-[link(>=30)]" options:0 metrics:nil views:NSDictionaryOfVariableBindings(link,_descriptionLabel)]; [self.view addConstraints:horizontal]; [self.view addConstraints:vertical];
第一個約束是控制標籤距離父視圖左右之間的距離,第二個控制標籤和”部落格園-FlyElephant"之間的垂直距離為100.當然如果你想通過字典控制垂直之間的距離可以按照下面這麼做:
NSArray *vertical=[NSLayoutConstraint constraintsWithVisualFormat:@"V:[_descriptionLabel]-Vertical-[link(>=30)]" options:0 metrics:@{@"Vertical":@200} views:NSDictionaryOfVariableBindings(link,_descriptionLabel)];
最後的結果:
友情提示在添加約束的時候不要和StoryBoard中的衝突,如果添加的水平約束StoryBoard中也有的話,就會出現下面這種情況:
2015-07-01 10:54:13.537 VFLDemo[2358:60863] Unable to simultaneously satisfy constraints.Probably at least one of the constraints in the following list is one you don‘t want. Try this: (1) look at each constraint and try to figure out which you don‘t expect; (2) find the code that added the unwanted constraint or constraints and fix it. (Note: If you‘re seeing NSAutoresizingMaskLayoutConstraints that you don‘t understand, refer to the documentation for the UIView property translatesAutoresizingMaskIntoConstraints) ( "<NSLayoutConstraint:0x7fc5e3732860 H:[UILabel:0x7fc5e372ef30‘\U535a\U5ba2\U56ed-FlyElephant‘]-(15)-[UIButton:0x7fc5e372d550‘\U7fa4:228407086‘]>", "<NSLayoutConstraint:0x7fc5e37344e0 H:[UILabel:0x7fc5e372ef30‘\U535a\U5ba2\U56ed-FlyElephant‘]-(60)-[UIButton:0x7fc5e372d550‘\U7fa4:228407086‘]>")Will attempt to recover by breaking constraint <NSLayoutConstraint:0x7fc5e37344e0 H:[UILabel:0x7fc5e372ef30‘部落格園-FlyElephant‘]-(60)-[UIButton:0x7fc5e372d550‘群:228407086‘]>Make a symbolic breakpoint at UIViewAlertForUnsatisfiableConstraints to catch this in the debugger.The methods in the UIConstraintBasedLayoutDebugging category on UIView listed in <UIKit/UIView.h> may also be helpful.
iOS開發-VFL(Visual format language)和Autolayout