AppWizardで作成したMDIのMFCアプリケーションでは、ファイルのドロップ処理はデフォルトで行われます。
SDIやダイアログベースのMFCアプリケーションでも、ちょっと処理を書いてやるだけで
けっこう簡単にファイルのドロップを扱う事が出来ます。
以下、SDIの場合を例にして説明します。 ダイアログの例は後ろにあります。
DropView.h:
class CDropView : public CView { 〜 // 生成されたメッセージ マップ関数 protected: //{{AFX_MSG(CDropView) afx_msg void OnDropFiles(HDROP hDropInfo); //}}AFX_MSG DECLARE_MESSAGE_MAP() 〜 };
DropView.cpp:
〜 BEGIN_MESSAGE_MAP(CDropView, CView) //{{AFX_MSG_MAP(CDropView) ON_WM_DROPFILES() //}}AFX_MSG_MAP END_MESSAGE_MAP() 〜 void CDropView::OnDropFiles(HDROP hDropInfo) { // TODO: この位置にメッセージ ハンドラ用のコードを追加するかまたはデフォルトの処理を呼び出してください CView::OnDropFiles(hDropInfo); }
これで、OnDropFiles()が呼ばれるようになります。
class CDropView : public CView
{
〜
// 生成されたメッセージ マップ関数
protected:
//{{AFX_MSG(CDropView)
afx_msg void OnDropFiles(HDROP hDropInfo);
afx_msg int OnCreate(LPCREATESTRUCT lpCreateStruct);
//}}AFX_MSG
DECLARE_MESSAGE_MAP()
〜
};
DropView.cpp:
〜 BEGIN_MESSAGE_MAP(CDropView, CView) //{{AFX_MSG_MAP(CDropView) ON_WM_DROPFILES() ON_WM_CREATE() //}}AFX_MSG_MAP END_MESSAGE_MAP() 〜 int CDropView::OnCreate(LPCREATESTRUCT lpCreateStruct) { if (CView::OnCreate(lpCreateStruct) == -1) return -1; // TODO: この位置に固有の作成用コードを追加してください DragAcceptFiles(); return 0; }
BOOL CDropView::PreCreateWindow(CREATESTRUCT& cs)
{
// TODO: この位置で CREATESTRUCT cs を修正して Window クラスまたはスタイルを
// 修正してください。
cs.dwExStyle |= WS_EX_ACCEPTFILES; //ファイルのドロップを受け付ける
return CListView::PreCreateWindow(cs);
}
DropView.cpp:
void CDropView::OnDropFiles(HDROP hDropInfo) { // TODO: この位置にメッセージ ハンドラ用のコードを追加するかまたはデフォルトの処理を呼び出してください //ドロップされたファイルの個数を取得 UINT uiCount=DragQueryFile(hDropInfo,~0lu,NULL,0); for(UINT i=0; i<uiCount; i++){ //ファイル名の長さを取得 UINT uiLen=DragQueryFile(hDropInfo,i,NULL,0); //ファイル名を取得 CString name; DragQueryFile(hDropInfo,i,name.GetBuffer(uiLen+1),uiLen+1); name.ReleaseBuffer(); //name(ファイル名)を使って何らかの処理を行う 〜 } // CView::OnDropFiles(hDropInfo); //必要ないと思われるので呼ばない }ただし、ディレクトリがドロップされた場合、そのディレクトリは ひとつのファイルとして扱われるので注意が必要です。
しかし、ダイアログではClassWizardでWM_DROPFILESが表示されないので、
自分でコーディングする必要があります。
また、初期化としてOnInitDialog関数が呼ばれるので、
OnCreateでなくOnInitDialogでDragAcceptFiles()を呼び出すといいでしょう。
DropDlg.cpp:
BOOL CDropDlg::OnInitDialog()
{
CDialog::OnInitDialog();
〜
// TODO: 特別な初期化を行う時はこの場所に追加してください。
DragAcceptFiles();
return TRUE; // TRUE を返すとコントロールに設定したフォーカスは失われません。
}
[1998-08-22]
しかし、ダイアログの場合、DragAcceptFiles()を呼ばないで済む方法があります。
ダイアログのリソースのプロパティーを開き、「拡張スタイル」タブの「ドラッグアンドドロップを許可」に
チェックを付けるだけです。