traitCollectionDidChange 中更新的约束无效

Posted

技术标签:

【中文标题】traitCollectionDidChange 中更新的约束无效【英文标题】:updated constraints in traitCollectionDidChange have no effect 【发布时间】:2017-08-21 16:35:41 【问题描述】:

通过我的自动布局,当我的图标需要更小时,我正在尝试为最小的屏幕实现一种特殊情况。我正在更改 traitCollectionDidChange() 中图标的约束。但是,更改没有任何效果。我尝试添加 SetNeedsLayout、SetNeedsDisplay、UpdateConstraints 等,但没有任何效果。

如果我在视图初始化时更改了这些约束,那么更改会起作用——但是当用户旋转设备并且我需要再次进行更改时,这对我没有帮助。但是,有趣的是,在程序启动时调用了 traitCollectionDidChange(),但是如果我在该函数中更改约束,它们将不起作用。它们仅在我在视图的 init() 函数中设置新约束时才有效。

可能是在使用约束之后调用此函数,除了 Apple 告诉我们将此函数仅用于此目的,在旋转时更改布局等。我不想使用 WillTransitionToSize 因为只有 ViewController 是用该函数调用的,而不是视图。不过接下来我可能会尝试。

traitCollectionDidChange() 在启动时和旋转时肯定会被调用。只是我的更改没有任何作用。有什么想法吗?

有什么想法吗?

override func traitCollectionDidChange(_ previousTraitCollection: UITraitCollection?) 

    super.traitCollectionDidChange(previousTraitCollection)

    // smaller icon constraints for iPhone 5/SE

    if let constraint = (self.imageView!.constraints.filter$0.firstAttribute == .width.first) 
        print("cwide \(constraint.constant)")
        if UIScreen.main.bounds.size.width <= 320 
            constraint.constant = 20.0
            self.radius = 4

        
        else 
            constraint.constant = 32.0
            self.radius = 8
        

    

    self.updateConstraints()

【问题讨论】:

这是UIViewUIViewController 的子类吗?如果在控制器中,最后一次调用需要调用self.view 而不是self。您也可以尝试在视图上调用layoutIfNeeded(),我使用该方法非常幸运。 它是一个 UIView 子类。我刚刚尝试添加 layoutIfNeeded() 不幸的是它没有帮助...... 所以我遇到了一个问题,即自定义字体不起作用,除非我在设置它们之前等待不到一秒钟。好像有别的东西在设置字体。也许同样的事情正在这里发生??如果您将所有代码提取到另一种方法中并在 1-2 秒内触发它,则可能会起作用。然后您可以将时间范围缩小到最小值或多次触发(这就是我们最终所做的)。这是一个非常令人讨厌的工作,但它可能会奏效。 啊!它可能是这样的。我实际上只是决定忘记约束并在其父视图的自定义绘制功能中手动更改子视图的大小。这是有效的,但如果它停止了,我会试试你的建议。 这不适用于向 tableview 单元格/标题添加约束。它似乎是在 reloadData 之后调用的。如果我在视图/单元格的初始化中添加约束,一切都很好。 【参考方案1】:

我有一个类似的功能,结果我忘记在 Interface Builder 中安装约束。

【讨论】:

以上是关于traitCollectionDidChange 中更新的约束无效的主要内容,如果未能解决你的问题,请参考以下文章

iOS深色模式适配

在 iOS 13 中,tableView 中 UIDatePicker 的无效更新在旋转时崩溃

如何在没有情节提要的情况下实现 Size-Class-Specific Layout?