2009年3月6日金曜日

backgroundworkerに2日間ハマる

 あるWebサービスに接続してXmlが返ってくるまでに10数秒かかるので、その間UIが固まったように見えるので、Ajax系でよくある「Loading...」のアニメーションを置いた別フォームを開いて、Xml取得後に閉じる処理を書いた。

 メインスレッド
   ↓
 backgroundworderのRunWorkerAsyncで別スレッドにて処理開始
   ↓                   ↓
 別フォームを作成し、表示する。   別スレッドにてXmlリクエスト
   ↓                   ↓
 フォーム内の変数監視Loop      Xml受信 Completedイベント
   ↓                   ↓
 変数がtrueになればフォームを閉じる RunWorkerCompleted処理で変数をTrueへ
   ↓                   ↓
  完了                受信データをUIへ

のハズがRunWorkerCompletedイベントが発生しません。
下記のコードで別スレッドの完了を監視しています。

 フォームを開いた後、
  while (!変数)
{
System.Threading.Thread.Sleep(100);
  }

 ブレークポイントをDoWork内に置くと、処理はされているのですが、DoWorkを抜けた後RunWorkerCompletedイベントが発生しません。

 使い方が悪いのかと、2日間調べまくりましたが分かりません。

 おまけに、上記のような監視Loopが走っていると、別フォームのアニメーションも固まって動きません。

 取りあえずアニメーションだけでも動かそうと、フォームを再描画するために

       Application.DoEvent();

 を足すと、アニメーションが動き始めました。

 ついでに、RunWorkerCompletedイベントも発生するようになりました。

 調べても見つからなかったので、書いておきます。


    

0 件のコメント: