Problem
OSXのユーザーインタフェースガイドライン的にモーダルダイアログはよろしくないらしいので,できるだけシートを使っていくことになります。
シートを出すにもその目的や,やりたいことに応じていろいろあります。本稿ではNSAlert
に着目し,次稿ではNSWindow
に着目します。
with NSAlert
Notify
お手軽。Windowsで言うところのMessageBoxに相当します。
表示は簡単。使いたい場所で以下のように書きます。
using (var alert = new NSAlert())
{
alert.AlertStyle = NSAlertStyle.Informational;
alert.MessageText = "タイトル";
alert.InformativeText = "メッセージ";
alert.RunSheetModal([NSWindow]);
}
[NSWindow]
には紐付けるウィンドウを指定します。null
にすると通常のダイアログ表示になります。
Confirm
ボタンを表示して結果を受け取る方法。
using (var alert = new NSAlert())
{
alert.AlertStyle = NSAlertStyle.Informational;
alert.MessageText = "タイトル";
alert.InformativeText = "聞きたいこと";
alert.AddButton("はい");
alert.AddButton("いいえ");
var ret = alert.RunSheetModal([NSWindow]);
return (ret == (int)NSAlertButtonReturn.First);
}
1アラートには3つまでボタンを設けることができ,どれが押されたかはNSAlertButtonReturn
列挙で取得できます(First, Second, Third)。AddButton
するとNSAlert
のButtons[]
に追加されるので,この順番になります。
追記(201408201515) 嘘です。結構好きな数追加できました。Thid以降は1004,1005...と返却されるint
がインクリメントされていきます。
Suppress
あとよくあるのは,「二度と表示してくれるな」チェックボックスです。こんな感じです。
using (var alert = new NSAlert())
{
alert.AlertStyle = NSAlertStyle.Informational;
alert.MessageText = "お節介";
alert.InformativeText = "お節介なメッセージ";
alert.AddButton("はい");
alert.AddButton("いいえ");
alert.AddButton("キャンセル");
alert.ShowsSuppressionButton = true;
var ret = alert.RunSheetModal(Window);
Debug.WriteLine(ret == (int)NSAlertButtonReturn.Third);
Debug.WriteLine(alert.SuppressionButton.State);
}
表示終了後に,SuppressionButton
のState (On/Off)
で判定できます。
表示が英語なのはOSの言語設定の依るもので,これもただのNSButton
なので,変更できます。上のコードで表示前にalert.SuppressionButton.Title = "もういいよそういうのは";
を追加するとこんな感じに。
Prompt
VBAとかでよくある,一行入力させるメッセージボックス的な。それを実現する方法。
var name = "default";
using (var alert = new NSAlert())
{
alert.AlertStyle = NSAlertStyle.Informational;
alert.MessageText = "おしえてくん";
alert.InformativeText = "おなまえはなにかな?";
alert.AddButton("確定");
alert.AddButton("取消");
var nameBox = new NSTextField(new RectangleF(0, 0, 200, 24));
alert.AccessoryView = nameBox;
var ret = alert.RunSheetModal(Window);
Debug.WriteLine(ret == (int)NSAlertButtonReturn.First);
name = nameBox.StringValue;
}
Debug.WriteLine(name);
NSAlert.AccessoryView
はNSView
なので,入れようと思えば何でも入りますが,そこまでするならNSWindow
をシート化したほうがいいです。アラートなので,ボタンを消すことはできませんし。
Conclusion
これでNSAlertはバッチリ。結果取得はBeginSheetForResponce
を呼び出すことで非同期にできます。