让ViewModel调用Actions而不是执行命令和发布事件

本文关键字:布事件 事件 命令 执行 调用 ViewModel Actions | 更新日期: 2023-09-27 18:15:29

在这个假设的问题中,假设ViewModel发布了一个View订阅的相当复杂的事件。然后View根据该事件中的状态操作多个屏幕元素。例如,几个按钮被设置为可见/隐藏,或启用/禁用,或者可能启动一个故事板。

// purely as an example:
public class SomeEvent
{
    public bool ShouldShowAddButton { get; set; }
    public bool ShouldShowDeleteButton { get; set; }
    public bool AddButtonEnabled { get; set; }
    public bool DeleteButtonEnabled { get; set; }
}

因为VM不知道关于View的任何事情,它实际上不能到达并做这些事情,而是依赖于事件。我想这是MVVM的标准做法。(另一种选择是将这些项目中的每一个都作为它们自己的发布事件,一个接一个地发送。)

然而,如果VM可以在不知道任何关于视图的情况下调用视图呢?

public class MyViewModel
{
    public Action OnShowAddButton { get; set; }
    public Action OnShowDeleteButton { get; set; }
    ...etc
    private void OnSomeStateChange()
    {
        // here, we'd normally publish the SomeEvent class
        // instead, we could just call OnShowAddButton (or whatever) instead
    }
}
public class MyView
{
    public MyView()
    {
        this.myViewModel.OnShowAddButton = () => ...;
        ...etc
    }
}

除了这不是MVVM设计的"典型"之外,还有什么原因会让人皱眉吗?据我所知,它仍然保持正确的分隔水平。

让ViewModel调用Actions而不是执行命令和发布事件

我认为这种变化是混合了一点MVC和一点MVVM,虽然它两者都不是。因此,通过将模型直接注入视图实现中,然后通过事件发送某种命令,可以解决模式的Model-View部分。

然后,您需要解决或绕过模式的View-Model部分,方法是在模型中提供可由视图直接设置的属性,或者在视图中公开一些事件并在模型中进行相同类型的注入。

我觉得会很难看。即使模型只是一组可观察实体,你从其他地方控制它们(控制器?:))。

我已经可以看到代码,无数的事件和属性混合在一起…但这都取决于你的UI会变得多复杂,你会有多少视图,它们会变得多复杂。在有10多个按钮和/或输入的视图中,我认为采用这种方法是一个坏主意。

我说,只要你没有一个专用的MVVM基础设施,如WPF或HTML,就没有必要实现你自己的。仅靠手工编码的框架是无法达到如此美妙的分离程度的。你需要一些支持来完全分离UI代码和模型,做绑定等等。

也许你可以评论一下你想用它做什么。如果你需要它用于客户端框架(如HTML/JS)或Windows窗体实现,那么你可以使用一些专用的解决方案,或者更好的是,你可以采用一些更简单的路径。

这一切都来自于一个在ASP之上实现MVP变体的家伙。NET Web窗体。要是时光能倒流就好了。