我希望有一个与应用程序的主UI线程关联的表单拥有其他几个表单,每个表单都有自己的线程(每个表单都与一个硬件相关联,我希望在这些表单上处理更新即使主表格忙碌一秒左右也会形成表格。所有权的主要目的是保持窗口堆叠行为(拥有的表单按Z顺序保持在所有者之上,但不强制在其他应用程序的窗口之上)。
关于SO的许多问题都询问了如何做到这一点,并且答案表明,在更改所有权时可能会将CheckForIllegalCrossThreadCalls
简要地设置为错误,但会被警告对话,表明人们暗示该方法不知道是否真的很安全。
我可以看到这些方法至少有两个可能的问题:
更改表单的Owner
会有效地呼叫其所有者的AddOwnedForm
和/或RemoveOwnedForm
。我不希望将CheckForIllegalCrossThreadCalls
设置为false会使该方法成为线程安全的。如果同时显示或隐藏绑定到不同线程的多个表单,则可能存在问题。我希望使用类似NewOwner.Invoke(() => NewOwner.AddOwnedForm(this))
的内容可以缓解这个问题。
据我所知,CheckForIllegalCrossThreadCalls
是一个全球财产。因此,我担心如果两个线程同时将其设置为false,则一个线程可能将其设置为true,而另一个线程仍然需要将其设置为false。将CheckForIllegalCrossThreadCalls
清除并重新设置为传递给跨线程Invoke
的方法的一部分似乎可以解决问题,如果主UI线程是唯一一个写入该线程的线程属性,但我不知道是否有任何.NET UI代码中的“隐藏”属性的写入。
目前,相关申请仅供内部使用。另一方面,拥有一种可以被认为足够强大的生产代码的方法会很好。自从其他答复写完以来,这方面是否有任何新的发现?建议的方法(在主线程中处理所有权获取/释放)是否足以使事情变得健壮?
PS - 如果有一些方法可以让子MDI窗口使用其他线程,那就更好了;从概念上讲,没有理由为什么这是不可能的(在父窗口的子窗口列表中添加或删除子窗口时,与父MDI窗口相互影响的唯一效果就是这种情况(类似于拥有窗口的情况),或者移动子窗口并暴露一些父窗口(这非常类似于移动某些其他应用程序窗口的情况并暴露父窗口 - 显然是WinForms常规处理的情况)。