iOS swift : UIViewControllerAnimatedTransitioning end frame in wrong position

标签 ios swift uiviewcontroller uiviewanimation

我有一个 Swift 项目,正在学习天气 API 并试图更好地处理 AnimatedTransitions。我有一个 UITableView 使用带有图像和文本的自定义 UITableViewCell。点击 tableView 中的单元格会转换为新的 UIViewController 作为显示(推送),整个内容嵌入到 UINavigationController 中。

当调用转换时,单元格中的图像应该移动到目标 viewController 上 UIImageView 的最终位置。然而,它所做的是在转换完成之前移动到屏幕的另一边,然后 View 发生变化,使图像看起来像快速回到 View 的中心。

screenshots

我阅读了很多试图解决这个问题的教程,也阅读了很多 StackOverflow,但都没有弄明白。有人可以向我指出我错过了什么吗?我要疯了,在这里。

在原始 ViewController 中调用转换的 segue:

func tableView(tableView: UITableView, didSelectRowAtIndexPath indexPath: NSIndexPath) {
  self.performSegueWithIdentifier("SHOW_DETAIL", sender: self)
}

override func prepareForSegue(segue: UIStoryboardSegue, sender: AnyObject?) {
  if segue.identifier == "SHOW_DETAIL" {
    let detailVC = segue.destinationViewController as DetailViewController
    let indexPathForForecast = self.tableView.indexPathForSelectedRow() as NSIndexPath!
    let detailForecast = self.forecasts?[indexPathForForecast.row]
    let cell = self.tableView.cellForRowAtIndexPath(indexPathForForecast) as WeatherCell
    let image = cell.forecastImage.image
    detailVC.forecastForDetail = detailForecast
    detailVC.forecastDetailImage = image
  }
}

func navigationController(navigationController: UINavigationController, animationControllerForOperation operation: UINavigationControllerOperation, fromViewController fromVC: UIViewController, toViewController toVC: UIViewController) -> UIViewControllerAnimatedTransitioning? {
  if fromVC == self && toVC.isKindOfClass(DetailViewController) {
    let transitionVC = AnimateToDetailVCController()
    return transitionVC
  } else {
    return nil
  }
}

这是来自 UIViewControllerAnimatedTransitioning 对象的 animateTransition 代码(编辑:解决方案代码已编辑到代码块中,感谢@jrturton!)

func animateTransition(transitionContext: UIViewControllerContextTransitioning) {
  let fromViewController = transitionContext.viewControllerForKey(UITransitionContextFromViewControllerKey) as ViewController
  let toViewController = transitionContext.viewControllerForKey(UITransitionContextToViewControllerKey) as DetailViewController

  let containerView = transitionContext.containerView()
  let duration = self.transitionDuration(transitionContext)

  let selectedRow = fromViewController.tableView.indexPathForSelectedRow()
  let cell = fromViewController.tableView.cellForRowAtIndexPath(selectedRow!) as WeatherCell
  let weatherSnapshot = cell.forecastImage.snapshotViewAfterScreenUpdates(false)
  weatherSnapshot.frame = containerView.convertRect(cell.forecastImage.frame, fromView: fromViewController.tableView.cellForRowAtIndexPath(selectedRow!)?.superview)
  cell.forecastImage.hidden = true

  toViewController.view.frame = transitionContext.finalFrameForViewController(toViewController)
  toViewController.view.alpha = 0
  toViewController.detailImageView.hidden = true

  containerView.addSubview(toViewController.view)
  containerView.addSubview(weatherSnapshot)

  var toFrame = toViewController.locationIs

  UIView.animateWithDuration(duration, animations: { () -> Void in
    // EDIT: This solved the issue, thanks JRTurton!
    toViewController.view.setNeedsLayout() // Solution: This is where it was needed
    toViewController.view.layoutIfNeeded() //  Solution: This is where it was needed

    toViewController.view.alpha = 1.0
    var endRect = containerView.convertRect(toViewController.detailImageView.frame, fromView: toViewController.view)
    weatherSnapshot.frame = endRect

  }) { (finished) -> Void in
    toViewController.detailImageView.hidden = false
    cell.forecastImage.hidden = false
    weatherSnapshot.removeFromSuperview()

    transitionContext.completeTransition(true)
  }

}

最佳答案

这很难说,但这是我的猜测:您使用的是尺寸类,以任意/任意尺寸进行设计,并且您的 View Controller 中的图像仍然以该尺寸为中心当你得到它的帧用于你的动画时,让它太靠右了。转换完成后,将进行布局传递并进行更正。

要修复,在设置 View Controller 的框架后,强制进行布局传递:

toViewController.view.setNeedsLayout()
toViewController.view.layoutIfNeeded()

在进行上述更改之前,您可以先通过检查动画之前 ImageView 的帧来确认这是否是问题所在。

关于iOS swift : UIViewControllerAnimatedTransitioning end frame in wrong position,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/27996873/

相关文章:

objective-c - 从调用无弧 C 函数的 ARC 方法中释放对象

iOS Facebook SDK : FBSDKGraphRequest not getting email, 尽管获得许可

ios - 当我们尝试使用 Appium 脚本导航到 iPhone safari 浏览器中的框架时,获取异常阻止了具有原点的框架

swift - 我可以使用泛型快速将 NSNumber 转换为 T 吗?

ios - 我使用哪种方式从照片库加载图像?

ios - 呈现 View Controller 时缺少导航和标签栏

ios - NSData 图像在内存中的权重是否与打开的图像一样大?

ios - 无法使用 ARKit (ARKit + CoreLocation) 对场景节点进行动画处理

ios - 可以不连续调用dismissModalViewController吗?

ios - PresentingViewController 如何收到其 PresentedViewController 自行关闭的通知?