UILabel 重绘视图。如何避免这种行为?

Posted

技术标签:

【中文标题】UILabel 重绘视图。如何避免这种行为?【英文标题】:UILabel redraws the view. How to avoid this behavior? 【发布时间】:2015-06-01 06:12:55 【问题描述】:

我有一个带有三个子视图的 viewController。 我也使用 AutoLayout 和 size 类。 这些视图是动画的,并且会改变位置和大小。 在动画之后我更新了一个标签,但整个视图被重绘,所以每个视图都处于它们的初始位置和大小。这不应该发生。 正如 Apple 开发人员参考中所说:

"UILabel 类的默认内容模式是 UIViewContentModeRedraw。这种模式会导致视图重绘它的 每次其边界矩形更改时的内容。你可以改变 此模式通过修改继承的 contentMode 属性 类。”

我似乎不清楚如何修改 -contentMode- 以更新该标签并保持视图不变。谁能给我一个线索? 提前致谢。

【问题讨论】:

显示您用于动画和更新的代码 【参考方案1】:

听起来您可能正在使用自动布局来布置您的视图(例如,通过 IB 中的约束),但是您正在直接为您的动画操作视图的frames - 是这样吗?如果是这样,您应该为约束的 constant 值或子视图的 transforms 设置动画。

如果您直接在使用自动布局的视图中操作框架,您的更改将在下次系统布局您的视图时被覆盖(例如,在标签的文本更改之后)。

您有 3 个选项来解决您的问题 -

    停止在 Storyboard/Xib 中使用 AutoLayout。

    不是一个很好的解决方案

    对子视图的transform 属性进行动画更改。例如myView.transform = CGAffineTransformMakeScale(2.0,2.0);

    对于演示和关闭动画很有用,但在 ios 8.0 之前混合使用 AutoLayout 和变换会有一些问题

    为您需要在动画中更改的约束添加 IBOutlets。对这些约束的constant 值进行动画更改。

    最强大的方法,但可能会导致复杂动画的大量属性和代码

【讨论】:

对不起,我没有提到它,但是是的,我正在为主视图控制器(包括子视图)内的每一件事使用自动布局。然后,我在 -viewWillAppear- 中设置了一些参数,在执行期间视图将执行一些动画,然后视图不会重绘,直到我调用 label.text=@"whatever"。感谢您提供的线索:它一定是关于常量值的……您认为我应该以编程方式设置它们而不是使用 IB 设置这些值吗?谢谢约翰。 在你的动画中,你是直接设置帧吗?如果是这样,那肯定是您问题的根源 - 请参阅上面的答案。 动画如下所示: [UIView animateWithDuration:tiempo delay: 0 options: (UIViewAnimationOptionCurveLinear) 动画:^ vista1.frame = CGRectMake(V1x, V1y-160, 80, 140); vista2.frame = CGRectMake(V2x, V2y+160, 80, 140); 完成:^(BOOL 完成) [UIView animateWithDuration:tiempo 延迟:0 选项:UIViewAnimationOptionCurveLinear 动画:^ vista1.frame = CGRectMake(V2x, V1y-160, 80, 140); vista2.frame = CGRectMake(V1x, V2y+160, 80, 140);... 所以我的假设是正确的 - 您正在尝试直接在使用自动布局的视图中设置框架。你不应该那样做。您有 3 个选项来解决您的问题,我将在我的答案中添加这些选项。 不错的方法!我正在研究第三种解决方案,但如前所述,这将是一段艰难的编码时间。我想如果我可以将新视图的大小和位置设置为默认值,那么一切都可以以某种方式修复,因此重绘应该不是问题。我不确定这是否可能......但这会很棒!再次感谢。【参考方案2】:

试试 contentMode = UIViewContentModeCenter。这应该可以防止您看到的重绘。虽然这可能不是您想要的 contentMode。

选项2是使用CATextLayer来绘制标签。它可以通过动画很好地调整大小,但设置起来需要更多的工作。

【讨论】:

谢谢戴夫。问题不在于为标签或其图层设置动画。我遇到的问题是,只是更改 label.text 值,它会重绘整个视图并重置子视图的值(大小和位置)(我试图避免)。作为记录,下次我将使用 CALayers。

以上是关于UILabel 重绘视图。如何避免这种行为?的主要内容,如果未能解决你的问题,请参考以下文章

检测 UIView/UILabel 何时重绘自身?

UITableViewCell 子视图在重绘之前不显示

旋转 UIL 标签辊

如何重绘标签栏控制器显示的视图

IOS-OC-基本控件之UILabel

IOS - UIView中使用AutoLayout的UILabel动态高度