前のページ次のページ上に戻るホーム SophiaFramework UNIVERSE 5.3

5.5. ダイアログ

5.5.1. ダイアログの作成と登録

ボタンを押すとマルチダイアログが表示されるようにします。

図 5.19. マルチダイアログ

マルチダイアログ

例 5.39. ボタン button5 のハンドラの宣言

SFMTYPEDEFCLASS(MyWindow)
class MyWindow : public SFRTitleWindow {
    SFMSEALCOPY(MyWindow)
public:
    MyWindow(Void) static_throws;
    virtual ~MyWindow(Void);
 
// *** 太字が追加部分
 
private:  
    // ポインタ型のメンバ変数として定義する
    SFRCheckboxControlPtr _checkbox1;
    SFRCheckboxControlPtr _checkbox2;
    SFRRadiobuttonControlPtr _radiobutton1;
    SFRRadiobuttonControlPtr _radiobutton2;
    SFRComboboxControlPtr _combobox;
  
    SFREditboxControlPtr _editbox;
 
    HANDLER_DECLARE_VOIDRENDER(OnRenderContent)
    HANDLER_DECLARE_BOOLEVENT(OnKey)
    HANDLER_DECLARE_VOIDCONTROL(OnButtonControl1)
    HANDLER_DECLARE_VOIDCONTROL(OnButtonControl2)
    HANDLER_DECLARE_VOIDCONTROL(OnButtonControl3)
    HANDLER_DECLARE_VOIDCONTROL(OnButtonControl4)
    HANDLER_DECLARE_VOIDCONTROL(OnButtonControl5)
 
    HANDLER_DECLARE_VOIDCONTROL(OnEditboxControl)

};

例 5.40. ボタン button5 のハンドラの登録

MyWindow::MyWindow(Void) : SFRTitleWindow(SFRApplication::GetInstance(),
    SFXRectangle(20, 20, 200, 250), "my window") static_throws
{
    // 描画ハンドラの登録
    if (static_try()) {
        static_throw(
            RegisterHandler(SREVT_RESPONDER_RENDER, 
                            SRP16_RENDER_CONTENT,
                            HANDLER_BEFORE, 
                            HANDLER_FUNCTION(OnRenderContent)));
    }
 
    // キーハンドラの登録
    if (static_try()) {
        static_throw(
            RegisterHandler(SFEVT_KEY, 
                            HANDLER_AFTER, 
                            HANDLER_FUNCTION(OnKey)));
    }
 
    // ボタンの作成
    SFRButtonControlPtr button1 = new SFRButtonControl(this, 
                                                       SFXRectangle(10, 10, 50, 25), 
                                                       "b1");

    SFRButtonControlPtr button2 = new SFRButtonControl(this, 
                                                       SFXRectangle(10, 45, 50, 25), 
                                                       "b2");

    SFRButtonControlPtr button3 = new SFRButtonControl(this, 
                                                       SFXRectangle(10, 80, 50, 25), 
                                                       "b3");

    SFRButtonControlPtr button4 = new SFRButtonControl(this, 
                                                       SFXRectangle(70, 10, 50, 25), 
                                                       "b4");

    SFRButtonControlPtr button5 = new SFRButtonControl(this, 
                                                       SFXRectangle(70, 45, 50, 25), 
                                                       "b5");

    // button1 を押したときのハンドラの登録
    if (static_try()) {
        static_throw(
            button1->RegisterHandler(SREVT_CONTROL, 
                                     HANDLER_BEFORE,
                                     HANDLER_FUNCTION(OnButtonControl1)));
    }
    // button2 を押したときのハンドラの登録
    if (static_try()) {
        static_throw(
            button2->RegisterHandler(SREVT_CONTROL, 
                                     HANDLER_BEFORE,
                                     HANDLER_FUNCTION(OnButtonControl2)));
    } 
    // button3 を押したときのハンドラの登録
    if (static_try()) {
        static_throw(
            button3->RegisterHandler(SREVT_CONTROL, 
                                     HANDLER_BEFORE,
                                     HANDLER_FUNCTION(OnButtonControl3)));
    }

    // button4 を押したときのハンドラの登録
    if (static_try()) {
        static_throw(
            button4->RegisterHandler(SREVT_CONTROL, 
                                     HANDLER_BEFORE,
                                     HANDLER_FUNCTION(OnButtonControl4)));
    }
    
    // button5 を押したときのハンドラの登録
    if (static_try()) {
        static_throw(
            button5->RegisterHandler(SREVT_CONTROL, 
                                     HANDLER_BEFORE,
                                     HANDLER_FUNCTION(OnButtonControl5)));
    }

    // チェックボックスの作成
    _checkbox1 = new SFRCheckboxControl(this, 
                                        SFXRectangle(10, 115, 90, 20), 
                                        "check1");
    _checkbox2 = new SFRCheckboxControl(this, 
                                        SFXRectangle(105, 115, 90, 20), 
                                        "check2");

    // ラジオボタンの作成
    _radiobutton1 = new SFRRadiobuttonControl(this, 
                                              SFXRectangle(10, 140, 90, 20), 
                                              "radio1");
    _radiobutton2 = new SFRRadiobuttonControl(this, 
                                              SFXRectangle(105, 140, 90, 20), 
                                              "radio2");

    // ラジオボタンのグループ化
    _radiobutton2->Group(_radiobutton1);
    // radiobutton1 を選択状態にする
    _radiobutton1->SetStatusCheck(true);

    // コンボボックスの作成
    SFXWideString item[] = {"item1", "item2", "item3"};
    _combobox = new SFRComboboxControl(this, 
                                       SFXRectangle(10, 165, 90, 20), 
                                       item, 
                                       lengthof(item));
  
    // コンボボックス の項目が選択されたときのハンドラの登録
    if (static_try()) {
        static_throw(
            _combobox->RegisterHandler(SREVT_CONTROL, 
                                       HANDLER_BEFORE,
                                       HANDLER_FUNCTION(OnComboboxControl)));
    }


    // テキストボックスの作成
    // 初期値 : "hello textbox"
    _editbox = new SFREditboxControl(this, 
                                     SFXRectangle(10, 190, 150, 28), 
                                     "hello textbox");

    // 最大文字数を設定する
    _editbox->SetMaxSize(255);
    
    // テキストの入力後やフォーカスが外れたときの
    // ハンドラの設定
    if (static_try()) {
        static_throw(
            _editbox->RegisterHandler(SREVT_CONTROL, 
                                      HANDLER_BEFORE,
                                      HANDLER_FUNCTION(OnEditboxControl)));
    }

    // テキストボックス上でセレクトキーを押したときに
    // 入力モードに移るようにセットする
    // ( SelectHandler は SophiaFramework UNIVERSE が用意しているセレクトキー用のハンドラ )
    if (static_try()) {
        static_throw(
            RegisterHandler(SFEVT_KEY, 
                            AVK_SELECT, 
                            HANDLER_AFTER,
                            HANDLER_FUNCTION(SelectHandler)));
    }
}

例 5.41. ボタン button5 のハンドラの実装

HANDLER_IMPLEMENT_VOIDCONTROL(MyWindow, OnButtonControl5, result, control)
{
    // マルチダ イアログ作成時のパラメータのための構造体
    SFRMultiDialog::ParamRec param;

    // ダイアログに表示するテキスト
    param.text = "アプリを終了します。よろしいですか?";

    // 第 1 ボタンのテキスト
    param.ok = "はい";

    // 第 2 ボタンのテキスト
    param.cancel = "いいえ";

    // 第 3 ボタンのテキスト ( 空テキスト:ボタン無し )
    param.another = ";

    // フォーカスの初期位置
    param.focus = SFRMultiDialog::FOCUS_OK;

    // アイコン画像
    param.image = SFBImageSmp(null);

    // ダイアログの作成
    SFRMultiDialogPtr multiDialog = new SFRMultiDialog(SFXRectangle(10, 40, 220, 140), 
                                                       "終了?", 
                                                       param);

    // ダイアログのハンドラの登録
    if (static_try()) {
        static_throw(
            multiDialog->RegisterHandler(SREVT_DIALOG, 
                                         HANDLER_BEFORE,
                                         HANDLER_FUNCTION(OnDialog)));
    }
}

例 5.42. マルチダイアログのハンドラの宣言

SFMTYPEDEFCLASS(MyWindow)
class MyWindow : public SFRTitleWindow {
    SFMSEALCOPY(MyWindow)
public:
    MyWindow(Void) static_throws;
    virtual ~MyWindow(Void);
 
// *** 太字が追加部分
 
private:  
    // ポインタ型のメンバ変数として定義する
    SFRCheckboxControlPtr _checkbox1;
    SFRCheckboxControlPtr _checkbox2;
    SFRRadiobuttonControlPtr _radiobutton1;
    SFRRadiobuttonControlPtr _radiobutton2;
    SFRComboboxControlPtr _combobox;
  
    SFREditboxControlPtr _editbox;
 
    HANDLER_DECLARE_VOIDRENDER(OnRenderContent)
    HANDLER_DECLARE_BOOLEVENT(OnKey)
    HANDLER_DECLARE_VOIDCONTROL(OnButtonControl1)
    HANDLER_DECLARE_VOIDCONTROL(OnButtonControl2)
    HANDLER_DECLARE_VOIDCONTROL(OnButtonControl3)
    HANDLER_DECLARE_VOIDCONTROL(OnButtonControl4)
    HANDLER_DECLARE_VOIDCONTROL(OnButtonControl5)
 
    HANDLER_DECLARE_VOIDCONTROL(OnEditboxControl)
    
    HANDLER_DECLARE_VOIDDIALOG(OnDialog)

};

例 5.43. マルチダイアログのハンドラの実装

// ダイアログで「はい」か「いいえ」を選んだときに実行されるコード
HANDLER_IMPLEMENT_VOIDDIALOG(MyWindow, OnDialog, result, dialog) {

    switch(result) {
        case SRP16_OK:     // 「はい」を選んだとき
            TRACE("OK");

            // アプリを終了する
            SFRApplication::Terminate();
            break;
        case SRP16_CANCEL: // 「いいえ」を選んだとき
            TRACE("CANCEL");

            // ダイアログを閉じる
            dialog->DialogHandler();
            break;
    }
}

図 5.20. 実行結果

実行結果

5.5.2. ダイアログのカスタマイズ

SFRFrameDialog クラスを継承するクラスを作成して、ダイアログをカスタマイズします。 ウィンドウと同じように描画ハンドラやキーハンドラを登録できます。

例 5.44. ダイアログの定義

SFMTYPEDEFCLASS(MyDialog)
class MyDialog : public SFRFrameDialog {
    SFMSEALCOPY(MyDialog)
public:
    MyDialog(Void) static_throws;
    virtual ~MyDialog(Void);
private:
    HANDLER_DECLARE_VOIDRENDER(OnRenderContent)
    HANDLER_DECLARE_BOOLEVENT(OnKey)
};

ダイアログの描画ハンドラとキーハンドラをコンストラクタで登録します。

例 5.45. ダイアログの実装

// コンストラクタ
MyDialog::MyDialog() : SFRFrameDialog(SFXRectangle(10, 40, 220, 80)) static_throws { 
    if (static_try()) {
        static_throw(
            RegisterHandler(SREVT_RESPONDER_RENDER, 
                            SRP16_RENDER_CONTENT,
                            HANDLER_BEFORE, 
                            HANDLER_FUNCTION(OnRenderContent)));
    }
    if (static_try()) {
        static_throw(
            RegisterHandler(SFEVT_KEY, 
                            HANDLER_AFTER, 
                            HANDLER_FUNCTION(OnKey)));
    }
}

// デストラクタ
MyDialog::~MyDialog(Void)
{
    return;
}

// 描画ハンドラ
HANDLER_IMPLEMENT_VOIDRENDER(MyDialog, OnRenderContent, graphics) {
    graphics->FillRectangle(GetContentWorld(), 
                            SFXRGBColor(0xCC, 0xFF, 0xFF, 0x00));
    graphics->DrawString("3 キーを押すと閉じます", 
                         SFXRectangle(10, 10, 200, 80), 
                         SFXRGBColor(0, 0, 0, 0),
                         IDF_ALIGN_LEFT | IDF_ALIGN_MIDDLE);
}

// キーハンドラ
HANDLER_IMPLEMENT_BOOLEVENT(MyDialog, OnKey, event)
{
    switch (event.GetP16()) {
        case AVK_3: // 3 キーのキーイベントを受信したとき
            // 自分自身を閉じる
            return Invoke(SFXEvent(SREVT_RESPONDER_TERMINATE, 
                                   SRP16_TERMINATE_INVOKE, 
                                   true));
    }
    return false;
}

2 キー を押すとダイアログを表示するようにキーハンドラを拡張します。

例 5.46. HelloWorld のキーハンドラ : 2 キー を押すとダイアログを表示するコード

// キーハンドラ
HANDLER_IMPLEMENT_BOOLEVENT(MyWindow, OnKey, event)
{
    switch (event.GetP16()) {
        ...
  
 // *** 太字が追加部分

        case AVK_2:
            if (static_try()) {
                MyDialogPtr dialog;
                // new 演算子でダイアログ作成
                if ((dialog = new MyDialog()) != null) {
                    // コードの残り部分はエラー処理
                    static_throw(*dialog);
                    if (!static_try()) {
                        delete dialog;
                    }
                }
                else {
                    static_throw(SFERR_NO_MEMORY);
                }
            }
            return true;
    }
    return false;
}

図 5.21. 実行結果

実行結果