它启动时,将数据传递给新的视图模型的最佳途径 [英] Best Way to Pass Data to new ViewModel when it is initiated

查看:90
本文介绍了它启动时,将数据传递给新的视图模型的最佳途径的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我的工作使用MVVM光强的框架WPF数据库应用程序。我使用SimpleIOC注入我的数据服务,和我的ViewModels连接到从XAML文件中的视图。但是,打开新的视图模型时,我通常也需要通过另一个目的是视图模型(可以说我传递一个CarId的整数,这样我就可以抓住从数据库中实际的汽车)。

I am working on an WPF database application using the MVVM-Light Framework. I am using SimpleIOC to inject my Data Services, and my ViewModels are connected to the view from the XAML file. However, when opening new View Models I usually also need to pass another object to the View Model (lets say I am passing a integer of a CarId so I can grab the actual Car from a database).

现在我通过这个使用上查看的使者,在InitializeComponent()之后。这然后被视图模型捕获。目前这不工作,但是它有一些挫折。

Right now I am passing this by using a messenger on the View, after InitializeComponent(). This is then caught by the View Model. This currently does work, however it has some set backs.

首先,消息不会发送到视图模型的构造函数被调用后。可以说,我曾在一个视图模型对象ThisCar财产,我有继发性就像一个被称为品牌的字符串,返回ThisCar.Brand。

First, the Message does not get sent until after the Constructor of the View Model is called. Lets say I had a ThisCar object Property in the ViewModel, and I had secondary properties like a string called Brand, that returns ThisCar.Brand.

    public const string ThisPersonPropertyName = "ThisCar";
    private Model.Car _thisCar;
    public Model.Car ThisCar
    {
        get
        {
            return _thisCar;
        }

        set
        {
            if (_thisCar== value)
            {
                return;
            }

            RaisePropertyChanging(ThisCarPropertyName);
            _thisCar= value;
            RaisePropertyChanged(ThisCarPropertyName);
        }
    }

    public const string BrandPropertyName = "Brand";
    public string Brand
    {
        get
        {
            return ThisCar.Brand;
        }

        set
        {
            if (ThisCar.Brand == value)
            {
                return;
            }

            RaisePropertyChanging(BrandPropertyName);
            ThisCar.Brand = value;
            RaisePropertyChanged(BrandPropertyName);
        }
    }

现在,当构造函数被调用,我必须初始化ThisCar在视图模型构造像这样,否则我得到的时候视图模型被创建ThisCar.Brand空的错误。

Now when the constructor gets called, I have to initialize ThisCar in the View Model Constructor Like so, otherwise I get a null error on ThisCar.Brand when the ViewModel gets created.

ThisCar = new CarObject();



然后,它被初始化为空对象后,该消息将被调用,我会拉从根据汽车ID数据库实车

Then, after it is initialized to an empty object, the Message will get called, and I will pull the real Car from the Database based on the Car ID.

ThisCar = webService.GetCar(carId);



然而,当我这样做,对品牌资产没有更新,因为没有被调用OnPropertyChanged为品牌。

However, when I do this, the Brand Property does not get updated, because nothing is calling the OnPropertyChanged for the Brand.

我有两个变通,但他们感觉更像是黑客给我。首先上手动调用OnPropertyChanged对于需要更新的属性。二是我删除所有的小属性,并直接绑定一切的ThisCar财产(这意味着我必须实现INotifyPropertyChanged在我的模型)。

I have two work arounds, but they feel more like hacks to me. First on is manually calling the OnPropertyChanged for any properties that need to be updated. Second is I remove all the small properties, and bind everything directly to the ThisCar property (which means I have to implement INotifyPropertyChanged in my model).

请让我知道如果我只是被挑剔,或者如果有更好的方法来做到这一点。我这样做的方式工作,但就是不跟我的权利坐。谢谢你。

Please let me know if I am just being picky, or if there is a better way to do this. The way I am doing it works, but just doesn't sit right with me. Thank you.

推荐答案

好了,这里是我想出了,请让我知道这是一个可怕的想法。

Ok, so here is what I came up with, please let me know if this is a horrible idea.

我创建了一个名为IRepository因为我使用依赖注射,以创建视图模型接口。下面是执行:

I created an Interface called IRepository since I am using Dependency Injections to create View Models. Here is the implementation:

public interface IRepository
{
    void GetCarId(Action<int> callback);
    void SetCarId(int value);
}



接下来,我创建一个从IRepository

Next I create a class which inherits from IRepository

public class Repository : IRepository
{
    private int CarId;
    public void GetCarId(Action<int> callback)
    {
        callback(CarId);
    }

    public void setDictionary(int carId)
    {
        CarId = carId;
    }
}

现在的值传递到存储库中,我把这到父视图模型

Now to pass the value into the repository, I put this into the parent View Model

 r.SetCarId(13);

和在我把这个在视图模型构造新的视图模型收到:

And to recieve in the new view Model I put this in the View Models Constructor:

    public View2ViewModel(IChildView i, IRepository r)
    {
        int CarId;
        r.GetCarId((id) => CarId = id);
        thisCar = GetCarFromDatabase(CarId);
    }

这在我看来,解决问题,不打破MVVM模式,因为我使用IoC容器创建所有的接口成员为staic,我会在我的意见中,这家数据。

This seems to me to fix the problem, without breaking the MVVM pattern, and since the IOC Container I am using creates all the Interface Members as staic, I will have this data throughout the rest of my Views.

主要的问题我有这这感觉就像一个全局变量,但是这是我能想出它是最好的。请让我知道这是一个非常糟糕的主意。谢谢你。

The main problem I have with this is that it feels like a global variable, but this is the best I could come up with on it. Please let me know if this is a really bad idea. Thank you.

这篇关于它启动时,将数据传递给新的视图模型的最佳途径的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆