天天看点

iOS开发-VFL(Visual format language)和Autolayout

AutoLayout不管是在StoryBorad还是在xib中都相对来说比较简单,VFL(Visual  fromat  language)可视化语言基本上用到的比较少,在xCode4时候自动布局的概念还没有,直接使用VFL会很方便,可视化语言依赖于oc运行时创建对应的约束,如果IBOutlet发生改变有的时候会造成莫名其妙的Bug。xCode5之后可视化语言用到的场景相对较少,但是作为一个工作的辅助还是可以稍微了解下。

在StotyBoard中添加一个标签一个按钮,不适用自动布局,简单的控制它们之间的水平距离为80,如下图所示:

iOS开发-VFL(Visual format language)和Autolayout

视图中添加约束:

1

2

<code>NSLayoutConstraint</code>  <code>*labelContraint=[</code><code>NSLayoutConstraint</code> <code>constraintWithItem:</code><code>self</code><code>.changeButton attribute:</code><code>NSLayoutAttributeLeft</code> <code>relatedBy:</code><code>NSLayoutRelationEqual</code> <code>toItem:</code><code>self</code><code>.descriptionLabel attribute:</code><code>NSLayoutAttributeRight</code> <code>multiplier:1.0 constant:60];</code>

<code>[</code><code>self</code><code>.view addConstraint:labelContraint];</code>

这个只是视图约束的一种方式,下面这种方式才是本文的主角:

3

4

<code>//使用可视化语言添加约束</code>

<code>NSDictionary</code>  <code>*viewDictionary=</code><code>NSDictionaryOfVariableBindings</code><code>(_descriptionLabel,_changeButton);</code>

<code>NSArray</code>  <code>*visualConstraint=[</code><code>NSLayoutConstraint</code> <code>constraintsWithVisualFormat:@</code><code>"[_descriptionLabel]-60-[_changeButton]"</code> <code>options:0 metrics:</code><code>nil</code> <code>views:viewDictionary];</code>

<code>[</code><code>self</code><code>.view addConstraints:visualConstraint];</code>

 这里面用到的constraintsWithVisualFormat方法,具体参数说明如下:

format:参数是vfl语句,语句的基本元素下面会详细解释一下;

opts:枚举参数,默认写0;

metrics:字典,当在format中使用了动态数据,会根据字典去匹配,接下来会具体有例子;

views:字典,传入需要用到的视图集合;

具体format需要参考一下表达式的意思:

水平方向          H:

垂直方向          V:

Views         [需要定义的视图]

SuperView      |

关系         &gt;=,==,&lt;=

间隙            -

视图内部约束           ()

通过VFL控制手动添加的标签的位置,具体效果如下:

iOS开发-VFL(Visual format language)和Autolayout

代码实现如下:

5

6

7

8

9

10

11

<code>UILabel *link=[[UILabel alloc]init];</code>

<code>link.text=@</code><code>"http://www.cnblogs.com/xiaofeixiang"</code><code>;</code>

<code>link.translatesAutoresizingMaskIntoConstraints=</code><code>NO</code><code>;</code>

<code>[link setBackgroundColor:[UIColor greenColor]];</code>

<code>[</code><code>self</code><code>.view addSubview:link];</code>

<code>NSArray</code> <code>*horizontal=[</code><code>NSLayoutConstraint</code> <code>constraintsWithVisualFormat:@</code><code>"H:|-40-[link]-20-|"</code> <code>options:0 metrics:</code><code>nil</code> <code>views:</code><code>NSDictionaryOfVariableBindings</code><code>(link)];</code>

<code>NSArray</code> <code>*vertical=[</code><code>NSLayoutConstraint</code> <code>constraintsWithVisualFormat:@</code><code>"V:[_descriptionLabel]-100-[link(&gt;=30)]"</code> <code>options:0 metrics:</code><code>nil</code> <code>views:</code><code>NSDictionaryOfVariableBindings</code><code>(link,_descriptionLabel)];</code>

<code>[</code><code>self</code><code>.view addConstraints:horizontal];</code>

<code>[</code><code>self</code><code>.view addConstraints:vertical];</code>

 第一个约束是控制标签距离父视图左右之间的距离,第二个控制标签和”博客园-FlyElephant"之间的垂直距离为100.当然如果你想通过字典控制垂直之间的距离可以按照下面这么做:

<code>NSArray</code> <code>*vertical=[</code><code>NSLayoutConstraint</code> <code>constraintsWithVisualFormat:@</code><code>"V:[_descriptionLabel]-Vertical-[link(&gt;=30)]"</code> <code>options:0 metrics:@{@</code><code>"Vertical"</code><code>:</code><code>@200</code><code>} views:</code><code>NSDictionaryOfVariableBindings</code><code>(link,_descriptionLabel)];</code>

 最后的结果:

iOS开发-VFL(Visual format language)和Autolayout

友情提示在添加约束的时候不要和StoryBoard中的冲突,如果添加的水平约束StoryBoard中也有的话,就会出现下面这种情况:

12

<code>2015-07-01 10:54:13.537 VFLDemo[2358:60863] Unable to simultaneously satisfy constraints.</code>

<code>    </code><code>Probably at least one of the constraints in the following list is one you don</code><code>'t want. Try this: (1) look at each constraint and try to figure out which you don'</code><code>t expect; (2) find the code that added the unwanted constraint or constraints and fix it. (Note: If you</code><code>'re seeing NSAutoresizingMaskLayoutConstraints that you don'</code><code>t understand, refer to the documentation </code><code>for</code> <code>the UIView property translatesAutoresizingMaskIntoConstraints)</code>

<code>(</code>

<code>    </code><code>"&lt;NSLayoutConstraint:0x7fc5e3732860 H:[UILabel:0x7fc5e372ef30'\U535a\U5ba2\U56ed-FlyElephant']-(15)-[UIButton:0x7fc5e372d550'\U7fa4:228407086']&gt;"</code><code>,</code>

<code>    </code><code>"&lt;NSLayoutConstraint:0x7fc5e37344e0 H:[UILabel:0x7fc5e372ef30'\U535a\U5ba2\U56ed-FlyElephant']-(60)-[UIButton:0x7fc5e372d550'\U7fa4:228407086']&gt;"</code>

<code>)</code>

<code>Will attempt to recover by breaking constraint</code>

<code>&lt;</code><code>NSLayoutConstraint</code><code>:0x7fc5e37344e0 H:[UILabel:0x7fc5e372ef30</code><code>'博客园-FlyElephant'</code><code>]-(60)-[UIButton:0x7fc5e372d550</code><code>'群:228407086'</code><code>]&gt;</code>

<code>Make a symbolic breakpoint at UIViewAlertForUnsatisfiableConstraints to </code><code>catch</code> <code>this</code> <code>in the debugger.</code>

<code>The methods in the UIConstraintBasedLayoutDebugging category on UIView listed in &lt;UIKit/UIView.h&gt; may also be helpful.</code>

本文转自Fly_Elephant博客园博客,原文链接:http://www.cnblogs.com/xiaofeixiang/p/4612683.html,如需转载请自行联系原作者

继续阅读