在执行代码之前等待 Swift 动画完成
Wait for Swift animation to complete before executing code
我正在尝试为 UIImageView 设置动画,然后在动画完成后隐藏图像视图。然而,imageview 在动画完成之前被隐藏。我查看了类似的问题,他们建议在完成后实现动画侦听器或在动画代码中执行 .hidden 代码,但是我不确定如何在下面的 shakeView() 函数中影响它。
如何显示摇动动画并仅在动画完成后隐藏图像视图?
使用以下代码调用动画:
shakeView(image1!)
shakeView(image2)
image1!.hidden = true
image2.hidden = true
动画函数本身如下所示:
func shakeView(iv: UIImageView){
var shake:CABasicAnimation = CABasicAnimation(keyPath: "position")
shake.duration = 0.1
shake.repeatCount = 2
shake.autoreverses = true
var from_point:CGPoint = CGPointMake(iv.center.x - 5, iv.center.y)
var from_value:NSValue = NSValue(CGPoint: from_point)
var to_point:CGPoint = CGPointMake(iv.center.x + 5, iv.center.y)
var to_value:NSValue = NSValue(CGPoint: to_point)
shake.fromValue = from_value
shake.toValue = to_value
iv.layer.addAnimation(shake, forKey: "position")
}
正如 Paulw11 在他的评论中提到的,您可以使用文档中提到的 animationDidStop:
方法。但此外,您应该为 CABasicAnimation/CAAnimation
对象添加一个键,以便您的 animationDidStop:
方法知道具体哪个已完成。
所以在你的 shake 方法中添加一个值键对来标识动画并将委托设置为 self,例如:
func shakeView(iv: UIImageView){
var shake:CABasicAnimation = CABasicAnimation(keyPath: "position")
shake.duration = 0.1
shake.repeatCount = 2
shake.autoreverses = true
// Add these two lines:
shake.setValue("shake", forKey: "animationID")
shake.delegate = self
// ...
然后添加 animationDidStop:
委托方法来提醒您动画何时完成,以便您可以开始执行代码:
override func animationDidStop(anim: CAAnimation!, finished flag: Bool) {
// Unwrap the optional value for the key "animationID" then
// if it's equal to the same value as the relevant animation,
// execute the relevant code
if let animationID: AnyObject = anim.valueForKey("animationID") {
if animationID as NSString == "shake" {
// execute code
}
}
}
您可以使用 CATransaction
在动画完成后调用完成块。
func shakeView(iv: UIImageView){
CATransaction.begin()
CATransaction.setCompletionBlock({
iv.hidden = true
})
var shake:CABasicAnimation = CABasicAnimation(keyPath: "position")
shake.duration = 0.1
shake.repeatCount = 21
shake.autoreverses = true
var from_point:CGPoint = CGPointMake(iv.center.x - 5, iv.center.y)
var from_value:NSValue = NSValue(CGPoint: from_point)
var to_point:CGPoint = CGPointMake(iv.center.x + 5, iv.center.y)
var to_value:NSValue = NSValue(CGPoint: to_point)
shake.fromValue = from_value
shake.toValue = to_value
iv.layer.addAnimation(shake, forKey: "position")
CATransaction.commit()
}
或者您也可以将两个动画组合在一个 CATransaction
中,如下所示。
func shakeView(iv: UIImageView){
var shake:CABasicAnimation = CABasicAnimation(keyPath: "position")
shake.duration = 0.1
shake.repeatCount = 21
shake.autoreverses = true
var from_point:CGPoint = CGPointMake(iv.center.x - 5, iv.center.y)
var from_value:NSValue = NSValue(CGPoint: from_point)
var to_point:CGPoint = CGPointMake(iv.center.x + 5, iv.center.y)
var to_value:NSValue = NSValue(CGPoint: to_point)
shake.fromValue = from_value
shake.toValue = to_value
iv.layer.addAnimation(shake, forKey: "position")
}
override func viewDidLoad() {
CATransaction.begin()
CATransaction.setCompletionBlock({
self.image1.hidden = true
self.image2.hidden = true
})
shakeView(image1)
shakeView(image)
CATransaction.commit()
}
我正在尝试为 UIImageView 设置动画,然后在动画完成后隐藏图像视图。然而,imageview 在动画完成之前被隐藏。我查看了类似的问题,他们建议在完成后实现动画侦听器或在动画代码中执行 .hidden 代码,但是我不确定如何在下面的 shakeView() 函数中影响它。
如何显示摇动动画并仅在动画完成后隐藏图像视图?
使用以下代码调用动画:
shakeView(image1!)
shakeView(image2)
image1!.hidden = true
image2.hidden = true
动画函数本身如下所示:
func shakeView(iv: UIImageView){
var shake:CABasicAnimation = CABasicAnimation(keyPath: "position")
shake.duration = 0.1
shake.repeatCount = 2
shake.autoreverses = true
var from_point:CGPoint = CGPointMake(iv.center.x - 5, iv.center.y)
var from_value:NSValue = NSValue(CGPoint: from_point)
var to_point:CGPoint = CGPointMake(iv.center.x + 5, iv.center.y)
var to_value:NSValue = NSValue(CGPoint: to_point)
shake.fromValue = from_value
shake.toValue = to_value
iv.layer.addAnimation(shake, forKey: "position")
}
正如 Paulw11 在他的评论中提到的,您可以使用文档中提到的 animationDidStop:
方法。但此外,您应该为 CABasicAnimation/CAAnimation
对象添加一个键,以便您的 animationDidStop:
方法知道具体哪个已完成。
所以在你的 shake 方法中添加一个值键对来标识动画并将委托设置为 self,例如:
func shakeView(iv: UIImageView){
var shake:CABasicAnimation = CABasicAnimation(keyPath: "position")
shake.duration = 0.1
shake.repeatCount = 2
shake.autoreverses = true
// Add these two lines:
shake.setValue("shake", forKey: "animationID")
shake.delegate = self
// ...
然后添加 animationDidStop:
委托方法来提醒您动画何时完成,以便您可以开始执行代码:
override func animationDidStop(anim: CAAnimation!, finished flag: Bool) {
// Unwrap the optional value for the key "animationID" then
// if it's equal to the same value as the relevant animation,
// execute the relevant code
if let animationID: AnyObject = anim.valueForKey("animationID") {
if animationID as NSString == "shake" {
// execute code
}
}
}
您可以使用 CATransaction
在动画完成后调用完成块。
func shakeView(iv: UIImageView){
CATransaction.begin()
CATransaction.setCompletionBlock({
iv.hidden = true
})
var shake:CABasicAnimation = CABasicAnimation(keyPath: "position")
shake.duration = 0.1
shake.repeatCount = 21
shake.autoreverses = true
var from_point:CGPoint = CGPointMake(iv.center.x - 5, iv.center.y)
var from_value:NSValue = NSValue(CGPoint: from_point)
var to_point:CGPoint = CGPointMake(iv.center.x + 5, iv.center.y)
var to_value:NSValue = NSValue(CGPoint: to_point)
shake.fromValue = from_value
shake.toValue = to_value
iv.layer.addAnimation(shake, forKey: "position")
CATransaction.commit()
}
或者您也可以将两个动画组合在一个 CATransaction
中,如下所示。
func shakeView(iv: UIImageView){
var shake:CABasicAnimation = CABasicAnimation(keyPath: "position")
shake.duration = 0.1
shake.repeatCount = 21
shake.autoreverses = true
var from_point:CGPoint = CGPointMake(iv.center.x - 5, iv.center.y)
var from_value:NSValue = NSValue(CGPoint: from_point)
var to_point:CGPoint = CGPointMake(iv.center.x + 5, iv.center.y)
var to_value:NSValue = NSValue(CGPoint: to_point)
shake.fromValue = from_value
shake.toValue = to_value
iv.layer.addAnimation(shake, forKey: "position")
}
override func viewDidLoad() {
CATransaction.begin()
CATransaction.setCompletionBlock({
self.image1.hidden = true
self.image2.hidden = true
})
shakeView(image1)
shakeView(image)
CATransaction.commit()
}