测试UIView是否处于动画中间

pro*_*ock 45 cocoa-touch core-animation uiview uiviewanimation ios

有没有办法判断UIView是否在动画中?当我在视图对象移动时打印出来时,我注意到有一个"动画"条目:

search bar should end editing: <UISearchBar: 0x2e6240; frame = (0 0; 320 88); text = ''; autoresize = W+BM; animations = { position=<CABasicAnimation: 0x6a69c40>; bounds=<CABasicAnimation: 0x6a6d4d0>; }; layer = <CALayer: 0x2e6e00>>
Run Code Online (Sandbox Code Playgroud)

当动画停止并且我打印视图时,"动画"条目现在消失了:

search bar should end editing: <UISearchBar: 0x2e6240; frame = (0 0; 320 88); text = ''; autoresize = W+BM; layer = <CALayer: 0x2e6e00>>
Run Code Online (Sandbox Code Playgroud)

Nic*_*ver 39

UIView有一个图层(CALayer).您可以向其发送animationKeys,它将为您提供一系列键,用于标识附加到图层的动画.我想如果有任何条目,动画正在运行.如果你想深入挖掘一下,看看CALayer采用的CAMediaTiming协议.它提供了有关当前动画的更多信息.


Vin*_*rci 25

动画实际上附加到底层的Core Animation CALayer

所以我想你可以检查一下 myView.layer.animationKeys

  • animationKeys是一条消息,就像任何属性访问者都是......点或括号,只是*style*的问题. (13认同)
  • 属性只是语义,一切都以消息结束:)它确实无关紧要,编译器/静态分析并不关心.如上所述,只是风格问题,我甚至使用像'UIView.class`或`UIColor.redColor`这样的东西......主要是因为一个点比2个括号更容易阅读和更快,并且是我的品味空间. (8认同)

dee*_*eej 14

iOS 9+方法,即使layer.animationKeys不包含任何键也可以使用:

let isInTheMiddleOfAnimation = UIView.inheritedAnimationDuration > 0
Run Code Online (Sandbox Code Playgroud)

从文档:

如果在UIView动画块中调用此方法,则仅返回非零值。


Rya*_*los 9

我不确定这个问题的背景,但我试图在开始第二个动画之前试图查看视图是否是动画以避免跳过.但是,有一个UIView动画选项UIViewAnimationOptionBeginFromCurrentState,如果需要,它将组合动画以提供流畅的外观.从而消除了我需要知道视图是否是动画.


Ech*_*lon 9

这里有很多过时的答案。UIView如果在同一个视图上运行一个动画,我只需要防止启动动画,所以我创建了一个类别UIView:-

extension UIView {

    var isAnimating: Bool {
        return (self.layer.animationKeys()?.count ?? 0) > 0
    }

}
Run Code Online (Sandbox Code Playgroud)

这样我就可以像这样检查任何视图的动画状态:-

if !myView.isAnimating {
  UIView.animate(withDuration: 0.4) {
    ...
  }
} else {
  // already animating
}
Run Code Online (Sandbox Code Playgroud)

这似乎没有用状态变量跟踪它那么脆弱。


C4 *_*vis 5

动漫诡计有一个障碍.

动画完成后,有时可能会有一些动画片徘徊.

这意味着非动画层可以返回一组animationKeys,即使它实际上不是动画.

您可以通过将动画的removedOnCompletion属性设置为YES来确保自动删除animationKeys.

例如

CABasicAnimation *animation = [CABasicAnimation animationWithKeyPath:@"aPath"];
animation.removedOnCompletion = YES;
Run Code Online (Sandbox Code Playgroud)

如果对应用于图层的所有动画执行此操作,则会确保在图层未设置动画时不存在animationKeys.