如何找到根 UIViewController
Posted
技术标签:
【中文标题】如何找到根 UIViewController【英文标题】:How to find root UIViewController 【发布时间】:2011-05-11 18:14:50 【问题描述】:我有一个处理广告的视图是UIViewController
(根)和一个UINavigationController
。在那个 UINavigationController 我有典型的控制器层。在我的自定义设置表视图控制器中,我有一个按钮可以联系我寻求支持。当用户单击此按钮时,我创建了一个 MFMailComposeViewController
并希望展示它。我无法从设置表视图中显示它,因为它将位于我的广告下方,因此我需要引用根视图并从那里显示它。我试过self.parentViewController.parentViewController
self 是设置表视图,但这不起作用。我应该如何参考这个。必须直接引用根视图并将其传递给设置视图似乎是一个糟糕的设计。
【问题讨论】:
你试过self.navigationController吗?我不清楚您的视图层次结构是如何设置的。 【参考方案1】:获取当前keyWindow:
UIWindow *window = [UIApplication sharedApplication].keyWindow;
获取它的rootViewController:
UIViewController *rootViewController = window.rootViewController;
注意:如果当前正在显示UIAlertView
,则会创建一个新窗口并将其指定为keyWindow。可能还有其他例外情况不会让您的应用程序窗口成为 keyWindow。
【讨论】:
顺便说一句,这只适用于 4.0+。 UIWindow 在 4.0 之前没有 rootViewController 属性。 @Jesse 好点 - 我很高兴我不再需要支持那些古老的砖块;)。 是的,很糟糕。我会说它至少占了我 50% 的时间。 只是一个快速警告。如果在屏幕上使用 ui 警报调用它,这将不起作用。 @ChrisMitchelmore a UIAlert 会打开一个新窗口,并在显示时将其设为键窗口。【参考方案2】:根据我的经验,这是获得rootViewController
的理想解决方案:
[[[[UIApplication sharedApplication] delegate] window] rootViewController]
注意:如果UIAlert
或UIActionSheet
处于活动状态,您将获得警报或操作表作为您的关键窗口。
【讨论】:
+1 这是唯一安全、可靠的方法。我花了很长时间才找到一个 alert + keyWindow 错误,这篇文章救了我! 第二个! keyWindow 方法(目前标记为正确答案)不可靠,因为关键窗口可以更改。 在 UIAlertView 期间使用 keyWindow 时也遇到了错误……谢谢!这是最好的使用方法。【参考方案3】:使用应用单例。比如:
[[[UIApplication sharedApplication] delegate] rootViewController]
应该得到它,如果你作为根的 viewController 被命名为rootViewController
【讨论】:
【参考方案4】:你总是可以用 1 行代码来解决这个问题,但我推荐这种 Swift 方法,你可以从任何地方调用它,它也是崩溃和错误安全的:
/// EZSwiftExtensions - Gives you the VC on top so you can easily push your popups
var topMostVC: UIViewController?
var presentedVC = UIApplication.sharedApplication().keyWindow?.rootViewController
while let pVC = presentedVC?.presentedViewController
presentedVC = pVC
if presentedVC == nil
print("EZSwiftExtensions Error: You don't have any views set. You may be calling them in viewDidLoad. Try viewDidAppear instead.")
return presentedVC
它作为标准功能包含在:
https://github.com/goktugyil/EZSwiftExtensions
【讨论】:
【参考方案5】:获取 UIApplication 对象。 循环遍历 windows 数组以找到 keyWindow。 然后获取 rootViewController 属性。
【讨论】:
以上是关于如何找到根 UIViewController的主要内容,如果未能解决你的问题,请参考以下文章