1. ホーム
  2. ios

[解決済み] 提示されたビューコントローラが破棄されたことを検出する

2022-09-24 11:22:44

質問

例えば、VC2というビューコントローラクラスのインスタンスがあるとします。 VC2には、それ自体を破棄する"cancel"ボタンがあります。 しかし、このボタンがトリガーされたときに、コールバックを受け取ることができません。 VC2はブラックボックスです。

ビューコントローラ(VC1と呼ばれる)は presentViewController:animated:completion: メソッドを用いてVC2を表示します。

VC1 は、VC2 が解散したことを検出するために、どのようなオプションを持っていますか?

編集:@rory mckinnelのコメントと@NicolasMiariの回答から、私は以下を試しました。

VC2にて。

-(void)cancelButton:(id)sender
{
    [self dismissViewControllerAnimated:YES completion:^{

    }];
//    [super dismissViewControllerAnimated:YES completion:^{
//        
//    }];
}

VC1では

//-(void)dismissViewControllerAnimated:(BOOL)flag completion:(void (^)(void))completion
- (void)dismissViewControllerAnimated:(BOOL)flag
                           completion:(void (^ _Nullable)(void))completion
{
    NSLog(@"%s ", __PRETTY_FUNCTION__);
    [super dismissViewControllerAnimated:flag completion:completion];
//    [self dismissViewControllerAnimated:YES completion:^{
//        
//    }];
}

しかし dismissViewControllerAnimated は呼び出されませんでした。

どのように解決するのですか?

docsによると、実際のdissueはpresenting controllerが担当します。提示されたコントローラが自分自身をdisuseする場合、提示者にそれを行うように依頼します。そのため、VC1コントローラでdissueViewControllerAnimatedをオーバーライドすると、VC2でcancelを押したときに呼び出されることになると思います。dismissを検出し、実際のdissueを行うスーパークラスのバージョンを呼び出します。

議論からわかったように、これはうまくいかないようです。基本的なメカニズムに依存するのではなく、代わりに dismissViewControllerAnimated:completion を VC2 自身で呼び出す代わりに dismissViewControllerAnimated:completionself.presentingViewController をVC2で実行します。これは、その後、あなたのオーバーライドを直接呼び出します。

より良い方法は、モーダルコントローラが完了したときに呼び出されるブロックを VC2 に提供させることです。

つまり、VC2 で、例えば onDoneBlock .

VC1では以下のように表示されます。

  • VC1において、VC2を作成します。

  • VC2のdone handlerを設定します。 VC2.onDoneBlock={[VC2 dismissViewControllerAnimated:YES completion:nil]};

  • self presentViewController:VC2 animated:YES completion:nil]でVC2コントローラーを通常通り提示する。

  • VC2において、ターゲットアクションのキャンセル呼び出しで self.onDoneBlock();

結果、VC2は上げた人に「終わったよ」と伝える。を拡張することができます。 onDoneBlock を拡張して、モーダルが完了したかどうか、キャンセルされたかどうか、成功したかどうかなどを示す引数を持たせることができます。