0

I am trying to call a method when I update one of the fields in my DataGrid. Right now, I have tried multiple different options but none will even call a method or DelegateCommand I have created. Here is the code for my DataGrid:

<DataGrid x:FieldModifier="public" x:Name="Classes" CanUserAddRows="False" AutoGenerateColumns="False" CanUserResizeColumns="False" AlternatingRowBackground="LightBlue" ItemsSource="{Binding Classes, Mode=TwoWay}" SelectedItem="{Binding SelectedClass}" >
        <DataGrid.Columns>
            <DataGridTextColumn Width="200" Header="Class" Binding="{Binding Class, Mode=TwoWay}" IsReadOnly="True"/>
            <DataGridTextColumn Width="200" Header="Semester" Binding="{Binding Semester, Mode=TwoWay}" IsReadOnly="True"/>
            <DataGridTextColumn Width="200" Header="Date Due" Binding="{Binding Date_Due, Mode=TwoWay, UpdateSourceTrigger=LostFocus}" />
            <DataGridTextColumn Width="200" Header="Importance" Binding="{Binding Importance, Mode=TwoWay}" IsReadOnly="True"/>
        </DataGrid.Columns>
    </DataGrid>

The Data Grid is bound to an Observable collection of an object I created. When the user updates the Date_Due field, I want to call a method in my ViewModel to update the database with the change. How would I go about doing this?

I am using an MVVM pattern so I don't have any code-behind.

Any help is appreciated.

anonymous-dev
  • 2,356
  • 2
  • 11
  • 17
  • Does `Date_Due` utilise `INotifyPropertyChanged`? – mjwills Aug 25 '17 at 23:05
  • The UI _should_ not be aware that this is going on. You are already getting an update through the property. You can wrap your data object so that changes to the `Date_Due` property propagate to the database. DynamicProxy could be helpful if you need this a lot of times. – Dennis Kuypers Aug 25 '17 at 23:07
  • It doesn't @mjwills, could that possibly solve my problem. – anonymous-dev Aug 25 '17 at 23:11
  • To summarize what you suggested @DennisKuypers, I could use something called DynamicProxy to update the data in the database when it is changed in the datagrid? – anonymous-dev Aug 25 '17 at 23:12
  • @SamMallabone I'll post an answer in a bit. Castle.DynamicProxy can be helpful if you start wrapping a lot of classes – Dennis Kuypers Aug 25 '17 at 23:17
  • `could that possibly solve my problem` Yes. – mjwills Aug 26 '17 at 00:37
  • Possible duplicate of [Raise an event whenever a property's value changed?](https://stackoverflow.com/questions/2246777/raise-an-event-whenever-a-propertys-value-changed) – mjwills Aug 26 '17 at 00:37

1 Answers1

1

You can wrap all of your ClassInfo-dataobjects (the object in the collection) with a thin layer that does your special logic (updating the DB).

// Your data object
public class ClassInfo
{
    public string Class { get; set; }
    public string Semester { get; set; }
    public DateTime Due { get; set; }
    public string Importance { get; set; }
}

// something that takes care of the update
public interface IDatabase
{
    void SendClassInfoUpdate(ClassInfo ci);
}

// a thin wrapper
public class ClassInfoViewModel
{
    IDatabase _db;
    ClassInfo _ci;

    public ClassInfoViewModel(IDatabase db, ClassInfo ci)
    {
        _db = db;
        _ci = ci;
    }

    public string Class
    {
        get => _ci.Class;
        set => _ci.Class = value;
    }
    public string Semester
    {
        get => _ci.Semester;
        set => _ci.Semester = value;
    }
    public DateTime Due
    {
        get => _ci.Due;
        set
        {
            _ci.Due = value;
            _db.SendClassInfoUpdate(_ci);
        }
    }
    public string Importance
    {
        get => _ci.Importance;
        set => _ci.Importance = value;
    }
}

The view doesn't know that it is dealing with your wrapper. This is also a fine way to prevent access on properties, add "view only" properties (calculated properties) and such. If you are doing INPC, you would have to proxy that as well.

You see a lot of code that only exists to proxy the calls to the inner object. That is what for example Castle.DynamicProxy can help you with. It provides an dynamic way to add such wrappers.

Dennis Kuypers
  • 546
  • 4
  • 16