如何在IOS的UIStackView中设置权重

Posted

技术标签:

【中文标题】如何在IOS的UIStackView中设置权重【英文标题】:How to set weight in UIStackView in IOS 【发布时间】:2015-12-08 16:15:46 【问题描述】:

UIStackView 类似于 android LinearLayout,但我不知道如何设置子视图的权重。

假设我有一个垂直的UIStackView 和 3 个UIImageViews。我想为UIImageViews 连续设置权重 3、6、1。我该怎么做?

【问题讨论】:

这完全是微不足道的。您只需使用 stack view 的 height == height 并设置分数。 【参考方案1】:

UIStackView 没有相同的权重概念。它可以使用子视图的intrinsicContentSize 作为权重,但设置特定的intrinsicContentSize 通常需要创建一个子类,并且它也用于其他情况(与您熟悉的android:layout_weight 属性不同,它仅由@ 使用987654328@).

但是由于UIStackView 通过对其排列的子视图应用约束来工作,因此您可以通过在子视图的高度之间设置额外的约束来获得权重的效果。 (UIStackView 旨在让您添加自己的约束来调整布局。)

在您的情况下,您希望将顶视图的高度限制为底视图高度的 3 倍,并且您希望将中间视图的高度限制为底视图高度的 6 倍。

您可以通过创建等高约束,然后编辑约束的乘数,在情节提要中设置比例高度约束。

在代码中,您可以这样做(在 ios 9.0 或更高版本上):

NSLayoutConstraint.activateConstraints([
    top.heightAnchor.constraintEqualToAnchor(bottom.heightAnchor, multiplier: 3),
    middle.heightAnchor.constraintEqualToAnchor(bottom.heightAnchor, multiplier: 6),
])

【讨论】:

"UIStackView 没有权重的概念" 实际上,是的。但权重是排列视图的固有特性。 能否不将stackview的distribution属性设置为fillProportionally 如果您使用fillProportionally,您必须将每个视图的intrinsicContentSize 设置为您想要的权重。由于intrinsicContentSizereadonly 属性,这意味着创建UIView 子类来覆盖intrinsicContentSize。如果使用约束,则不必创建子类。 堆栈视图本身并没有内置的权重概念。因为,您只需使用 stack view 的 height == height 并设置分数。这是完全司空见惯的,到处都在使用。 (在示例中,您显然将三个分数设置为“.3、.6、.1”。)如果堆栈视图内置了一个加权数组,我们都会说“这太奇怪了,因为显然你无论如何,只需将每个元素的高度设置为分数”。 当堆栈视图的distribution 设置为.fillProportionally 时,它将每个排列的子视图的intrinsicContentSize 视为权重。 “Views are resized proportionally based on their intrinsic content size along the stack view’s axis.” 如果您不认为这是“重量概念”或“内置”,那么我想我们对这些词有不同的定义。 ?‍♂️【参考方案2】:

内在内容大小等完全不涉及。

要设置分数高度,只需设置分数高度:

    固定堆栈视图的高度(例如,整个屏幕)

    放入三个视图A、B、C

    对于 A,将高度约束设为堆栈视图高度的 0.3

    对于 B,将高度限制为堆栈视图高度的 0.6

将堆栈视图设置为distribution:Fill。

如果你在功能强大的 iPhone 上运行它,它会发现 C 是“0.1”。

你已经完成了。

【讨论】:

【参考方案3】:

首先,你真的需要一个堆栈视图吗?直接使用比例高度约束来安排这个会容易得多。

但是,如果您真的想使用堆栈视图,可以使用堆栈视图来执行此操作。秘密在于,有问题的“重量”只是排列视图的intrinsicContentSize().height。知道了这一点,我可以轻松地设置一个堆栈视图,其中包含您要求的比例的三个图像视图:

出于演示的目的,这些是相同的图像重复三次:一张在 3x 高度,一张在 6x 高度,一张在 1x 高度。

我是怎么做到的?我在情节提要中分别给出了三个图像视图tag 的值 300、600 和 100。 (当然,我可以为此使用 IBInspectable 自定义属性,在现实生活中,我会这样做。)然后我将它们全部设为我的 UIImageView 子类 MyImageView 的所有实例,其代码如下所示:

class MyImageView: UIImageView 
    override func intrinsicContentSize() -> CGSize 
        print(self.tag)
        return CGSizeMake(CGFloat(self.tag), CGFloat(self.tag))
    

堆栈视图的分布配置为按比例填充。图像视图的内容模式配置为按比例填充。结果:堆栈视图在布置其排列的视图时参考了intrinsicContentSize 方法,因此做了正确的事情。

【讨论】:

我并不是建议使用 only 约束。我建议在使用堆栈视图的同时添加约束。我认为这比重写intrinsicContentSize 更简单。 iOS 和 Mac OS X 上的堆栈视图都明确设计为允许您使用约束来调整布局。 @robmayoff 我同意你关于他应该做什么。我只是表明他指定的事情实际上可以完成。

以上是关于如何在IOS的UIStackView中设置权重的主要内容,如果未能解决你的问题,请参考以下文章

当我们使用不同尺寸和类型的屏幕时,如何在 iOS 中设置 UI 控件的宽度和高度约束?

使用swift在UiStackview中设置UiLabel的高度

我应该如何确定 UIKit 将打开哪个场景,以便我可以在正确的窗口中设置我的 UI? (iOS 13+)

在 UIStackView 中设置锚点和位置

如何在 MLPClassifier 中设置初始权重?

如何在sklearn逻辑回归中设置样本权重?