【问题标题】:Custom Viewcontroller transition doesn't resize properly自定义 Viewcontroller 转换无法正确调整大小
【发布时间】:2015-12-05 11:44:54
【问题描述】:

我的应用中的导航控制器有一个自定义视图控制器转换。执行转换时,它没有正确调整子视图控制器的内容大小。默认过渡确实会调整它的大小。 I have added an example project on Github to demonstrate the issue.

导航控制器中嵌入的 VC

import UIKit

class PopoverVCViewController: UIViewController, UIViewControllerTransitioningDelegate, UINavigationControllerDelegate {

    let animator = Animator()

    override func viewDidLoad() {
        super.viewDidLoad()
        navigationController?.delegate = self
        // Do any additional setup after loading the view.
    }

    override func didReceiveMemoryWarning() {
        super.didReceiveMemoryWarning()
        // Dispose of any resources that can be recreated.
    }

    func navigationController(navigationController: UINavigationController, animationControllerForOperation operation: UINavigationControllerOperation, fromViewController fromVC: UIViewController, toViewController toVC: UIViewController) -> UIViewControllerAnimatedTransitioning? {
            animator.reverse = operation == .Pop
            return animator
    }

}

动画师

class Animator: NSObject, UIViewControllerAnimatedTransitioning {

    var reverse: Bool = false

    func animateTransition(transitionContext: UIViewControllerContextTransitioning) {

        // get reference to our fromView, toView and the container view that we should perform the transition in
        let container = transitionContext.containerView()!
        let fromView = transitionContext.viewForKey(UITransitionContextFromViewKey)!
        let toView = transitionContext.viewForKey(UITransitionContextToViewKey)!

        // set up from 2D transforms that we'll use in the animation
        let offScreenRight = CGAffineTransformMakeTranslation(container.frame.width, 0)
        let offScreenLeft = CGAffineTransformMakeTranslation(-container.frame.width, 0)

        // start the toView to the right of the screen
        if (self.reverse == false) {
            toView.transform = offScreenRight
        }
        else {
            toView.transform = offScreenLeft
        }

        // add the both views to our view controller
        container.addSubview(toView)
        container.addSubview(fromView)

        // get the duration of the animation
        // DON'T just type '0.5s' -- the reason why won't make sense until the next post
        // but for now it's important to just follow this approach
        let duration = self.transitionDuration(transitionContext)

        // perform the animation!
        // for this example, just slid both fromView and toView to the left at the same time
        // meaning fromView is pushed off the screen and toView slides into view
        // we also use the block animation usingSpringWithDamping for a little bounce
        UIView.animateWithDuration(duration, delay: 0.0, usingSpringWithDamping: 1.0, initialSpringVelocity: 0.0, options: UIViewAnimationOptions.CurveEaseInOut, animations: {

            if (self.reverse == false) {
                fromView.transform = offScreenLeft
            }
            else {
                fromView.transform = offScreenRight
            }

            toView.transform = CGAffineTransformIdentity

            }, completion: { finished in

                // tell our transitionContext object that we've finished animating
                transitionContext.completeTransition(true)

        })

    }

    // return how many seconds the transiton animation will take
    func transitionDuration(transitionContext: UIViewControllerContextTransitioning?) -> NSTimeInterval {
        return 0.3
    }

    // MARK: UIViewControllerTransitioningDelegate protocol methods

    // return the animataor when presenting a viewcontroller
    // remmeber that an animator (or animation controller) is any object that aheres to the UIViewControllerAnimatedTransitioning protocol
    func animationControllerForPresentedController(presented: UIViewController, presentingController presenting: UIViewController, sourceController source: UIViewController) -> UIViewControllerAnimatedTransitioning? {
        return self
    }

    // return the animator used when dismissing from a viewcontroller
    func animationControllerForDismissedController(dismissed: UIViewController) -> UIViewControllerAnimatedTransitioning? {
        return self
    }

}

【问题讨论】:

  • 当你点击让我们执行你希望它发生在你的主vc上的segue?
  • 导航控制器中嵌入的VC,感谢指出,我把标题从“主VC”改成了“嵌入在导航控制器中的VC”。

标签: ios swift uiviewcontroller uinavigationcontroller uiviewanimationtransition


【解决方案1】:

你可以设置toView的边框来匹配fromView的高宽:

let container = transitionContext.containerView()!
let fromView = transitionContext.viewForKey(UITransitionContextFromViewKey)!
let toView = transitionContext.viewForKey(UITransitionContextToViewKey)!

toView.frame = CGRectMake(toView.frame.origin.x, toView.frame.origin.y, fromView.frame.width, fromView.frame.height)

【讨论】:

    【解决方案2】:

    或者像这样:

    UIViewController* toController = [transitionContext viewControllerForKey:UITransitionContextToViewControllerKey];
    UIViewController* fromController = [transitionContext viewControllerForKey:UITransitionContextFromViewControllerKey];
    

    然后在您的动画例程结束时进行设置:

    toController.view.frame=fromController.view.frame;

    【讨论】:

      猜你喜欢
      • 2013-09-25
      • 1970-01-01
      • 2011-11-11
      • 2015-10-10
      • 1970-01-01
      • 1970-01-01
      • 2017-01-24
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多