2011-08-16 16 views
1

この質問はExperts-Exchangeにあります。 コントロールのOnExitが別のウィンドウを表示するときに新しいコントロールのmouseupイベントを食べる

問題は簡単に複製することができ、別のウィンドウを表示するとき

コントロールのフォーカス喪失時には、新しい制御のためのmouseUpイベントを食べます。

場所に3つのテジットがあります。 edit1のonexitイベントでshowmessage( 'exit')を書きます。プログラムを実行します。edit1フォーカスを与えます。 edit3フォーカスをクリックして、showmessageにokをクリックします.edit3の何かをクリックするまで表示します。マウスのどこか フォームに! edit2フォーカスを与え、次にedit3フォーカスを与えるためにマウスに使用 edit3であなたが望むものをどのように入力することができるか観察する!

これまでのところ、私はこの問題は、古いコントロールがどのような種類のウィンドウを表示 イベントをフォーカス喪失時ときEDIT3 はのmouseup、メッセージを受信して​​いないという事実にある、私は同様にそれを試してみたことが確立されました同じ結果のonExitイベントで私自身の フォームを示しています。実際には、Windowsは、あなたがshowmessage

に[OK]をクリックしたマウスを 後EDIT3の上に押されているという印象の下に である私は、それは、Delphi/Windowsのバグだと思うが、それを回避する方法?

:私は似何かをしようとしています

適用いつも私は私がEDIT3のOnMouseDownイベントの(プロセスで呼び出さ 以来の最後のイベント)にWM_LBUTTONUPを強制することができます知っている それは退屈ではなく、より です

onexitイベントでは、警告ボックスを表示してから、通常どおりに進んでください。ユーザーが実際にクリックした場所にフォーカスを移動します。 これは可能ですか?

+2

OnExitイベントハンドラでモーダル警告を表示しないでください。警告を視覚資料に限定する。モーダル警告を表示する必要がある場合は、フォームを送信するときに(OKをクリックして)行います。 – NGLN

答えて

6

もう一度PostMessageをレスキューする! Windowsがフォーカスの変更を完了できるように、ダイアログをちょっと遅らせてください。自分自身の代わりに、直接対話を示すのメッセージ投稿:

const 
    WM_SHOWMYDIALOG = WM_APP + 321; 

TForm1 = class(TForm) 
    Edit1: TEdit; 
    Edit2: TEdit; 
    procedure Edit1Exit(Sender: TObject); 
private 
    procedure WMSHOWMYDIALOG(var Message: TMessage); message WM_SHOWMYDIALOG; 
end; 

procedure TForm1.Edit1Exit(Sender: TObject); 
begin 
    PostMessage(Self.Handle, WM_SHOWMYDIALOG, 0, 0); 
end; 

procedure TForm1.WMSHOWMYDIALOG(var Message: TMessage); 
begin 
    ShowMessage('Nice one'); 
end; 

、すべてが大丈夫です:)を

4

私は行動の理由を食べマウスメッセージであることをとてもよく分かりません。いずれにしても、そうであるかどうかにかかわらず、コントロールのOnExitイベントでウィンドウをアクティブにするときに、フォーカスが変化している間にフォーカスを変更していることです。これは、新しくフォーカスされたコントロールが戻るために、ウィンドウがWM_SETFOCUSより前にアクティブ化されるためです。これは推奨され、以下の引用は「Win32 Activation and Focus」、MSDNのブログエントリの「ベストプラクティス」セクションから、次のとおりです。

避け取得及び/またはフォーカスを失ったときに、手動でピントを変更します。この は、通常、エラーが発生する可能性があります。


コントロールは確かに助けないと起動し、ウィンドウのモーダル性質のためにフォーカス転送時に無効になっているという事実。実際にこれを行う必要がある場合は、Heinrich's answerのようなアプローチでは、少なくともフォーカスの転送が完了するまでウィンドウの起動が遅れることになります。

2

onexitイベントで私は警告ボックスを表示してから、通常どおり進めたいと思っています。ユーザーが実際にクリックした場所にフォーカスを移動します。それは可能ですか? ShowMessageの呼び出しの前と後:

はい、(Screen.)ActiveControlは常にEdit3を指します

procedure TForm1.Edit1Exit(Sender: TObject); 
begin 
    ShowMessage('Exit'); 
    PostMessage(ActiveControl.Handle, WM_LBUTTONUP, 0, 0); 
end; 

しかし、これはちょうどあなたの質問に完全酒です!そして確かにヒントやアドバイスはありません!その理由についてSertacの答えを見てください。

関連する問題