我有一个界面IScreenViewModel,为了简化我可以
的问题RedScreenViewModel : IScreenViewModel
GreenScreenViewModel : IScreenViewModel
等。 这意味着我有一个RedScreenView.xaml,它可以生成一个RedScreenViewModel实例,同样适用于所有后续的彩色屏幕。
IScreenViewModel has some properties that you must implement e.g.
interface IScreenViewModel
{
public Color ScreenColor{get;set;}
}
我有一个ViewmodelWrapper类,它包含所有viewmodels实例。 ScreenViewModels,MenuViewModels等...... 因为我使用的是DevExpress,所以我无法直接在Main.xaml.cs文件中绑定DataContext,原因我还不知道。 所以以主要为例。 我不能拥有
ScreenLabel.DataContext = viewModelWrapper.ScreenViewModel
我必须做的主要是:
DataContext = viewModelWrapper;
这样,父窗口可以看到所有子元素。
在RedScreenView.xaml中,我可以这样:
<Label Background="ScreenViewModel.ScreenColor"/>
希望数据绑定应该在ViewModelWrapper中查找IScreenViewModel.ScreenViewModel对象,并使用动态绑定/多态性使用正确的ScreenColor对象。
有些情况下,屏幕可以有更多属性,所以让我们说
GreenScreenViewModel继承了ScreenColor属性,它可以拥有自己的属性DifferentProperty
。
问题是:我有一个Factory,它根据用户想要的屏幕返回一个屏幕对象。它返回正确的屏幕对象,但当它通知View更新自身时,它会查看新对象,但使用错误的XAML 。如果那有意义的话。 我在ViewModelWrapper方法中执行类似的操作。
MainGui.ScreenWrapper.LayoutRoot.Clear() ;
MainGui.ScreenWrapper.Items.Clear() ;
MainGui.ScreenWrapper.LayoutRoot.Add(screenFactory.GetSelectedScreen("RedScreen").GetLayoutRoot()
MainGui.UpdateLayout() ;
ScreenViewModel = screenFactory.GetSelectedScreen("RedScreen").GetViewModel() ;
忽略我两次打电话给工厂的事实...... ScreenWrapper是用于保存屏幕的LayoutGroup。当我使用该代码交换视图(屏幕)时,我希望它将使用正确的绑定。 因此,假设我从GreenScreenViewModel交换到RedScreenViewModel,请记住GreenScreenViewModel比RedScreenViewModel多一个属性,在GreenScreenView中,我有类似这样的内容:
<Label Content="ScreenViewModel.DifferentProperty"/>
当完成交换并且ScreenViewModel通知现在指向RedScreenViewModel时,它会抛出异常。我强烈认为这是因为布局没有刷新,它仍然使用错误的视图。 调试模式下的输出错误是 “在viewModelWrapper.ScreenModel中找不到属性DifferentProperty” 这是不对的,因为我已经删除了那个GreenScreenView,我更新了布局,我知道有一个LayoutChanged事件或类似的东西,所以可能已经提出了,那么为什么它仍然看到错误的视图? 如何更新ScreenWrapper.LayoutRoot以使用不同的绑定代码“查看”新视图。 天哪,我希望很清楚。 编辑:迈克尔感谢您的回复。是的,在我使用的第三方dll中有一个实际的异常 - “NullReferenceException”。那是因为它无法找到属性。我确信我没有说清楚,但也许问题应该是:当从可视树中删除和插入用户控件时 - 我可以刷新可视树以查看新绑定吗?如果我可以刷新可视树,它应该解决我的问题。 UpdateLayout()不起作用
编辑: 迈克尔谢谢你的回复。是的,在我使用的第三方dll中有一个实际的异常 - “NullReferenceException”。那是因为它无法找到属性。当我调用OnPropertyChanged时抛出异常,是的,处理程序不为null! 我确信我没有说清楚,但问题应该是: 从可视树中删除和插入用户控件时 - 如何刷新可视树以查看新绑定?如果我可以刷新可视树,它应该解决我的问题。 UpdateLayout()不起作用。
答案 0 :(得分:0)
首先,你说
因为我使用的是DevExpress,我无法直接在Main.xaml.cs文件中绑定DataContext,原因我还不知道。
快递不应该是这里的问题。您需要绑定到的东西将返回相应的ViewModel。看看here有关此主题的讨论。
其次,你说错误是
在viewModelWrapper.ScreenModel
中找不到属性DifferentProperty
这不一定是个问题,也不会引起异常。当您动态更改绑定时,INotifyPropertyChanged事件会飞到各处,并且可能存在一段“不确定性”。我假设您的ViewModel实现了INotifyPropertyChanged。
我认为密钥可能正在仔细查看异常,如果有的话(因为“找不到属性”是调试消息,而不是异常)。为了清楚起见,您可能希望关闭绑定消息,如here所述。如果存在实际异常,请编辑详细信息。