3

我正在制作具有 2 个 UIViewControllers 的简单故事板应用程序,并且我正在使用模态 segue 在它们之间切换。每个 UIViewController 都有一个 UIButton,用于对另一个 UIViewController 执行 segue。在 viewDidLoad 方法中,我在每个 UIViewController 上为该 UIButton 的外观设置动画。我正在使用 Cross Dissolve Modal segue。

当我在第一个 UIViewController 上按下 UIButton 时,我导航到第二个 UIViewController 并执行动画并显示第二个 UIViewController。在我按下第二个 UIView 控制器上的 UIButton 后,显示第一个 UIViewController 并执行它的动画。一切看起来都很好,每当我导航到每个 UIViewController 时,都会调用 viewDidLoad 方法。这很棒。

我现在尝试将 Modal segue 类型从 Cross Dissolve 更改为 XCode Interface Builder 中默认提供的其他两种。我改为 Cover Vertical,一切正常,没有任何变化。但是当我尝试Flip Horizo​​ntal Modal segue时,我发现了一个问题。

执行翻转水平模态序列时,两个 UIViewControllers 上的 UIButton 都会显示,但动画未执行。我尝试调试,我确定正在执行动画命令,但没有显示动画。

所以这是我的第一个问题:有谁知道这些类型的模态转场之间有什么区别可能导致我的动画不显示?

其他问题与segues和内存管理的基本理论有关。当我执行 segue 并导航到某个 UIViewController 时,每次都会调用 viewDidLoad 方法。那么,这是否意味着每次执行 viewDidLoad 方法时我都会创建新的对象实例?

我还注意到从未调用 viewDidUnload 方法。那么,如果对上一个问题的回答是肯定的(每次 viewDidLoad 执行都会创建新的对象实例),这是否意味着我的 UIViewController 对象实例永远不会被卸载和删除?还是 ARC 在幕后进行垃圾收集?

如果有人可以解释故事板转场和内存管理/对象生命周期是如何工作的,以及为什么永远不会调用 viewDidUnload 方法,我将不胜感激。


[编辑#1:在执行模态转场后尝试卸载 UIViewController]

[更新#1:不应该这样做,viewDidUnload 将被自动调用]

我在附加到 UIButton 点击​​的 IBAction 中进行 segue。我已经编写了这段代码来执行模态搜索。

@try
{
    [self performSegueWithIdentifier:segueToPerform sender:self];
}
@catch (NSException *exception) 
{
    NSLog(@"Exception: %@", exception);
}
@finally
{
    [self viewDidUnload];
}

我在@finally 块中手动调用了viewDidUnload,并且我检查了天气viewDidUnload 在运行时被调用,是的 - 它被调用了。

这是否意味着我设法卸载了我在使用另一个 UIViewController 的模态 segue 导航到它时创建的 UIViewController 对象并将其从内存中删除?

这种方法是否经常替代:

[self dismissViewControllerAnimated:YES completion:nil];

因为上面这行将我返回到 UIViewController,我从中导航到当前 UIViewController,但这不符合我的需要,因为我需要从当前 UIViewController 到其他 UIViewController 执行新的转场(除了返回到我导航到当前的 UIViewController一)?


[编辑#2:完成]

最后,在为这些 UIView 创建单独的 XIB 文件后,我更改了实现模型并在单个 UIViewController 下加载了新的 UIView。我已将@dasblinkenlight 的答案标记为正确的答案,因为它包含许多有用的信息,并且关于该答案的讨论很好地回答了有关使用模态序列的一些疑问。

4

2 回答 2

4

我不知道您问题第一部分的答案,但是一旦您了解了第二部分的答案,我相信您无论如何都会采用不同的解决方案。

viewDidLoad每次都会调用方法。那么,这是否意味着每次viewDidLoad执行方法时我都会创建新的对象实例?

绝对地。“模态”segue 导致新视图完全遮盖旧视图,直到新视图关闭。如果您来回多次,您的代码将在当前视图下方累积一整个“堆栈”视图。

我还注意到viewDidUnload永远不会调用该方法。那么,如果对上一个问题的回答是肯定的(每次viewDidLoad执行都会创建新的对象实例),这是否意味着我的UIViewController对象实例永远不会被卸载和删除?

这是正确的,您创建的所有视图控制器仍然存在,准备好关闭其顶部的视图。

还是 ARC 在幕后进行垃圾收集?

ARC 不是垃圾收集器,它是一种引用计数机制,编译器有一点自动化。物体还在。

你应该改变你的代码来调用

[self dismissModalViewControllerAnimated:YES];

在第二个控制器中,而不是使用将您带回第一个控制器的模态转场。

于 2012-09-03T16:11:05.340 回答
0

我遇到了一个类似的问题,我有一个复杂的 VC 导航网络,结果使用 segues(没有 UINavigationController)占用了太多内存。您可能想看看这个问题/答案,看看我的最终解决方案。uerceg 和 dasblinkenlight 之间的对话帮助我找到了这个解决方案。

Segues 并从内存中清除历史 ViewController

于 2013-01-02T01:57:21.970 回答