所以我正在开发一个带有在应用程序(主应用程序)中使用的UI的插件。为了在主应用程序工作时使我的UI响应,我将在其单独的线程中启动我的UI,如下所示:
public void ShowDialog(IIFCConverter ifcConverter)
{
thread = new Thread(x =>
{
thread.Name = "UI-thread";
window = new MainWindow();
var mainViewModel = ServiceLocator.Current.GetInstance<MainWindowViewModel>();
mainViewModel.SetIFCConverter(x as IIFCConverter);
ViewModelLocator.MainWindow = window;
window.ShowDialog();
});
thread.SetApartmentState(ApartmentState.STA);
thread.Start(ifcConverter);
}
我第一次启动插件时一切正常。第二次我启动它并尝试引发事件(比如OnCollectionChanged)我得到一个带有消息的NotSupportedException:“这种类型的CollectionView不支持从不同于Dispatcher线程的线程更改其SourceCollection”
这是我的方法之一:
private void AddNewFile(AddNewFileMessage obj)
{
if (!(obj.Sender is ButtonViewModel)) return;
if (string.IsNullOrEmpty(obj.Path)) return;
var ifcFileViewModel = new IFCFileViewModel(new Common.Model.IFCFile { Path = obj.Path, Active = true });
DispatcherHelper.CheckBeginInvokeOnUI(() =>
{
ListBoxItems.Insert(ListBoxItems.Count - 1, ifcFileViewModel);
});
}
我得到了这个事件,尽管我正在使用MVVM灯的DispatcherHelper。 我尝试使用“普通”调度程序,但这给了我相同的结果。
首先,我很想知道它为什么这样做的机制? 我检查了我的线程,我可以看到从我的UI线程调用OnOllectionChanged。 我似乎无法找到第一次运行(有效)和以下之间的线程结构的任何差异。
其次,我该怎么办呢?
我测试的东西没有帮助:
实际上有效的方法是将动作包装在try Catch-block中,如下所示:
private void AddNewFile(AddNewFileMessage obj)
{
if (!(obj.Sender is ButtonViewModel)) return;
if (string.IsNullOrEmpty(obj.Path)) return;
var ifcFileViewModel = new IFCFileViewModel(new Common.Model.IFCFile { Path = obj.Path, Active = true });
DispatcherHelper.CheckBeginInvokeOnUI(() =>
{
try
{
ListBoxItems.Insert(ListBoxItems.Count - 1, ifcFileViewModel);
}
catch(Exception ex)
{
}
});
}
然而,我觉得这很难看,想避免它,为什么这样做呢?当我将所有动作包装在try Catch-blocks中时,一切似乎都能正常工作。
答案 0 :(得分:2)
好的,所以我找到了真正的问题。 视图模型确实是在与我的插件UI相同的线程上创建的。
但是:我正在使用MVVMLight工具包中可用的Messenger来处理视图模型之间的通信,而我忘记在我的窗口关闭时取消注册视图模型。所以我第二次打开窗口并开始在我的视图模型之间发送消息。第一个视图模型做出反应,这就是导致问题的原因。 这也是try-Catch-block工作的原因,因为有正确的线程进行了第二次调用。 我在viewmodel的构造函数中添加了一个datetime,并且确实调用了两个不同的viewmodel。我不明白为什么我得到那个例外。如果有的话,第一个视图模型应该通过datacontext连接到第一个视图。它就像视图已经连接到两个不同视图模型的事件。
无论如何,它现在有效:我只是在我的窗口关闭时从消息服务取消注册视图模型,它就像一个魅力。
答案 1 :(得分:0)