コンボボックスのドロップダウンリストの位置変更をするには?

解決


桜井  2011-05-31 17:40:44  No: 72690  IP: 192.*.*.*

環境:WindowsXP 以降
VC++2008 MFC

コンボボックスで、▼を押下したときに表示される
ドロップダウンリストを下記の様に表示できないでしょうか?
******************
表示イメージ
    ┌──┬┐
    └──┴┘← コンボボックス
┌─────┐
│          │
│          │← ドロップダウンリスト
│          │
└─────┘
******************

ドロップダウンリストの幅は
SetDroppedWidth
を使用すれば変更できる事は分かっていてい実装もできています。

編集 削除
桜井  2011-06-01 09:30:44  No: 72691  IP: 192.*.*.*

追記
コンボボックスより長い文字がリストに登録されていて、
ドロップダウンリストを表示した時に、
コンボボックスと、ドロップダウンリストの右側をそろえて表示したいです。

編集 削除
gak  2011-06-01 18:14:40  No: 72692  IP: 192.*.*.*

GetComboBoxInfo() でドロップダウンリストのウィンドウハンドル取得して
サブクラス化 + WM_WINDOWPOSCHANGING をhook、としてやれば可能かと。

以下部分抜粋ソースサンプル

// .h
class ComboL : public CWnd {
protected:
    HWND owner_;
    bool autorelease_;
public:
    ComboL() : autorelease_(false) {}
    static bool SubclassWithAutorelease(HWND combo);
    bool Subclass(HWND combo);
    :
}

// .cpp
bool ComboL::SubclassWithAutorelease(HWND combo) {
    ComboL *list = new ComboL;
    if (!list->Subclass(combo)) {
        delete list;
        return false;
    }
    list->autorelease_ = true;
    return true;
}

bool ComboL::Subclass(HWND combo) {
    ::COMBOBOXINFO info = { sizeof(::COMBOBOXINFO) };
    return ((owner_ = combo) != NULL && ::GetComboBoxInfo(combo, &info) && SubclassWindow(info.hwndList));
}

void ComboL::OnWindowPosChanging(WINDOWPOS* lpwndpos) { // WM_WINDOWPOSCHANGING
    CWnd::OnWindowPosChanging(lpwndpos);
    RECT rect;
    ::GetWindowRect(owner_, &rect);
    ::MapWindowPoints(NULL, ::GetParent(m_hWnd), LPPOINT(&rect) + 1, 1);
    lpwndpos->x = (rect.right - lpwndpos->cx); // 右端揃え
}

void ComboL::PostNcDestroy() { // CWnd::PostNcDestroy() オーバーライド
    CWnd::PostNcDestroy();
    if (autorelease_) {
        delete this;
    }
}

// 例
xxxx::OnInitDialog() {
    ComboL::SubclassWithAutorelease(::GetDlgItem(m_hWnd, IDC_COMBO1));
}

編集 削除
桜井  2011-06-10 12:06:31  No: 72693  IP: 192.*.*.*

gak さん、回答ありがとうございます。
返事が遅くなってしまいすみませんでした。

gakさんの提示してくれたサンプルでできました。

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

編集 削除