所以我注意到在iOS上的iOS8 beta 3(更新:仍然在iOS 11.2中发生),尝试在UIActionSheet
的委托方法中呈现视图控制器时, "无"发生并将日志消息输出到调试控制台,说明在转换警报控制器时尝试了演示:
Warning: Attempt to present <UIViewController: 0x...> on <ViewController: 0x...> which is already presenting <UIAlertController: 0x...>
答案 0 :(得分:138)
更新:从iOS 9 SDK开始,UIActionSheet
已弃用,因此不要指望针对此问题进行修复。最好在可能的情况下开始使用UIAlertController
。
问题似乎来自Apple在内部使用UIAlertController
来实现警报视图和操作表的功能。这个问题主要出现在iPad和操作表上,因为在iPad上,操作表在指定视图中显示为弹出窗口,而Apple所做的就是在响应者链中行进,直到找到视图控制器并调用presentViewController:animated:completion:
为止内部UIAlertController
。问题在iPhone和警报视图上不那么明显,因为Apple实际上创建了一个单独的窗口,一个空的视图控制器并在其上面显示内部UIAlertController
,因此它似乎不会干扰其他演示。< / p>
我已针对此问题打开了错误报告: rdar:// 17742017 。请复制它,让Apple知道这是一个问题。
作为一种解决方法,我建议使用以下方法将演示文稿延迟到下一个runloop:
dispatch_async(dispatch_get_main_queue(), ^ {
[self presentViewController:vc animated:YES completion:nil];
});
答案 1 :(得分:31)
您可以尝试在
中完成工作(呈现视图控制器)- (void) actionSheet:(UIActionSheet *)actionSheet
didDismissWithButtonIndex:(NSInteger)buttonIndex {}
而不是
- (void) actionSheet:(UIActionSheet *)actionSheet
clickedButtonAtIndex:(NSInteger)buttonIndex {}
@LeoNatan说,&#34;问题似乎来自Apple在内部使用UIAlertController来实现警报视图和操作表的功能&#34; 。因此,您必须等待操作表被解除,然后呈现您想要的视图控制器。
@LeoNatan的解决方案只是在主线程中阻止UI,因此它还确保在操作表被解除后显示视图控制器。
答案 2 :(得分:4)
遗憾的是,这段代码对我来说并不起作用,我认为因为我的问题不是直接调用presentController方法,而是在prepareForSegue方法中使用
[segue destinationViewController]
我注意到如果segue是&#34;推&#34;一切都正常,但如果它是&#34; modal&#34;,只是在ipad中,我得到了那个错误。
然后我在segue面板中的故事板中找到了一些新选项,并且我选择了#34;当前环境&#34; for Presentation选项
我希望这对其他人有帮助... 这是关于选项
的屏幕截图
答案 3 :(得分:2)
我有同样的问题。我在appdelegate中为警报和操作表创建了一个单独的窗口,并在其上显示警报。它对我有用!
self.alertWindow = [[UIWindow alloc] initWithFrame:[[UIScreen mainScreen] bounds]];
// Override point for customization after application launch.
self.alertWindow.backgroundColor = [UIColor clearColor];
UIViewController *dummy = [[UIViewController alloc] init];
[self.alertWindow setRootViewController:dummy];
你可以表现为:
[[myAppDelegate appDelegate].alertWindow makeKeyAndVisible];
[[myAppDelegate appDelegate].alertWindow.rootViewController presentViewController:alertController animated:YES completion:nil];
答案 4 :(得分:2)
我使用以下代码
在Swift 3中修复它 DispatchQueue.main.async {
self.present(alertController, animated: true, completion: nil)
}
答案 5 :(得分:1)
发布
[self.navigationController dismissViewControllerAnimated:YES completion:nil];
on
- (void)actionSheet:(UIActionSheet *)actionSheet clickedButtonAtIndex:(NSInteger)buttonIndex
在尝试呈现另一个模态视图之前为我工作。
答案 6 :(得分:1)
使用
- (void)actionSheet:(UIActionSheet *)actionSheet didDismissWithButtonIndex:(NSInteger)buttonIndex
而不是
- (void)actionSheet:(UIActionSheet *)actionSheet clickedButtonAtIndex:(NSInteger)buttonIndex
动作视图显示在当前VC之上,因此导致警告/错误。 当调用didDismiss时,动作视图已被解除,因此根本没有问题:))
答案 7 :(得分:0)
尝试
[[NSOperationQueue mainQueue] addOperationWithBlock:^{
// action sheet presentation
// or modal view controller presentation
// or alert view presentation
}];
答案 8 :(得分:0)
在iOS 8中,Apple在内部使用UIAlertController来实现警报视图和操作表的功能。所以当你想在委托方法中显示UIActionSheet或UIAlertView之后以模态方式显示UIViewController,如
(void)actionSheet:(UIActionSheet *)actionSheet clickedButtonAtIndex:(NSInteger)buttonIndex
和
(void)alertView:(UIAlertView *)alertView clickedButtonAtIndex:(NSInteger)buttonIndex
你必须首先解雇UIAlertController,如下所示:
if(SYSTEM_VERSION_GREATER_THAN_OR_EQUAL_TO(@"8.0"))
{
UIViewController *vc = [[[[UIApplication sharedApplication] delegate] window] rootViewController];
[vc dismissViewControllerAnimated:NO completion:^{
}];
}
现在你可以在iOS 8中呈现一个模态UIViewController。