分享

Xcode 8 Auto Layout新手体验

 xiaotianyueye 2016-12-07


Auto Layout自动布局是基于约束的一套布局系统。它充许开发者设计出能够响应屏幕大小及设备横竖屏方向的适配界面。一些初学者会觉得难学并且不愿使用,甚至有些开发者会避免使用它们。但请相信我,一但掌握并懂得使用它后你肯定会欲罢不能。


随着iphone6及iphone6s 的发布,苹果手机的屏幕尺寸也不尽相同,其中包括3.5英寸、4英寸、4.7英寸以及5.5英寸的显示器。如果不使用自动布局,你很难开发出一个可以支持所有屏幕尺寸的app,自动布局为你提供了解决此问题的绝佳方案。而且从xcode6开始就可以使用自动布局来设计用户界面了。这就是为什么我在这篇文章开头就教你如何使用自动布局而不是莽撞地直接用代码开发布一款App。


在这篇教程中,我想帮助你夯实Auto Layout的基础知识,使用自动布局来构建一个适配用户界面的APP。


其实,自动布局并没有某些开者想的那难。一旦理解了它的原理,你就可以使用自动布局为所有的iOS设备开发出复杂的用户界面。


提示:本教程改编自我们 Swift书中的Beginning iOS 10 Programming with Swift的章节内容。如果想看全书可以点击下载


为什么要使用Auto Layout?


让我给你来举例,对于为什么有必要使用自动布局你会有更清楚的认知。下载并打开 starter project。在iPhone 6 plus 或 iPhone 5 模拟器上运行APP,而不是在iPhone6/iPhone 6s模拟器上。最终的显示效果与下图相似。当运行iPhone 6/6s以外的设备时,会发现安钮并没有居中显示。



我们尝试另一种方式。


点击Xcode中停止按钮并使用iPhone 6/6s 模拟器,模拟器启动后,找到 menu->Hardware->Rotate Left(或者Rotate Right),旋转设备到横屏模式。或者你也可以按下 command+左箭头/右箭头来旋转设备(device sideway),再试一次,Hello World 按钮还是没有居中。


为什么呢?出什么岔子了?


正如你所知道的那样,iPhone有着不同屏幕大小的差异:


  • iPhone 5/5s,屏幕处于纵向模式,由水平方向上320个点(或640个像素) 和垂直方向上568个点(或1136个像素)组成。

  • iPhone 6/6s,屏幕处于纵向模式,由水平方向上375个点(或750个像素) 和垂直方向上667个点(或1334个像素)组成。

  • iPhone 6/6s Plus,屏幕处于纵向模式,由水平方向上414个点(或1242个像素) 和垂直方向上736个点(或2208个像素)组成。

  • iPhone 4s,屏幕处于纵向模式,由水平方向上320个点(或640个像素) 和垂直480个点(或960个像素)组成。


为什么用点而不是像素?


早在2007年,苹果推出了3.5英寸大小,分辨率为320*480的初代iPhone。该显示器水平像素为320,垂直像素为480。之后推出的iPhone3G和iPhone3GS也都是遵循这样的分辨率。显然,如果你在这个时候创建一个App,一个点对一个像素。后来,苹果推出iPhone4使用的是Retina屏。屏幕分辨率翻倍成640*960,所以Retina屏上的一个点就对应了两个像素。


点阵系统简化了开发者的工作难度。不管屏幕分辨率如何变化(也就是说,分辨率*2变成了1280*1920),我们还是会基于320*480来处理显示的宽度(例如 320×480 for iPhone 4/4s 或者 320×568 for iPhone 5/5s)。点和像素之间的对应关系就交由iOS来处理。


如果不使用自动布局,按钮在StoryBoard 的位置就会固定不变,我们需要大量且难以维护的代码针每一种设备进行重新布局和移位。在我们的的案例中,“Hello World”按钮的坐标设置成(147,318),不管理你使用的是3.5英寸还是4英寸还是5.5英寸的模拟器,iOS绘制出来的按钮都会在规定的位置上--(147,318)坐标。下面这张图说明了button在不同设备中的坐标原点。它解释了为什么“Hello World”按钮只会在iPhone 6/6s上是居中的。而在其它设备中会偏移中心位置,同样的在横屏模式下也会出现这种情况。



显然,我们想让App在所有型号的iPhone中,无论处于横屏还是竖屏模式下都能表现的很好。这就是为什么我们要学习如何自动布局。正如我们刚刚讨论的,它就是布局问题的答案。


所有Auto Layout都与Constraints相关


正如前面提到的,自动布局是其于约束的一套布局系统。它充许开发者开发出一套能够响应不同尺寸设备以及方向的界面。听起来好像很厉害的样子。但是基于“基于约束布局”是什么意思呢?


再拿 “Hello World”按钮来说,如果想把它放在视图的中心,你该如何描述它的位置呢?你可能会像这样来描述它:


无论屏幕的分辨率和方向如何,按钮应该处于水平和垂直居中位置。


你确切的会定义两个约束:

  • 水平居中

  • 垂直居中


这些约束用来表达按钮在界面上显示的规则。


虽然我们使用的是文字的方式来进行描述的,但这些约束在自动布局中会被表达成数形式。比如,定义一个按钮的位置,你可能会说“按钮左边距离容器左边距离为30个点.”它会被翻译成


button.left = (container.left + 30)


不过并不需要处理这样公式,但你必须知道如何表达约束条件并使用Interface Builder 来创建它们。


好吧,我们很透彻的讲解了自动布局的理论。现在我们来看下如何在Interface Builder定义 “Hello World”按钮居中的约束条件。


Interface Builder实时预览


首先,打开HelloWorld 项目中的 Main.storyboard (点击下载),在用户界面添加布局约束之前,先来介绍下Xcode 8的新特性。


Xocde 8 在Interface Buidler中提供一个 configuration bar来实时展现用户界面,而不是在模拟器中展示App界面。


默认情况下,Interface Builder会显示iPhone 6s上的UI。想查看你的APP在其它设备上的效果,点击 View as: iPhone 6s 按钮弹出configuration bar,然后选择 iPhone/iPad设备来进行测试。你也可以选择设备的方向来查看你 APP UI表现效果,下面这张图用来展现Hello World 应用在iPhone 6s 中横屏即时效果。



configuration bar 在Xcode是一个非常棒的特性,多花点时间玩玩这玩意儿。


注意: 你可能很想知道“wC hC”是什么意思。暂时跳过它吧,把注意力放在学习自动布局上,你有兴趣想学得更多可以点击查看我的Swift book


使用自动布局居中按钮


现在讨论一下自动布局,Xcode提供了两种式来定义自动布局的约束:

  • Auto layout bar

  • Control-drag


接下来演示这两种方式。首先,从Auto layout bar开始入手。Interface Builder 编辑窗口的右下角的角落里找到4个按钮,这些按钮共同组成了layout bar。你可以使用它们来定义各种各样布局约束。



每个Button都有它自己的作用:


  • Align — 创建对齐约束,例如使两个视图左对齐。

  • Pin — 创建间隔约束,例如定义一个UI的宽度控制。

  • Issues — 解决布局问题

  • Stack  —  嵌入视图到一个堆叠视图。Stack View在Xcode7开始才有的新特性。下篇文章中我们继续讨论这个放题。


正如前面所讨论的,将“Hello World”按钮居中,你必须定义两个约束:水平居中和垂直居中。视图要同时满足这两个条件。


创建这两个约束,使用Align功能。首先在Interface Builder中选中该按钮,点击Align icon。在弹出的菜单中,选择“Horizontal in container”和“Vertically in container”,然后点击“Add 2 Constraints”按钮。



小提示:你可以住Command+0键来隐藏项目导航栏。可以节省更多屏幕空间。


现在你应该可以看到一组约束线,如果你展开document outline视图中的Constraints选项,你将发现为按钮新增了两个约束。这些约束可以确保此按钮总是处于视图的中心位置,另外,你也可以在Size inspector中查看约束。



小提示:当你的视图布局配置清晰正确时,约束线是蓝色的。


好了,可以测试应用了,你可以在iPhone6/6s Plus(或者iPhone 4s)上运行你的APP了。


另一种方法,在configuration bar选择其它设备,或更改设备方向来验证你的布局是否可行。不管屏幕尺寸和方向,按钮都是居中的。


修复布局约束中的错误


我们上边正确地设置了layout contraints。但也不总是这样,Xcode可以智能检测所有约束问题。


把Hello World按钮拖到屏幕左下方。Xcode会立即检测出布局错误并更正,相应的约束线也会变成橙色来指出错误的约束项。



当所创建的布局约束有问题时,自动布局的issues就会发生。就是说按钮本应处于容器水平且垂直居中的位置,但现在按钮却处于视图的左下角,因此会用橙色的线来标识布局错误。


不管是哪种布局问题,Document outline视图都会显示一个红色/黄色箭头。点击错误提示剪头会列出所有的issues。Interface Builder非常聪明地为我们解决了布局问题。点击指示器图标会弹出视图展示一系列解决方案。案例中,选择“更新坐标” 选项,或者点击“修复错位”按钮,按钮就会移动到视图的居中位置。



这个布局问题是手动触发的。我只是想用它来展示如何查找问题并修复它们。当你经过下面章节的练习之后,你可能会遇到类似的布局问题。你应该可以快速毫无压力的解决这样的问题。


预览Storyboards的另一种方式


虽然可以使用configuration bar 实时预览APP UI,不过Xcode为开发者提供了一种同时在不同设备上预览用户界面的功能。


在Interface Builder中,打开Assistant pop-up menu->Preview(1)。按住option键的同时点击Main.Storyboard(Preview),你可以参照下图步骤:



Xcode会在assistant editor中显示预览APP 界面。默认会在iPhone6s 设备上显示预览。你可以点击assistant editor的左下角的 +按钮添加其它的设备(例如iPhone 4s/SE)来进行预览。如想查看横屏显示效果,单击旋转按钮。在设计app用户界面时这是一个非常有用的新特性。当你在storyboard 添加一个新的按钮时,你可以一次性的查看UI在所有所选设备上的效果。



如果你想更多的显示预览面板,时同按下command+option键然后再按住 o 键陷藏活动区域。


小提示:当你在preview assistant添加更多的设备时,Xcode并不能完好在屏幕上同时展示所有的设备,如果你使用的是触控板,可以通过使用两个手指在触控板上左右滑动来滚动预览,如果你仍然是使用事滚动轮的鼠标,按住 shift键水平滚动。


添加label


现在你肯定对自动布局和预览特性有些想法,现在在视图的右下角添加一个label并查看如何为它定义布局约束。Label在iOS中通常用来显示简单的文本及信息。


在Interface Builder编辑器中,从Object Library拖出一个Label并放置视图的右下角。双击Label把标题文字改成”Welcom to Auto Layout”或者你想要的标题。



再次打开预览会看到UI立马就变了,再没有为Lable被定义好布局约束的情况下,除了iPhone6s和iPhone 6s Plus,在其它作何iPhone手机上面都显示不出来。



我们如何解决这个问题呢?显然,需要定义两个约束使它能够正常显示。但问题是:我们需要给它加什么约束?


我们使用文字来描述Label所必须的约束条件,你可能会这样描述:Lable 应该处于示图的右下角。


不够精确。使用精确的方式来描述Label的位置如下:这个 Label处于距离视图右边0个点并且距离视图底部20个点。


这样就再好不过了,当你精确的描述了一个item的位置之后,你就很容易的得出布局约束条件。看这里,我们这样定义约束:


  • Label距离视图右边0个点

  • Label距离视图底部20个点


在自动布局中,我们把这种约束称为间隔约束。创建间隔约束可使用Pin布局按钮。但这时我们使用 拖拽的途径应用自动布局。在Interface Builder中,当想新增一个约束时你可以从一个控件线轴拖到另一个控制上。


按住 control键,把label向右边拖拽,直到视图变成蓝色高亮显示。松开之后你就会看到弹出菜单列出来的可选项。


选择Trailing space to container margin来添加一个从lable到视图右边缘的间隔约束。



在document outline视图中你应该可以看到一个新的约束。现在会显示出一条红色的约束线。这很正常,因为你还没有定义第二个约束条件。


同样的,从Label拖出一根轴线到view底部,然后放开,在弹出菜单中选择“Vertical Sapcing to Botton Layout Guide”。这就从Label视图底部创建了一个间隔约束。



创建两个约束后,所有的约束线会变成蓝色,当前在模拟器中运行APP或预览UI的时候,Label在所有的屏幕都可以正常显示,即使是横屏模式下。



Top and Bottom Layout Guide


你可能会想Bottom Layout Guide(底部布局参考线)会是一个什么玩意儿,通常来说,Bottom Layout Guide指的是视图的底部的参照线。就像下面图片例子中所显示的那条蓝色的线(顶部布局参考线)。有时候,Bottom Layout Guide会有所变动。例如如果你使用了NavigacitonCtroller,APP运行的时候底部会有一条BottomBar。有时候你使有了Tab Bar底部也会有一条Tab Bar。在此种情况下,底部布局参考线会以BottomBar或Tab Bar的顶部作为参考线。就Top Layout Guide来说,它位于距离视图顶部20个点的位置。



这些布局向导对定义布局约束非常的有用,因为当视图布局改变时它可以自动更改其位置。举个例子,如果视图包含导航栏,top layout guide会在导航栏的下方(见 5-17图)。因此只要UI对象相对于top/bottom layout guide进行了约束,那么即便你在界面上天界了导航或者tab栏,界面布局也会正确显示。



编辑约束


 “Welcome to Auto Layout”标签现在距离视图右边0个点,如果你想在Lable 与父视图之间加间隔约束,你改如何来做?


Interface Buidler 提供了一种非常方便的方式来编辑约束常量。


你可以单击 document outline视图中的约束条件,选中”trailingMargin” 约束,在Attributes inspector面板,你可以找到约束相关的属性,包括关系、常量、优先级。现在constant  是0,你可以把它改成20。



练习


现在,我希望你对APP UI布局和屏幕大小适配有所了解了,在我们进入下一章节之前我们来做一个简单的练习。你需要添加一个新的label并命名为”Learn Swift”,给它添加如下约束:


  • 这个新的Labe距离top layout guide 40个点

  • 这个新的label水平居中


你也可以将Label的字体增加到30个点。打开Attributes inspector并编辑Font option改变字体的大小。你最终的结果如下所示:


小结


在这章中,我们学习了自动布局的知识,但都是一些基础的东西。当我们深入研究并且创建一个真正的app的时候,我们会继续讲解auto layout中的其它特性。


大多数的初学都避免使用他们因为它看起来是那么的复杂。如果你理解了我这章中所覆盖的内容,你正走在牛逼iOS开发者的路上。第一款iPhone是在2007年发布的。过去了那么年,iOS开发领域发生了巨大的变化。过去APP只运行在3.5尺寸设备的美好日子一去不复返了。现在你必须要适配不同分辨率和尺寸。这就是为会我要花一整篇文章来讲解它的原因。


所以花点时间好好的琢磨它。


    本站是提供个人知识管理的网络存储空间,所有内容均由用户发布,不代表本站观点。请注意甄别内容中的联系方式、诱导购买等信息,谨防诈骗。如发现有害或侵权内容,请点击一键举报。
    转藏 分享 献花(0

    0条评论

    发表

    请遵守用户 评论公约

    类似文章 更多