在显示新视图之前,iOS 转场冻结了几秒钟 [英] iOS segue freeze for many seconds before showing new view

查看:15
本文介绍了在显示新视图之前,iOS 转场冻结了几秒钟的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

在我的应用程序的主视图中,我有一个表格视图和两个原型单元格.我已经使用故事板为每个单元格配置了 segue.在视图控制器中,我覆盖了 prepareForSegue 以将所选单元格的信息传递到目标视图.

In the main view of my app I have a table view and two prototype cells. I have configured the segues for each cell using the storyboard. In the view controller I override prepareForSegue to pass information on the selected cell to the destination view.

目标视图并不是特别复杂,当然也不需要任何繁重的加载处理.

The destination view isn't particularly complex and certainly doesn't require any heavy processing to load.

问题

当我第一次点击主控制器中的一个单元格时,目标视图会在很长的延迟后出现,从 5 到 40 秒.

When I tap on a cell in the main controller for the very first time, the destination view appears after a long delay, from 5 to 40 seconds.

EDIT #2:后续点击通常会更快

注意:

  • 如果我在目标视图出现之前再次点击同一个单元格,这会触发目标视图立即出现.
  • 同上,但点击不同的单元格会导致视图立即出现,但包含第一个单元格中的数据.
  • 同上,但点击不同的控件(没有关联的转场)会立即触发目标视图.
  • 随后的点击"通常表现出较少的延迟.
  • 时间分析器 - 就我所见 - 显示在这几秒钟的延迟期间绝对没有发生任何事情.
  • 我尝试了不同类型的转场,但没有任何区别
  • 一些 println 显示发生了以下事件序列:

  • If I tap on the same cell again before the destination view has appeared, this triggers the destination view to appear immediately.
  • As above, but tapping on a different cell results in the view appearing immediately but with the data from the first cell.
  • As above, but tapping on a different control (with no associated segues) triggers the destination view to appear immediately.
  • Subsequent "taps" generally manifest less delay.
  • The Time Profiler - for what I can see - shows that absolutely nothing is happening during those many seconds of delay.
  • I have tried different type of segues, but it made no difference
  • A few println's show that the following sequence of events occurs:

  • 在主视图中,prepareForSegue 被执行(无延迟)
  • 然后执行目标 viewDidLoad(无延迟)
  • ...长时间的延迟...
  • 目标控制器中的集合视图和表视图开始调用数据源相关方法以从控制器获取数据.
  • 视图终于出现了(有一个不需要的动画,顺便说一句,但这是一个不同的问题)

根据我对本主题的了解,我怀疑该问题可能与在后台线程中发生的上述某些操作有关.

From what I have read on this topic, I suspect the problem is potentially related to some of the above operations happening in a background thread.

知道我做错了什么吗?

EDIT #1:添加了一些代码

在主视图控制器中,segues 已经使用故事板链接(CTRL-将两个原型单元格拖到目标视图中).

In the main view controller the segues have been link using the story board (CTRL-drag the two prototype cells into the destination view).

代码看起来有点像下面:

The code looks a bit like below:

override func prepareForSegue(segue: UIStoryboardSegue, sender: AnyObject?)
{
    var assetIndex = assetsTable.indexPathForSelectedRow()?.row

    println("prepare for segue - start: (assets[assetIds[assetIndex!]]!.Name)")

    if let destination = segue.destinationViewController as? AssetThingsListViewController
    {
        destination.bundlesRepository = bundlesRepository!
        destination.asset = assets[assetIds[assetIndex!]]
    }

    println("prepare for segue - end")
}

编辑 #3 我在 BitBucket 上提供了一个示例项目>

EDIT #3 I have made a sample project available on BitBucket

推荐答案

我检查了你的项目.虽然我也找不到其他任何东西,但我也怀疑是线程问题.

I checked your project. And while I also couldn't find anything else, I also suspect that it's a problem with threading.

我通过为 tableview 实现一个委托并在代码中呈现新的控制器来解决这个问题:

I managed to fix the problem by implementing a delegate for the tableview and present the new controller in code:

func tableView(tableView: UITableView, didSelectRowAtIndexPath indexPath: NSIndexPath) {

    let destination = storyboard?.instantiateViewControllerWithIdentifier("BuilderToysListViewController") as! BuilderToysListViewController
    destination.botsRepository = botsRepository!
    destination.builder = builders[builderIds[indexPath.row]]

    dispatch_async(dispatch_get_main_queue(), { () -> Void in
        self.presentViewController(destination, animated: true) { () -> Void in

        }
    })

}

请注意,您已经设置了视图控制器故事板 ID:BuilderToysListViewController 并设置了 tableview 委托.不要忘记删除 segue.

Notice you have the set the view controller storyboard id: BuilderToysListViewController and also set the tableview delegate. Don't forget to remove the segues.

最后在新的视图控制器中关闭视图使用以下代码:

At the end to dissmis the view in the new view controller use this code:

@IBAction func backButton(sender: AnyObject)
{
    dismissViewControllerAnimated(true, completion: { () -> Void in

    })
//        performSegueWithIdentifier("segueToysByBuilder", sender: nil)        

}

这将允许您正确关闭视图而不是错误地创建一个新视图.

This would allow you to properly close the view instead of wrongly creating a new one.

这篇关于在显示新视图之前,iOS 转场冻结了几秒钟的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆