自定义推送过渡不起作用,而相同的自定义呈现过渡有效
Custom push transition isn't working whereas the same custom present transition is
我已关注 this tutorial and watched the WWDC video 这个主题,但找不到答案。
我的代码中有几乎相同的转换。当我将其作为呈现视图而不是推送视图时,它工作得很好。
它应该将推送视图的快照从 CGRect 动画化到全屏,反之亦然。
这是我的代码 UIViewControllerAnimatedTransitioning
class:
class ZoomingTransitionController: NSObject, UIViewControllerAnimatedTransitioning {
let originFrame: CGRect
let isDismissing: Bool
init(originFrame: CGRect, isDismissing: Bool) {
self.originFrame = originFrame
self.isDismissing = isDismissing
}
func transitionDuration(using transitionContext: UIViewControllerContextTransitioning?) -> TimeInterval {
return Constant.Animation.VeryShort
}
func animateTransition(using transitionContext: UIViewControllerContextTransitioning) {
let containerView = transitionContext.containerView
guard let fromVC = transitionContext.viewController(forKey: UITransitionContextViewControllerKey.from),
let toVC = transitionContext.viewController(forKey: UITransitionContextViewControllerKey.to) else {
return
}
let finalFrame = transitionContext.finalFrame(for: toVC)
toVC.view.frame = finalFrame
let snapshot = self.isDismissing ? fromVC.view.snapshotView(afterScreenUpdates: true) : toVC.view.snapshotView(afterScreenUpdates: true)
snapshot?.frame = self.isDismissing ? finalFrame : self.originFrame
snapshot?.layer.cornerRadius = Constant.FakeButton.CornerRadius
snapshot?.layer.masksToBounds = true
containerView.addSubview(toVC.view)
containerView.addSubview(snapshot!)
if self.isDismissing {
fromVC.view.isHidden = true
} else {
toVC.view.isHidden = true
}
let duration = transitionDuration(using: transitionContext)
UIView.animate(withDuration: duration,
animations: {
snapshot?.frame = self.isDismissing ? self.originFrame : finalFrame
},
completion: { _ in
if self.isDismissing {
fromVC.view.isHidden = false
} else {
toVC.view.isHidden = false
}
snapshot?.removeFromSuperview()
transitionContext.completeTransition(!transitionContext.transitionWasCancelled)
})
}
}
然后,我尝试使用两种方式展示一个新的视图控制器:呈现它和推送它。
我的 FromViewController
是 class UINavigationControllerDelegate
和 UIViewControllerTransitioningDelegate
的子class。
FromViewController
class 呈现 ToViewController
(效果很好):
func buttonAction(_ sender: AnyObject) {
self.tappedButtonFrame = sender.frame
let toVC = self.storyboard!.instantiateViewController(withIdentifier: "ToViewController")
toVC.transitioningDelegate = self
self.present(toVC, animated: true, completion: nil)
}
func animationController(forPresented presented: UIViewController, presenting: UIViewController, source: UIViewController) -> UIViewControllerAnimatedTransitioning? {
let transitionController = ZoomingTransitionController(originFrame: self.tappedButtonFrame, isDismissing: false)
return transitionController
}
func animationController(forDismissed dismissed: UIViewController) -> UIViewControllerAnimatedTransitioning? {
let transitionController = ZoomingTransitionController(originFrame: self.tappedButtonFrame, isDismissing: true)
return transitionController
}
FromViewController
class 推动 ToViewController
(不起作用):
func buttonAction(_ sender: AnyObject) {
self.tappedButtonFrame = sender.frame
let toVC = self.storyboard!.instantiateViewController(withIdentifier: "ToViewController")
self.navigationController?.pushViewController(toVC, animated: true)
}
func navigationController(_ navigationController: UINavigationController, animationControllerFor operation: UINavigationControllerOperation, from fromVC: UIViewController, to toVC: UIViewController) -> UIViewControllerAnimatedTransitioning? {
switch operation {
case .push:
return ZoomingTransitionController(originFrame: self.tappedButtonFrame, isDismissing: false)
case .pop:
return ZoomingTransitionController(originFrame: self.tappedButtonFrame, isDismissing: true)
default:
return nil
}
}
当 pushing 时,委托方法被调用并且 ZoomingTransitionController 执行其代码正常(进入 animateTransition
直到结束没有明显问题)。但是在屏幕上,任何时候都不会显示快照视图。 ToVC 出现在过渡持续时间之后,但同时没有任何其他内容。
我运行不知道如何调试...你有什么想法吗?
谢谢!!
我通过用 toVC
的 CGAffineTransform
替换快照元素(导致问题)找到了答案。
代码与 here 几乎相同。
我已关注 this tutorial and watched the WWDC video 这个主题,但找不到答案。
我的代码中有几乎相同的转换。当我将其作为呈现视图而不是推送视图时,它工作得很好。
它应该将推送视图的快照从 CGRect 动画化到全屏,反之亦然。
这是我的代码 UIViewControllerAnimatedTransitioning
class:
class ZoomingTransitionController: NSObject, UIViewControllerAnimatedTransitioning {
let originFrame: CGRect
let isDismissing: Bool
init(originFrame: CGRect, isDismissing: Bool) {
self.originFrame = originFrame
self.isDismissing = isDismissing
}
func transitionDuration(using transitionContext: UIViewControllerContextTransitioning?) -> TimeInterval {
return Constant.Animation.VeryShort
}
func animateTransition(using transitionContext: UIViewControllerContextTransitioning) {
let containerView = transitionContext.containerView
guard let fromVC = transitionContext.viewController(forKey: UITransitionContextViewControllerKey.from),
let toVC = transitionContext.viewController(forKey: UITransitionContextViewControllerKey.to) else {
return
}
let finalFrame = transitionContext.finalFrame(for: toVC)
toVC.view.frame = finalFrame
let snapshot = self.isDismissing ? fromVC.view.snapshotView(afterScreenUpdates: true) : toVC.view.snapshotView(afterScreenUpdates: true)
snapshot?.frame = self.isDismissing ? finalFrame : self.originFrame
snapshot?.layer.cornerRadius = Constant.FakeButton.CornerRadius
snapshot?.layer.masksToBounds = true
containerView.addSubview(toVC.view)
containerView.addSubview(snapshot!)
if self.isDismissing {
fromVC.view.isHidden = true
} else {
toVC.view.isHidden = true
}
let duration = transitionDuration(using: transitionContext)
UIView.animate(withDuration: duration,
animations: {
snapshot?.frame = self.isDismissing ? self.originFrame : finalFrame
},
completion: { _ in
if self.isDismissing {
fromVC.view.isHidden = false
} else {
toVC.view.isHidden = false
}
snapshot?.removeFromSuperview()
transitionContext.completeTransition(!transitionContext.transitionWasCancelled)
})
}
}
然后,我尝试使用两种方式展示一个新的视图控制器:呈现它和推送它。
我的 FromViewController
是 class UINavigationControllerDelegate
和 UIViewControllerTransitioningDelegate
的子class。
FromViewController
class 呈现 ToViewController
(效果很好):
func buttonAction(_ sender: AnyObject) {
self.tappedButtonFrame = sender.frame
let toVC = self.storyboard!.instantiateViewController(withIdentifier: "ToViewController")
toVC.transitioningDelegate = self
self.present(toVC, animated: true, completion: nil)
}
func animationController(forPresented presented: UIViewController, presenting: UIViewController, source: UIViewController) -> UIViewControllerAnimatedTransitioning? {
let transitionController = ZoomingTransitionController(originFrame: self.tappedButtonFrame, isDismissing: false)
return transitionController
}
func animationController(forDismissed dismissed: UIViewController) -> UIViewControllerAnimatedTransitioning? {
let transitionController = ZoomingTransitionController(originFrame: self.tappedButtonFrame, isDismissing: true)
return transitionController
}
FromViewController
class 推动 ToViewController
(不起作用):
func buttonAction(_ sender: AnyObject) {
self.tappedButtonFrame = sender.frame
let toVC = self.storyboard!.instantiateViewController(withIdentifier: "ToViewController")
self.navigationController?.pushViewController(toVC, animated: true)
}
func navigationController(_ navigationController: UINavigationController, animationControllerFor operation: UINavigationControllerOperation, from fromVC: UIViewController, to toVC: UIViewController) -> UIViewControllerAnimatedTransitioning? {
switch operation {
case .push:
return ZoomingTransitionController(originFrame: self.tappedButtonFrame, isDismissing: false)
case .pop:
return ZoomingTransitionController(originFrame: self.tappedButtonFrame, isDismissing: true)
default:
return nil
}
}
当 pushing 时,委托方法被调用并且 ZoomingTransitionController 执行其代码正常(进入 animateTransition
直到结束没有明显问题)。但是在屏幕上,任何时候都不会显示快照视图。 ToVC 出现在过渡持续时间之后,但同时没有任何其他内容。
我运行不知道如何调试...你有什么想法吗?
谢谢!!
我通过用 toVC
的 CGAffineTransform
替换快照元素(导致问题)找到了答案。
代码与 here 几乎相同。