iOS8でのアクションシート：廃止されるUIActionSheetと推奨されるUIAlertController

iOSでアクションシート表示用のクラスUIActionSheetがiOS8からdeprecatedになるため、
UIActionSheetを使用した際の挙動と推奨されているUIAlertControllerの使い方についてまとめました。

(本記事の内容は[一般公開されているiOS8の情報](https://developer.apple.com/library/prerelease/iOS/navigation/)に基づいています。
iOS8に関するスクリーンショットは掲示していません。)

#iOS8で廃止されるUIActionSheetを使用した際の挙動
deprecatedされたメソッドを使用した場合、アプリが落ちるなどの問題が発生することがありますが、
iOS8 beta3の環境ではシミュレータ・実機ともに問題なく表示できます。
2014/7/12現在では継続してUIActionSheetを使用したままでも問題無いようです。

公式にdeprecatedと宣言されているため挙動が変わる可能性は否定できません。
推奨されているUIAlertControllerへの移行をおすすめします。

#アクションシートの使い所
![iOS7_ActionSheet.jpg](https://qiita-image-store.s3.amazonaws.com/0/34488/a13504c7-59a2-ed1f-e7f9-1ffef45ca46c.jpeg)

ユーザへの注意喚起の方法はアクションシート以外にもダイアログの表示があります。
どのように使い分けるかは「[iOS ヒューマンインターフェース ガイドライン](https://developer.apple.com/jp/devcenter/ios/library/documentation/UserExperience/Conceptual/MobileHIG/Alerts/Alerts.html#//apple_ref/doc/uid/TP40006556-CH14-SW2)」でAppleが公式に以下のように述べています。

|条件                                |推奨UI|
|:----------------------------------|:-----------------------------|
|ユーザが承認したタスクの確認を求める場合|アクションシート|
|致命的なエラーをユーザに通知する場合   |ダイアログ|

#推奨されているUIAlertControllerのメリット
これまでのUIActionSheetにはtitleしかありませんでしたが、
新たなUIAlertControllerには<b>message</b>のパラメータが追加されています。
タイトルの下に説明文を表示できるようになりました。


#iOS7以前のOSをサポートする際の注意点
開発中のアプリの中にはiOS7以前をサポートするアプリもあるかと思います。
そのためにはUIActionSheetとUIAlertControllerをコード内で併用して使い分けることが必要です。

その際にボタンが押された時の処理に注意してください。
UIActionSheetではdelegateメソッドで処理しますが、
UIAlertControllerはクロージャで処理します。

UIActionSheetとUIAlertControllerを併用する際にはボタンが押された時のメソッドを作成して、
そのメソッドを両者で使い回すことをオススメします。

#サンプルコード
##UIAlertController

###Objective-C
```objc:UIAlertController

UIAlertController *alertController = [UIAlertController alertControllerWithTitle:@"UIAlertControllerStyle.ActionSheet" message:@"iOS8" preferredStyle:UIAlertControllerStyleActionSheet];

[alertController addAction:[UIAlertAction actionWithTitle:@"はい" style:UIAlertActionStyleDefault handler:^(UIAlertAction *action) {
    // otherボタンが押された時の処理                                                      
    [self otherButtonPushed];
}]];
[alertController addAction:[UIAlertAction actionWithTitle:@"いいえ" style:UIAlertActionStyleDefault handler:^(UIAlertAction *action) {
    // cancelボタンが押された時の処理                                                      
    [self cancelButtonPushed];
}]];

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

- (void)cancelButtonPushed {}
- (void)otherButtonPushed {}

```

##UIActionSheet (deprecated in iOS8)

```objc
UIActionSheet *actionSheet = [[UIActionSheet alloc] initWithTitle:@"ActionSheet"
                                                             delegate:nil
                                                    cancelButtonTitle:@"いいえ"
                                               destructiveButtonTitle:nil
                                                    otherButtonTitles:@"はい",nil];
[actionSheet showInView:self.view];

...

- (void)actionSheet:(UIActionSheet *)actionSheet clickedButtonAtIndex:(NSInteger)buttonIndex {
    switch (buttonIndex) {
        case 0:
            // otherボタンが押されたときの処理
            [self otherButtonPushed];
            break;
    }
}

- (void)actionSheetCancel:(UIActionSheet *)actionSheet {
    // cancelボタンが押された時の処理
    [self cancelButtonPushed];
}

- (void)cancelButtonPushed {} 
- (void)otherButtonPushed {} 

```

### Swift
```swift:UIAlertController

var alertController = UIAlertController(title: "UIAlertControllerStyle.ActionSheet", message: "iOS8", preferredStyle: .ActionSheet)

let otherAction = UIAlertAction(title: "はい", style: .Default) {
    action in NSLog("はいボタンが押されました")
}
let cancelAction = UIAlertAction(title: "いいえ", style: .Cancel) {
    action in NSLog("いいえボタンが押されました")
}

alertController.addAction(otherAction)        
alertController.addAction(cancelAction)
        
presentViewController(alertController, animated: true, completion: nil)

```

#iPadでのcancelボタンの非表示
iPadではアクションシートをポップオーバー外に表示させた場合、cancelボタンが表示されません。
これは「アクションシートの外側をタップすればアクションシートを消せるためcancelボタンは不要である」という[公式のポリシー](https://developer.apple.com/jp/devcenter/ios/library/documentation/UserExperience/Conceptual/MobileHIG/Alerts/Alerts.html#//apple_ref/doc/uid/TP40006556-CH14-SW36)によるものです。


#参考
公式Class Reference
https://developer.apple.com/library/prerelease/iOS/documentation/UIKit/Reference/UIAlertController_class/index.html#//apple_ref/occ/cl/UIAlertController