2010-10-29 50 views
4

在WPF應用程序,我使用文本框,在其中的ContextMenu被重寫這樣的自定義樣式:文本框自定義文本菜單的風格,多線程錯誤

<Style TargetType="{x:Type TextBox}"> 
    <Setter Property="ContextMenu"> 
     <ContextMenu> 
     <MenuItem Header="Copy"/> 
     </ContextMenu> 
    </Setter> 
    </Style> 

這工作完全直到我會在不同的線程一樣的TextBox運行窗口這樣的:

Thread thread = new Thread(()=> 
           { 
           TestWindow wnd = new TestWindow(); 
           wnd.ShowDialog(); 
           }); 
thread.SetApartmentState(ApartmentState.STA); 
thread.IsBackground = true; 
thread.Start(); 

但是這會導致InvalidOperationException異常「調用線程,因爲不同的線程擁有它不能訪問該對象。」

如何避免此問題?

回答

4

問題是你的風格被重用作優化,所以ContextMenu被重用 - 這是標準的,適用於單線程,但不適用於多線程。

我會嘗試的風格移動到ResourceDictionary中,並引用它作爲一個靜態資源,我會再與標記: X:共享=「假」 這將創建一個新的實例每次在訪問資源 - 我不是確保它適用於「抓住所有」鍵的風格較少。 然後,您可以將contextmenu作爲資源並將其引用爲StaticResource - 應該這樣做。

+0

另一種解決方案是使用事件訂閱器進行右鍵單擊並快速創建ContextMenu。 – 2010-11-01 15:10:13

0

在你的一段代碼中,你想修改非UI線程中的UI,這是不允許的。

在應用UI更新時,您必須確保您處於UI線程中。您可以通過檢查object.InvokeRequired的值來檢查這是否是必需的。如果需要,您可以調用object.Invoke([delegate])來調用該方法。

除此之外,您還可以使用調度程序,請參閱MSDNthis blog。快樂閱讀