[C#] Thread から Form コントロールへの delegate を使ったアクセス方法

2011-8-26 09:00
このエントリーをはてなブックマークに追加

C# のスレッド内から、フォームのコントロールのプロパティにアクセスしようとすると次のような警告が出ます。

有効ではないスレッド間の操作: コントロールが作成されたスレッド以外の
スレッドからコントロール 'XXXX' がアクセスされました。 

「Windows フォームコントロールへのアクセスは、本質的にスレッドセーフではないため、コントロールの状態を操作する複数のスレッドがある場合、コントロールが一貫性のない状態に陥る可能性がある」という理由でこの警告が出ています。

この警告を出さないようにするには、CheckForIllegalCrossThreadCallsfalse をセットすればよいとヘルプに書かれていますが、本質的な解決ではありません。

//インスタンスではなくクラスのプロパティ
Form1.CheckForIllegalCrossThreadCalls = false;

コントロールのプロパティにスレッドから安全にアクセスするには Invoke とデリゲートを使用します。デリゲートとはわかりにくいですが、メソッドを参照するための型で、宣言すると System.Delegate クラスの派生クラスして扱われます。

//Delegate を宣言しておく
delegate void MyDelegate(string text);

//リストボックスにテキストを追加していくメソッド
internal void AddText(string text) {
   ListBox1.Items.Add(text);
}
  
//スレッド内からデリゲートを介して以下のようにして呼ぶ
Invoke(new MyDelegate(AddText), "テキスト文");

これでスレッドから安全にフォームコントロールにアクセスでき、警告は出なくなります。

コメントはまだありません

No comments yet.

Sorry, the comment form is closed at this time.

33 queries. HTML convert time: 0.067 sec. Powered by WordPress. Valid XHTML
Copyright © 2003-2017 @ futuremix.org ログイン