我有一个在 UICollectionView 之间切换的函数:
func toggleCollectionView(target: NSObject, targetName:String){
self.view.userInteractionEnabled = false
if let tempTarget = target as? UICollectionView {
//if selected item is same as active one, won't do anything
if(targetName != activeToolbarName){
tempTarget.hidden = false
tempTarget.frame.origin.y = screenSize.height
UIView.animateWithDuration(0.4, delay: 0.0, options: .CurveEaseOut, animations: {
if let tempActiveToolbar = self.activeToolbar as? UICollectionView {
tempActiveToolbar.frame.origin.y = self.screenSize.height
}
tempTarget.frame.origin.y = self.screenSize.height - tempTarget.frame.height - self.selectorsContainer.frame.height
}, completion: { finished in
if let tempActiveToolbar = self.activeToolbar as? UICollectionView {
tempActiveToolbar.hidden = true
self.activeToolbar = target
self.activeToolbarName = targetName
self.view.userInteractionEnabled = true
}
})
}
}
}
它是由屏幕上的几个按钮触发的,如下所示:
@IBAction func showFontsTool(sender: UIBarButtonItem) {
toggleCollectionView(fontsCV, targetName:"fontsCV")
}
如果用户快速点击按钮,completion
block 有时不会被调用,self.view.userInteractionEnabled
也不会被启用。如何确保 completion
block 总是在开始动画后被调用?
更新
固定功能正常工作:
func toggleCollectionView(target: NSObject, targetName:String){
if let tempTarget = target as? UICollectionView {
//if selected item is same as active one, won't do anything
if(targetName != activeToolbarName){
tempTarget.hidden = false
tempTarget.frame.origin.y = screenSize.height
if (runningAnimation == false){
runningAnimation = true
self.activeToolbarName = targetName
UIView.animateWithDuration(0.4, delay: 0.0, options: .CurveEaseOut, animations: {
if let tempActiveToolbar = self.activeToolbar as? UICollectionView {
tempActiveToolbar.frame.origin.y = self.screenSize.height
}
tempTarget.frame.origin.y = self.screenSize.height - tempTarget.frame.height - self.selectorsContainer.frame.height
}, completion: { finished in
if let tempActiveToolbar = self.activeToolbar as? UICollectionView {
tempActiveToolbar.hidden = true
self.activeToolbar = target
self.runningAnimation = false }
})
}
}
}
}
最佳答案
这是解决方法:
创建一个 bool 变量 animationTriggering
,当您按下按钮时将其自身设置为 true。这个变量可以作为一个标志供你检查;如果为真,则不要再次执行 UIView 动画。您只会在 UIView 动画处于 false 状态时执行它。
UIView 动画完成后,将其设置回 false,以便下次再次触发。
我猜这个问题是由于多线程问题引起的。我以前遇到过这种情况,并且绕过了它,但我真的没有信心声称我知道问题出在哪里。
如果我可以大胆猜测的话,那就是 UIView 动画有一个内部异步线程,如果您发送请求太快,它会相互干扰。
关于ios - 如何确保在 animateWithDuration() 中调用完成,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/30501060/