I have no idea about the frame rate. It is the speed that is lower - WAAY lower. Just like when you set the slow animations item on the iOS simulator. I'd not thought of running instruments. I'll try that when I have some time.
There is more than one way the animations are kicked off. The main one, the one that recenters the maze is done with a property of type UIViewPropertyAnimator. I call it mainAnimator. The basic logic goes like this:
if mainAnimator.isRunning {
mainAnimator.stopAnimation(true)
// some logic to set the bounds of my maze view.
self.mainAnimator = UIViewPropertyAnimator(duration: newDuration, curve: .easeOut, animations: {
self.fieldView.bounds.origin = CGPoint(x: relativeToPuzzleCenter.x, y: relativeToPuzzleCenter.y)
})
} else {
// some logic to calculate the duration of the animation
self.mainAnimator = UIViewPropertyAnimator(duration: duration, curve: .easeInOut, animations: {
self.fieldView.bounds.origin = CGPoint(x: relativeToPuzzleCenter.x, y: relativeToPuzzleCenter.y)
}
}
mainAnimator.addCompletion ...
The completion block has a UIView.animate(withDuration) call in it. However, this is called only if the maze is completed. So this is not really relevant, since the issue happens before the maze is finished.
For the popup scores that animate off, the logic goes like this:
Instantiate a view with appropriate label and add it as a subview.
Use a timer to let it stay in place for some period of time before animating it off:
timer = Timer.scheduledTimer(withTimeInterval: delay, repeats: false) {
// logic to do the popup animation
}
Popup animation:
sup.addSubview(labelHolder)
let animator = UIViewPropertyAnimator(duration: 2.0, curve: .linear) {
labelHolder.center = endingPositionInSup
labelHolder.alpha = 0
}
animator.addCompletion { (position) in
label.removeFromSuperview()
}
animator.startAnimation()
For moving the token on the board, I use
UIView.animate(withDuration: 0.2, delay: 0, options: .curveEaseInOut) {
token.center = CGPoint(x: token.center.x + movement.x, y: token.center.y + movement.y)
} completion: { (finished) in
// some stuff unrelated to animation.
}
Having said all this, I can play multiple games with hundreds of movements per game without the slowdown happening. When the slowdown happens, it's sudden. Possibly a clue: when the slowdown happens, the popups originate from the wrong place. I'll add an appropriate assert there, although, I don't see how a location error would cause unrelated animations to slow down.
Note that when the animation slowdowns happen it is ALL animations, including system animations that I didn't code. I should have mentioned that earlier.
P.S. I've been meaning to eliminate all instances of UIView.animate.... with property animators. But that's still a to-do.