0
votes

I've got a small WPF form with a Listview (bound to an observablecolletion)

    <ListView Name="Employees_Listview" ItemsSource="{Binding Employees, UpdateSourceTrigger=PropertyChanged}" SelectedItem="{Binding YourSelectedItem, Mode=TwoWay}" Height="86" IsSynchronizedWithCurrentItem="True">
        <ListView.View>
            <GridView>
                <GridViewColumn Header="FirstName" DisplayMemberBinding="{Binding FirstName}"/>
                <GridViewColumn Header="LastName" DisplayMemberBinding="{Binding LastName}"/>
            </GridView>
        </ListView.View>
    </ListView>

2 textboxes

<TextBox Name="FirstName" Width="136" Text="{Binding SelectedItem.FirstName, ElementName=Employees_Listview, Mode=TwoWay}" />
<TextBox Name="LastName" Width="136" Text="{Binding SelectedItem.LastName, ElementName=Employees_Listview, Mode=TwoWay}" />

and a button

<Button Command="{Binding UpdateEmployeeCommand}" Margin="0,0,10,0">Update</Button>

Both textboxes are bound to the selected item in listview so when I update a textbox value it will automatically reflect the changes in the listview. Now I would like to update the database first and if there is no error I would like to update the listview. My update code looks like this

    var container = ContainerConfig.Configure();
    using (var scope = container.BeginLifetimeScope())
    {
        var SelectedEmployee = scope.Resolve<IEmployeeRepository>();
        if (!SelectedEmployee.Update(YourSelectedItem))
        {
            MessageBox.Show("Datensatz konnte nicht aktualisiert werden!" + "\n" + "Bitte den Administrator verständigen!");
            return;
        };
    }

I tried to set the textbox mode to OneWay but due the fact it's bound to the SelectedItem I can't get the new textbox value, only the "old" listview value. How can I check and update my database first before refreshing the listview?

UPDATE Maybe I have to choose another approach like this: TextBox bound a new property declared

View

<TextBox Text="{Binding NewFirstName}" Width="123"></TextBox>

and my ViewModel

//TEST
private string newfirstname;


public string NewFirstName
{
    get { return newfirstname; }
    set
    {
        newfirstname= value;
        RaisePropertyChanged("NewFirstName");
    }
}
//TEST
public EmployeeEntity YourSelectedItem
{
    get
    {
        return _yourSelectedItem;
    }
    set
    {
        NewFirstName = value.FirstName;
        _yourSelectedItem = value;
        RaisePropertyChanged("YourSelectedItem");
    }
}

Guess this is not the best way to go :/

1
Are you saying that the ListView updates but the TextBox values do not? - Chris Mack
No, it's working correctly (click on ListView item --> FirstName and LastName are filled out based on selection - immediately --> update text in textBox --> ListView is updated immediately). What I want to do is update the source (ObservableCollection) AFTER I have updated my database so in case of an error I can stick with the old value. Unfortunately my textboxes are bound directly to my ListView so I guess I have to create a new property (please see my updated question ) - Moritz

1 Answers

1
votes

I would do it like this:

  1. Update the database.
  2. Either return the updated data entity from the update method, or, query the database after the update to retrieve the updated data entity.
  3. Update the object in your application with the new values.

I would strongly recommend having a unique identifier/ID both in your database and in your classes within the application to facilitate this if you don't already.

Also, you'd need to have INotifyPropertyChanged implemented on your Model classes, as updating an item within an ObservableCollection won't have any impact on your View, as ObservableCollection only raises notifications when the collection itself changes, e.g., add/remove, and not when properties within its members change.