2011-12-07 31 views
2

私はこの質問をタイプしたので、おそらくそれはすべきだと分かります。TForm.ManualDockはonFormShowを呼び出す必要がありますか?

フォームをTPageControlにドッキングすると、form.Create()が呼び出されたときとform.ManualDock(pagecontrol、pagecontrol.alClient)が呼び出されたときにFormShowが呼び出されます。

フォームをアンドッキングするとshowも呼び出されます。ドッキング/ドッキング解除時にフォームが実際に「リセット」されていると仮定します。

これが設計通りであれば、私はonCreateに(それが悪い設計でない限り)発火したくないコードをリファクタリングします。

+1

FormShowは、マニュアルForm.Hideの後にも呼び出されます。 Form.Show;あまりにも。あなたがそれを記述する方法では、コードを一度しか実行したくないので、FormCreateはもっと良い場所になります。フォームを隠すことがない場合でも、他のプログラムもフォームを隠すことができます。 – hvd

答えて

2

技術的な質問よりも哲学的であるべきかどうか。 TForm.OnShowイベントは、ManualDock機能によっても使用される制御メッセージCM_DOCKCLIENTを実行することによって起動されます。内部的には、このメッセージはCM_SHOWINGCHANGEDにイベント自体を起動させます。

次の例では、Form1(ページコントロールとボタン付き)とForm2(空とドッキング可能)の2つのフォームを使用します。私は両方が自動作成されていると推測します。

次のコードは、CM_DOCKCLIENT制御メッセージによってOnShowイベントが発生したことの証明です。ボタンをクリックすると、CM_DOCKCLIENTメッセージが実行され、Form2のOnShowイベントが発生します。

をForm1

procedure TForm1.FormShow(Sender: TObject); 
begin 
    Form2.Show; 
end; 

procedure TForm1.Button1Click(Sender: TObject); 
var 
    DockObject: TDragDockObject; 
begin 
    DockObject := TDragDockObject.Create(Form2); 
    try 
    // sending the CM_DOCKCLIENT message internally performs also the 
    // CM_SHOWINGCHANGED message which triggers the TForm.OnShow event 
    PageControl1.Perform(CM_DOCKCLIENT, WPARAM(DockObject), LPARAM(SmallPoint(0, 0))); 
    finally 
    DockObject.Free; 
    end; 
end; 

そしてForm2のが唯一のOnShowイベントハンドラ

procedure TForm2.FormShow(Sender: TObject); 
begin 
    ShowMessage('FormShow'); 
end; 

簡単な回避策は、(OnShowイベントで)自身のことで、手動でのForm2をドッキングすることはありませんが、ドックを持っているため、コードそれを作成者が表示するか、それを表示する形式で言うことにします。前の例ではForm1.OnShowイベントにForm2を表示していましたので、手動で簡単にドッキングすることができます。

procedure TForm1.FormShow(Sender: TObject); 
begin 
    Form2.Show; 
    Form2.ManualDock(PageControl1); 
end; 

procedure TForm2.FormShow(Sender: TObject); 
begin 
    // no manual docking of this form by itself 
end; 
+0

ありがとう - 私はOnCreateで必要なものを投げただけです。 –

関連する問題