【问题标题】:viewWillAppear being called twice in iOS5viewWillAppear 在 iOS5 中被调用两次
【发布时间】:2011-12-10 06:01:17
【问题描述】:

我正在运行我的所有应用程序以确保它不仅仅是一个应用程序,并且在我拥有的每个应用程序中,当我在 iOS5 模拟器或设备上运行时,viewWillAppear 方法在每个视图上都会被调用两次。我有一个简单的NSLog(@"1");,每次都会在我的控制台中出现两次。这只是我,还是发生了什么事? (在 iOS4 中只调用一次)

这是调用 viewWillAppear 两次的视图的代码:

     CloseDoorViewController *closeVC;

     if (UI_USER_INTERFACE_IDIOM() == UIUserInterfaceIdiomPad) {
            closeVC = [[ CloseDoorViewController alloc] initWithNibName:@"CloseDoorViewIpad" bundle:nil];
        } else {
            closeVC = [[ CloseDoorViewController alloc] initWithNibName:@"CloseDoorViewController" bundle:nil];
        }

        [self.view addSubview:closeVC.view];
        [self presentModalViewController:closeVC animated:NO];

【问题讨论】:

    标签: iphone objective-c ios5


    【解决方案1】:

    这是 -addSubview: 方法。

    添加或删除视图控制器的视图时,必须有人调用视图控制器的'View Event'方法,例如-viewWillAppear:等。

    实际上,在 iOS 5 之前,不推荐使用 -addSubview:/-removeFromSuperView 视图控制器的视图,因为它不调用“视图事件”方法(您可以/应该自己调用它)。相反,建议使用“间接”方式来执行此操作,例如 -presentModalViewController: 您使用(它确实代表您调用“查看事件”方法)。

    在 iOS 5 上,Apple 更改了 -addSubview:/-removeFromSuperView 方法的行为,以允许直接对视图控制器进行视图管理。所以现在,当你在 viewController 的视图上使用这些方法时,'View Event' 方法将被自动调用。

    所以它被调用了两次。

    另请参阅here 上的视频“实施 UIViewController 遏制”。

    【讨论】:

    • 小注:iOS
    • 这应该是公认的答案。我一直在疯狂地试图弄清楚为什么自从 iOS5 以来 addSubview/removeFromSuperview 的行为有所不同。
    【解决方案2】:

    因为您要显示两次视图。

    第一次通过添加视图作为当前视图的子视图:

    [self.view addSubview:closeVC.view];
    

    第二次将视图的控制器推到当前视图的控制器之上:

    [self presentModalViewController:closeVC animated:NO];
    

    我不知道为什么在 iOS4 中 viewWillAppear 只被调用一次,因为 iOS5 调用它两次是正确的,因为您按照上面的说明显示了两次视图。

    只需删除其中一行就可以了(我建议删除addSubview 并保留presentModalViewController 之一)。

    【讨论】:

    • 哦哇不知道。不知道为什么,但我一直在这样做。问题:如果这是我表达观点的方式,我现在应该在何时何地发布该 CloseVC?
    • 您可以在发布的 sn-p 中直接释放或自动释放它——您不再需要拥有引用,因为您不会再次使用指针。
    • @mohabitar 或者您迁移代码以使用“自动引用计数”,您不必再担心保留、释放和自动释放。
    • 如何启用自动引用计数?
    • NM,找到链接:mikeash.com/pyblog/…
    【解决方案3】:

    如果您想在视图控制器中恢复旧的 (iOS 4) 行为,您应该实现以下方法:

    - (BOOL)automaticallyForwardAppearanceAndRotationMethodsToChildViewControllers {
        return NO;
    }
    

    【讨论】:

      【解决方案4】:

      更新:由于您已编辑问题以包含代码示例,因此很清楚问题所在。 Lukman 上面的回答是正确/优秀的。

      包含代码之前的原始答案:

      我会尝试在此类的-init 方法中放置一个断点(或日志语句)。如果它被命中两次,那么就会创建两个视图控制器。

      (请注意,如果您尚未覆盖此类中的 -init 方法,请确保覆盖指定的初始化程序 -[UIViewController initWithNibName:bundle:]

      http://developer.apple.com/library/ios/#DOCUMENTATION/UIKit/Reference/UIViewController_Class/Reference/Reference.html

      【讨论】:

      • 谢谢,请查看编辑。这段代码有什么问题吗
      • 你在说这个init方法吗:- (id)initWithNibName:(NSString *)nibNameOrNil bundle:(NSBundle *)nibBundleOrNil
      • 你只被调用一次
      • 实际上,我很确定在这种情况下您无需致电-addSubview:。尝试删除该行,我认为问题可能会得到解决。
      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2016-03-24
      相关资源
      最近更新 更多