LoginSignup
0
0

More than 3 years have passed since last update.

Objective-C UIAlertControllerを便利に利用する為に既存クラス(UIViewController)へのカテゴリの追加を行う

Posted at

目的

アプリ内で呼び出し箇所多いと、その都度UIAlertControllerを初期化するのは手間が大きすぎるので、ある程度共通化したメソッドを用意しよう。

UIViewControllerのカテゴリクラスであれば、UIViewControllerを継承している大抵のクラスにて呼び出し出来るので容易と考えた。

実装内容

UIViewController+AlertController.h

#import <UIKit/UIKit.h>

@interface  UIViewController (AlertController)
- (void)showAlertController:(NSString *)title msg:(NSString*)msg isJapanese:(BOOL)language okHandler:(void(^)())okBlock cancelHandler:(void(^)())cancelBlock;

@end

UIViewController+AlertController.m


#import "UIViewController+AlertController.h"


@implementation UIViewController (AlertController)

- (void)showAlertController:(NSString *)title msg:(NSString*)msg isJapanese:(BOOL)language okHandler:(void(^)())okBlock cancelHandler:(void(^)())cancelBlock{

    UIAlertController *alertController = [UIAlertController alertControllerWithTitle:title
                                                                             message:msg
                                                                      preferredStyle:UIAlertControllerStyleAlert];

    // addActionした順に左から右にボタンが配置されます
    [alertController addAction:[UIAlertAction actionWithTitle:(language? @"はい":@"OK")
                                                        style:UIAlertActionStyleDefault
                                                      handler:^(UIAlertAction *action) {
        // okボタンが押された時の処理
        if(okBlock) okBlock();
                                                      }]];

    [alertController addAction:[UIAlertAction actionWithTitle:(language? @"いいえ":@"Cancel")
                                                        style:UIAlertActionStyleDestructive
                                                      handler:^(UIAlertAction *action) {
        // cancelボタンが押された時の処理
        if(cancelBlock) cancelBlock();

                                                      }]];

    [self presentViewController:alertController animated:YES completion:nil];
}



@end

使用方法

下記のように引数title,msg,language(OK,Cancelもしくは「はい,いいえ」),ok押下時のblock処理,cancel押下時のblock処理を呼び出し先に渡せます。

例)ViewController.m

// ボタン押下後に呼び出される。
- (IBAction)tapButton:(id)sender {
    [self showAlertController:@"AlertController" msg:@"AlertControllerを閉じますか?" isJapanese:YES okHandler:^{
        NSLog(@"AlertView:OKが押下された");
    } cancelHandler:^{
        NSLog(@"AlertView:Cancelが押下された");
    }];
}

実際に開発現場で使われるような動きとコード

ログインを有するアプリにて、ログアウトされている場合は強制的に画面を閉じる処理などあります。

その場合にAlertControllerが開いていると都合が悪いんですよね。

今回はアプリをバックグラウンド待機させて、もし再度アプリを開いた時(フォアグラウンド状態)UIAlertControllerが開いていればdismissViewControllerAnimated:する処理を記載します。

AppDelegate.m

// アプリがバックグラウンドからフォアグラウンドに呼び出された時に呼び出される。
- (void)applicationWillEnterForeground:(UIApplication *)application {

    UIViewController *topController = [UIApplication sharedApplication].keyWindow.rootViewController;
    while (topController.presentedViewController) {
        topController = topController.presentedViewController;
    }

    // 継承している場合も含める(isKindOfClass:)
    if([topController isKindOfClass:[UIAlertController class]]){
        [topController dismissViewControllerAnimated:YES completion:nil];
    }

}
0
0
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
0
0