StoryBoard+AutoLayout实战开发小技巧

来源:互联网 发布:golang select 编辑:程序博客网 时间:2024/05/17 02:56

  使用xib、storybard、纯代码开发项目,这三种方法本人都尝试过。纯代码格式写的好,非常容易读、理解。合作开发也确实比storyboard方便,不需要像xib、storyboard那样经常切换几个界面,经常为了一个属性连线而报错,或者连线错误,纯代码编写易控制,易读。xib一般都是与代码混合编写,多用于自定义单元格之类的视图。使用storyboard整个应用流程,结构显得非常清楚,开发迅捷,但是自定义视图不是特别方便,比如自定义一个遮罩HUD视图。storyboard开发非常快,特别配合sizeclass、autolayout来适配6.0、7.0、8.0各种系统版本,4、5、6、6p各种屏幕尺寸非常之简单。强烈推荐使用storyboard+autolayout来开发,苹果的意愿也是如此。这里说一些storyboard和autolayout上的一些使用小技巧,也是对我前面部分工作的总结吧。

一、storyboard上的小技巧:

1、同时添加多个outlet

在IB中,选中一个view并右键点击,将会出现灰色的HUD,可以在其上方便地拖拉或设定事件和outlet。你可以同时打开多个这样的面板来一 次性添加所有outlet。右键点击面板,随便拖动一下面板,然后再打开另一个。你会发现前一个面板也留下来了,这样你就可以方便地进行拖拽设定了。


2、多个Outlet HUD 

当然,对于成组和行为类似的IBOutlet,应该直接使用IBOutletCollection来进行处理会更方便。


3、option键的妙用

(1)、可视化坐标距离

选中一个label,然后按住option键并将鼠标移动到其他label上试试?你可以发现view之间的距离都以很容易理解的方式显示出来了。不仅是同层次的view,被选中view与其他层次的view之间的距离关系也可以同样显示。


(2)、控件复制

选中一个label,然后按住option键,并用鼠标按住它拖动到另一个位置,结果有了两label,新的label和原来label属性相同,比cmd+c、cmd+v好用吧。

4、添加辅助线

双击某个view,然后Cmd+Shift+-或者Cmd+Shift+|即可在选中的view上添加一条水平或者垂直中心的辅助线。当然这个辅助线是可以随意移动的。如果干过设计的同学肯定明白这个的意义了,在之后的对其和设计变更的时候都有重要的参考价值。


5.添加自定义视图

如图这样,把它当做xib来处理就行了。不用额外创建xib了,方便实用吧。


6.User Undefined Runtime Attributes妙用

例如在storyboard上设置这类属性,圆角。

keypath写上你想要设置的属性,根据名字就知道它支持访问对象的指定属性的字符串序列,type就是属性的类型,value还支持颜色哦。



7.使view的size与view的content相适应
选中任意的一个view,然后Editor->Size to Fit Content,或者简单的按 ⌘=
接着就会按照下面的规则对选中view的Size做出与之Content对应的适应:
  • (1)ImageView/Button的size会设置为图像的原始size(最常见的用法)。
  • (2)Label/Button的size会被设置为与当前text内容相当的尺寸。
  • (3)parent container view会与其subviews的frames相适应。
  • 8.Editor->Embed In View,UnEmbed
  • 你是不是对此素手无策呢:你希望将已有的一些subviews放入到不同的parent view中,甚至是不同的.xib文件中,但是当你把一些view重新设置之后,它们为自动的位于新的parent view中心?

    如图所示,你怎么把1-12个数字label保持原有的样子放入到scrollView中呢?

    点击选中12个label,再选择editor中的embed in view:


    把view拖到scrollview中去,再次点击scrollView的unembed:


    OK,大功告成,很Esay是不,赶紧尝试吧。

    9.对不在最上面的视图进行位置移动。

    一般做法就是先将非最上面的view临时设置到最上面,移动好位置之后,在设置回去。费时费力不讨好。

    最简单的方法:

    在document outline上双击view,就可以用箭头移动view了。

    10.编辑出界的scrollView、tableview内容。

    当scrollView、tableview中控件超出了它们的frame,怎么编辑控件呢?

    点击控件,然后滑动滑轮,直到把目标控件给滑动出来。


二、Autolayout上的小技巧:

1.ScrollView上添加约束。

很多人都会遇到这种报错:


这是因为ScrollView的ContentSize没有确定。

contentSize在布局中实际上是scroll view的子view :content view的宽和高实现的。往往对于scrollview中的子view,我 们同样也可以将其放在同一个父的container view中,然后将这个container view作为scrollview的子view也即content view,这样我们对scroll view 的布局就可以简化为对content view的布局,而content view里面的子view相对于content view的布局就是普通的布局了,剩下的只需要我们解决好scroll view和content view的布局即可。


这时有个奇怪的现象:

ContentView上下距离约束怎么不与其高度约束冲突呢?

原来content view和scroll view的top, bottom, leading和trailing contstraints,这四个约束的使用在scroll view中做了变化:它不再是确定content view尺寸的依据,而是帮助scroll view中content view四周的边界(or你可以理解为留白),进而确定scroll view的contentSize属性。

2.UILabel添加约束

Label只需要添加top, leading约束即可,宽度会根据文字内容多少自动适应。

假若把Label的height再次固定,则高度会自动适应。

比如:银行名称与尾号左对齐,并且尾号一直在名称的底部。这里切记勾选上label的preferred width 。不然iOS8.0以下程序会crash掉。





3.TableViewCell高度自适应

(1)设置好布局约束条件,使得cell子视图的边缘固定(pin)到cell的contentView的边缘(最重要的是要有顶部和底部的边距约束条件),这样cell就能确定自己的高度了。


(2)高度代理协议heightForRowAtIndexPath:千万别实现它。

加上

tableview.rowheight=UITableviewAutomaticDimension;

tableview.estimatedRowheight=44;

(3)设置好正确的preferredMaxLayoutWidth  

[super layoutSubViews];

_contentLbl.preferredMaxLayoutWidth=_contentLbl.frame.size.width;

 [super layoutSubViews];

效果:


4、动画处理

把滑动视图的高度减小,_bgScrollViewHeightLayout定义在这里:

@property (weak,nonatomic) IBOutLet NSLayoutConstraint *bgScrollViewHeightLayout;

[_bgScrollView layoutIfNeeded];

_bgScrollViewHeightLayout.constant=kScreenHeight-64-height;

[UIView animateWithDuration:duration animations:^{

[_bgScrollView layoutIfNeeded];

}];;

5、约束调试:

我们在iOS中遇到不可满足的约束条件,我们只能在输出的日志中看到视图的内存地址。尤其是在更复杂的布局中,有时很难辨别出视图的哪一部分出了问题。然而,在这种情况下,还有几种方法可以帮到我们。

首先,当你在不可满足的约束条件错误信息中看到NSLayoutResizingMaskConstraints时,你肯定忘了为你某一个视图设定translatesAutoResizingMaskIntoConstraints为NO。Interface Builder中会自动设置,但是使用代码时,你需要为所有的视图手动设置。

如果不是很明确那个视图计算问题,你需要通过内存地址来辨认视图。最简单的方法是使用调试控制台。你可以打印视图本身或它父视图的描述,甚至递归描述的树视图。这通常会提示你需要处理哪个视图。

(1)使用po 命令

  

(2)一个更直观的方法是在控制台修改有问题的视图,这样你可以在屏幕上标注出来。比如,你可以改变它的背景颜色:

<span style="font-size:12px;">(lldb) expr ((UIView *)0x7731880).backgroundColor = [UIColor purpleColor] </span>

确保重新执行程序后改变不会在屏幕上显示出来。还要注意将内存地址转换为(UIView *),以及额外的圆括号,这样我们就可以使用点操作。另外,你当然也可以通过发送消息:

<span style="font-size:12px;">(lldb) expr [(UIView *)0x7731880 setBackgroundColor:[UIColor purpleColor]] </span>

(3)另一种方法是使用Instrument的allocation模板,根据图表分析。一旦你从错误消息中得到内存地址(运行Instruments时,你从控制台中获得的错误消息),你可以将Instrument切换到Objects List的详细视图,并且用Cmd-F搜索那个内存地址。这将会为你显示分配视图对象的方法,这通常是一个很好的暗示(至少找到创建视图对象的代码了)。

(4)你也可以在iOS中弄懂不可满足的约束条件错误,这比改善错误消息来的更简单。我们可以在一个category中重写NSLayoutConstraint的描述,并且将视图的tags包含进去:

<span style="font-size:12px;">@implementation NSLayoutConstraint (AutoLayoutDebugging) #ifdef DEBUG - (NSString *)description {     NSString *description = super.description;     NSString *asciiArtDescription = self.asciiArtDescription;     return [description stringByAppendingFormat:@" %@ (%@, %@)", asciiArtDescription, [self.firstItem tag], [self.secondItem tag]]; } #endif @end </span>

如果是整数的属性标签信息是不够的,我们还可以得到更多新奇的东西,为视图类增加我们自己命名的属性,然后可以打印到错误消息中。我们甚至可以在Interface Builder中,使用identity inspector中的 “User Defined Runtime Attributes”为自定义属性分配值。

<span style="font-size:12px;">@interface UIView (AutoLayoutDebugging) - (void)setAbc_NameTag:(NSString *)nameTag; - (NSString *)abc_nameTag; @end   @implementation UIView (AutoLayoutDebugging) - (void)setAbc_NameTag:(NSString *)nameTag {     objc_setAssociatedObject(self, "abc_nameTag", nameTag, OBJC_ASSOCIATION_RETAIN_NONATOMIC); }   - (NSString *)abc_nameTag {     return objc_getAssociatedObject(self, "abc_nameTag");} @end @implementation NSLayoutConstraint (AutoLayoutDebugging) #ifdef DEBUG - (NSString *)description { NSString *description = super.description;     NSString *asciiArtDescription = self.asciiArtDescription;     return [description stringByAppendingFormat:@" %@ (%@, %@)", asciiArtDescription, [self.firstItem abc_nameTag], [self.secondItem abc_nameTag]]; } #endif @end </span>

通过这种方法错误消息变得更可读,并且你不需要找出内存地址对应的视图。然而,对你而言,你需要做一些额外的工作以确保每次为视图分配的名字都是有意义。





0 0
原创粉丝点击