UIViewController 状态恢复 - 弱关系

Posted

技术标签:

【中文标题】UIViewController 状态恢复 - 弱关系【英文标题】:UIViewController State Restoration - weak relationships 【发布时间】:2013-12-18 18:15:54 【问题描述】:

ios 6 中,Apple 为 UIViewController 和相关类添加了状态恢复功能。这允许应用程序在终止时保存状态,并在用户恢复应用程序时恢复状态。

一切似乎都很好,但是我遇到了一个不适合这种模式的奇怪场景。

假设我们有两个视图控制器,ViewControllerOneViewControllerTwo,它们都存储了一些成功恢复的任意状态。现在让我们假设ViewControllerOne 有一个delegate 属性,而ViewControllerTwo 就是那个委托(这是模态视图控制器的常见模式)。谁负责恢复这种关系?它应该如何存储/恢复?

在我的特殊情况下,不涉及情节提要,恢复发生在代码中,通过 restorationClass 属性。我的第一个直觉是在 restoreClass 中创建视图控制器时尝试恢复关系,但是由于 restorationClass 不知道其他现有控制器,它无法完全恢复这种关系。

或者,如果是声明delegate属性的视图控制器,应该恢复关系,那么现在在其他类中恢复的控制器实例如何?

简而言之,这似乎是一个记录不充分的场景,我希望有人能对此有所了解。

【问题讨论】:

【参考方案1】:

我会说,任务落在委托视图控制器上,将自己设置为这样,就像你在推送另一个视图控制器之前所做的那样。

关于如何做到这一点,您有多种选择。

您可以将对视图控制器的弱引用存储在全局可访问的位置(例如,应用程序委托),并在 application:didDecodeRestorableStateWithCoder: 中使用这些值来设置委托 - 这就是此方法在 API 中的用途.

或者,您可以从代理监听的顶部视图控制器发布“hereIAmThisIsMe”通知(包含用户信息的self)并将自己设置为代理。

【讨论】:

虽然这绝对是一种合理的做事方式,但你不同意它不是最优雅的吗?即,感觉第一个提议的解决方案有点破坏封装(AppDelegate 变成了“无所不知”,而不是你想要的东西)?第二种是更有趣的方法,你会在哪里发送这个通知,在 decodeRestorableStateWithCoder:? 发送有一个选项,但你得担心时机——先恢复哪个控制器。 @HenriNormak BTW,第一种方法不一定会破坏封装。您可以实现一个协议,我们称之为PostRestorationHandler,其中有一个方法didFinishRestoration,并让委托视图控制器在那里设置委托。 AppDelegate 只知道视图控制器的存在(以及它们关于应用程序委托),但它不涉及内部。 喜欢这种方法,但是,如果不是将协议和 AppDelegate 作为调用者,我会在应用程序委托获取 didDecode... 回调时触发通知。这样,每个控制器都可以按照您描述的方式恢复自己的关系(假设他们存储了引用)。 @HenriNormak 小心这种方法。每当 Apple 决定更改其中的内容时,它都可能会崩溃。

以上是关于UIViewController 状态恢复 - 弱关系的主要内容,如果未能解决你的问题,请参考以下文章

UIViewController 自定义转换和状态恢复

状态恢复发出警告 - 导致莫名的视觉异常

弱引用委托未恢复

我必须实现UIDataSourceModelAssociation吗?

iOS 可达性和应用挂起/恢复行为

MonoTouch 中的弱事件模式