在关键帧动画的另一项测试中,我将theImage
沿贝塞尔路径移动 UIImageView(称为 我的初始代码中包含这些元素来启动动画:
UIImageView* theImage = ....
float scaleFactor = 2.0;
....
theImage.center = destination;
theImage.transform = CGAffineTransformMakeScale(1.0,1.0);
CABasicAnimation *resizeAnimation = [CABasicAnimation animationWithKeyPath:@"bounds.size"];
[resizeAnimation setToValue:[NSValue valueWithCGSize:CGSizeMake(theImage.image.size.height*scaleFactor, theImage.image.size.width*scaleFactor)]];
resizeAnimation.fillMode = kCAFillModeBackwards;
resizeAnimation.removedOnCompletion = NO;
CAKeyframeAnimation *pathAnimation = [CAKeyframeAnimation animationWithKeyPath:@"position"];
pathAnimation.path = [jdPath path].CGPath;
pathAnimation.fillMode = kCAFillModeBackwards;
pathAnimation.removedOnCompletion = NO;
CAAnimationGroup* group = [CAAnimationGroup animation];
group.animations = [NSArray arrayWithObjects:pathAnimation, resizeAnimation, nil];
group.timingFunction = [CAMediaTimingFunction functionWithName:kCAMediaTimingFunctionEaseInEaseOut];
group.removedOnCompletion = NO;
group.duration = duration;
group.delegate = self;
[theImage.layer addAnimation:group forKey:@"animateImage"];
然后,当动画完成时,我想保留更大尺寸的图像,所以我实现:
- (void)animationDidStop:(CAAnimation *)theAnimation finished:(BOOL)flag
{
theImage.transform = CGAffineTransformMakeScale(scaleFactor,scaleFactor);
}
这一切都有效..有点。问题是动画结束时会theImage
短暂闪烁 - 足以让它看起来很糟糕。我猜这是动画结束时的过渡,我将变换设置为新大小。
在对此进行试验时,我尝试了一种稍微不同的上述形式,但仍然得到相同的闪烁:
CAKeyframeAnimation *resizeAnimation = [CAKeyframeAnimation animationWithKeyPath:@"transform"];
NSValue* startSizeKey = [NSValue valueWithCATransform3D:CATransform3DScale (theImage.layer.transform, 1.0, 1.0, 1.0)];
NSValue* endSizeKey = [NSValue valueWithCATransform3D:CATransform3DScale (theImage.layer.transform, scaleFactor, scaleFactor, 1.0)];
NSArray* sizeKeys = [NSArray arrayWithObjects:startSizeKey, endSizeKey, nil];
[resizeAnimation setValues:sizeKeys];
....
theImage.transform = CGAffineTransformMakeScale(scaleFactor,scaleFactor);
但是当我以与原始大小相同的动画结束时,没有闪烁:
CAKeyframeAnimation *resizeAnimation = [CAKeyframeAnimation animationWithKeyPath:@"transform"];
NSValue* startSizeKey = [NSValue valueWithCATransform3D:CATransform3DScale (theImage.layer.transform, 1.0, 1.0, 1.0)];
NSValue* middleSizeKey = [NSValue valueWithCATransform3D:CATransform3DScale (theImage.layer.transform, scaleFactor, scaleFactor, 1.0)];
NSValue* endSizeKey = [NSValue valueWithCATransform3D:CATransform3DScale (theImage.layer.transform, 1.0, 1.0, 1.0)];
NSArray* sizeKeys = [NSArray arrayWithObjects:startSizeKey, middleSizeKey, endSizeKey, nil];
[resizeAnimation setValues:sizeKeys];
....
theImage.transform = CGAffineTransformMakeScale(1.0,1.0);
所以我最大的问题是如何在没有闪烁的情况下为该图像设置动画,并在动画结束时以不同的大小结束?
3月2日编辑
我最初的测试是放大图像。我只是尝试缩小它(IE scaleFactor = 0.4)并且闪烁更加明显,并且对于我所看到的更加明显。这是事件的顺序:
- 原始大小的图像被绘制在屏幕上的起始位置。
- 当图像沿着路径移动时,它会平滑收缩。
- 完全缩小的图像到达路径的末端。
- 然后以原始大小绘制图像。
- 最终以缩小后的尺寸绘制图像。
所以这似乎是我看到的第 4 步闪烁。
编辑 3 月 22 日
我刚刚向 GitHub 上传了一个演示项目,该项目展示了对象沿贝塞尔路径的移动。代码可以在PathMove找到
我还在我的博客“在 iOS 中沿贝塞尔路径移动对象”中写到了它