在 View 中访问 ViewModel 数据

Accessing ViewModel data in View

我只想问一下View后台访问ViewModel's数据是否可以?

基本上我只需要检查一下是否设置了 ViewModel's 属性(当用户 select 时设置),如果没有,我会只需将用户重定向到另一个 View 告诉他他需要先 select 一些东西。这是一个糟糕的设计实践还是可以,只是为了像这样的小检查?真的不想实现静态 class 并将数据外推到它,而是检查它。

另一个与此密切相关的问题是,我可以从 View 调用一个方法(当 View 关闭时),从 IoC 容器中注销那个特定的 ViewModel (这个 ViewModel 不是单例)。另一种方法是在 View 关闭时从视图向 ViewModel 发送消息,当 ViewModel 收到该消息时,它会自行注销。我试图解决的问题是,每次请求 ViewModel 时,它都必须是一个新的,但我的 IoC 容器缓存了它们,使我的程序成为内存大户。所有 ViewModels 都在应用程序退出时释放,这意味着 x ViewModels 仍将存在于缓存中,即使它们很可能不需要。

Basically I just need a check to see if a ViewModel's property is set (which gets set when the user selects something), and if it's not I'll just redirect the user to another View telling him he needs to select something first. Is this a poor-design practice or is it OK, just for a minor check like this?

查了一些ViewModel属性的值,反映在View这边的变化好像也没有错。 View 状态可以通过 WPF 数据绑定机制“绑定”到 ViewModel 状态:BindingTriggersTriggerDataTrigger , EventTrigger), Commands (包括EventToCommand), 等等

但有时 ViewModel 本身使用 UI 服务来处理 ViewModel 状态更改很有用。例如,可以引入 IWindowService 接口以允许从 ViewModel 实现的上下文中打开 windows。

Another question tightly related to this, is can I call a method from the View (when the View is closing), that unregisters that particular ViewModel from the IoC container (this ViewModel isn't singleton).

...

The problem I'm trying to solve with this is that, every time that ViewModel is requested it has to be a new one, but my IoC container caches them, making my program a memory hog. All of the ViewModels get released on application exit, meaning x ViewModels will still exist in the cache even though they're most likely not needed.

当注册被指定为“resolve per call behavior”(不是“singleton behavior”)时,描述的依赖容器“缓存效应”存在,这似乎很奇怪。请检查注册是否指定为“解析每次调用行为”(例如,PerResolveLifetimeManager 表示 Unity Container Lifetime Managers)。

更新

由于使用了 SimpleIoC 容器,因此存在 ViewModel 生命周期问题。 我想推荐使用另一个依赖注入容器(具有适当的生命周期管理)来使实现不那么复杂和容易出错。

但是,如果 强烈需要 使用 SimpleIoC 容器,可以使用以下方法实现某种 ViewModel 生命周期管理:

  • SimpleIoc.Default.GetInstance<ViewModel>(key); 方法调用以解析 ViewModel;
  • 的实例
  • SimpleIoc.Default.Unregister(key); 在不再需要时注销实例(Closed 事件等)。

可以在此处找到实现:answer #1, answer #2