什么时候在常见情况下使用Core Animation而不是UIView动画更合适?

8
这与许多小错误有关,这些错误在一个人看来可能被认为是次要的,但在另一个人看来却是重大的。
我越来越注意到的是,在使用所有UIView animateWithDuration:的变体时,它实际上会不必要地修改很多东西,例如我的视图的多个属性,以执行简单的隐藏/显示样式动画等。
在某些情况下,例如UINavigationBar在某些旋转转换中无法正确地动画到位置,或者当头部视图的框架更新时,它不会随着状态栏一起动画,当一个视图的子层在其父视图的属性更改时会隐式动画不同...
因此,我已经回顾了其中许多,并将其转换为CAAnimations,因为它们似乎更容易管理,因为它们实际上不会修改我的视图的目标属性值。
一个简单的例子是,使用[view setHidden:],然后将其动画化或从视图中移除,但实际上视图在动画运行时已经可见或隐藏。
另一个例子是,需要对UINavigationController的视图进行变换/旋转/缩放,并使用CAAnimation来完成它,因为如果我修改UINavigationController的视图及其任何父视图的变换属性值,则UINavigationBar不会移动到其正确的位置。
因此,总的来说,我一直在反复思考,并找到了适合我的情况的更合适的方法,但主要是,我想听听别人对这些情况的看法,以及是否有关于Apple提供的内容的见解,让我对自己的方法更有信心。
提前感谢。
1个回答

24

最终,所有基于UIKit风格的动画都会被转换成基于Core Animation风格的动画;也就是说,实际上所有动画都是使用Core Animation来实现的。两种API之间的差异主要在于方便性:UIKit风格的动画函数更新模型值,将动画反映到呈现层中以反映这种变化随时间的推移。

你还需要小心地选择你要对其进行动画处理的属性,确保它们是UIKit支持的。例如,虽然你可以在UIScrollView上技术性地动画处理诸如contentSizecontentOffset之类的属性,但它们并没有得到官方支持,因此你可能需要处理一些副作用。

此外,frame是一个特殊情况,因为它实际上是一个派生属性,由centertransformbounds组成(还有CALayer上的anchorPoint,而UIView不会暴露)。尝试对视图的frame进行动画处理时,可能会出现一系列意外问题,通常涉及旋转。Core Animation没有这个问题,因为frame不是CALayer上的可以显式动画化的属性。如果在UIKit风格的动画中遇到涉及该视图仿射变换(例如缩放、平移、旋转)的奇怪行为,请尝试使用boundscenter

的确,在UIKit中对某些视图进行动画处理可能会产生意外的副作用或错误,因为你除了动画处理之外还要更新模型值。而Core Animation则更加灵活,因为你可以精细地控制它何时以及如何更新模型层或呈现层。

但我不同意UIKit在不必要地修改东西。它修改需要修改的内容,以提交你请求的动画更改以及更新其模型值。当你动画处理像frame这样的属性时,它将在当前运行循环后隐式地调用该视图的layoutSubviews()方法,这可能会级联到其他子视图等等。

如果你希望UIKit在动画执行之前完成所有布局逻辑,则需要在调用动画块之前调用setNeedsLayout()layoutIfNeeded()。如果您希望UIKit实际上在提交动画时同时对整个子视图层次结构中的更改进行动画处理,则需要指定UIViewAnimationOptions.layoutSubviews选项。这将立即触发子视图布局,在动画块内进行,因此这些值也会被动画化。否则,动画更改的模型值将在下一个运行循环中触发布局更新。
一般来说,我很少注意到使用UIKit-style动画函数时出现问题。所以作为在iOS上进行大量动画制作的人,我想说:
尽可能使用UIKit-style动画,在每个地方都非常方便。当您遇到UIKit-style动画问题或需要对图层的模型和呈现值进行特定控制时,应使用Core Animation-style动画。

1
我想跟进一下您已经思考过的回答。首先,我不知道您仍然可以在CATransaction中包装UIView动画并适当地修改它们,这很有用。其次,自从更熟悉UIView方法和其内部工作之后,我几乎不需要再退回到CA了。但是,让人感到遗憾的是,我需要如此多的未记录知识,希望有更好的文档将CA与基于UIKit的动画链接起来。 - drkibitz
2
Core Animation是由苹果公司一位(杰出的)工程师为最初的iPhone创建的,因此可以理解文档在某些方面有些欠缺。如果苹果公司花时间更全面地完善它们并更好地与UIKit相结合,那将是很好的。最近可能已经这样了,但我有一段时间没有检查过它们。 - CIFilter

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接