CFileDialogの表示サイズを変更するには?

解決


minaduki  2008-06-05 06:42:45  No: 68492

CFileDialogにて表示するダイアログのサイズを変更したいと考えております。

アプリを起動して、ファイルを開くボタンを押下した段階で任意のサイズにて表示したいのですが、上手く行きません。

CFileDialogを派生して、OnSizeやOnInitDialog などでMoveWindowなどを行ったのですが上手く行かず・・・

何か方法、ありませんでしょうか。

ご存知の方、よろしければご教授願います。


rin  2008-06-05 21:15:43  No: 68493

Spy++で見るとわかりますが
CFileDialog(その派生)は入出力を扱う機能がメインで
表示されているのは別のダイアログです

イメージ的には
**************
[呼び出したウィンドウ]

[表示されるウィンドウ](*1)

[CFileDialog]
**************

こうなっています。
ので、CFileDialogから、GetParent()で*1にアクセスして
MoveWindowすればサイズ変更できます。

ですが、やってみるとわかると思うのですが
表示されてる多数のコントロール(リストボックスなど)は何も変わないので
これらも全部手動で変更する必要があります。

ここまでくると、CFileDialogにこだわるより
そっくりさんのダイアログを自作するほうが早いです。


NGA  2008-06-06 11:43:50  No: 68494

環境が提示されてないんで WinXP sp2 VC++6.0 sp5 MFC で試してみた。
SetWindowsHookEx API で WH_CALLWNDPROCRET を指定して、フックプロシージャ内で WM_SHOWWINDOW 時に CFileDialog の親ウィンドウに対して SetWindowPos API を呼ぶ。
コントロールの面倒を見なくてもいけた。


minaduki  2008-06-06 20:46:58  No: 68495

>rin様
ご回答ありがとうございます。

CFileDialogの挙動、勉強になりました。
新規ダイアログの作成も視野に入れ、もう少し考えたいと思います。

>NGA様
ご回答ありがとうございます。

環境の件、記載無く申し訳ないです。
偶然ですが同一の環境で作成しています。

もしよろしければもう少し詳しくご教授願えますでしょうか。

フックプロシージャ内でCFileDialogの親を取得するあたりで躓いております。


NGA  2008-06-07 07:56:54  No: 68496

簡単にまとめるとこんな感じになる。

static HHOOK g_hHookProcRet;
static HWND g_hWnd;
static RECT g_rectInit;       // DoModal() を呼ぶ前に初期表示位置を設定しておく。

LRESULT CALLBACK CallWndRetFileDlgProc(int nCode, WPARAM wParam, LPARAM lParam)
{
        if(nCode < 0)
        {
                return ::CallNextHookEx(g_hHookProcRet, nCode, wParam, lParam);
        }

        LPCWPRETSTRUCT pMsg = reinterpretcast<LPCWPRETSTRUCT>(lParam);

        switch(pMsg->message)
        {
        case WM_SHOWWINDOW:
                if(g_hWnd && pMsg->hwnd == ::GetParent(g_hWnd))
                {
                        ::SetWindowPos(pMsg->hwnd, NULL, g_rectInit.left, g_rectInit.top,
                                g_rectInit.right - g_rectInit.left, g_rectInit.bottom - g_rectInit.top, SWP_NOZORDER);
                }
                break;
        }

        return ::CallNextHookEx(g_hHookProcRet, nCode, wParam, lParam);
}

CMyFileDialog::CMyFileDialog(BOOL bOpen, LPCTSTR lpszDefExt, LPCTSTR
        lpszFileName, DWORD dwFlags, LPCTSTR lpszFilter, CWnd* pParentWnd)
        : CFileDialog(bOpen, lpszDefExt,  lpszFileName, dwFlags, lpszFilter, pParentWnd)
{
        g_hHookProcRet = ::SetWindowsHookEx(WH_CALLWNDPROCRET, CallWndRetFileDlgProc,
                NULL, ::GetCurrentThreadId());
}

CMyFileDialog::~CMyFileDialog()
{
        g_hWnd = NULL;

        if(g_hHookProcRet)
        {
                ::UnhookWindowsHookEx(g_hHookProcRet);
                g_hHookProcRet = NULL;
        }
}

// CFileDialog::OnInitDialog() をオーバーライドして CFileDialog のウィンドウハンドルを取得する。
BOOL CMyFileDialog::OnInitDialog()
{
        CFileDialog::OnInitDialog();
        g_hWnd = GetSafeHwnd();

        return TRUE;
}


NGA  2008-06-07 07:58:31  No: 68497

Tab は入力できないのね。orz


minaduki  2008-06-09 00:43:57  No: 68498

NGA様

ソースの掲示、ありがとうございます。

なるほど・・
派生クラスにしてやる必要があったんですね。

参考にさせていただきます。

実装できましたらまた書き込みに参ります。

ありがとうございました。


minaduki  2008-06-12 09:08:25  No: 68499

教えていただいた方法で意図どおりの機能を実装することが出来ました。

ありがとうございましたm(_ _)m


※返信する前に利用規約をご確認ください。

※Google reCAPTCHA認証からCloudflare Turnstile認証へ変更しました。






  このエントリーをはてなブックマークに追加