更改UIWindow的rootViewController

时间:2013-07-13 16:23:53

标签: ios uiviewcontroller uiwindow rootview

首次加载我的应用时,我将rootViewController的{​​{1}}属性设置为UIWindow

在我的应用中的某个时间,我选择将controllerA更改为rootViewController

问题在于,有时当我在controllerB进行翻转过渡时,我会看到controllerB后面的观点。由于某种原因,视图没有被删除。更令人担忧的是,在将controllerA设置为rootViewController后,controllerB的{​​{1}}方法永远不会被解雇。

我已尝试在切换到controllerA之前手动删除dealloc的子视图,这解决了在后台查看UIWindow视图但controllerB'的问题s dealloc仍然没有被召唤。 这里发生了什么?

苹果文档说:

  

根视图控制器提供窗口的内容视图。将视图控制器分配给此属性(以编程方式或使用Interface Builder)将视图控制器的视图安装为窗口的内容视图。如果窗口具有现有视图层次结构,则在安装新视图之前将删除旧视图。

更新

这是我的AppDelegate的代码:

controllerA

5 个答案:

答案 0 :(得分:10)

事实证明,有两个不同的问题。 1)我在控制器A中有一个保留周期,所以它从来没有得到dealloc'd。其次,为了更改根视图控制器,您必须首先删除Windows子视图(即使文档建议不这样做)

答案 1 :(得分:1)

问题可能在于你的ControllerA或ControllerB的实现,它们可能在代码中保留'self',因此ARC无法自动解除你的ViewController。你可以发布ControllerA和ControllerB实现。

答案 2 :(得分:0)

var loginNavigationController: OnBoardViewController?{
    willSet{
        if newValue == nil {
            loginNavigationController?.view.removeFromSuperview()
        }
    }
}

loginNavigationController = nil

答案 3 :(得分:0)

这是苹果的错误,我们假设ViewControllerA为当前的rootViewController:

// ViewControllerA.m
- (void)buttonClick {
    [self dismissViewControllerAnimated:YES completion:^{
        // [((AppDelegate *)[[UIApplication sharedApplication] delegate]) resetRoot]; // OK
    }];

    [((AppDelegate *)[[UIApplication sharedApplication] delegate]) resetRoot]; // ViewControllerA's view will not dealloc 
}

// AppDelegate.m
- (void)resetRoot {
    ViewControllerB *controller = [[ViewControllerB alloc] init];
    self.window.rootViewController = controller;
}

如果将重置窗口的rootViewController设置为此代码,则ViewControllerA的视图将永远不会取消分配。

答案 4 :(得分:0)

一个更简单的解决方案是将新窗口的backgroundColor设置为.white或任何颜色。默认值为nil,这将导致透明背景。这就是为什么可以看到旧窗口(在新窗口的顶部可见)的原因。