看板 C_Sharp 關於我們 聯絡資訊
1.原本的做法 // 有一方法可以create出Canvas物件 private Canvas createCanvas(string canvasString) { .... } // 今天有某個迴圈建立了Canvas的集合 IList<Canvas> canvasList = new List<Canvas>(); for(....) { canvasList.Add(createCanvas(..)); } // 再把Canvas集合加到同一個Canvas, 目前為止是ok的 Canvas canvas = new Canvas(); foreach(Canvas c in canvasList) { canvas.Children.Add(c); } 2. 我遇到的問題...多執行緒的做法 // 在上述的第二個迴圈改為 // inner class class ThreadParameter { public string CanvasContentString { get; set; } public IList<Canvas> CanvasList { get; set; } } void ThreadMethod(object obj) { ThreadParameter para = (ThreadParameter)obj; para.CanvasList.Add(createCanvas(para.CanvasContentString)); } IList<Canvas> canvasList = new List<Canvas>(); IList<Thread> threadList = new List<Thread>(); for(...) { ThreadParameter para = new ThreadParameter() { CanvasList = canvasList, CanvasContentString = ...}; Thread t = new Thread(new ParameterizedThreadStart(ThreadMethod)); t.SetApartmentState(ApartmentState.STA); threadList.Add(t); t.Start(para); } foreach(Thread t in threadList) { // 等待執行緒跑完 t.Join(); } // 以上都還沒問題, 以下就是問題, Add到canvas的過程發生Exception Canvas canvas = new Canvas(); foreach(Canvas c in canvasList) { canvas.Children.Add(c); } 例外訊息為 "呼叫執行緒無法存取此物件,因為此物件屬於另一個執行緒" 不知道怎辦 試了Dispatcher的做法 Canvas canvas = new Canvas(); foreach(Canvas c in canvasList) { canvas.Dispatcher.Invoke(DispatcherPriority.Normal, new AddOverLapXaml(canvas.Children.Add), c); } delegate int AddOverLapXaml(UIElement ui); 但仍然有Exception "引動的過程傳回例外" 請問在WPF中 如果是不同Thread所建立的物件想要Add或被Add到UIElementCollection 那個做法是什麼 雖然都用主執行緒可以執行, 但效能真得有差 感恩 -- ※ 發信站: 批踢踢實業坊(ptt.cc) ◆ From: 60.251.1.226 ※ 編輯: kairy 來自: 60.251.1.226 (10/25 09:50)
zhadow:canvas.Dispatcher 改成 Application.Current.Dispatcher 10/25 23:49
zhadow:或用 window的 dispatcher 試看看 10/25 23:51
kairy:To 樓上的板友, 我剛剛試了, 結果還是不行, 錯誤訊息是 10/26 07:38
kairy:"引動過程的目標傳回例外狀況。", InnerException是 10/26 07:39
kairy:{"呼叫執行緒無法存取此物件,因為此物件屬於另一個執行緒。 10/26 07:39
kairy:不過還是非常感謝您~ 10/26 07:39
zhadow:那把 canvas 的create 放在UI thread中,如果 canvas 的 10/26 16:13
zhadow:create 中跟ui無關且會佔用cpu太久的部份再另外用thread做 10/26 16:14