在调用setViewControllers:animated:后改变设备方向导致崩溃

6
我一直在处理这个(有点)随机的问题,但无法找出问题所在。情况是这样的:我正在创建一个UISplitView iPad应用程序,其中包含一个UINavigationController作为Master视图中的子视图: 主菜单为红色,子菜单为绿色,主内容为紫色 主菜单为红色,子菜单为绿色,主内容为紫色。 由于我需要一些空间来放置垂直菜单,因此此UINavigationController并未填充整个Master视图。当用户在垂直侧面菜单上选择按钮时,会设置新的东西到UINavigationController以显示具有选项的UITableView。我在每个菜单选择上所做的是:
[self.subMenu setViewControllers:@[subMenuViewController] animated:YES];

发生的情况是我不需要保留菜单历史记录,所以我每次都会为subMenu设置一个新的根视图控制器。

问题出现在当我开始调整设备方向时。它没有明显的模式,但有时候,在旋转时,我的应用程序会崩溃。现在,当我使用Instruments运行它时,这就是我得到的结果:

167 Zombie      -1  00:32.101.527   UIKit   -[UITableView _spacingForExtraSeparators]

有趣的是,访问错误发生在子菜单的上一个根视图控制器上。所以如果我点击“Events”,然后再点击“Podcasts”,那么在尝试访问“EventsViewController”时会发生访问错误。

所以我猜测,在替换子菜单UINavigationController的根视图控制器的方式上存在问题,但我不确定是什么问题。也许我需要确保当前的根视图控制器在设置新的根视图控制器之前被释放了?

非常感谢任何帮助。 :)


1
您正在调用已释放的实例。在应用程序中添加一个“异常断点”,并尝试复制您的问题:应用程序应该停在导致问题的确切点上。 - Marco Pace
@MarcoPace 我已经这样做了,但它总是在UIApplicationMain上给我Bad Access错误。 - diogocarmo
你是否在分割视图控制器中使用了 viewContainers - danypata
2个回答

4

由于某些设置不正确,系统库代码崩溃并不罕见。这可能是因为您的UIWindow、UIApplicationMain或其内容视图,或者您的视图控制器实例未被保留或以某种方式被释放。

如果您的控制器已经不存在了,那么shouldrotate方法将毫无帮助。

这是为了确定哪个对象被释放。

对于特别棘手的问题,您可以向一个可疑的类添加release,retain和dealloc方法(记录并调用super),然后查看谁在释放它。记录-retaincount以跟踪(我只用于诊断目的)。

或者您可以尝试在-[UIDevice setOrientation:]上设置断点,然后通过调试器逐步执行代码。

为了使调试更容易,您可以在调试器控制台中键入call (void)instrumentObjcMessageSends(YES)来开始记录objc_msgSends到/tmp/,然后继续执行,它将跟踪所有发送的消息直到崩溃。


我很喜欢在"setOrientation:"上设置一个断点的想法,但是我应该把断点放在哪里? - diogocarmo
你做了,但我在我的代码中没有使用 [UIDevice setOrientation:]。这就是为什么我问的原因。 - diogocarmo

2
首先,您应该在包含UITableView的视图控制器中实现willRotateToInterfaceOrientationwillAnimateToInterfaceOrientationdidRotateToInterfaceOrientation方法(检查这些方法的实际签名)。
在每个方法中,检查您的表视图数据源和委托。我认为这种崩溃是由于释放委托或表视图数据源引起的。
此外,您还应该检查旋转过程中调用了哪些表视图委托/数据源方法。
最后,请确保丢弃旧的subMenuViewController实例,并将它们正确地从父视图控制器中删除。

好主意!我会这样做并看看是否有帮助。谢谢! - diogocarmo
1
请告诉我结果 ;) - danypata

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接