2016-10-06 100 views
0

我不能理解为什么这不起作用。iOS交互式动画Swift

有两名风险投资:A和B.

我想向右滑动VC的一个揭示VC B,而要使它互动,使用户可以在两个风投之间拖动(像Instagram的主屏幕上时,你左右滑动去相机和信息)。目前,它不会“拖拽”。您可以刷卡上VC A和它会去VC B.

这里是我的动画对象向右滑动:

class SlideRightTransitionAnimator: NSObject { 

let duration = 0.5 
var isPresenting = false 
let customInteractiveTransition = CustomInteractiveTransition() 

} 

// MARK: UIViewControllerTransitioningDelegate 
extension SlideRightTransitionAnimator: UIViewControllerTransitioningDelegate { 

// Return the animator when presenting a VC 
func animationController(forPresented presented: UIViewController, presenting: UIViewController, source: UIViewController) -> UIViewControllerAnimatedTransitioning? { 
    isPresenting = true 
    return self 
} 

// Return the animator used when dismissing from a VC 
func animationController(forDismissed dismissed: UIViewController) -> UIViewControllerAnimatedTransitioning? { 
    isPresenting = false 
    return self 
} 

// Add the interactive transition for Presentation only 
func interactionControllerForPresentation(using animator: UIViewControllerAnimatedTransitioning) -> UIViewControllerInteractiveTransitioning? { 
    return customInteractiveTransition.transitionInProgress ? customInteractiveTransition : nil 
} 
} 

// MARK: UIViewControllerTransitioningDelegate 
extension SlideRightTransitionAnimator: UIViewControllerAnimatedTransitioning { 

// Return how many seconds the transiton animation will take 
func transitionDuration(using transitionContext: UIViewControllerContextTransitioning?) -> TimeInterval { 
    return duration 
} 

// Animate a change from one VC to another 
func animateTransition(using transitionContext: UIViewControllerContextTransitioning) { 

    // Get reference to our fromView, toView and the container view that we should perform the transition 
    let container = transitionContext.containerView 
    let fromView = transitionContext.view(forKey: UITransitionContextViewKey.from)! 
    let toView = transitionContext.view(forKey: UITransitionContextViewKey.to)! 

    // Set up the transform we'll use in the animation 
    let offScreenRight = CGAffineTransform(translationX: container.frame.width, y: 0) 
    let offScreenLeft = CGAffineTransform(translationX: -container.frame.width, y: 0) 

    // Start the toView to the right of the screen 
    if isPresenting { 
     toView.transform = offScreenLeft 
    } 

    // Add the both views to our VC 
    container.addSubview(toView) 
    container.addSubview(fromView) 

    // Perform the animation 
    UIView.animate(withDuration: duration, delay: 0.0, usingSpringWithDamping: 1.0, initialSpringVelocity: 1.0, options: [], animations: { 

     if self.isPresenting { 
      fromView.transform = offScreenRight 
      toView.transform = CGAffineTransform.identity 
     } 
     else { 
      fromView.transform = offScreenLeft 
      toView.transform = CGAffineTransform.identity 
     } 

     }, completion: { finished in 
      // Tell our transitionContext object that we've finished animating 
      transitionContext.completeTransition(true) 
    }) 
} 

} 

这里是我的互动转变控制器

class CustomInteractiveTransition: UIPercentDrivenInteractiveTransition { 

weak var viewController : UIViewController! 
var shouldCompleteTransition = false 
var transitionInProgress = false 
var completionSeed: CGFloat { 
    return 1 - percentComplete 
} 

func attachToViewController(viewController: UIViewController) { 
    self.viewController = viewController 
    setupPanGestureRecognizer(view: viewController.view) 
} 

private func setupPanGestureRecognizer(view: UIView) { 
    view.addGestureRecognizer(UIPanGestureRecognizer(target: self, action: #selector(handlePanGesture))) 
} 

func handlePanGesture(gestureRecognizer: UIPanGestureRecognizer) { 
    let viewTranslation = gestureRecognizer.translation(in: gestureRecognizer.view!.superview!) 
    var progress = (viewTranslation.x/200) 
    progress = CGFloat(fminf(fmaxf(Float(progress), 0.0), 1.0)) 

    switch gestureRecognizer.state { 
    case .began: 
     transitionInProgress = true 
     viewController.dismiss(animated: true, completion: nil) 
    case .changed: 
     shouldCompleteTransition = progress > 0.5 
     update(progress) 
    case .cancelled, .ended: 
     transitionInProgress = false 
     if !shouldCompleteTransition || gestureRecognizer.state == .cancelled { 
      cancel() 
     } else { 
      finish() 
     } 
    default: 
     print("Swift switch must be exhaustive, thus the default") 
    } 
} 

} 

而且最后的代码VC - 答:

class ViewControllerA: UITableViewController { 

let slideRightTransition = SlideRightTransitionAnimator() 
let customInteractiveTransition = CustomInteractiveTransition() 

override func viewDidLoad() { 
    super.viewDidLoad() 

    // Add a Pan Gesture to swipe to other VC 
    let swipeGestureRight = UISwipeGestureRecognizer(target: self, action: #selector(swipeGestureRightAction)) 
    swipeGestureRight.direction = .right 
    view.addGestureRecognizer(swipeGestureRight) 
} 

    // MARK: Pan gestures 
func swipeGestureRightAction() { 
    performSegue(withIdentifier: "showMapSegue", sender: self) 
} 

// MARK: Prepare for segue 
override func prepare(for segue: UIStoryboardSegue, sender: Any?) { 

    if segue.identifier == "showVCB" { 

     // This gets a reference to the screen that we're about to transition to and from 
     let toViewController = segue.destination as UIViewController 

     // Instead of using the default transition animation, we'll ask the segue to use our custom SlideRightTransitionAnimator object to manage the transition animation 
     toViewController.transitioningDelegate = slideRightTransition 

     // Add the Interactive gesture transition to the VC 
     customInteractiveTransition.attachToViewController(viewController: toViewController) 
    } 
} 

谢谢提前!

回答

2

在VC A的viewDidLoad中,您需要用UIPanGestureRecognizer替换该UISwipeGestureRecognizer。然后在手势处理函数中实现适当的.changed状态。编辑:此外,要实现控制器之间的滑动转换,我强烈建议使用UIPageViewController来代替。这或者甚至可以是自定义的UICollectionView解决方案。

+0

很抱歉这么晚才回复,但肯定你是对的 - 关键是要使用UIPageViewController。谢谢 – Danny

0
在功能

handlePanGesture你是从一个VC服用翻译参考(即,gestureRecognizer.view!.superview!) 但而不是采取全球化志愿服务青年从一个UIWindow。 (即,UIApplication.shared.windows.last

更换gestureRecognizer.view!.superview!UIApplication.shared.windows.last

it's worked for me.