スポンサーリンク

VC++でwxWidgetsを試す(2) ウィジェットを追加

wxWidgetsでボタンを追加する。

CallAfter使用

ウィンドウ生成前に作ってしまうとボタンサイズが画面いっぱいに広がってしまうので、CallAfter関数を使い、ウィンドウ生成イベントが完了してからコントロール生成用関数を呼び出している。

// https://docs.wxwidgets.org/3.0/overview_helloworld.html

// プリプロセッサに以下二つを追加
// __WXMSW__
// WXUSINGDLL

// サブシステムをWindowsに設定(WinMainで呼び出すので)
// Windows (/SUBSYSTEM:WINDOWS)

#ifndef WX_PRECOMP
#include <wx/wx.h>
#endif

#include <wx/gdicmn.h> // wxPointに必要
#include <wx/frame.h>  // wxFrameに必要


#pragma comment(lib,"wxbase32u.lib")
#pragma comment(lib,"wxbase32u_net.lib")
#pragma comment(lib,"wxbase32u_xml.lib")
#pragma comment(lib,"wxmsw32u_adv.lib")
#pragma comment(lib,"wxmsw32u_aui.lib")
#pragma comment(lib,"wxmsw32u_core.lib")
#pragma comment(lib,"wxmsw32u_gl.lib")
#pragma comment(lib,"wxmsw32u_html.lib")
#pragma comment(lib,"wxmsw32u_media.lib")
#pragma comment(lib,"wxmsw32u_propgrid.lib")
#pragma comment(lib,"wxmsw32u_qa.lib")
#pragma comment(lib,"wxmsw32u_ribbon.lib")
#pragma comment(lib,"wxmsw32u_richtext.lib")
#pragma comment(lib,"wxmsw32u_stc.lib")
#pragma comment(lib,"wxmsw32u_webview.lib")
#pragma comment(lib,"wxmsw32u_xrc.lib")



/////////////////////////////////////
/////////////////////////////////////
/////////////////////////////////////

// ウィンドウ作成
class MyFrame : public wxFrame
{
    // ボタン
    wxButton* m_button;

public:

    void PostCreate() {

        m_button = new wxButton(this, wxID_ANY, wxT("クリックしてください"));// ボタン作成
        m_button->Show();

    }

    MyFrame(const wxString& title, const wxPoint& pos, const wxSize& size) 
        : wxFrame(NULL, wxID_ANY, title, pos, size)
    {

        // CallAfter : 現在処理中のイベントが終わったらPostCreateを実行
        // コンストラクタはウィンドウ生成イベント扱い
        CallAfter(&MyFrame::PostCreate);

        // ウィンドウ生成中にnew wxButtonするとボタンが一画面いっぱいに広がってしまう。
        // ウィンドウ生成処理が終わってからボタンを生成しなければいけない

    }

    
};

/////////////////////////////////////
/////////////////////////////////////
/////////////////////////////////////

// wxWidgetsのアプリケーション作成
class MyApp : public wxApp {
public:

    virtual bool OnInit() {
        MyFrame* frame = new MyFrame("Hello World", wxPoint(50, 50), wxSize(450, 340));
        frame->Show(true);

        return true;
    }

};

/////////////////////////////////////
/////////////////////////////////////
/////////////////////////////////////

// WinMainをマクロで定義
wxIMPLEMENT_APP(MyApp);

wxBoxSizer使用

MyFrameのコンストラクタ内でボタンを生成する場合、ボタンが画面いっぱいに広がらないためにsizerを使用する。

// ウィンドウ作成
class MyFrame : public wxFrame
{
    // ボタン
    wxButton* m_button;

public:

    MyFrame(const wxString& title, const wxPoint& pos, const wxSize& size) 
        : wxFrame(NULL, wxID_ANY, title, pos, size)
    {

        //MyFrame処理中にウィジェットを作る場合、
        //ボタンを生成してからwxBoxSizerで配置を決定する。

        m_button = new wxButton(this, wxID_EXIT, "Quit");

        // ウィンドウのサイズ変更時にボタンが中央に表示されるように設定
        wxBoxSizer* sizer = new wxBoxSizer(wxVERTICAL);
        sizer->AddStretchSpacer();
        sizer->Add(m_button, 0, wxALIGN_CENTER);
        sizer->AddStretchSpacer();
        SetSizer(sizer);

    }



private:
    
    // イベント処理しないときはこれを入れない
    // wxDECLARE_EVENT_TABLE();
};

Bindでイベントハンドラ追加する場合

// ウィンドウ作成
class MyFrame : public wxFrame
{
    // ボタン
    wxButton* m_button;

public:

    MyFrame(const wxString& title, const wxPoint& pos, const wxSize& size) 
        : wxFrame(NULL, wxID_ANY, title, pos, size)
    {

        m_button = new wxButton(this, 1000/*ID*/, "ボタン1");

        //// ウィンドウのサイズ変更時にボタンが中央に表示されるように設定
        wxBoxSizer* sizer = new wxBoxSizer(wxVERTICAL);
        sizer->AddStretchSpacer();
        sizer->Add(m_button, 0, wxALIGN_CENTER);
        sizer->AddStretchSpacer();
        SetSizer(sizer);

        // イベントハンドラの設定
        Bind(wxEVT_BUTTON, &MyFrame::OnButtonClicked, this, m_button->GetId());

    }

    void OnButtonClicked(wxCommandEvent& event)
    {
        // オブジェクトのポインタを取得
        wxObject* obj = event.GetEventObject();
        wxButton* button = (wxButton*)obj;

        auto c = button->GetLabel().c_str().AsChar();
        wxMessageBox(c, "タイトル", wxOK | wxICON_INFORMATION, this);

        // GetID()でIDから判断してもいい。
        // if (m_button->GetId() == event.GetId()) { ... }
    }

};

wxDECLARE_EVENT_TABLEでイベントハンドラ追加する場合

#define BUTTON_1 100

// ウィンドウ作成
class MyFrame : public wxFrame
{
    // ボタン
    wxButton* m_button;

public:

    MyFrame(const wxString& title, const wxPoint& pos, const wxSize& size) 
        : wxFrame(NULL, wxID_ANY, title, pos, size)
    {

        m_button = new wxButton(this, BUTTON_1/*ID*/, "ボタン1");

        //// ウィンドウのサイズ変更時にボタンが中央に表示されるように設定
        wxBoxSizer* sizer = new wxBoxSizer(wxVERTICAL);
        sizer->AddStretchSpacer();
        sizer->Add(m_button, 0, wxALIGN_CENTER);
        sizer->AddStretchSpacer();
        SetSizer(sizer);

    }

    void OnButtonClicked(wxCommandEvent& event)
    {
        // オブジェクトのポインタを取得
        wxObject* obj = event.GetEventObject();
        wxButton* button = (wxButton*)obj;

        auto c = button->GetLabel().c_str().AsChar();
        wxMessageBox(c, "タイトル", wxOK | wxICON_INFORMATION, this);

    }


private:

    // 自分でBindしないときはこれとwxBEGIN_EVENT_TABLEが必要
    wxDECLARE_EVENT_TABLE();
};


wxBEGIN_EVENT_TABLE(MyFrame, wxFrame)
EVT_BUTTON(BUTTON_1, MyFrame::OnButtonClicked)
wxEND_EVENT_TABLE()

コメントを残す

メールアドレスが公開されることはありません。 が付いている欄は必須項目です

日本語が含まれない投稿は無視されますのでご注意ください。(スパム対策)


この記事のトラックバックURL: