UIDocumentPickerViewController取消父视图控制器

时间:2016-12-11 11:57:34

标签: xcode wkwebview uidocumentpickervc

我在视图控制器中有一个WKWebView。当用户点击“上传文件”按钮(显示在网页上)时,会弹出UIDocumentPickerViewController。这是预期的,而且是完全必要的,但是:

每当用户点击任何按钮(“上传照片或视频”,“取消”)时,UIDocumentPickerViewController就会解除其自身及其所在的父视图控制器。

我为[UIViewController dismissViewControllerAnimated:completion:]添加了一个符号断点,确实看到-dismissViewController...被调用了两次。在第一次之后它解除UIDocumentPickerViewController,在第二次之后 - 我的父视图控制器。

顺便说一句,在iPad上没有任何问题,可能是因为UIDocumentPickerViewController被视为弹出窗口。

为什么会这样,我该怎么办?

谢谢!

4 个答案:

答案 0 :(得分:2)

好吧,我想我找到了解决这个问题的方法。 WebKit是开源的,你可以看到有问题的类是WKFileUploadPanel,特别是_dismissDisplayAnimated: method过于激进而无意中触发了你的视图控制器被解雇。为了避免这种情况,您需要阻止来自-dismissViewControllerAnimated:completion:的{​​{1}}调用,您可以通过查找堆栈来执行此操作。这是解决此问题的实现。

上面提到的解决方案不起作用,因为它依赖于查看特定类的调用堆栈符号,该类在实际设备上运行时会被混淆。这是我采取的另一种解决方法:

  1. WKFileUploadPanel weak属性添加到模态视图控制器类。
  2. 覆盖模态类中的UIDocumentMenuViewController以检查并查看显示的视图控制器是否为-presentViewController:animated:completion:,如果是,则将其设置为步骤1中弱属性的值。
  3. 覆盖UIDocumentMenuViewController以检查您的弱属性是否为-dismissViewControllerAnimated:completion:,如果它不是nil且您的模态nilpresentedViewController则表示WebKit试图在不应该的情况下解雇你的模态。在这种情况下,您可以避免调用nil,否则继续调用它。
  4. 您还可以调动super的{​​{3}}以更加谨慎对待自己的视图控制器,但这会带来很大的风险。

答案 1 :(得分:2)

我遇到了同样的问题,最终设法找到了解决方法。

在我的视图控制器中,如果保存按钮未被点击且与dismiss完美配合,我会覆盖UIImagePickerController方法删除托管对象。

从我的应用程序使用UIDocumentPickerViewController开始,每次调用documentPicker(_ controller: UIDocumentPickerViewController, didPickDocumentAt url: URL)时都会删除我的托管对象,因为这会导致presentingViewController.dismiss

所以我的解决方案是从presentingViewController检查presentedViewControllernil是否dismiss知道UIDocumentPickerViewController方法是否被dismiss调用

所以这是我的视图控制器中的覆盖override func dismiss(animated flag: Bool, completion: (() -> Void)? = nil) { if self.presentedViewController == nil { // dismissed by the user myDocument.delete() } else { // dismissed by the UIDocumentPickerViewController // do nothing } super.dismiss(animated: flag, completion: completion) } 方法。

<div>     
     <p-calendar #fromCal [(ngModel)]="value" [showIcon]="true" readOnlyInputText="true"></p-calendar>
</div>   

希望它对你有所帮助。

答案 2 :(得分:1)

我也遇到过同样的问题,这是在使用文档选择器时发生的,并且发生在11.4以下的iOS版本中。在使用文档选择器的任何地方使用以下代码。从不同论坛上阅读的内容来看,文档选择器存在问题,并且在更高版本的iOS中已解决。

声明文档选择器的弱属性。

@property (weak, nonatomic) UIDocumentPickerViewController *_Nullable docPicker;

然后实现视图控制器委托方法:

- (void)presentViewController:(UIViewController *)viewControllerToPresent animated: (BOOL)flag completion:(void (^ __nullable)(void))completion
{
    if ([viewControllerToPresent isKindOfClass:[UIDocumentPickerViewController class]])
    {
        _docPicker = (UIDocumentPickerViewController*)viewControllerToPresent;
    }

    [super presentViewController:viewControllerToPresent animated:flag completion:completion];
}

- (void)dismissViewControllerAnimated:(BOOL)flag
                           completion:(void (^)(void))completion
{
    if (_docPicker != nil && self.presentedViewController == nil)
    {

    }
    else
    {
        [super dismissViewControllerAnimated:flag completion:completion];
    }
}

答案 3 :(得分:0)

试试这个(工作):

navigationController?.dismiss(animated: true, completion: nil)