1

大家好,感谢阅读,

我试图使用动画块制作一个简单的波浪动画:

[UIView animateWithDuration:0.6 delay:i*delay options:UIViewAnimationOptionBeginFromCurrentState | UIViewAnimationOptionAutoreverse animations:^{
        tab.frame = CGRectMake(tab.frame.origin.x,
                               tab.frame.origin.y-WAVE_SIZE,
                               tab.frame.size.width,
                               tab.frame.size.height);
    } completion:^(BOOL finished) {

        tab.frame = CGRectMake(tab.frame.origin.x,
                               tab.frame.origin.y+WAVE_SIZE,
                               tab.frame.size.width,
                               tab.frame.size.height);
    }];

问题是当动画结束时,当我试图将视图返回到以前的状态时,一个奇怪的跳转会潜入(因为我正在使用重复效果)注意完成块。

如果有人遇到这样的问题,请分享,

再次感谢。

4

2 回答 2

2

这与完成块触发时从视图的模型值更新图层有关,这些值设置为动画的中间。我发现让这种事情在 100% 的时间内工作而无需放弃 API 的唯一方法CAAnimation是将动画链接成两半,而不是UIViewAnimationOptionAutoreverse像这样使用:

[UIView animateWithDuration:0.3
                      delay:i*delay
                    options:UIViewAnimationOptionBeginFromCurrentState | UIViewAnimationCurveEaseIn
                 animations:^{
                     tab.frame = CGRectMake(tab.frame.origin.x,
                                            tab.frame.origin.y-WAVE_SIZE,
                                            tab.frame.size.width,
                                            tab.frame.size.height);
                 }
                 completion:^(BOOL finished) {
                     [UIView animateWithDuration:0.3
                                           delay:0.0
                                         options: UIViewAnimationCurveEaseOut
                                      animations:^{
                                          tab.frame = CGRectMake(tab.frame.origin.x,
                                                                 tab.frame.origin.y+WAVE_SIZE,
                                                                 tab.frame.size.width,
                                                                 tab.frame.size.height);
                                      }
                                      completion:NULL];

                 }];

这确保在每个动画结束时,视图的模型值(即其当前位置)与动画的最后一帧相同。这意味着您不会得到那种抖动效果。

这让人UIViewAnimationOptionAutoreverse显得有些无意义。如果它可以使视图的模型值与动画的最后一帧不同,为什么还要使用它?好吧,当与UIViewAnimationOptionRepeat它结合使用时,会产生相当令人愉悦的效果,该效果会来回移动直到被移除。

于 2012-10-14T21:05:10.337 回答
2

斜杠是对的。在这个简单的场景中解决问题的另一种更简单的方法是在动画之前保存帧,然后恢复它,a la:

CGRect oldFrame = tab.frame;

[UIView animateWithDuration:0.6 delay:i*delay options:UIViewAnimationOptionBeginFromCurrentState | UIViewAnimationOptionAutoreverse animations:^{
    CGRect newFrame = oldFrame;
    newFrame.origin.y -= WAVE_SIZE;
    tab.frame = newFrame;
} completion:^(BOOL finished) {
    tab.frame = oldFrame;
}];
于 2012-10-15T15:19:51.967 回答