欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页  >  IT编程

三十六

程序员文章站 2024-01-09 20:03:52
MasonryMasonry的添加布局主要有三个,三个方法的作用分别是创建约束;更新某个约束,其他约束不变;移除先前所有约束,添加新到的约束。(NSArray *)mas_makeConstraints:(void(NS_NOESCAPE ^)(MASConstraintMaker *make))block;(NSArray *)mas_updateConstraints:(void(NS_NOESCAPE ^)(MASConstraintMaker *make))block;(NSAr...

Masonry
Masonry的添加布局主要有三个,三个方法的作用分别是创建约束;更新某个约束,其他约束不变;移除先前所有约束,添加新到的约束。

  • (NSArray *)mas_makeConstraints:(void(NS_NOESCAPE ^)(MASConstraintMaker *make))block;

  • (NSArray *)mas_updateConstraints:(void(NS_NOESCAPE ^)(MASConstraintMaker *make))block;

  • (NSArray *)mas_remakeConstraints:(void(NS_NOESCAPE ^)(MASConstraintMaker *make))block;

给subView视图添加约束:
[subView mas_makeConstraints:^(MASConstraintMaker *make) { make.left.equalTo(self.view).offset(10); make.top.equalTo(self.view).offset(10); make.right.equalTo(self.view).offset(-10); make.bottom.equalTo(self.view).offset(-10);}];
[subView mas_makeConstraints:^(MASConstraintMaker *make) {
make.left.equalTo(self.view).offset(10);
make.top.equalTo(self.view).offset(10);
make.right.equalTo(self.view).offset(-10);
make.bottom.equalTo(self.view).offset(-10);
}];
可以把 self.view → self ,Masonry内部会自动处理的
可以设置 edges 来简化代码:
[subView mas_makeConstraints:^(MASConstraintMaker *make) {
make.edges.equalTo(self).with.insets(UIEdgeInsetsMake(10, 10, 10, 10));
}];
设置一个具体的数值 宽:
[subView mas_makeConstraints:^(MASConstraintMaker *make) {
make.width.equalTo(@10);
}];
因为equalTo 这个函数的参数必须是一个对象类型,所以可以使用 mas_equalTo 这个函数:
[subView mas_makeConstraints:^(MASConstraintMaker *make) {
make.width.mas_equalTo(10);
}];
也可以在我们的文件之前加上一个 #define MAS_SHORTHAND_GLOBALS 这样的宏定义,就可以直接使用equalTo(10)了:
#define MAS_SHORTHAND_GLOBALS

[subView mas_makeConstraints:^(MASConstraintMaker *make) {
make.width.equalTo(10);
}];
想要设置subView的宽度等于父视图的宽度的50%,可以用到 multipliedBy 和 dividedBy这两个方法:
[subView mas_makeConstraints:^(MASConstraintMaker *make) {
make.width.equalTo(self).multipliedBy(0.5);
}];
[subView mas_makeConstraints:^(MASConstraintMaker *make) {
make.width.equalTo(self).dividedBy(2);
}];
想要subView的宽度等于高度的2倍,
需要指定equalTo()里面具体的值(实际上是传一个 MASViewAttribute 对象),而不是简单的传一个控件对象:
[subView mas_makeConstraints:^(MASConstraintMaker *make) {
make.width.equalTo(subView.mas_height).multipliedBy(2);
}];
想让subView和subView2,subView3的宽度相等:
[subView mas_makeConstraints:^(MASConstraintMaker *make) { make.width.equalTo(@[subView2.mas_width, subView3.mas_width]);}];
[subView mas_makeConstraints:^(MASConstraintMaker *make) { make.width.equalTo(@[subView2, subView3]);}];
// 三者相等,并且宽度为200个像素点[subView mas_makeConstraints:^(MASConstraintMaker *make) { make.width.equalTo(@[subView2, subView3,@200]);}];

约束优先级设置:
Masonry为我们提供了三个优先级的方法,priorityLow()、priorityMedium()、priorityHigh(),这三个方法内部对应着不同的默认优先级,当然也可以使用priority() 设置具体的数值。
[subView mas_makeConstraints:^(MASConstraintMaker *make) {
make.width.equalTo(subView4).priorityLow();
make.width.equalTo(@[subView2, subView3,@100]).priorityHigh();
make.width.equalTo(@300).priority(888);
}];
如果想让subView的宽度是 父视图的宽度的50% + 20个单位长度,不能设置两条约束条件,如果那样设置了,后面的约束条件就会把前面的约束条件给覆盖掉:
[subView mas_makeConstraints:^(MASConstraintMaker *make) {
make.width.equalTo(self).offset(20).multipliedBy(0.5);
}];

约束优先级 以及 intrinsicContentSize:
假设设置在一个superView(宽度为 200)中的一个View子视图的左右边距都为0,然后第二个约束是视图的宽度为100,这时候就会出现问题,因为如果左右边距都为0,那么视图宽度为200,这样和第二个约束条件就发生了冲突,这时候就需要通过设置约束优先级来解决这一类问题,系统通过比较两个”相互冲突的约束”的优先级,从而忽略低优先级的某个约束,达到正确布局的目的约束优先级默认都是1000.所以我们给设定一个根据具体情况设置一个合适的值即可。
[subView mas_makeConstraints:^(MASConstraintMaker *make) {
make.left.right.equalTo(self);
make.width.equalTo(@100).priority(888);
}];

约束优先级主要是应对与单个视图中多个约束发生冲突的时候解决问题的方案.而 intrinsicContentSize 主要应对于多个视图约束发生冲突的解决方案
在AutoLayout中, intrinsicContentSize的作用其实很简单,它会自己根据内容计算出控件的固有宽高,在布局过程当不指定宽高约束的时候,它就会生效。
[label1 mas_makeConstraints:^(MASConstraintMaker *make) {
make.left.equalTo(superView);
make.top.equalTo(superView);
}];

[label2 mas_makeConstraints:^(MASConstraintMaker *make) {
make.left.equalTo(label1.mas_right);
make.top.equalTo(superView);
}];
因为 intrinsicContentSize 属性的原因,我们轻松完成布局任务,但是当我们给 label2 添加一个 右边距等于superView.
[label2 mas_makeConstraints:^(MASConstraintMaker *make) {
make.left.equalTo(label1.mas_right);
make.right.equalTo(superView);
make.top.equalTo(superView);
}];
这时候就会出现问题,label1 和 label2 必然有一个不能满足 intrinsicContentSize 约束条件,必然有一个需要拉伸才能完成约束布局任务,这种问题叫做 Intrinsic冲突.
解决 Intrinsic冲突 一共有两种方案,一种是直接指定冲突的label 1 和 label 2的宽高约束信息.第二种就是利用 content Hugging/content Compression Resistance.

  • (void)setContentHuggingPriority:(UILayoutPriority)priority forAxis:(UILayoutConstraintAxis)axis API_AVAILABLE(ios(6.0));
  • (void)setContentCompressionResistancePriority:(UILayoutPriority)priority forAxis:(UILayoutConstraintAxis)axis API_AVAILABLE(ios(6.0));

Content Hugging 约束(不想变大约束)表示:如果组件的此属性优先级比另一个组件此属性优先级高的话,那么这个组件就保持不变,另一个可以在需要拉伸的时候拉伸。属性分横向和纵向2个方向。
Content Compression Resistance 约束(不想变小约束)表示:如果组件的此属性优先级比另一个组件此属性优先级高的话,那么这个组件就保持不变,另一个可以在需要压缩的时候压缩。属性分横向和纵向2个方向。意思很明显。上面UIlabel这个例子中,很显然,如果某个UILabel使用Intrinsic Content Size的时候,另一个需要拉伸。所以需要调整两个UILabel的 Content Hugging约束的优先级。
所以可以通过设置这两个方法来解决 Intrinsic冲突 问题,假设 我们想让 label 2 拉伸,label1尽量不拉伸,可以这样:

[label1 setContentHuggingPriority:UILayoutPriorityRequired forAxis:UILayoutConstraintAxisHorizontal];
[label2 setContentHuggingPriority:UILayoutPriorityDefaultLow forAxis:UILayoutConstraintAxisHorizontal];

本文地址:https://blog.csdn.net/m0_46296191/article/details/107598521

相关标签: 笔记