WPF / MVVM /模型不更新视图模型

时间:2019-09-17 00:26:54

标签: c# wpf mvvm model viewmodel

上下文:

  • 我的MVVM应用程序中的绑定属性有问题。现在,我做了一个小项目来测试这个案例。它仅包括窗口,视图模型,模型,BindableObject(具有INotifyProperyChanged的抽象类)和Command类。所有类都在同一个命名空间中,在视图中设置了datacontext,模型和vm具有INotifyProperyChanged,视图中的文本绑定到了绑定到模型属性的vm属性。构造函数设置模型属性,它会影响viewmodel和view中的属性。

问题:

  • 当我更改模型中的属性时,它不会更改viewmodel和view中的属性。

这是BaseModel和Command类:

    abstract class BindableObject : INotifyPropertyChanged
    {
        public event PropertyChangedEventHandler PropertyChanged;
        public void OnPropertieChanged ([CallerMemberName]string name = "")
        {
            PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(name));
        }
    }


    class Command : ICommand
    {
        private Action<object> execute;
        private Func<object, bool> canExecute;

        public Command(Action<object> execute, Func<object, bool> canExecute = null)
        {
            this.execute    = execute;
            this.canExecute = canExecute;
        }

        public event EventHandler CanExecuteChanged
        {
            add     { CommandManager.RequerySuggested += value; }
            remove  { CommandManager.RequerySuggested -= value; }
        }

        public bool CanExecute(object parameter)
        {
            return this.canExecute == null || this.canExecute(parameter);
        }

        public void Execute(object parameter)
        {
            this.execute(parameter);
        }
    }

型号:

    public class Model : BindableObject
    {
        private int modelValue;
        public int ModelValue { get => modelValue; set { modelValue = value; OnPropertieChanged(); } }

        public Model ()
        {
            ModelValue = 111;
        }

        public void ChangeValue ()
        {
            ModelValue = 777;
        }

    }

ViewModel:

    class MainVM : BindableObject
    {
        private int myValue;
        public int MyValue { get => myValue; set { myValue = value; OnPropertieChanged(); } }

        public ICommand Command1 { get; set; }

        public MainVM()
        {
            var model = new Model();
            MyValue  = model.ModelValue;
            Command1 = new Command( (obj) => model.ChangeValue() );
        }

    }

查看:

    <Window>
    ...
        <Window.DataContext>
            <local:MainVM/>
        </Window.DataContext>

        <StackPanel>
            <TextBlock Text="{Binding MyValue}"/>
            <Button Command="{Binding Command1}"/>
        </StackPanel>

    </Window>

1 个答案:

答案 0 :(得分:0)

问题是视图模型中的命令正在调用模型实例上的方法,但是xaml绑定到类型为int(MyValue)的视图模型中的单独属性。这就是为什么MyValue在vm构造函数中设置一次,但从未使用命令进行更新的原因。

使Model类的实例成为视图模型中的属性:

        private Model _myModel;

        public Model MyModel
        {
            get
            {
                return _myModel;
            }
            set
            {
                _myModel = value;
                OnPropertieChanged();
            }
        }

        public ICommand Command1 { get; set; }

        public MainVM()
        {
            MyModel = new Model();           
            Command1 = new Command((obj) => MyModel.ChangeValue());
        }

并绑定到xaml中的ModelValue属性。

    <StackPanel>
        <TextBlock Text="{Binding MyModel.ModelValue}"/>
        <Button Height="50" Width="100" Command="{Binding Command1}"/>
    </StackPanel>

但是,通常,模型类通常不执行逻辑。相反,逻辑要么在服务类中的模型实例上执行,要么在视图模型中的客户端上执行。但这是一个单独的讨论。

相关问题