2017-06-23 14 views
-1

特定のクラス内にpublic staticメソッドがあります。 UIスレッドで作成されたアイテム(コンボボックス、datagridviewsなど)を使用します。 "追加情報:クロススレッド操作が有効ではありません:コントロール 'CompanycheckedListBox'が、作成されたスレッド以外のスレッドからアクセスされました。」というメッセージが表示されます。UIスレッド項目を使用して別のスレッドで関数を実行する

新しいスレッドから関数を実行しても、UIスレッドで作成されたこれらのアイテムはどのように使用できますか?

私はこのコード行を使用しました。新しいスレッド(delegate(){functionName();})。

+0

'Form.BeginInvoke'が役立つ可能性がありますhttps://msdn.microsoft.com/en-us/library/system.windows.forms.form.begininvoke(v=vs.110).aspx – NibblyPig

+0

実行しないでください他のUIスレッド上でUIコントロールを「操作」する関数です。代わりに、他のスレッドで必要な計算を実行します - 計算されたデータを返し、正しい環境でUIコントロールを更新してください。 – Fabio

+0

「Fabio」と同じです。 '' NibblyPig's''コメントはあなたのためのものですが、あなたの "idea"が何か他のものであれば、別の選択肢があるかもしれません。 –

答えて

0

短い答え:できません。これらのコンポーネントは、UIスレッドのみでアクセスできます。しかし、関数呼び出しをUIスレッドにディスパッチする方法があります。

ほとんどのUIフレームワークは完全にシングルスレッドです。 uiスレッドとは別のスレッドからコンポーネントにアクセスすることはできません。

現在のUIスレッドにディスパッチする必要があります。コントロール名で見ると、winformsやWPFアプリケーションのように見えます。あなたが戻ってUIスレッドに派遣するために、次のコードを必要とするのWinFormsで

:WPFで

public void UpdateUI(object parameter) 
{ 
    if (this.InvokeRequired) 
    { 
     Dispatcher.BeginInvoke(new Action(() => UpdateUI(parameter))); 
     return; 
    } 

    // Update or access here 
} 

次スニップあなたが別のスレッドを形成するUIを変更することができます:

public void UpdateUI(object parameter) 
{ 
    if (!Dispatcher.CheckAccess()) 
    { 
     Dispatcher.BeginInvoke(new Action(() => UpdateUI(parameter))); 
     return; 
    } 

    // Do update or access here 
} 

ここで注意すべき重要なことは、これらの関数がUIスレッドで実行され、呼び出しスレッドでは実行されないことです。

編集:オブジェクトパラメータは完全にオプションです。これは、パラメータを持つ関数でこのメソッドを使用する方法の例として意図されています。

+0

ありがとうございました。関数がUIスレッド上で実行される場合、UIスレッドは解放されません。では、この方法は私に何を提供していますか? – Jonathan

+0

と「オブジェクトパラメータ」について - 私はそこに何を入れますか?私が呼びたい機能は? – Jonathan

+0

WPFでは、 'data-binding'を使用すると、他のスレッドのデータソース(viewmodel)を更新すると、手動でディスパッチせずにUIコントロールが自動的に更新されます。 – Fabio

関連する問題