当我从导航控制器弹出顶视图控制器时,我当前需要实现一些代码。有没有办法检测视图控制器何时从导航控制器堆栈弹出?
我希望尽可能远离使用viewWillDisappear
或viewDidDisappear
,因为我在项目中使用splitview
,并在主视图中选择不同的行将还会触发viewWillDisappear
/ viewDidDisappear
方法。
答案 0 :(得分:77)
您可以使用视图控制器的isMovingFromParentViewController
属性检测是否正在弹出视图,如下所示:
- (void)viewWillDisappear:(BOOL)animated
{
[super viewWillDisappear:animated];
if ([self isMovingFromParentViewController])
{
NSLog(@"View controller was popped");
}
else
{
NSLog(@"New view controller was pushed");
}
}
<强> isMovingFromParentViewController 强>
返回一个布尔值,指示视图控制器所在的值 从父母那里被移除的过程。
答案 1 :(得分:22)
更新20150430
基于phatmann的反馈(下面的第一条评论),我很好奇自从我在一年前回答这个问题以来发生了什么变化。我整理了一个简单的示例应用程序,并且有一些有趣的结果。
选项1,示例
https://github.com/greymouser/TestNVC
我没有能力轻松测试8.x之前的版本,所以我不确定自那时起是否有变化。但是,我最初描述的行为仍然会发生。 然而,多亏了将测试应用程序放在一起,我确实注意到了之前没有的奇怪之处。
如果我只依赖{will,did}MoveToParentViewController
,我注意到在rootVC上推送第一个非rootVC时出现虚假的didMoveToParentViewController:
调用,使用parent!= nil(暗示它已被添加,未被删除) )。我在原始答案的时候没有遇到过这个问题,因为我通常在我的NVC上有“永久”rootVC,并且没有在那里实现回调。请参阅示例应用,将日志记录设置为LOG_WILL_DID_MTPVC
(在ViewController.m中)。这是 - 为空间编辑 - 我看到的快照:
TestNVC[] -[vc(rootVC) willMoveToParentViewController [entering]
TestNVC[] -[vc(rootVC) didMoveToParentViewController [entering]
TestNVC[] -[vc(1) willMoveToParentViewController [entering]
TestNVC[] -[vc(rootVC) didMoveToParentViewController [entering] # <-- this is odd
TestNVC[] -[vc(1) didMoveToParentViewController [entering]
...
我的原始答案建议单独使用{will,did}MoveToParentViewController
,因为它是处理此行为的“一站式服务”。但是,既然我已经看到了对rootVC的虚假调用,我建议混合使用{will,did}MoveToParentViewController
以及标准UINavigationControllerDelegate
回调。对于示例应用中的此行为,请将日志记录设置为LOG_WILL_DID_MTPVC_LEAVING_AND_NVC_WILL_DID_SHOW_VC
。现在我们看到以下内容:
TestNVC[] -[nvcD willShowViewController]: rootVC
TestNVC[] -[nvcD didShowViewController]: rootVC
TestNVC[] -[nvcD willShowViewController]: 1
TestNVC[] -[nvcD didShowViewController]: 1
TestNVC[] -[nvcD willShowViewController]: 2
TestNVC[] -[nvcD didShowViewController]: 2
TestNVC[] -[vc(2) willMoveToParentViewController [leaving]
TestNVC[] -[nvcD willShowViewController]: 1
TestNVC[] -[vc(2) didMoveToParentViewController [leaving]
TestNVC[] -[nvcD didShowViewController]: 1
TestNVC[] -[vc(1) willMoveToParentViewController [leaving]
TestNVC[] -[nvcD willShowViewController]: rootVC
TestNVC[] -[vc(1) didMoveToParentViewController [leaving]
TestNVC[] -[nvcD didShowViewController]: rootVC
......现在这更有意义了。
选项2
我没有探索的另一个选择是使用您的NVC sublcass,覆盖- pushViewController:animated:
和- popViewControllerAnimated:
,并将您想要的任何行为应用于被推送的VC,或者从pop返回的VC 。 (如果您尝试这样做,请务必记住在覆盖中调用super
。)
更新摘要
所以,感谢phatmann有机会重新开始。我认为现在我的回答是更多正确。但是,我不太确定它是否“完全不真实”。 ; - )
<强> ORIGINAL 强>
如果您描述的确切行为是您要查找的内容,请在您的子视图控制器上覆盖以下内容:
- (void)willMoveToParentViewController:(UIViewController *)parent;
- (void)didMoveToParentViewController:(UIViewController *)parent;
输入时将使用parent!= nil调用 willMoveToParentViewController:
,并在离开时调用parent == nil。 didMoveToParentViewController:
将永远有父!= nil。
有时,viewDidDisappear
可能有意义。但是,如果你真的想从父容器视图控制器中寻找push和pop,那么上面的那些方法就是你想要的。
答案 2 :(得分:0)
对于Swift用户(Swift 3-4.2):
我想检测何时从堆栈中弹出视图控制器,所以我无法使用viewWillDisappear
或viewDidDisappear
回调,因为这些回调将在视图控制器被调用时被调用不再可见,并且从堆栈中弹出时也不再可见。
但是您可以通过执行以下操作来使用导航控制器“委托” UINavigationControllerDelegate
:
让您的控制器符合UINavigationControllerDelegate
:
class ViewController : UIViewController {
override func viewDidLoad() {
super.viewDidLoad()
self.navigationController?.delegate = self
}
}
extension ViewController : UINavigationControllerDelegate {
override func willMove(toParentViewController parent: UIViewController?) {
/*You can detect here when the viewcontroller is being popped*/
}
}
希望这会有所帮助,祝你好运
答案 3 :(得分:0)
如果您不需要在删除视图控制器之前就知道它,而只需要知道它已被弹出,则也可以使用deinit
。
class ViewController: UIViewController {
deinit {
// View controller has been popped/dismissed and it's being released
}
}
此方法可以很好地通知协调员或其他代表。
答案 4 :(得分:0)
我在iOS 13上的经验是Sub SelectAllEquations()
Dim xMath As OMath
Dim I As Integer
With ActiveDocument
.DeleteAllEditableRanges wdEditorEveryone
For I = 1 To .OMaths.Count
Set xMath = .OMaths.Item(I)
xMath.Range.Paragraphs(1).Range.Editors.Add wdEditorEveryone
Next
.SelectAllEditableRanges wdEditorEveryone
.DeleteAllEditableRanges wdEditorEveryone
End With
End Sub
的属性值并不总是一致的。当搜索控制器处于活动模式时(点按搜索文本字段),返回到父视图将为此属性设置isMovingFromParent
值。
这是我确定视图是否来自父视图的方法:
false