Iphone 如何在多视图控制器中正确释放和切换视图?
我正在尝试为游戏创建一个多视图控制器,其中一个根视图控制器在切换到另一个视图之前释放视图。子视图控制器本身又是子根视图控制器,因为它们包含其他视图控制器 例如,我的singlePlayerViewController将有一个shakeObjectViewController,可能还有其他控制器。使用actionsheets在视图之间切换,将应用程序委托作为actionsheet的委托,当从单机版视图切换到另一个视图时,一切都按预期进行 但是,当我尝试使用相同的init方法创建新的singlePlayerViewController时,当我尝试插入子视图(即shakeObjectViewController.view)时,调试器会抛出EXCIphone 如何在多视图控制器中正确释放和切换视图?,iphone,cocoa-touch,Iphone,Cocoa Touch,我正在尝试为游戏创建一个多视图控制器,其中一个根视图控制器在切换到另一个视图之前释放视图。子视图控制器本身又是子根视图控制器,因为它们包含其他视图控制器 例如,我的singlePlayerViewController将有一个shakeObjectViewController,可能还有其他控制器。使用actionsheets在视图之间切换,将应用程序委托作为actionsheet的委托,当从单机版视图切换到另一个视图时,一切都按预期进行 但是,当我尝试使用相同的init方法创建新的singlePl
\u BAD
\u访问错误
目前的初始化情况如下所示:
应用程序委托使用默认的init方法初始化窗口
- (void)applicationDidFinishLaunching:(UIApplication *)application {
// Override point for customization after application launch
[window addSubview:rootViewController.view];
[window makeKeyAndVisible];
}
然后在rootViewController.m的viewDidLoad中
if(singlePlayerViewController == nil) {
SinglePlayerViewController *singleController = [[SinglePlayerViewController alloc]
initWithNibName:@"SinglePlayerView" bundle:nil];
self.singlePlayerViewController = singleController;
[singleController release];
}
[self.view insertSubview:singlePlayerViewController.view atIndex:0];
然后是singleplayervewcontroller.m
- (void)viewDidLoad {
self.view.tag = kSinglePlayerView; // tag the view
ShakeObjectViewController *shakeController = [[ShakeObjectViewController alloc]
initWithNibName:@"ShakeObjectView" bundle:nil];
self.shakeObjectViewController = shakeController;
self.view = shakeController.view;
[shakeController release];
}
请注意,我的singlePlayerViewController并没有插入子视图,而是将自己的视图替换为子视图控制器的视图。(不知道这是否是一种好的做法:?:)
切换视图时,应用程序代理执行以下操作:
for(UIView *subview in [rootViewController.view subviews])
{
[subview removeFromSuperview];
}
[rootViewController.singlePlayerViewController release]
[rootViewController initMultiplayerView];
然后,当切换回单人模式时,执行rootViewController.m的viewDidLoad中相同的init方法,调试器在“[self.view insertSubview:singlePlayerViewController.view atIndex:0]”行上抛出错误
有没有关于为什么没有创建新视图的想法?我尝试将singlePlayerViewController设置为nil而不是释放,但随后在“self.view=shakeController.view;”行中抛出错误。
我的理解是,如果视图属性当前为零,则在下次访问视图时会自动为您创建一个新属性
initWithNibName是否只执行一次?或者我的设计方式在“视图控制器”方面过于复杂?您的设计看起来确实有点过于复杂,但这并不意味着调试器应该抛出随机错误!:)不过,尝试简化可能会有所帮助。我不明白为什么你想要一个单人视图,如果你要立即用一个抖动对象视图来代替它 我肯定认为您希望将singlePlayerViewController设置为nil,因为否则rootViewControllers viewDidLoad方法中的行“if(singlePlayerViewController==nil){”将为false,并且不会生成新的视图控制器,这就是为什么会出现第一个错误 在“self.view=shakeController.view”行中,我只看到了3种可能导致访问错误的方法:
- shakeController不是nil,而是垃圾。这似乎不太可能,因为它只是初始化的,除非它的viewDidLoad释放自己或类似的东西
- self不是nil,但是垃圾。同样,不太可能,但可能-可能检查调试器,看看self是什么样子(它的变量有意义吗,等等)
- 当您调用self.view=…,它将向原始视图发送一个释放。单人视图的dealloc方法中是否有可能导致访问错误的代码
[self setView:[shakeController view]]
如果这些为nil,则不会崩溃,因为允许向nil发送消息。是的,所有@property语句都标记为(nonatomic,retain) 也许问题可以重述为,如何从nib多次创建视图控制器?第二次创建VC时,无论是否释放同一类的先前VC,关联视图都不会创建,并抛出错误访问错误 请注意,我的singlePlayerViewController没有插入子视图,而是将自己的视图替换为子视图控制器的视图。(不知道这是否是一种好的做法:?:) 这里有巨大的警告标志。听起来好像你有一个视图和两个视图控制器。这很糟糕 请考虑插入和删除子视图:
- 根视图
- SinglePlayerView(可以删除并替换为MutliplayerView)
- 沙克维尤
- SinglePlayerView(可以删除并替换为MutliplayerView)
这就是框架的使用方式。你这样做的方式让我非常困惑,我认为这是你的错误的原因。我正在逐行检查,试图找出它崩溃的原因,但还没有完全弄清楚,但同时我很难弄清楚vie到底发生了什么切换过程中的ws 我会按照Kailoa的建议用三个不同的视图控制器来重写它。每个视图都应该有自己的控制器。一个视图不应该替换它自己,它应该被它的superview控制器替换
我怀疑她身上的某个地方有什么东西被释放了,然后被发送了消息,然后你试图通过返回该消息来做一些事情,认为某个东西是一个对象,而它不是。singleplayer视图最终将在其他视图之间切换,而不仅仅是shake视图。尝试注释“如果”(SinglePlayerServiceController==nil)“行并实例化一个新的控制器。同样的错误。“NSLog(@“shake's view=%@”,shakeController.view);”,引发相同的错误。还尝试完全跳过singleplayer视图控制器,并在根控制器中直接使用shakeObject VC。相同的错误。如果我不尝试释放视图,则切换btw视图可以正常工作,但我每次都需要一个新视图。感谢回复。