Form表示後に処理を行う
|
33 |
FormShowAfterEvent |
動作確認 |
Delphi2007 |
更新日 |
2008/01/16(水) 2010/07/06(火) |
FormShow イベントでコンポーネントの表示関係の操作を行うと
> ---------------------------
> OnShow/OnHide イベントの処理中は表示状態の変更はできません.
> ---------------------------
> OK
> ---------------------------
このようなメッセージが表示されて動作がうまくいかない場合があります。
FormCreate イベントの場合でも困る時もあります。
そこで、FormShow 後にFormが表示されてから処理を行いましょう。
主に知られている次の2つのやり方があります。
1、CM_SHOWINGCHANGEDメッセージを使う。
2、独自のメッセージ定義してFormCreateやFormShowイベント内でPostMessageする。
以前は2のやり方をテクニックとして公開していましたが、
1のやり方の方が効率よさそうなので記述しておきます。
2のやり方もコードを乗せておきます。
どちらのやり方でもメッセージハンドラを定義している例ですが
ApplicationEventsのOnMessageイベントを使って
メッセージを受け取る実装も可能です。
◆CM_SHOWINGCHANGEDメッセージを使う。
────────────────────
type
TForm1 = class(TForm)
…
private
procedure CMShowingChanged(var Msg:TMessage);message CM_SHOWINGCHANGED;
end;
procedure TForm1.MemoLogWrite(LogText: String);
begin
Memo1.Lines.Add(
Format('%s:%s', [
FormatDateTime('yyyy/mm/dd hh:nn:ss', Now),
LogText]) );
end;
procedure TForm1.FormShow(Sender: TObject);
begin
MemoLogWrite('FormShowEvent');
end;
procedure TForm1.CMShowingChanged(var Msg: TMessage);
begin
inherited;
if Visible = False then Exit;
Self.Update; //更新を行っておく
//処理を記述
MemoLogWrite('CMShowingChanged');
end;
procedure TForm1.FormCreate(Sender: TObject);
begin
Timer1.Interval := 5000;
Timer1.Enabled := True;
end;
procedure TForm1.Timer1Timer(Sender: TObject);
begin
Self.Visible := not Self.Visible;
end;
────────────────────
このようにしておくと、
FormShowEvent
CMShowingChanged
の順番でログが記述されます。
上記のコードのタイマーイベントで設定しているように
CMShowingChanged イベントは表示状態がON/OFFされる時に発生するため
Visible = False になる際にも呼び出されるので
イベント内で
if Visible = False then Exit;
としています。
◆独自のメッセージ定義してPostMessageする。
次のコードで実現できます。
────────────────────
const WM_ShowWaitEvent=WM_USER+$100;
type
TForm1 = class(TForm)
…
private
procedure WMShowWaitEvent(var Msg: TMessage); message WM_ShowWaitEvent;
end;
procedure TForm1.FormShow(Sender: TObject);
begin
MemoLogWrite('FormShowEvent');
PostMessage(Self.Handle,WM_ShowWaitEvent, 0, 0);
end;
procedure TForm1.WMShowWaitEvent(var Msg: TMessage);
begin
//処理を記述
MemoLogWrite('WMShowWaitEvent');
end;
────────────────────
これも
FormShowEvent
WMShowWaitEvent
の順番でログが記述されます。
参考────────────────────
Delphi壁の穴 - [1.Delphiを覗く]
http://delfusa.main.jp/delfusafloor/archive/VA009712_take/delphi/kabedel.htm
[Delphi] フォームが表示し終えたとき - くろねこ研究所
http://www.blackcatlab.com/article.php/ProgramingFAQ_del0049
[Delphi Memo] Shimosoft
http://www12.plala.or.jp/selen/Delphi/
Delphi Tips
http://www.occn.zaq.ne.jp/maekawa/delphitip/index.html
|