我能否在viewWillAppear方法中知道它是在导航控制器返回(使用返回按钮)后被调用的?

26

假设我有UIViewController A 和 B。 用户通过 push segue 从 A 跳转到 B。 然后,用户按下返回按钮并回到A。

现在调用A的viewWillAppear。 在这里,我能否知道我是通过返回按钮(navigationController popTo...)而不是其他方式进入的?而且不需要在B视图控制器中编写特殊代码。


3个回答

32

嗯,也许你可以在viewWillAppear中使用self.isMovingToParentViewController,请参考文档。如果它的值为NO,那么它就意味着当前视图控制器已经位于导航堆栈上。


我已经尝试过了。不适用。看起来没有办法解决,除非在B视图控制器中编写一些内容。 - adsurbum
是的,这对我有用!! if (self.isMovingToParentViewController) { // 仅在第一次移动到父视图控制器时执行某些操作,而不是在返回按钮上执行 } - Phamer
2
这个答案是不正确的。如果视图控制器位于被弹出的视图控制器下方,在 viewWillAppear 调用时,它的 isMovingToParentViewController 总是为 false - Eric
帮了我很多。 - liushuaikobe
@Eric 这就是答案所说的。 - Ruiz

14

我喜欢在视图控制器A中做以下事情:

- (void) viewWillAppear:(BOOL)animated {
    [super viewWillAppear:animated];

    if (_popping) {
        _popping = false;
        NSLog(@"BECAUSE OF POPPING");
    } else {
        NSLog(@"APPEARING ANOTHER WAY");
    }

    //keep stack size updated
    _stackSize = self.navigationController.viewControllers.count;

    ....
}
- (void) viewWillDisappear:(BOOL)animated {
    [super viewWillDisappear:animated];

    _popping = self.navigationController.viewControllers.count > _stackSize;

    ....
}

你正在跟踪你的视图控制器(A)是否消失,因为另一个视图控制器(B)被推出或其他原因。然后(如果您没有修改子视图控制器的顺序),它应该准确地告诉您,如果(A)由于导航控制器上的弹出而出现。


如果视图控制器A被弹出、保留并重新推入堆栈,将导致意外行为。 - Ruiz

4

UIViewController A中添加一个BOOL属性:

@property (nonatomic) BOOL alreadyAppeared;

然后在您的 viewWillAppear: 方法中添加以下内容:

if (!self.alreadyAppeared) {
    self.alreadyAppeared = YES;
    // Do here the stuff you wanted to do on first appear
}

2
但是,一个视图控制器也可以通过标签栏点击出现,例如(它已经出现了,但不是通过返回按钮调用的)。 - adsurbum
@adsurbum 我在我的应用程序中使用了委托来处理这种情况。 - Coldsteel48
这似乎是模态视图控制器解除的最佳选项(我不想调用viewWillAppear)。添加这个布尔值就可以解决了。 - Paul Razvan Berg

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接