684

我在 Apple 文档中找不到关于 Cocoa Autolayout 内容拥抱和抗压缩性区别的明确答案。

有人可以解释他们的用法和区别吗?

4

8 回答 8

1371

概念的快速总结:

  • 拥抱 => 内容不想增长
  • 抗压性 => 内容不想收缩

例子:

假设你有一个这样的按钮:

[       Click Me      ]

并且您已将边缘固定到优先级为 500 的更大超级视图。

然后,如果拥抱优先级 > 500,它将如下所示:

[Click Me]

如果拥抱优先级 < 500,它将如下所示:

[       Click Me      ]

如果 superview 现在缩小了,如果 Compression Resistance 优先级 > 500,它看起来像这样

[Click Me]

否则,如果抗压优先级 < 500,则可能如下所示:

[Cli..]

如果它不能像这样工作,那么你可能还有其他一些限制正在搞乱你的好工作!

例如,您可以将其固定到优先级为 1000 的超级视图。或者您可以设置宽度优先级。如果是这样,这可能会有所帮助:

编辑器 > 大小以适合内容

于 2013-04-29T14:29:25.980 回答
310

看看这个关于 Autolayout 的视频教程,他们仔细解释

在此处输入图像描述

于 2014-04-21T18:23:30.913 回答
241

在此处输入图像描述

来源:@mokagio

内在内容大小- 非常不言自明,但内容可变的视图知道其内容有多大,并通过此属性描述其内容的大小。具有固有内容大小的视图的一些明显示例是 UIImageViews、UILabels、UIButtons。

内容拥抱优先级- 此优先级越高,视图越能抵抗大于其固有内容大小的增长。

内容压缩阻力优先级- 此优先级越高,视图越能抵抗缩小到小于其固有内容大小的程度。

在这里查看更多解释:自动布局魔术:内容大小优先级

于 2017-09-10T14:00:21.377 回答
44

假设您有一个带有“Click Me”文本的按钮。该按钮的宽度应该是多少?

首先,您绝对不希望按钮小于文本。否则,文本将被剪切。这是水平抗压优先级。

其次,你不希望按钮比它需要的大。看起来像这样的按钮 [ Click Me ] 显然太大了。您希望按钮在没有太多填充的情况下“拥抱”其内容。这是横向内容拥抱优先级。对于一个按钮来说,它不如水平抗压优先级强。

于 2013-04-07T16:07:58.607 回答
20

如果view.intrinsicContentSize.width != NSViewNoIntrinsicMetric,则自动布局创建一个特殊的类型约束NSContentSizeLayoutConstraint。此约束的作用类似于两个普通约束:

  • view.width <= view.intrinsicContentSize.width要求具有水平拥抱优先级的约束,以及
  • view.width >= view.intrinsicContentSize.width要求具有水平抗压优先级的约束。

在 Swift 中,使用 iOS 9 的新布局锚点,您可以像这样设置等效约束:

let horizontalHugging = view.widthAnchor.constraint(
    lessThanOrEqualToConstant: view.intrinsicContentSize.width)
horizontalHugging.priority = view.contentHuggingPriority(for: .horizontal)

let horizontalCompression = view.widthAnchor.constraint(
    greaterThanOrEqualToConstant: view.intrinsicContentSize.width)
horizontalCompression.priority = view.contentCompressionResistancePriority(for: .horizontal)

类似地,如果view.intrinsicContentSize.height != NSViewNoIntrinsicMetric, 那么自动布局会创建一个NSContentSizeLayoutConstraint类似于对视图高度的两个约束的行为。在代码中,它们看起来像这样:

let verticalHugging = view.heightAnchor.constraint(
    lessThanOrEqualToConstant: view.intrinsicContentSize.height)
verticalHugging.priority = view.contentHuggingPriority(for: .vertical)

let verticalCompression = view.heightAnchor.constraint(
    greaterThanOrEqualToConstant: view.intrinsicContentSize.height)
verticalCompression.priority = view.contentCompressionResistancePriority(for: .vertical)

您可以在布局运行后通过打印来查看这些特殊NSContentSizeLayoutConstraint实例(如果它们存在) 。view.constraints例子:

label.constraints.forEach { print($0) }

// Output:
<NSContentSizeLayoutConstraint:0x7fd82982af90 H:[UILabel:0x7fd82980e5e0'Hello'(39)] Hug:250 CompressionResistance:750>
<NSContentSizeLayoutConstraint:0x7fd82982b4f0 V:[UILabel:0x7fd82980e5e0'Hello'(21)] Hug:250 CompressionResistance:750>
于 2015-08-14T20:29:33.473 回答
15

Content Hugging 和 Content Compression Resistence Priorities 适用于可以根据传入的内容本质上计算其大小的元素。

来自苹果文档

在此处输入图像描述

于 2016-02-09T09:16:23.747 回答
12

Content hugging priority就像放置在视图周围的橡皮筋。优先级值越高,橡皮筋越强,它就越想拥抱它的内容大小。优先级值可以想象成橡皮筋的“强度”

而且,视图“抵抗”变小Content Compression Resistance的多少 具有较高抵抗优先级值的视图是抵抗压缩的视图。

于 2017-05-21T06:04:32.910 回答
-1

contentCompressionResistancePriority – 当没有足够的空间容纳所有内容时,具有最低值的视图会被截断intrinsicContentSize

contentHuggingPriorityintrinsicContentSize –当有剩余空间可以填充时,具有最低值的视图会扩展到超出其范围

于 2017-11-14T21:54:15.817 回答