Following the strategy from this SO answer, in iOS 7 I could find the top window in my app like so:
UIWindow *topWindow = [[[UIApplication sharedApplication].windows sortedArrayUsingComparator:^NSComparisonResult(UIWindow *win1, UIWindow *win2) {
return win1.windowLevel - win2.windowLevel;
}] lastObject];
However, since iOS8 there may be one or more UITextEffectsWindow
s which may be the lastObject
in the above strategy. No good.
Initially I could run a predicate filter on the array of windows and test which windows are UIWindow
s like so:
NSPredicate *filter = [NSPredicate predicateWithBlock:^BOOL(id obj, NSDictionary *bind) {
return [obj isMemberOfClass:[UIWindow class]];
}];
However, the top UIWindow
may not be UIWindow
, but some subclass like NRWindow. Here is an example:
[[NRWindow class] isKindOfClass:[UIWindow class]]; // true
[[UITextEffectsWindow class] isKindOfClass:[UIWindow class]]; // true
My question is this: How can I safely differentiate/find the top UIWindow
subclass so I can do things like
[[topWindow rootViewController] presentViewController:mailComposer animated:YES completion:nil];
(Note: Testing for UITextEffectsWindow
directly is frowned upon, and [[UIApplication sharedApplication] keyWindow]
unfortunately isn't reliable.)
I assume that you only want to present from windows that you have created. So you could: