Swift编程之Snapkit

写在前面(Github地址)
主要记录了,我在学习Snapkit中的一些整理记录
学习目标
好好学习如何用代码来做自动布局
使用SnapKit做了一个修改密码的表单

效果图

  1. Snapkit的安装
    Cocoapods安装
    在项目的Podfile下添加如下信息
    在终端中执行:pod install(注意路径是当前项目中Podfile锁在路径)
swiftsource'https://github.com/CocoaPods/Specs.git'platform :ios,'8.0'use_frameworks!pod'SnapKit','~> 0.15.0'

Carthage安装
Carthage是一种分散式依赖管理库用来自动为你的Cocoa应用添加第三方框架
1) 通过下面命令行执行安装Carthage
swiftbrewupdatebrewinstallcarthage
2) 通过下面命令行继承SnapKit到你的项目中的Cartfile

swiftgithub"SnapKit/SnapKit">=0.15.0

3.)通过直接讲SnapKit的源代码拖放到自己的项目目录当中
这也是我比较喜欢的一种方式,这样可以比较自由的讲代码拖放到自己执行的目录下

  1. SnapKit的兼容操作
    如果希望SnapKit支持IOS7版本,需要在自己的项目的 Build Setting 中搜索的 OTHER_SWIFT_FLAGS,在其下面添加 -DSNAPKIT_DEPLOYMENT_LEGACY,如下图所示:(否则会报错!)


示意图

  1. Snapkit官方文档翻译
    通用模式:
swiftletbox =UIView()superview.addSubview(box)box.snp_makeConstraints { (make) ->Voidin//解释:box对象相对于父视图上边距为20像素make.top.equalTo(superview).offset(20)  make.left.equalTo(superview).offset(20)  make.bottom.equalTo(superview).offset(-20)  make.right.equalTo(superview).offset(-20)}

注意:在SnapKit当中 X轴向右方向;Y轴向下方向 为正

缩写形式
swiftlet box = UIView()superview.addSubview(box)box.snp_makeConstraints { (make) -> Void in//注释:box距离父
视图上下左右边距都是20像素make.edges.equalTo(superview).inset(UIEdgeInsetsMake(20,20,20,20))}

SnapKit还可以通过下面几个步骤来实现缩短代码和提高代码可读性
确定最佳的普通视图安装限制。
保持轨道的约束安装所以他们可以很容易地被删除后。
在所有适当的视图上确保setTranslatesAutoresizingMaskIntoConstraints(false)属性被设置
SnapKit中并不局限于 等于(equalTo)

.equalTo:等于
.lessThanOrEqualTo 小于等于
.greaterThanOrEqualTo 大于等于
1.视图属性
//当前视图对象的中心x坐标小于等于view视图的左边的x左边make.centerX.lessThanOrEqualTo(view.snp_left)
视图属性:
上 :上边对应的Y轴 (top)
下: 下边对应的Y轴 (bottom)
左: 左边对应的Y轴 (left)
右: 右边对应的X轴 (right)
视图属性(ViewAttribute)布局属性 (NSLayoutAttribute)
view.snp_leftNSLayoutAttribute.Left
view.snp_rightNSLayoutAttribute.Right
view.snp_topNSLayoutAttribute.Top
view.snp_bottomNSLayoutAttribute.Bottom
view.snp_leadingNSLayoutAttribute.Leading
view.snp_trailingNSLayoutAttribute.Trailing
view.snp_widthNSLayoutAttribute.Width
view.snp_heightNSLayoutAttribute.Height
view.snp_centerXNSLayoutAttribute.CenterX
view.snp_centerYNSLayoutAttribute.CenterY
view.snp_baselineNSLayoutAttribute.Baseline

2.视图关系(UIView/NSView)
如果你想 视图 view.left 大于等于 label.left ,执行下面代码:

swift//下面这两者的约束是完全一样的make.left.greaterThanOrEqualTo(label)make.left.greaterThanOrEqualTo(label.snp_left)

3.严格检测(Strick Checks)
自动布局允许将宽度和高度属性设置为常量值。如果你想对视图设置一个最小和最大宽度,你必须先给他一个初始的平等块:

设置宽度>= 200 && <= 400

你也可以用其他的约束和结构来建立你的约束,像这样:

swiftmake.top.equalTo(42)make.height.equalTo(20)make.size.equalTo(CGSizeMake(50,100))make.edges.equalTo(UIEdgeInsetsMake(10,0,10,0))make.left.equalTo(view).offset(UIEdgeInsetsMake(10,0,10,0))

4.学习优先级

.priority: 允许您指定一个确切的优先级
.priorityHigh: 高优先级 等价于 UILayoutPriority.DefaultHigh
.priorityMedium:中优先级
.priorityLow:低优先级 UILayoutPriority.DefaultLow

优先级可以放在约束链的结束处,例如

swift//当前视图的左边>=label的底部 低优先级make.left.greaterThanOrEqualTo(label.snp_left).priorityLow()//当前视图与label的顶部齐平,优先级:600make.top.equalTo(label.snp_top).priority(600)

5.组成,组成,组成

SnapKit 也可以提供一些便利的方法来同时创建多约束
edges(边缘)
swift//让当前视图 的 上下左右(top,left,bottom,right) 等于 view2make.edges.equalTo(view2)// make top = superview.top + 5; left = superview.left +10// bottom = superview.bottom -15; right = superview.right - 20make.edges.equalTo(superView).inset(UIEdgeInsetsMake(5,10,15,20))

2.size(尺寸)

swift//当前视图宽高 >= titleLabelmake.size.greaterThanOrEqualTo(titleLabel)//make width = superview.width + 100; height = superview.height -50//即 当前视图宽 = 父视图 + 100,高 = 父视图.高 - 50make.size.equalTo(superview).offset(CGSizeMake(100, -50))
3.center(中心)
swift//当前视图与 button1中心相同 (centerX 和 centerY)make.center.equalTo(button1)//make centerX = superview.centerX - 5; centerY = superview.centerY +10make.center.equalTo(superview).offset(CGPointMake(-5,10))
您可以串连视图属性增加可读性
swift//所有边缘除了top都等于父视图, top为20make.left.right.bottom.equalTo(superview)make.top.equalTo(20)
6.Hold on for dear life
有时候你需要修改已经存在的约束为了移动或者移除、代替约束。在SnapKit 有一些不同的方法更新约束
1.引用(References)
你可以通过将约束的结果赋值给一个局部变量或一个类属性来保持一个特定的约束的引用。您还可以将多个约束引用存储在数组中。
swiftvartopConstraint:Constraint? =nil//当制作约束时view1.snp_makeConstraints{ (make) ->Voidinself.topConstrain = make.top.equalTo(superview).offset(padding.top).constraint        make.left.equalTo(superview).offset(padding.left)// 然后接下来你可以这样self.topConstraint.uninstall()//或者如果你想要更新约束self.topConstraint.updateOffset(5)
2.snp_updateConstraints(更新约束)
如果你仅仅想更新一个常数给一个约束,你可以使用方法snp_updateConstraints来代替snp_makeConstraints
swift//这是一个苹果官方推荐的添加和更新约束的地方//这个方法在响应setNeedsUpdateConstraints
多次调用//这个方法可以倍UIKit调用overridefuncupdateConstraints(){self.growingButton.snp_updateConstraints{ (make) ->Voidinmake.center.equalTo(self);                make.width.equalTo(self.buttonSize.width).priorityLow()                make.height.equalTo(self.buttonSize.height).priorityLow()                make.width.lessThanOrEqualTo(self)                make.height.lessThanOrEqualTo(self)        }//父类可以调用super.updateConstraints()}
3.snp_remakeConstraints(重做约束)
snp_remakeConstraints与snp_makeConstraints类似,但是首先会先清除掉所有被SnapKit设置的约束
swiftfuncchangeButtonPosition(){self.button.snp_remakeConstraints{ (make) ->Voidinmake.size.equalTo(self.buttonSize)iftopLeft {                        make.top.left.equalTo(10)                }else{                        make.bottom.equalTo(self.view).offset(-10)                        make.right.equalTo(self.view).offset(-10)                }        }}
4.Demo的具体代码(我的Github)
创建属性
swiftvaroldPassword:UITextField!varnewPassword:UITextField!varconfirmPassword:UITextField!varformView:UIView!varconfirmButton:UIButton!vartopConstraint:Constraint?
UI初始化
swift    func initUI(){self.title="修改密码"self.view.backgroundColor=UIColor.redColor()//登录框背景self.formView=UIView()self.formView.layer.borderWidth=0.5self.formView.layer.borderColor=UIColor.lightGrayColor().CGColorself.formView.backgroundColor=UIColor.whiteColor()self.formView.layer.cornerRadius=5self.view.addSubview(self.formView)//最常规的设置模式self.formView.snp_makeConstraints{ (make) -> Voidinmake.left.equalTo(15)            make.right.equalTo(-15)//存储top属性self.topConstraint= make.top.equalTo(200).constraintmake.height.equalTo(220)        }//密码图let imgLock1 =UIImageView(frame:CGRectMake(11,11,22,22))        imgLock1.image=UIImage(named:"iconfont-password")//密码图let imgLock2 =UIImageView(frame:CGRectMake(11,11,22,22))        imgLock2.image=UIImage(named:"iconfont-password")//密码图let imgLock3 =UIImageView(frame:CGRectMake(11,11,22,22))        imgLock3.image=UIImage(named:"iconfont-password")//旧密码输入框self.oldPassword=UITextField()self.oldPassword.delegate=selfself.oldPassword.tag=100self.oldPassword.placeholder="请输入旧密码"self.oldPassword.layer.cornerRadius=5self.oldPassword.layer.borderColor=UIColor.lightGrayColor().CGColorself.oldPassword.layer.borderWidth=0.5self.oldPassword.leftView=UIView(frame:CGRectMake(0,0,44,44))self.oldPassword.leftViewMode=UITextFieldViewMode.Alwaysself.oldPassword.returnKeyType=UIReturnKeyType.Next//密码输入框左侧图标self.oldPassword.leftView!.addSubview(imgLock1)self.formView.addSubview(self.oldPassword)//布局self.oldPassword.snp_makeConstraints{ (make) -> Voidinmake.left.equalTo(30)            make.top.equalTo(20)            make.right.equalTo(-30)            make.height.equalTo(44)        }//新密码输入框self.newPassword=UITextField()self.newPassword.delegate=selfself.newPassword.tag=101self.newPassword.placeholder="请输入新密码"self.newPassword.layer.cornerRadius=5self.newPassword.layer.borderColor=UIColor.lightGrayColor().CGColorself.newPassword.layer.borderWidth=0.5self.newPassword.leftView=UIView(frame:CGRectMake(0,0,44,44))self.newPassword.leftViewMode=UITextFieldViewMode.Alwaysself.newPassword.returnKeyType=UIReturnKeyType.Next//密码输入框左侧图标self.newPassword.leftView!.addSubview(imgLock2)self.formView.addSubview(self.newPassword)//布局self.newPassword.snp_makeConstraints{ (make) -> Voidinmake.left.equalTo(30)            make.top.equalTo(self.oldPassword.snp_bottom).offset(20)            make.right.equalTo(-30)            make.height.equalTo(44)        }//确认新密码输入框self.confirmPassword=UITextField()self.confirmPassword.delegate=selfself.confirmPassword.tag=102self.confirmPassword.placeholder="请重复新密码"self.confirmPassword.layer.cornerRadius=5self.confirmPassword.layer.borderColor=UIColor.lightGrayColor().CGColorself.confirmPassword.layer.borderWidth=0.5self.confirmPassword.leftView=UIView(frame:CGRectMake(0,0,44,44))self.confirmPassword.leftViewMode=UITextFieldViewMode.Alwaysself.confirmPassword.returnKeyType=UIReturnKeyType.Done//密码输入框左侧图标self.confirmPassword.leftView!.addSubview(imgLock3)self.formView.addSubview(self.confirmPassword)//布局self.confirmPassword.snp_makeConstraints{ (make) -> Voidinmake.left.equalTo(30)            make.top.equalTo(self.newPassword.snp_bottom).offset(20)            make.right.equalTo(-30)            make.height.equalTo(44)        }self.confirmButton=UIButton()self.confirmButton.setTitle("确认修改", forState:UIControlState.Normal)self.confirmButton.setTitleColor(UIColor.whiteColor(), forState:UIControlState.Normal)self.confirmButton.layer.cornerRadius=5self.confirmButton.backgroundColor=UIColor(colorLiteralRed:0.99, green:0.82, blue:0.04, alpha:1)self.view.addSubview(self.confirmButton)self.confirmButton.snp_makeConstraints{ (make) -> Voidinmake.left.equalTo(15)            make.top.equalTo(self.formView.snp_bottom).offset(20)            make.right.equalTo(-15)            make.height.equalTo(44)        }    }
UITextField的代理
swiftextensionSnapkitViewController:UITextFieldDelegate{//输入框获取焦点开始编辑functextFieldDidBeginEditing(textField:UITextField){lettag = textField.tagswitchtag {case100:UIView.animateWithDuration(0.5, animations: { () ->Voidinself.topConstraint?.updateOffset(150)self.view.layoutIfNeeded()            })case101:UIView.animateWithDuration(0.5, animations: { () ->Voidinself.topConstraint?.updateOffset(100)self.view.layoutIfNeeded()            })case102:UIView.animateWithDuration(0.5, animations: { () ->Voidinself.topConstraint?.updateOffset(70)self.view.layoutIfNeeded()            })default:print("error")        }    }//输入框返回时操作functextFieldShouldReturn(textField:UITextField)->Bool{lettag = textField.tagswitchtag {case100:self.newPassword.becomeFirstResponder()case101://下一个self.confirmPassword.becomeFirstResponder()case102://收起键盘textField.resignFirstResponder()UIView.animateWithDuration(0.5, animations: { () ->Voidinself.topConstraint?.updateOffset(200)self.view.layoutIfNeeded()            })default:print(textField.text)        }returntrue}}

5.总结一下 UITextField

样式
swiftUITextBorderStyle.None:无边框UITextBorderStyle.Line:直线边框UITextBorderStyle.RoundedRect:圆角矩形边框UITextBorderStyle.Bezel:边线+阴影
输入提示
textField.placeholder="请输入用户名"
内容设置
swift//当文字超出文本框宽度时,自动调整文字大小textField.adjustsFontSizeToFitWidth =true//最小可缩小的字号textField.minimumFontSize =14
对齐方式
swift//水平右对齐textField.textAlignment = .Right//水平居中对齐textField.textAlignment = .Center//水平左对齐textField.textAlignment = .Left//垂直向上对齐textField.contentVerticalAlignment = .Top//垂直居中对齐textField.contentVerticalAlignment = .Center//垂直向下对齐textField.contentVerticalAlignment = .Bottom
设置清除按钮
swift//编辑时出现清除按钮textField.clearButtonMode=UITextFieldViewMode.WhileEditing//编辑时不出现,编辑后才出现清除按钮textField.clearButtonMode=UITextFieldViewMode.UnlessEditing//一直显示清除按钮textField.clearButtonMode=UITextFieldViewMode.Always
设置键盘的类型
swiftDefault:系统默认的虚拟键盘ASCII Capable:显示英文字母的虚拟键盘Numbers and Punctuation:显示数字和标点的虚拟键盘URL:显示便于输入数字的虚拟键盘NumberPad:显示便于输入数字的虚拟键盘Phone Pad:显示便于拨号呼叫的虚拟键盘Name Phone Pad:显示便于聊天拨号的虚拟键盘Email Address:显示便于输入Email的虚拟键盘DecimalPad:显示用于输入数字和小数点的虚拟键盘Twitter:显示方便些Twitter的虚拟键盘Web Search:显示便于在网页上书写的虚拟键盘//例子textField.keyboardType = UIKeyboardType.NumberPad
焦点
swift//获取焦点textField.becomeFirstResponder()//移除焦点textField.resignfirstresponder()
设置返回return样式跟功能
swift//表示完成输入textField.returnKeyType=UIReturnKeyType.Done//表示完成输入,同时会跳到另一页textField.returnKeyType=UIReturnKeyType.Go//表示搜索textField.returnKeyType=UIReturnKeyType.Search//表示注册用户或添加数据textField.returnKeyType=UIReturnKeyType.Join//表示继续下一步textField.returnKeyType=UIReturnKeyType.Next//表示发送textField.returnKeyType=UIReturnKeyType.Send
代理
swift//开始编辑时的操作functextFieldDidBeginEditing()//点击返回按钮时的操作functextFieldShouldReturn()

转载自:Swift编程(六):Snapkit的启示录 - 简书

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 157,298评论 4 360
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 66,701评论 1 290
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 107,078评论 0 237
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 43,687评论 0 202
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 52,018评论 3 286
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 40,410评论 1 211
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 31,729评论 2 310
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 30,412评论 0 194
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 34,124评论 1 239
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 30,379评论 2 242
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 31,903评论 1 257
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 28,268评论 2 251
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 32,894评论 3 233
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 26,014评论 0 8
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 26,770评论 0 192
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 35,435评论 2 269
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 35,312评论 2 260

推荐阅读更多精彩内容