如何在 Avalonia UI MVVM 中将多个控件绑定到单个模型值而不使模型对象包含 [ObservableProperty]

问题描述 投票:0回答:1

当使用 MVVM Community Toolkit、C#、.NET 和 Avalonia UI 时,我发现自己使模型对象变得可观察,因为它解决了我在从多个控件编辑模型值时遇到的重复出现的问题。

但是,我认为这是不好的做法。有一个 GitHub Repo 支持这个问题,https://github.com/danieljfarrell/QuestionApp1,它是一个演示该问题的 Avalonia UI 应用程序。 enter image description here

简而言之...

我喜欢用简单的属性定义模型对象,

namespace QuestionApp1.Models
{
    public class VolumeSetting
    {
        public int Volume { set; get; }

        public VolumeSetting(int volume)
        {
            Volume = volume;
        }
    }
}

一个单个控件可以很好地编辑它的值。

但是,我经常希望多个控件能够绑定到并改变模型对象属性的值。

在这种情况下,我倾向于使模型对象可观察,

public partial class ObservableVolumeSetting : ObservableObject
{
    [ObservableProperty]
    public int volume;

    public ObservableVolumeSetting(int volume)
    {
        Volume = volume;
    }
}

即使多个控件发生值突变,更改通知现在也会保持值同步。

我听说过这种不好的做法!

  1. 有人可以让我知道使模型对象可观察的危险吗?对于这个特定问题来说,这似乎是一个务实的解决方案
  2. 你能建议更好的方法吗?

非常感谢您的建议。

c# mvvm avaloniaui avalonia community-toolkit-mvvm
1个回答
0
投票

可观察属性只是具有专门更改通知事件的属性。 根据模型的预期用途,使用这种方法没有任何问题。 在模型中使用事件甚至回调方法根本不是一个坏习惯,这就是 MVVM 中应该做的事情。 MVVM 中真正重要的租户只有 3 个:

  1. 如果没有 ViewModel,View 和 Model 无法直接通信。
  2. View 只能直接调用 ViewModel,但 ViewModel 必须使用事件进行通信。 (即 ViewModel 不知道 View 的存在)。
  3. ViewModel 可以直接调用 Model,但 Model 必须使用事件(或回调)进行通信。 (即模型对外界一无所知。)

您需要注意的是不允许视图订阅这些事件。 如果视图直接感知模型,那么您就失去了 MVVM 提供的隔离性。

通常,当我需要特定行为时,我会使用自己的事件而不是实现 INotfiyPropertyChanged。 虽然整体行为没有什么不同,但视图无法真正对任何其他事件做出反应,因此它阻止了模型的不当使用。 这种方法的缺点是您无法使用 CommunityToolkit 中方便的生成器属性来执行此操作。

© www.soinside.com 2019 - 2024. All rights reserved.