Masonry的简单使用

作者: 璞大大 | 来源:发表于2015-07-05 18:23 被阅读69110次

    首先,在正式使用Masonry之前,我们先来看看在xib中我们是如何使用AutoLayout


    从图中我们可以看出,只要设置相应得局限,控制好父视图与子视图之间的关系就应该很ok的拖出你需要的需求。这里就不详细讲解具体拖拽的方法.....

    然后,我们按着上图的属性来看看如何简单得使用Masonry

    这里是Masonry给我们的属性

     @property (nonatomic, strong, readonly) MASConstraint *left;         //左侧

     @property (nonatomic, strong, readonly) MASConstraint *top;        //上侧

     @property (nonatomic, strong, readonly) MASConstraint *right;      //右侧

    @property (nonatomic, strong, readonly) MASConstraint *bottom;   //下侧

    @property (nonatomic, strong, readonly) MASConstraint *leading;   //首部

    @property (nonatomic, strong, readonly) MASConstraint *trailing;   //尾部

    @property (nonatomic, strong, readonly) MASConstraint *width;     //宽

    @property (nonatomic, strong, readonly) MASConstraint *height;    //高

    @property (nonatomic, strong, readonly) MASConstraint *centerX;  //横向居中

    @property (nonatomic, strong, readonly) MASConstraint *centerY;  //纵向居中

    @property (nonatomic, strong, readonly) MASConstraint *baseline; //文本基线

    属性有了,接着我们应该怎么在视图中添加约束呢,Masonry给我们提供了3个方法

    //新增约束
     - (NSArray *)mas_makeConstraints:(void(^)(MASConstraintMaker *make))block;

    //更新约束
     - (NSArray *)mas_updateConstraints:(void(^)(MASConstraintMaker *make))block;

    //清楚之前的所有约束,只会保留最新的约束
     - (NSArray *)mas_remakeConstraints:(void(^)(MASConstraintMaker *make))block;
     
     合理的利用这个3个函数,基本上可以应对任何情况了

    准备工作已经完成,我们来看几个小demo

    1.居中一个view

        // 防止block中的循环引用
        __weak typeof (self) weakSelf = self;
        // 初始化一个View
        UIView *bgView = [[UIView alloc]init];
        bgView.backgroundColor = [UIColor redColor];
        [self.view addSubview:bgView];
        // 使用mas_makeConstraints添加约束
        [bgView mas_makeConstraints:^(MASConstraintMaker *make) {
            make.center.equalTo(weakSelf.view);
            make.size.mas_equalTo(CGSizeMake(200, 200));
        }];

    效果图1

    是不是很简单,这里有一点要必须注意下,添加约束前必须要把view添加到视图上。

    那我要是不想固定他得宽高呢,让view的大小根据间距来控制怎么做

    我们来设置一个基于父视图间距为10的view

    [bgView mas_makeConstraints:^(MASConstraintMaker *make) {
            make.center.equalTo(weakSelf.view);
            make.edges.mas_offset(UIEdgeInsetsMake(10, 10, 10, 10));
     }];

    这样就ok了!!!

    make.edges.mas_offset(UIEdgeInsetsMake(10, 10, 10, 10));

    等同于 

        make.top.equalTo(weakSelf.view).with.offset(10);
        make.left.equalTo(weakSelf.view).with.offset(10);
        make.bottom.equalTo(weakSelf.view).with.offset(-10);
        make.right.equalTo(weakSelf.view).with.offset(-10);

    2.多个view

    2个view横向居中,第二个view距离第一个view间距为10

        UIView *view1 = [[UIButton alloc]init];
        view1.backgroundColor = [UIColor redColor];
        [self.view addSubview:view1];
        [view1 mas_makeConstraints:^(MASConstraintMaker *make) {
            make.size.mas_equalTo(CGSizeMake(90, 90));
            make.centerX.equalTo(weakSelf.view);
            make.top.width.offset(90);
        }];
       
        UIView *view2 = [[UILabel alloc]init];
        view2.backgroundColor = [UIColor yellowColor];
        [self.view addSubview:view2];
        [view2 mas_makeConstraints:^(MASConstraintMaker *make) {
            make.size.mas_equalTo(CGSizeMake(100, 100));
            make.centerX.equalTo(view1);
            make.top.equalTo(view1.mas_bottom).with.offset(20);
        }];

    效果图2

    大家有没有看到第二个view代码中

    make.top.equalTo(view1.mas_bottom).with.offset(20);

    view1.mas_bottom 是什么意思呢?如果只写view1,Masonry会默认是view1中最上面开始算起,也就是view2 间距view1 Y轴开始20的间距

    通过这个也就可以很方便的设置view同另一个view之间上下左右的间距了

    大家不妨试试view.mas_top  view.mas_left  view.mas_right 的效果是什么样得了

    下面我附上一个完整的界面demo,大家可以看看

    效果图3

    代码如下:

    - (void)setupFrame {
        __weak typeof(self) weakSelf = self;

        //上传头像
        UIButton *iconBtn = [[UIButton alloc]init];
        [iconBtn setCornerRadius:45];
        [iconBtn setBackgroundImage:[UIImage imageNamed:@"huantouxiang"] forState:UIControlStateNormal];
        [iconBtn addTarget:self action:@selector(iconButton) forControlEvents:UIControlEventTouchDown];
        [self.view addSubview:iconBtn];
        self.iconBtn = iconBtn;

        [self.iconBtn mas_makeConstraints:^(MASConstraintMaker *make) {
            make.size.mas_equalTo(CGSizeMake(90, 90));
            make.centerX.equalTo(weakSelf.view);
            make.top.width.offset(90);
        }];
       
        //上传社区头像文字提醒
        UILabel *iconLabel = [[UILabel alloc]init];
        iconLabel.textColor = c3;
        iconLabel.text = @"上传社团头像";
        iconLabel.font = [UIFont systemFontOfSize:15];
        [self.view addSubview:iconLabel];
       
        [iconLabel mas_makeConstraints:^(MASConstraintMaker *make) {
            make.centerX.equalTo(iconBtn);
            make.top.equalTo(iconBtn.mas_bottom).with.offset(20);
        }];
       
        //社团编辑图标
        UIImageView *editIcon = [[UIImageView alloc]init];
        editIcon.image = [UIImage imageNamed:@"bianxie"];
        [self.view addSubview:editIcon];
       
        [editIcon mas_makeConstraints:^(MASConstraintMaker *make) {
            make.size.mas_equalTo(CGSizeMake(25, 20));
            make.left.equalTo(weakSelf.view).with.offset(10);
            make.top.equalTo(iconLabel.mas_bottom).with.offset(30);
        }];
       
        //社团名
        UITextField *nameText = [[UITextField alloc]init];
        nameText.placeholder = @"请填写社区名(社团名最多6个字)";
        [self.view addSubview:nameText];
        self.nameText = nameText;
       
        [nameText mas_makeConstraints:^(MASConstraintMaker *make) {
            make.height.mas_equalTo(@20);
            make.centerY.equalTo(editIcon);
            make.right.equalTo(weakSelf.view).with.offset(-10);
            make.left.equalTo(editIcon.mas_right).with.offset(5);
        }];
       
        //分割线
        UIImageView *xian = [[UIImageView alloc]init];
        xian.backgroundColor = DBColor(226, 226, 226);
        [self.view addSubview:xian];
       
        [xian mas_makeConstraints:^(MASConstraintMaker *make) {
            make.height.mas_equalTo(@1);
            make.left.equalTo(weakSelf.view).with.offset(10);
            make.right.equalTo(weakSelf.view).with.offset(-10);
            make.top.equalTo(editIcon.mas_bottom).with.offset(5);
        }];
       
        //选择标签
        UILabel *tagLabel = [[UILabel alloc]init];
        tagLabel.text = @"选择标签";
        tagLabel.textColor = c3;
        tagLabel.font = [UIFont systemFontOfSize:15];
        [self.view addSubview:tagLabel];
       
        [tagLabel mas_makeConstraints:^(MASConstraintMaker *make) {
            make.height.mas_equalTo(@20);
            make.width.mas_equalTo(@60);
            make.left.equalTo(weakSelf.view).with.offset(10);
            make.top.equalTo(xian).with.offset(35);
        }];
       
        //跳转标签选择
        UITextField *tagText = [[UITextField alloc]init];
        tagText.placeholder = @"美容颜";
        tagText.borderStyle=UITextBorderStyleRoundedRect;
        tagText.delegate = self;
        [tagText addTarget:self action:@selector(textTag) forControlEvents:UIControlEventTouchDown];
        [self.view addSubview:tagText];
       
        [tagText mas_makeConstraints:^(MASConstraintMaker *make) {
            make.centerY.equalTo(tagLabel);
            make.right.equalTo(weakSelf.view).with.offset(-10);
            make.left.equalTo(tagLabel.mas_right).with.offset(5);
        }];
       
        //tagView
        self.tagView = ({
            SKTagView *view = [SKTagView new];
            view.backgroundColor = [UIColor clearColor];
            view.padding    = UIEdgeInsetsMake(0, 0, 0, 0);
            view.insets    = 15;
            view.lineSpace = 10;
            __weak SKTagView *weakView = view;
            view.didClickTagAtIndex = ^(NSUInteger index){
                //Remove tag
                [weakView removeTagAtIndex:index];
            };
            view;
        });
        [self.view addSubview:self.tagView];
        [self.tagView mas_makeConstraints:^(MASConstraintMaker *make) {
            make.left.equalTo(weakSelf.view).with.offset(10);
            make.right.equalTo(weakSelf.view).with.offset(-10);
            make.top.equalTo(tagText.mas_bottom).with.offset(10);
        }];
       
        //label标识语
        UILabel *label = [[UILabel alloc]init];
        label.font = [UIFont systemFontOfSize:13];
        label.textColor = [UIColor redColor];
        label.text = @"PS:成员和视频越多得社团越容易被发现!";
        [self.view addSubview:label];
       
        [label mas_makeConstraints:^(MASConstraintMaker *make) {
            make.left.equalTo(weakSelf.view).with.offset(10);
            make.right.equalTo(weakSelf.view).with.offset(-10);
            make.top.equalTo(self.tagView.mas_bottom).with.offset(20);
        }];
       
        UIButton *commitBtn = [[UIButton alloc]init];
        [commitBtn setCornerRadius:5];
        [commitBtn setBorderWidth:1 color:DBTextThemeColor];
        [commitBtn setTitleColor:DBTextThemeColor forState:UIControlStateNormal];
        commitBtn.titleLabel.font = [UIFont systemFontOfSize:15];
        [commitBtn setTitle:@"确认发布" forState:UIControlStateNormal];
        [commitBtn addTarget:self action:@selector(commitButton) forControlEvents:UIControlEventTouchDown];
        [self.view addSubview:commitBtn];
       
        [commitBtn mas_makeConstraints:^(MASConstraintMaker *make) {
            make.height.mas_equalTo(@30);
            make.left.equalTo(weakSelf.view).with.offset(10);
            make.right.equalTo(weakSelf.view).with.offset(-10);
            make.top.equalTo(label.mas_bottom).with.offset(50);
        }];
    }

    第一次写博客,写的比较乱 。 希望大家多多提意见......

    相关文章

      网友评论

      • 浅浅浅丶蓝:你好, SKTagView 的源码能给一下吗
        璞大大:@浅浅浅丶蓝 太久远了 已经找不到了
      • 杨振可:make.top.width.offset(90);这句不是太懂
        杨振可:@着小铺 那个不是应该是间距吗。或者叫距离顶部的高度。宽度用的很是转不过弯。
        璞大大:@杨振可 到顶部90的宽度
      • 庄欲以莘:你好,有这个类的写法么?SKTagView 就是不会用masonry写标签
        庄欲以莘:@着小铺 明白了 谢谢
        璞大大:@庄欲以莘 不好意思哈 这个是一个标签的控件 你可以用别的控件代替
      • 庄欲以莘:你好,有这个类的写法么?SKTagView 就是不会用masonry写标签
      • 庄欲以莘:你好,有这个类的写法么?SKTagView 就是不会用masonry写标签
      • 谢谢生活:可以不用weakSelf吧
      • 4ca121cd0274:你好选择标签的view是怎么实现的
      • 0faa6f881ade:self.tagView 属性定义是什么 怎么还能等于 () 呢?
      • 个性小资:问下,在这里设置了上传头像按钮的大小是90*90,那如果在不同分辨率的机型下,是会等比缩放,还是就固定了尺寸了?
        [self.iconBtn mas_makeConstraints:^(MASConstraintMaker *make) {
                make.size.mas_equalTo(CGSizeMake(90, 90));
                make.centerX.equalTo(weakSelf.view);
                make.top.width.offset(90);
            }];
      • __Feng:有没有一个demo地址啊,这个复制过去好多空格有问题。。
        璞大大:@__Feng 这个好老了 不建议在参考了
      • Lotty周小鱼:Masonry 中不需要写 weakSelf。请参考 『深入研究Block用weakSelf、strongSelf、@weakify、@strongify解决循环引用』http://www.jianshu.com/p/701da54bd78c
        璞大大:@小鱼周凌宇 哈哈 谢谢指教了 这篇 太早了 应该更新了
      • 若雨千寻:下边的标签怎么布局啊?好像是随机的
        若雨千寻:嗯嗯,好的
        璞大大:@若雨千寻 SKTagView 网上搜一下
      • 青空逸隐:温故而知新
      • ca04a13f364c:请问一下make.top.width.offset(90); 和 make.top.equalTo(viewA).with.offset(90); 是一个意思吗
        璞大大:@nolews 默认是基于父视图 这个主要看使用场景
      • Rickie_Lambert:__weak typeof(self) weakSelf = self;

        这句话 做什么用的?? 我发现 好多人都喜欢用这个 weakSelf, 到底是做什么用的? 请指教
        Rickie_Lambert:@_Angelo_ 谢谢
        6f32d34c09c6:@Mr_Rain 防止循环引用
      • HuLL乐乐:不错不错,写的不不乱,你好谦虚呀
      • 别叫我超人:写的很好 只是__weak typeof(self) weakSelf = self;这没必要进行弱引用,这里的block是局部的
      • 凯文Kevin21:有那个图片素材吗
      • 凯文Kevin21:我想要最后一个Demo的源码
      • 凯文Kevin21:最后一个Demo可以共享一下源码到github上吗。。楼主,,,
      • 凯文Kevin21:Mark,写得很好。,。特别是最后一个Demo,
      • code_间特门:还有 你下面的标签怎么做 能否给个demo
      • code_间特门:能否再问一下,weakSelf到底什么时候使用,我看到你的代码了,好像都是在约束的时候使用weakSelf!!!!
        琥珀之剑:block里面用防止循环引用
      • code_间特门:这个我看懂了,这可以很简单的去约束空间的位置。但我还想问的是,在不同的机型上适配,向我们用的例如:make.top.equalTo(iconBtn.mas_bottom).with.offset(20),这个“20”是否要变成比例的如:(假如用的是4s)是否这样写才能适配各种机型make.top.equalTo(iconBtn.mas_bottom).with.offset((20/480)*KScreen.size.height),
      • 深蓝_S:你的SKTagView这里是自己又创建的类吗? 这里不太明白。。求解
        璞大大:@Mr_Chen_Ly 自己的控件
      • 华之曦:用markDown编辑下效果会好很多哦。
      • d18d3ce70d1d:设置头像约束时的 centerX,和center以及centerY的区别是什么?刚接触Masonry,请指教!
        18aa8f12b69d:@龍轶绯於 center 也可以理解水平垂直都剧中
        琥珀之剑:centerX水平居中,center中心点,centerY垂直居中
      • WorkFromHome:有些地方看不太懂
      • 朋友有朋:你上面对于storyboard的讲解非常的好,正是我需要的
      • 朋友有朋:这个宽高不用设置吗·?
        璞大大:@朋友有朋 看你是否需要固定Label的位置 ,不设置的话,Label会根据内容自适应,前提是你的约束要设置正确
      • 朋友有朋:伙计,我有个地方不是很懂,还希望指导文/赵璞(简书作者)
        原文链接:http://www.jianshu.com/p/f0b17ecfd04e
        著作权归作者所有,转载请联系作者获得授权,并标注“简书作者”。

        //上传社区头像文字提醒    UILabel *iconLabel = [[UILabel alloc]init];    iconLabel.textColor = c3;    iconLabel.text = @"上传社团头像";    iconLabel.font = [UIFont systemFontOfSize:15];    [self.view addSubview:iconLabel];        [iconLabel mas_makeConstraints:^(MASConstraintMaker *make) {        make.centerX.equalTo(iconBtn);        make.top.equalTo(iconBtn.mas_bottom).with.offset(20);    }];这个为什么没有设置UILabel的宽高?
        85732d8c0045:label不设置就会自适应
      • clb:讲的很好哈 多谢了
      • qBryant:正好项目用了,学习了。。。 :smile:
      • 最初九月雪:UIView *view1 = [[UIButton alloc]init];
        view1.backgroundColor = [UIColor redColor];
        [self.view addSubview:view1];
        [view1 mas_makeConstraints:^(MASConstraintMaker *make) {
        make.size.mas_equalTo(CGSizeMake(90, 90));
        make.centerX.equalTo(weakSelf.view);
        make.top.width.offset(90);
        }];
        这里的make.top.width.offset(90);应该是make.top.with.offset(90);吧?
        我没太看懂
        aee79f239e71:@Booooooooom 但是已经设置过width,这么写就重复了,容易误导读者,建议修改
        Booooooooom:@luckychenhc 实质上就是 make.top.and.width.offset(90); 是一种链式语句,可以看做是让上和宽偏移量为90,很简单易懂的,就跟读短句一样
        qBryant:@luckychenhc 这里的top和width如果offset相同的话,都是90的,可以连起来写,make.top.width.offset(90);
      • 七七飞机大神:楼主好,我想问一下,Masonry是不是已经做了对各种机型屏幕的适配啊?还有关于图片适配的问题,系统会自动根据屏幕的分辨率寻找@2x图片和@3X的图片吗?
      • 01b85ef5c24a:直接拖的话应该引哪个头文件呢
        个性小资:@colaios 创建个PCH文件,引用下就可以了,可以在GITHUB下载Masonry的项目,看看demo中的例子,PCH里就直接引用了 #import "Masonry.h"
      • 601f2985c406:熟悉了一定改用这个
      • a92b53eda0ed:Masonry是直接拖进工程的还是pods管理的?我的直接拖进工程报错~
        个性小资:@lizi17 都可以,然后在项目中创建个PCH文件,引用下就可以了,可以在GITHUB下载Masonry的项目,看看demo中的例子
        璞大大:@lizi17 两种方法都可以,报错要看看是什么原因
      • Teehom:嗯第一次,有些讲得不是透切
      • 璞大大:@我不是艾小璞 程序猿的世界 :stuck_out_tongue:
      • 1a2f450a1361:你发的我都👀不懂呢
        aa04fc7c8d9c:@叶舞清风 首尾对应left和right,国内两者木有区别,国外就不一定了
        叶舞清风:上下和首尾有什么区别吗???
        LIANGMIAOPM:@阿拉蕾的艾小璞 那是因为你对autolayout不熟悉

      本文标题:Masonry的简单使用

      本文链接:https://www.haomeiwen.com/subject/zxwsqttx.html