2012-04-24 8 views
1

今、ほとんどの人がこの種の質問を見ると、「ああ、代表者を使う」と思っています。さて、私はです。そしてこれはこれまでのところ彼らと一緒に働くことを拒否する唯一のコントロールです。私はBackgroundWorkerも使用していません。ToolStripProgressBarの値をスレッドから設定するにはどうすればよいですか?

私は自分自身で、System :: Threading :: Threadのラッパークラスを作成しました。私はクラスにさまざまなデリゲートイベントを与え、UIスレッドと対話できるようにしました。主にステータスバーのステータスを設定するために使用しています。私はまた未使用のプログレスバーを持っていたので、私はそれを追加したかったのです。私はそれをデリゲートを与えたが、私はそれを実行したときに、それがでクラッシュ悪名高い:

「System.InvalidOperationException」種類の未処理の例外が発生したのSystem.Windows.Forms.dllに

追加情報:クロススレッド操作が無効です:コントロール '' は、作成されたスレッド以外のスレッドからアクセスされました。

私が知っている限り、他のコントロールと同じようにデリゲートを使用しているので、私は今混乱しています。これは特別ですか?私は遠くに、インターネットを検索し、私が得るのはC#BackgroundWorkerの質問ですが、実際にはこれには当てはまりません。

デリゲート:

delegate void    OnThreadProgressUpdateDel(int progress, String^ status); 

イベントを保持する変数:

OnThreadProgressUpdateDel^ m_updateProgressEvent; 

イベントがバインドされている方法:

thread->OnThreadProgressUpdate += gcnew ObjectLoadThread::OnThreadProgressUpdateDel(this, &CObjectLoader::ProgressUpdate); 

ここに私のデリゲートのためのコードですイベント:

void CObjectLoader::ProgressUpdate(int progress, String^ status) 
{ 
    gGlobal->ProgramProgress->Maximum = 100; 
    gGlobal->ProgramProgress->Value = progress; //Crash here... 
    gGlobal->SetProgramStatus(status); 
} 

はここに呼び出されます:

それはC++ CLRを使用して:(

更新したくないになり、この愚かなToolStripProgressBarについてとても特別な何

m_updateProgressEvent->Invoke(1, "Loading objects..."); 

、WindowsはマイクロソフトのVisual C++ 2008 Express Editionの中で、フォームアプリケーション。

答えて

1

Windowsコントロールは、作成された同じスレッドから変更する必要があります。制御&操作に応じて、MDAまたは例外が発生しませんが、それは標準に従うことをはるかに最善である:

if(InvokeRequired) control.Invoke();

パターンをスレッドとコントロールを扱う時はいつでも。

http://msdn.microsoft.com/en-us/library/ms171728(v=vs.80).aspx

+0

ToolStripProgressBarは 'Invoke'方法を持ちません。 'GetCurrentParent()'を使って 'Invoke'メソッドを取得できますか? 'InvokeRequired'でも同じことが言えます。 – smoth190

+0

@ smoth190ホストフォームの場合でも、同じスレッドに存在するコンポーネントを使用できます。 –

+0

ああ、良い。私はそれがうまくいくかどうかを確認するためにこのメソッドを実装します。 – smoth190

2

"ToolStripProgressBarは、Invokeメソッドを持っていません。"

正しいですか。 toolStripProgressBar.ProgressBar.InvokeとInvokeRequiredは存在し、期待どおりに機能します。

0

//以下のコードを使用してください。Ahmad abbulkmailer。com

SetControlPropertyValue1(ProgressBar2、 "value"、67);

delegate void SetControlValueCallback1(ToolStripProgressBar oControl、string propName、object propValue); プライベートvoid SetControlPropertyValue1(ToolStripProgressBar oControl、string propName、オブジェクトpropValue){ if(oControl.GetCurrentParent()。InvokeRequired){ SetControlValueCallback1 d = new SetControlValueCallback1(SetControlPropertyValue1); oControl.GetCurrentParent()。呼び出し(d、新しいオブジェクト[] {oControl、propName、propValue});他 } {

  Type t = oControl.GetType(); 
      PropertyInfo[] props = t.GetProperties(); 

      foreach (PropertyInfo p in props) { 
       if (p.Name.ToUpper() == propName.ToUpper()) { 
        p.SetValue(oControl, propValue, null); 
       } 
      } 
     } 


    } 
関連する問題