0

WINAPI で親のないボタンを作成できますか?

私はやってみました:

CreateWindowEx(0, "Button", "BTN", WS_POPUP | BS_PUSHBUTTON, 0, 0, 15, 15, nullptr, nullptr, nullptr, nullptr);

次に、後で親を指定されたウィンドウに設定し、ShowWindow を使用してボタンを表示します。これにより、実際に見栄えの良いボタンが作成されました。

ただし、ボタンには ID がなく、ID が 0 であるため WM_COMMAND で識別できません。2 つのボタンが親のない場合、それらを区別する方法はありません。HMENU パラメータで ID を指定すると、次のようになります。

CreateWindowEx(0, "Button", "BTN", WS_POPUP | BS_PUSHBUTTON, 0, 0, 15, 15, nullptr, 15, nullptr, nullptr);

GetLastError() は「無効なメニュー ハンドル」を出力し、ボタンは作成されません。

親と WS_CHILD を指定しないと、理解できる最上位の子ウィンドウを作成できないと表示されます。

そこで私がしたことは、Parent を GetDesktopWindow() に設定し、ボタンに ID を与えることでした。それは機能しますが、ボタンは親なしではありません..

ボタンに ID を与え (WM_COMMAND で識別できるように)、同時にその親を NULL にして、後で親を設定できるようにする方法はありますか? Windowsフォームはどのようにそれを行いますか? Form.add(ButtonName); を実行するまで、ボタンは親なしにすることができます。

WINAPIでも同じ効果が得られるでしょうか?

4

2 に答える 2

4

これは一見、非常にばかげた質問のように見えます。

ボタン コントロールは定義上、子コントロールであるためCreateWindowEx、ボタンの作成に使用する関数の呼び出しでもWS_CHILDスタイルを指定する必要があります。

もちろん、あなたが言及したように、親のない子コントロールを作成することはできません。エラーが発生します。トップレベルの子ウィンドウのようなものはありません。

では、最初の質問の答えは

WINAPI で親のないボタンを作成できますか?

明らかにいいえです。ボタンは子コントロールであり、すべての子コントロールには親が必要です。

Windows ではWS_POPUP、ボタン コントロールを作成するときにフラグを指定できないからといって、それが有効な組み合わせであるとは限りません。

関数のドキュメントを読み直すことを強くお勧めしCreateWindowExます。特に、hMenuパラメータはその意味に関してオーバーロードされていることに注意してください。オーバーラップ ウィンドウまたはポップアップ ウィンドウ (WS_OVERLAPPEDまたはWS_POPUP) を作成している場合は、メニューへのハンドルを指定します。子ウィンドウ ( ) を作成している場合は、子ウィンドウWS_CHILDの識別子を指定します。ウィンドウのスタイルに応じて、同じパラメーターが両方に使用されるという事実は、何かを教えてくれるはずです。

Windowsフォームはどのようにそれを行いますか? Form.add(ButtonName); を実行するまで、ボタンは親なしにすることができます。

彼らは間違いなくできません。ボタン コントロールは、フォームまたは他の親コントロールに追加するまで作成されません。クラス コンストラクターはSystem.Windows.Forms.ButtonWin32 ウィンドウを作成しません。適切な場合に、基になる Win32 ウィンドウを作成するために使用される必要なスタイルのコレクションを保持するだけです。

もちろん、C++Buttonクラスを作成して同じことを行うこともできます。単純な実装では、すべてのメンバーが設定されると、Win32 ウィンドウを作成するために実際に呼び出すメンバー関数CreateWindowExと、パラメーターに対応するメンバー変数が含まれます。必要なメンバーの 1 つがまだ有効な値に設定されていない場合、メソッドは例外をスローする可能性があります。CreateCreateWindowExCreate

私はそれを解決しました。親パラメーターとして HWND_MESSAGE を渡す必要がありました。SetParent を呼び出すと、そのパラメーターが親のハンドルに変更され、すべて問題ありません。

いいえ、これは実際には問題の「解決策」ではありません。kero が指摘しているように、ボタン コントロールの親をメッセージのみのウィンドウに設定しただけです。繰り返しますが、これは機能しているように見えますが、かなり奇妙なことであり、解決策としてはほとんどお勧めしません.

本当にハックしたい場合は、独自の非表示の最上位ウィンドウを作成して、「親のない」子コントロールの親として使用することをお勧めします。次に、呼び出しの同じトリックを使用して、SetParentそれらを再親化できます。

于 2013-03-10T12:39:01.717 に答える
1

私はそれを解決しました。親パラメーターとして HWND_MESSAGE を渡す必要がありました。SetParent を呼び出すと、そのパラメーターが親のハンドルに変更され、すべて問題ありません。

いいえ、「Parent-Less Button」を取得していません。メッセージのみのボタンの親ウィンドウは、「メイン」のメッセージのみのウィンドウ (クラス「Message」) です。

于 2013-03-09T23:30:23.030 に答える