接上篇,本篇继续对Masonry 进行学习,接上篇示例:

(6)Masonry 布局实现iOS 计算器

 - (void)exp4 {
     WS(weakSelf);
     // 申明区域,displayView 是显示布局,keyboardView 是键盘区域
     UIView *displayView = [UIView new]; // 创建并添加 显示区域
     [displayView setBackgroundColor:[UIColor blackColor]];
     [self.view addSubview:displayView];

     UIView *keyboardView = [UIView new];
     [self.view addSubview:keyboardView]; // 添加键盘区域
     // 先按1:3分割 displayView (显示结果区域)和keyboardView (键盘区域)
     [displayView mas_makeConstraints:^(MASConstraintMaker *make) {
         make.top.equalTo(weakSelf.view.mas_top);
         make.left.and.right.equalTo(weakSelf.view); // 顶部和左右 和self.view  相等
         make.height.equalTo(keyboardView).multipliedBy(0.3f); // displayView 的高度是 keyboardView 的高度乘以 0.3 keyboardView 的高度是displayView 高度的三倍
     }];

     [keyboardView mas_makeConstraints:^(MASConstraintMaker *make) {
         make.top.equalTo(displayView.mas_bottom); // 键盘区域的top 紧接着显示结果区域的bottom
         make.bottom.equalTo(weakSelf.view.mas_bottom); // 键盘区域的底部等于self.view 的底部
         make.left.and.right.equalTo(weakSelf.view); // 左右相等
     }];

     // 设置显示位置的数字为0
     UILabel *displayNum = [[UILabel alloc] init];
     [displayView addSubview:displayNum];
     displayNum.text = ";
     displayNum.font = [UIFont fontWithName:]; // 设置字体 @"HeiTi SC"
     displayNum.textColor = [UIColor whiteColor];
     displayNum.textAlignment = NSTextAlignmentRight;
     [displayNum mas_makeConstraints:^(MASConstraintMaker *make) {
         make.left.and.right.equalTo(displayView).with.offset(-); // 左和右各缩进 10
         make.bottom.equalTo(displayView).with.offset(-); // 底部也缩进 10 // label 的高度能根据label 的内容自动适应高度 只要确定一个底部或者顶部就能确定label 的约束 label 的宽度要确定才能确定高度
     }];
     // 定义键盘键名称,? 号代表合并的单元格
     NSArray *keys = @[@"AC", @"+/-", @"%", @"÷"
                       , ", @"x"
                       , ", @"-"
                       , ", @"+"
                       , ", @"?", @".", @"="];
     ;
     for (NSString *key in keys) {
         // 循环所有键
         indexOfKeys++;
          ==  ? indexOfKeys /  : indexOfKeys /  + ; // 求各个key 的行和列 注意是从 1 开始的 求行的时候, 先对 4 取余数, 如果是 0 的话正好是 4 的倍数 ,那就是最后一列的key  indexOfKeys 这个时候是 4 或 8 或 12 或 16 或 20 , 这个时候取 indexOfKeys 的商正好是key 所在的行 ,其他的同理
          ==  ?  : indexOfKeys % ;
         NSLog(@"index is: %d and row: %d, col: %d", indexOfKeys, rowNum, colNum);
         // 键样式
         UIButton *keyView = [UIButton buttonWithType:UIButtonTypeCustom];
         [keyboardView addSubview:keyView];
         [keyView setTitleColor:[UIColor blackColor] forState:UIControlStateNormal];
         [keyView setTitle:key forState:UIControlStateNormal];
         [keyView.layer setBorderWidth:];
         [keyView.layer setBorderColor:[UIColor blackColor].CGColor];
         [keyView.titleLabel setFont:[UIFont fontWithName:]]; // 设置字体 @"Arial-BoldItalicMT"
         // 键约束
         [keyView mas_makeConstraints:^(MASConstraintMaker *make) {
             // 处理 0 合并单元格
             "] || [key isEqualToString:@"?"]) {
                 "]) {
                     [keyView mas_makeConstraints:^(MASConstraintMaker *make) {
                         make.height.equalTo(keyboardView.mas_height).with.multipliedBy(.2f); // 高度是keyboardView 的高度的五分之一
                         make.width.equalTo(keyboardView.mas_width).multipliedBy(.); // 宽度是keyboardView 的宽度的二分之一
                         make.left.equalTo(keyboardView.mas_left); // 左边相等
                         make.baseline.equalTo(keyboardView.mas_baseline).with.multipliedBy(.9f); // 这个baseline 没有看太懂是什么意思
                     }];
                 } if ([key isEqualToString:@"?"]) { // 如果是问号的话直接被移除了
                     [keyView removeFromSuperview];
                 }
             }
             // 正常的单元格
             else {
                 make.width.equalTo(keyboardView.mas_width).with.multipliedBy(.25f); // 正常的单元格的话 宽度是 keyboardView 的宽度的四分之一
                 make.height.equalTo(keyboardView.mas_height).with.multipliedBy(.2f); // 高度是keyboardView 的高度的五分之一
                 // 按照行和列添加约束,这里添加行约束
                 switch (rowNum) {
                     :
                     {
                         make.baseline.equalTo(keyboardView.mas_baseline).with.multipliedBy(.1f);
                         keyView.backgroundColor = [UIColor colorWithRed: green: blue: alpha:];
                     }
                         break;
                         :
                     {
                         make.baseline.equalTo(keyboardView.mas_baseline).with.multipliedBy(.3f);
                     }
                         break;
                     :
                     {
                         make.baseline.equalTo(keyboardView.mas_baseline).with.multipliedBy(.5f);
                     }
                         break;
                         :
                     {
                         make.baseline.equalTo(keyboardView.mas_baseline).with.multipliedBy(.7f);
                     }
                         break;
                         :
                     {
                         make.baseline.equalTo(keyboardView.mas_baseline).with.multipliedBy(.9f);
                     }
                         break;
                     default:
                         break;
                 }
                 switch (colNum) {
                     :
                     {
                         make.left.equalTo(keyboardView.mas_left);
                     }
                         break;
                         :
                     {
                         make.right.equalTo(keyboardView.mas_centerX);
                     }
                         break;
                         :
                     {
                         make.left.equalTo(keyboardView.mas_centerX);
                     }
                         break;
                         :
                     {
                         make.right.equalTo(keyboardView.mas_right);
                         [keyView setBackgroundColor:[UIColor colorWithRed: green: blue: alpha:]];
                     }
                         break;
                     default:
                         break;
                 }
             }
         }];
     }
 }

(7)基础设计页面

 - (void)HYB {
     UIView *greenView = UIView.new;
     greenView.backgroundColor = UIColor.greenColor;
     greenView.layer.borderColor = UIColor.blackColor.CGColor;
     greenView.layer.borderWidth = ;
     [self.view addSubview:greenView];

     UIView *redView = UIView.new;
     redView.backgroundColor = UIColor.redColor;
     redView.layer.borderColor = UIColor.blackColor.CGColor;
     redView.layer.borderWidth = ;
     [self.view addSubview:redView];

     UIView *blueView = UIView.new;
     blueView.backgroundColor = UIColor.blueColor;
     blueView.layer.borderColor = UIColor.blackColor.CGColor;
     blueView.layer.borderWidth = ;
     [self.view addSubview:blueView];

     // 使三个控件等高
     CGFloat padding = ;
     [greenView mas_makeConstraints:^(MASConstraintMaker *make) {
         make.top.mas_equalTo(padding);
         make.left.mas_equalTo(padding);
         make.right.mas_equalTo(redView.mas_left).offset(-padding);
         make.bottom.mas_equalTo(blueView.mas_top).offset(-padding);
         // 三个控件等高
         make.height.mas_equalTo(@[redView, blueView]);
         // 红绿这两个控件等宽
         make.width.mas_equalTo(redView);
     }];

     [redView mas_makeConstraints:^(MASConstraintMaker *make) {
         make.top.height.bottom.mas_equalTo(greenView);
         make.right.mas_equalTo(-padding);
         make.left.mas_equalTo(greenView.mas_right).offset(padding);
     }];

     [blueView mas_makeConstraints:^(MASConstraintMaker *make) {
         make.height.mas_equalTo(greenView);
         make.bottom.mas_equalTo(-padding);
         make.left.mas_equalTo(padding);
         make.right.mas_equalTo(-padding);
     }];
 }

约束使用链式方式,使用方法很简单,看起来像一句话。

看这句话:make.top.height.bottom.mas_equalTo(greenView),意思是:使我的顶部、高度和底部都与greenView的顶部、高度和底部相等。因此,只要greenView的约束添加好了,那么redView的顶部、高度和底部也就自动计算出来了。

大多时候,我们并不会将一句话完整地写出来,而是使用简写的方式。

如:make.right.mas_equalTo(-padding);

其完整的写法为:

make.right.mas_equalTo(bludView.superView.mas_right).offset(-padding);

当我们是要与父控件相对约束时,可以省略掉父视图。注意,并不是什么时候都可以省略,只有约束是同样的才可以省略。比如,约束都是right才可以。如果是一个left一个是right,那么就不能省略了。当然如果是两个不同的控件也是不能省略的。

(8)动画的形式更新约束(Masonry 以动画的形式更新约束,初始一个很小的按钮,点击就不断放大,最大就放大到全屏幕)

 #import "ViewController.h"
 #import "Masonry.h"

 #define WS(weakSelf) __weak __typeof(&*self) weakSelf = self;

 @interface ViewController ()

 @property(nonatomic, strong) UIButton *growingButton;
 @property(nonatomic, assign) CGFloat scacle;

 @end

 @implementation ViewController

 - (void)viewDidLoad {
     [super viewDidLoad];
   // 动画更新约束
     WS(weakSelf);
     self.growingButton = [UIButton buttonWithType:UIButtonTypeSystem];
     [self.growingButton setTitle:@"点我放大" forState:UIControlStateNormal];
     self.growingButton.layer.borderColor = UIColor.greenColor.CGColor;
     self.growingButton.layer.borderWidth = ;
     [self.growingButton addTarget:self action:@selector(onGrowButtonTaped:) forControlEvents:UIControlEventTouchUpInside];
     [self.view addSubview:self.growingButton];

     self.scacle = 1.0;

     [self.growingButton mas_makeConstraints:^(MASConstraintMaker *make) {
         make.center.mas_equalTo(weakSelf.view);
         // 初始宽、高为100,优先级最低
         make.width.height.mas_equalTo( * weakSelf.scacle).priorityLow();
         // 最大放大到整个View
         make.width.height.lessThanOrEqualTo(weakSelf.view);
     }];
 }

 #pragma mark - updateViewConstraints
 - (void)updateViewConstraints {
     WS(weakSelf);
     [self.growingButton mas_updateConstraints:^(MASConstraintMaker *make) {
         make.center.mas_equalTo(weakSelf.view);
         // 初始宽高为100 优先级最低
         make.width.height.mas_equalTo( * weakSelf.scacle).priorityLow();
         // 最大放大到整个View
         make.width.height.lessThanOrEqualTo(weakSelf.view);
     }];

     [super updateViewConstraints];
 }

 - (void)onGrowButtonTaped:(UIButton *)sender {
     WS(weakSelf);
     self.scacle += 0.5; // 一次增加 0.5 倍
     // 告诉self.view 约束需要更新
     [self.view setNeedsUpdateConstraints];
     // 调用此方法告诉self.view 检测是否需要更新约束,若需要则更新,下面添加动画效果才起作用
     [self.view updateConstraintsIfNeeded];

     [UIView animateWithDuration:0.3 animations:^{
         [weakSelf.view layoutIfNeeded];
     }];
 }

[self.growingButton mas_makeConstraints:^(MASConstraintMaker *make) {

make.center.mas_equalTo(weakSelf.view);

// 初始宽、高为100,优先级最低

make.width.height.mas_equalTo(100 * weakSelf.scacle).priorityLow(); // 让控件的宽和高相等且优先级最低。关于优先级,后面再讲

// 最大放大到整个View

make.width.height.lessThanOrEqualTo(weakSelf.view); // 让控件的宽和高小于或者等于self.view 的宽和高, 因此这个控件的最多能放大到全屏幕

}];

将这三行代码放在一起,形成的话就是:使控件与父视图始终保持居中,控件的宽和高最大不能超过屏幕,且控件的宽和高可以变化。由于我们设置了第二行的代码优先级为priorityLow,因此其优先级是最低的,所以就可以保证宽高不能超过屏幕。 其实,当我们将更新代码放到updateViewConstraints这个方法中时,这些约束就不需要了,这里写上去的目的只是想说明用于不用都没有关系。

  // 告诉self.view 约束需要更新

看下面的方法,就是动画更新约束的核心代码:

[self.view setNeedsUpdateConstraints];

  // 想要更新约束时添加动画,就需要调用关键的一行代码:setNeedsUpdateConstraints,这是选择对应的视图中的约束需要更新

  // 调用此方法告诉self.view 检测是否需要更新约束,若需要则更新,下面添加动画效果才起作用

[self.view updateConstraintsIfNeeded];

  // 对于updateConstraintsIfNeeded这个方法并不是必须的,但是有时候不调用就无法起到我们的效果。但是,官方都是这么写的,从约束的更新原理上讲,这应该写上。我们要使约束立即生效,就必须调用layoutIfNeeded此方法,[UIView animateWithDuration:0.3 animations:^{ [self.view layoutIfNeeded]; }];

(9)移除约束

 #import "RemakeContraintsViewController.h"
 #import "Masonry.h"

 @interface RemakeContraintsViewController ()

 @property(nonatomic, strong) UIButton *growingButton;
 @property(nonatomic, assign) BOOL isExpanded;

 @end

 @implementation RemakeContraintsViewController

 - (void)viewDidLoad {
     [super viewDidLoad];
     // Do any additional setup after loading the view.
     self.view.backgroundColor = [UIColor whiteColor];

     self.growingButton = [UIButton buttonWithType:UIButtonTypeSystem];
     [self.growingButton setTitle:@"点我展开" forState:UIControlStateNormal];
     self.growingButton.layer.borderColor = UIColor.greenColor.CGColor;
     self.growingButton.layer.borderWidth = ;
     self.growingButton.backgroundColor = [UIColor redColor];
     [self.growingButton addTarget: self  action:@selector(onGrowButtonTaped:) forControlEvents:UIControlEventTouchUpInside];
     [self.view addSubview:self.growingButton];
     self.isExpanded = NO;
 }

 - (void)updateViewConstraints {
     // 这里使用update 也是一样的
     // remake 会将之前的全部移除, 然后重新添加
     [self.growingButton mas_remakeConstraints:^(MASConstraintMaker *make) {
         make.top.mas_equalTo();
         make.left.right.mas_equalTo();
         if (self.isExpanded) {
             make.bottom.mas_equalTo();
         } else {
             make.bottom.mas_equalTo(-);
         }
     }];

     [super updateViewConstraints];
 }

 - (void)onGrowButtonTaped:(UIButton *)sender {
     self.isExpanded = !self.isExpanded;
     if (!self.isExpanded) {
         [self.growingButton setTitle:@"点我展开" forState:UIControlStateNormal];
     } else {
         [self.growingButton setTitle:@"点我收起" forState:UIControlStateNormal];
     }
     // 告诉self.view 约束需要更新
     [self.view setNeedsUpdateConstraints];
     // 调用此方法告诉self.view 检测是否需要更新,若需要则更新,下面添加动画效果才起作用
     [self.view updateConstraintsIfNeeded];

     [UIView animateWithDuration:0.3 animations:^{
         [self.view layoutIfNeeded];
     }];
 }

(10)整体动画更新约束

 #import "TotalUpdateViewController.h"
 #import "Masonry.h"

 @interface TotalUpdateViewController ()

 @property(nonatomic, strong) UIView *purpleView;
 @property(nonatomic, strong) UIView *orangeView;
 @property(nonatomic, assign) BOOL isExpaned;

 @end

 @implementation TotalUpdateViewController

 - (void)viewDidLoad {
     [super viewDidLoad];
     // Do any additional setup after loading the view.
     self.view.backgroundColor = [UIColor whiteColor];

     UIView *purpleView = [[UIView alloc] init];
     purpleView.backgroundColor = UIColor.purpleColor;
     purpleView.layer.borderColor = UIColor.blackColor.CGColor;
     purpleView.layer.borderWidth = ;
     [self.view addSubview:purpleView];

     UITapGestureRecognizer *tap = [[UITapGestureRecognizer alloc] initWithTarget:self action:@selector(onTap)];
     [purpleView addGestureRecognizer:tap];
     self.purpleView = purpleView;

     UIView *orangeView = UIView.new;
     orangeView.backgroundColor = UIColor.orangeColor;
     orangeView.layer.borderColor = UIColor.blackColor.CGColor;
     orangeView.layer.borderWidth = ;
     [self.view addSubview:orangeView];
     self.orangeView = orangeView;

     // 这里,我们不使用updateViewConstraints 方法,但是我们一样可以做到
     // 不过苹果推荐在updateViewConstraints 方法中更新约束或者添加约束
     [self updateWithExpand:NO animated:NO];

     UILabel *label = [[UILabel alloc] init];
     label.numberOfLines = ;
     label.textColor = [UIColor redColor];
     label.font = [UIFont systemFontOfSize:];
     label.textAlignment = NSTextAlignmentCenter;
     label.text = @"点击purple 部分放大,orange 部分最大值 250 ,最小值 90 ";
     [self.purpleView addSubview:label];

     [label mas_makeConstraints:^(MASConstraintMaker *make) {
         make.bottom.mas_equalTo(); // 0 就是和底部相等
         make.left.right.mas_equalTo();
     }];
 }

 - (void)updateWithExpand:(BOOL)isExpanded animated:(BOOL)animated {
     self.isExpaned = isExpanded;

     [self.purpleView mas_updateConstraints:^(MASConstraintMaker *make) { // 更新紫色的约束
         make.left.top.mas_equalTo();
         make.right.mas_equalTo(-); // 右边和底部 0 是相等 小于0 的是缩进 大于的0 的是伸展 而左边和顶部正好相反
         if (isExpanded) {
             make.bottom.mas_equalTo(-);
         } else {
             make.bottom.mas_equalTo(-);
         }
     }];

     [self.orangeView mas_updateConstraints:^(MASConstraintMaker *make) { // 更新橙色的约束
         make.center.mas_equalTo(self.purpleView);
         // 这里使用优先级处理
         // 设置其最大值为 250 ,最小值为 90
         if (!isExpanded) {
             make.width.height.mas_equalTo( * 0.5).priorityLow();
         } else {
             make.width.height.mas_equalTo( * ).priorityLow();
         }

         // 最大值为 250
         make.width.height.lessThanOrEqualTo(@);
         // 最小值为90
         make.width.height.greaterThanOrEqualTo(@);
     }];

     if (animated) {
         [self.view setNeedsUpdateConstraints];
         [self.view updateConstraintsIfNeeded];

         [UIView animateWithDuration:0.5 animations:^{
             [self.view layoutIfNeeded];
         }];
     }
 }

 - (void)onTap {
     [self updateWithExpand:!self.isExpaned animated:YES];
 }

展开与收起的关键代码在这里.设置最大最小值,这样就不会超出我们预期的范围。

// 最大值为250

make.width.height.lessThanOrEqualTo(@250);

// 最小值为90

make.width.height.greaterThanOrEqualTo(@90);

我们设置其固定的宽高,并且设置其优先级为最低,以保证我们所设置的最大最小值始终生效。

想要更新约束时添加动画,就需要调用关键的一行代码:setNeedsUpdateConstraints,这是选择对应的视图中的约束需要更新。

对于updateConstraintsIfNeeded这个方法并不是必须的,但是有时候不调用就无法起到我们的效果。但是,官方都是这么写的,从约束的更新原理上讲,这应该写上。我们要使约束立即生效,就必须调用layoutIfNeeded此方法。下面的方法,就是动画更新约束的核心代码:

     if (animated) {
         // 告诉self.view 约束需要更新
         [self.view setNeedsUpdateConstraints];
         // 调用此方法告诉self.view 检测是否需要更新约束,若需要则更新,下面添加动画效果才起作用
         [self.view updateConstraintsIfNeeded];

         [UIView animateWithDuration:0.5 animations:^{
             [self.view layoutIfNeeded];
         }];
     }

(11)比例(multipliedBy)

 // 首先创建4 个的View 视图 顶部和底部的View 平分屏幕
     // 顶部View 红色
     UIView *topView = [UIView new];
     topView.backgroundColor = [UIColor redColor];
     [self.view addSubview:topView];
     // 顶部内部的View 绿色
     UIView *topInnerView = [UIView new];
     topInnerView.backgroundColor = [UIColor greenColor];
     [topView addSubview:topInnerView];
     // 底部View
     UIView *bottomView = [UIView new];
     bottomView.backgroundColor = [UIColor blackColor];
     [self.view addSubview:bottomView];
     // 底部内部的View 蓝色
     UIView *bottomInnerView = [UIView new];
     bottomInnerView.backgroundColor = [UIColor blueColor];
     [bottomView addSubview:bottomInnerView];

     [topView mas_makeConstraints:^(MASConstraintMaker *make) {
         make.left.right.top.mas_equalTo(); // 上左右 等于 0
         make.height.mas_equalTo(bottomView); // 高度两者相等
     }];

     // width = height / 3
     [topInnerView mas_makeConstraints:^(MASConstraintMaker *make) {
         make.left.right.mas_equalTo(topView); // 左右相等
         make.width.mas_equalTo(topInnerView.mas_height).multipliedBy(); // topInnerView 的宽度等于高度乘以3
         make.center.mas_equalTo(topView); // 中心重合

         // 设置优先级
         make.width.height.mas_equalTo(topView).priorityLow();
         make.width.height.lessThanOrEqualTo(topView); // 宽度和高度最大也比topView 小于等于
     }];

     [bottomView mas_makeConstraints:^(MASConstraintMaker *make) {
         make.left.right.bottom.mas_equalTo(); // 左右底等于0
         make.height.mas_equalTo(topView); // 高度和topView 相等
         make.top.mas_equalTo(topView.mas_bottom); // top 等于 topView 的bottom
     }];

     // width / height / 比为 1 / 3.0 要求是同一个控件的属性比例
     [bottomInnerView mas_makeConstraints:^(MASConstraintMaker *make) {
         make.top.bottom.mas_equalTo(bottomView); // 顶部和底部等于bottomView 的顶部和底部
         make.center.mas_equalTo(bottomView); // 中心相等
         // 注意,这个multipliedBy 的使用只能是设置同一个控件,比如这里的bottonInnerView
         // 设置高 / 宽 为 3:1
         make.height.mas_equalTo(bottomInnerView.mas_width).multipliedBy(); // 高度等于宽度乘以 3 

         make.width.height.mas_equalTo(bottomView).priorityLow(); // 宽和高设置优先级
         make.width.height.lessThanOrEqualTo(bottomView); // 宽度和高度最高也小于bottomView 的高度和宽度
     }];

     [topInnerView mas_makeConstraints:^(MASConstraintMaker *make) {
         make.left.right.mas_equalTo(topView); // 左右相等
         make.width.mas_equalTo(topInnerView.mas_height).multipliedBy(); // topInnerView 的宽度等于高度乘以3
         make.center.mas_equalTo(topView); // 中心重合

         // 设置优先级
         make.width.height.mas_equalTo(topView).priorityLow();
         make.width.height.lessThanOrEqualTo(topView); // 宽度和高度最大也比topView 小于等于
     }];

提示:使用multipliedBy必须是对同一个控件本身,比如,上面的代码中,我们都是对bottomInnerView.mas_width本身的,如果修改成相对于其它控件,会出问题。

bottomInnerView的约束如何添加。 希望width/height比为1/3.0,首先,设置了其topbottom与父视图一致且始终在父视图中居中显示,设置了bottomInnerView的高为宽的3倍,然后设置了宽和高与父视图相等,但是优先级为最低,以保证子视图的宽高不超过父视图,然后通过make.width.height.lessThanOrEqualTo设置了宽、高的最大值与父视图相同,:

     // width / height / 比为 1 / 3.0 要求是同一个控件的属性比例
     [bottomInnerView mas_makeConstraints:^(MASConstraintMaker *make) {
         make.top.bottom.mas_equalTo(bottomView); // 顶部和底部等于bottomView 的顶部和底部
         make.center.mas_equalTo(bottomView); // 中心相等
         // 注意,这个multipliedBy 的使用只能是设置同一个控件,比如这里的bottonInnerView
         // 设置高 / 宽 为 3:1
         make.height.mas_equalTo(bottomInnerView.mas_width).multipliedBy(); // 高度等于宽度乘以 3 

         make.width.height.mas_equalTo(bottomView).priorityLow(); // 宽和高设置优先级
         make.width.height.lessThanOrEqualTo(bottomView); // 宽度和高度最高也小于bottomView 的高度和宽度
     }];

接下篇...

Coding源码学习第四部分(Masonry介绍与使用(二))的更多相关文章

  1. Coding源码学习第四部分(Masonry介绍与使用(三))

    接上篇继续进行Masonry 的学习. (12)tableViewCell 布局 #import "TableViewController.h" #import "Tes ...

  2. Coding源码学习第四部分(Masonry介绍与使用(一))

    Masonry GitHub:https://github.com/SnapKit/Masonry Masonry是一个轻量级的布局框架,拥有自己的描述语法,采用更优雅的链式语法封装自动布局,简洁明了 ...

  3. MVC系列——MVC源码学习:打造自己的MVC框架(二:附源码)

    前言:上篇介绍了下 MVC5 的核心原理,整篇文章比较偏理论,所以相对比较枯燥.今天就来根据上篇的理论一步一步进行实践,通过自己写的一个简易MVC框架逐步理解,相信通过这一篇的实践,你会对MVC有一个 ...

  4. mongo源码学习(四)服务入口点ServiceEntryPoint

    在上一篇博客mongo源码学习(三)请求接收传输层中,稍微分析了一下TransportLayer的作用,这篇来看下ServiceEntryPoint是怎么做的. 首先ServiceEntryPoint ...

  5. Java集合源码学习(四)HashMap分析

    ArrayList.LinkedList和HashMap的源码是一起看的,横向对比吧,感觉对这三种数据结构的理解加深了很多. >>数组.链表和哈希表结构 数据结构中有数组和链表来实现对数据 ...

  6. java源码学习(四)ArrayList

    ArrayList ​ ArrayList是基于数组实现的,是一个动态数组,其容量能自动增长,类似于C语言中的动态申请内存,动态增长内存. ​ ArrayList不是线程安全的,只能用在单线程环境下, ...

  7. Java集合源码学习(四)HashMap

    一.数组.链表和哈希表结构 数据结构中有数组和链表来实现对数据的存储,这两者有不同的应用场景,数组的特点是:寻址容易,插入和删除困难:链表的特点是:寻址困难,插入和删除容易:哈希表的实现结合了这两点, ...

  8. jquery 源码学习(四)构造jQuery对象-工具函数

    jQuery源码分析-03构造jQuery对象-工具函数,需要的朋友可以参考下.   作者:nuysoft/高云 QQ:47214707 EMail:nuysoft@gmail.com 声明:本文为原 ...

  9. mongo源码学习(四)invariant

    前言 在看MongoDB源码的时候,经常会看到这个玩意儿:invariant. invariant的字面意思是:不变式. 在emacs上跳转到函数定义要安装一个插件,ggtags,费了老大劲儿.这都可 ...

随机推荐

  1. c语言快速入门3

    如果你想快速入门计算机,可以参考我的上一篇帖子,先了解一些必备的软知识,然后再来进行语言的快速入门 计算机入门基础知识 c语言快速入门1 c语言快速入门2 3.4.1 字符和字符串 字符:'' 单个  ...

  2. BZOJ3083: 遥远的国度

    传送门 BZOJ100题辣(已经无法直视的正确率 树剖板子题,注意和dfs序结合,根据根的变化变换统计的方式即可. //BZOJ 3083 //by Cydiater //2016.10.23 #in ...

  3. 从idea上通过路径去导入项目

    这里我用git来演示导入. 首先确定你要导入项目的路径.(我这里用码云路径图片做演示) 1.选择 2.填写

  4. 转 纯CSS设置Checkbox复选框控件的样式

    Checkbox复选框是一个可能每一个网站都在使用的HTML元素,但大多数人并不给它们设置样式,所以在绝大多数网站它们看起来是一样的.为什么不把你的网站中的Checkbox设置一个与众不同的样式,甚至 ...

  5. 【LeetCode】223 - Rectangle Area

    Find the total area covered by two rectilinear rectangles in a 2D plane. Each rectangle is defined b ...

  6. SQL Server 索引 之 书签查找 <第十一篇>

    一.书签查找的概念 书签可以帮助SQL Server快速从非聚集索引条目导向到对应的行,其实这东西几句话我就能说明白. 如果表有聚集索引(区段结构),那么书签就是从非聚集索引找到聚集索引后,利用聚集索 ...

  7. vim一个快速切换主题的插件(change-colorscheme,原创)

    概述 有时候我们想快速浏览主题并找到一款合适的主题,change-colorscheme将会满足我们的要求. 安装 git https://github.com/chxuan/change-color ...

  8. oracle约束条件状态

    Oracle完整性约束有一下4种: • DISABLE NOVALIDATE • ENABLE NOVALIDATE • DISABLE VALIDATE • ENABLE VALIDATE   •  ...

  9. Dialog样式的Activity

    效果图: 设置全屏模式: @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInst ...

  10. Android多Module下的Application引用方式

    版权声明:本文为HaiyuKing原创文章,转载请注明出处! 前言 Android开发时,Application一般都放在APP中,Lib模块如果想引用Application则需要在APP中进行传递, ...