ドラッグ&ドロップの実装は、SetDropTargetにwxFileDropTarget を継承したクラスを指定する。
すると、ドラッグ時にMyFileDropTarget::OnDropFilesが呼び出されるので、そこから(必要であれば)MyFrame::OnDropFilesを呼び出す。
この時ただ関数呼び出しするのではなくてwxDropFilesEvent 型のイベントオブジェクトを作ってwxPostEventする。
この時、wxDropFilesEvent オブジェクトに渡したwxString* pathはwxWidgetsが管理する(らしい)のでdelete[]は書かない。
// プリプロセッサに以下二つを追加 // __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に必要 #ifdef _DEBUG #pragma comment(lib,"wxbase32ud.lib") #pragma comment(lib,"wxbase32ud_net.lib") #pragma comment(lib,"wxbase32ud_xml.lib") #pragma comment(lib,"wxmsw32ud_adv.lib") #pragma comment(lib,"wxmsw32ud_aui.lib") #pragma comment(lib,"wxmsw32ud_core.lib") #pragma comment(lib,"wxmsw32ud_gl.lib") #pragma comment(lib,"wxmsw32ud_html.lib") #pragma comment(lib,"wxmsw32ud_media.lib") #pragma comment(lib,"wxmsw32ud_propgrid.lib") #pragma comment(lib,"wxmsw32ud_qa.lib") #pragma comment(lib,"wxmsw32ud_ribbon.lib") #pragma comment(lib,"wxmsw32ud_richtext.lib") #pragma comment(lib,"wxmsw32ud_stc.lib") #pragma comment(lib,"wxmsw32ud_webview.lib") #pragma comment(lib,"wxmsw32ud_xrc.lib") #else #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") #endif #include <string> // ドラッグドロップに必要 #include <wx/dnd.h> ///////////////////////////////////// ///////////////////////////////////// /////////////////////////////////////
// ドラッグ&ドロップに対応するクラス class MyFileDropTarget : public wxFileDropTarget { wxWindow* m_owner; public: MyFileDropTarget(wxWindow* owner) : m_owner(owner) {}
virtual bool OnDropFiles(wxCoord x, wxCoord y, const wxArrayString& filenames) override { size_t nFiles = filenames.GetCount(); // wxString* の配列を作成。このメモリはwxWidgetsが管理する(らしい)のでdelete[]しないko wxString* paths = new wxString[nFiles]; for (size_t i = 0; i < nFiles; i++) { paths[i] = filenames[i]; } wxDropFilesEvent event(wxEVT_DROP_FILES, nFiles, paths); wxPostEvent(m_owner, event);// MyFrame::OnDropFilesを呼び出す return true; }
};
// ウィンドウ作成 class MyFrame : public wxFrame { public: void PostCreate() { this->Layout(); // レイアウトの更新 } MyFrame(const wxString& title, const wxPoint& pos, const wxSize& size) : wxFrame(NULL, wxID_ANY, title, pos, size) { // CallAfter : 現在処理中のイベントが終わったらPostCreateを実行 // コンストラクタはウィンドウ生成イベント扱い CallAfter(&MyFrame::PostCreate); // ドラッグ&ドロップを有効にする SetDropTarget(new MyFileDropTarget(this)); // ドラッグドロップされた時に呼ばれるイベントを設定 Bind(wxEVT_DROP_FILES, &MyFrame::OnDropFiles, this); }
// wxEVT_DROP_FILES に対応するイベントハンドラ void OnDropFiles(wxDropFilesEvent& event) { wxString* filePaths = (wxString*)event.GetFiles();// ファイル名一覧を取得 wxString str; for (size_t i = 0; i < event.GetNumberOfFiles(); i++) { str += filePaths[i]; str += "\n"; } wxMessageBox(str); // 管理はwxWidgetsが行っているので解放しない //delete[] filePaths; }
private: }; ///////////////////////////////////// ///////////////////////////////////// ///////////////////////////////////// // 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);