使用绑定和MVVM模式更改WPF ComboBox选择以匹配给定值

时间:2017-12-05 11:10:04

标签: wpf vb.net mvvm

我刚开始使用WPF和MVVM模式进行冒险。在我的项目中,我有DataGrid,它通过Entity Framework从SQL数据库填充 - 一切正常。现在我正在尝试添加基本功能 - 添加,编辑和删除此DataGrid和底层数据库表中的数据。它将通过新的对话窗口完成,其中包含用于编辑数据行中每个字段的控件。这是代码片段。 DataGrid和按钮:

                   <DataGrid x:Name="RouteListDataGrid" Grid.Column="0" Grid.Row="3" IsReadOnly="True" ItemsSource="{Binding RouteList}" SelectedItem="{Binding RouteSelected}" SelectionMode="Single"/>
                    <StackPanel Grid.Column="0" Grid.Row="4" Orientation="Horizontal">
                        <Button Content="➕" Click="OpenRouteDialogAdd"/>
                        <Button Content="" IsEnabled="{Binding SelectedItems.Count, ElementName=RouteListDataGrid, Mode=OneWay}" Click="OpenRouteDialog"/>
                        <Button Content="➖" IsEnabled="{Binding SelectedItems.Count, ElementName=RouteListDataGrid, Mode=OneWay}" Command="{Binding RouteCmdDelete}"/>
                    </StackPanel>

在添加或编辑模式下打开模态窗口的代码:

Private Sub OpenRouteDialog(sender As Object, e As RoutedEventArgs)
    Dim routeDialog As New RouteDialog With {
        .Owner = Me,
        .DataContext = DataContext
    }
    routeDialog.ShowDialog()
End Sub

Private Sub OpenRouteDialogAdd(sender As Object, e As RoutedEventArgs)
    Dim viewModel As MainWindowViewModel = DataContext
    viewModel.RouteSelected = New Trasa
    viewModel.RouteSelected.DataZaladunku = DateTime.Today
    viewModel.RouteSelected.DataDostawy = DateTime.Today
    viewModel.RouteSelected.PojazdID = 1
    viewModel.RouteSelected.KierowcaID = 1
    Dim routeDialog As New RouteDialog With {
        .Owner = Me,
        .DataContext = DataContext
    }
    routeDialog.ShowDialog()
End Sub

对话窗口的XAML:

<Window
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
    xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
    xmlns:local="clr-namespace:MrLogistic"
    xmlns:i="http://schemas.microsoft.com/expression/2010/interactivity" x:Class="RouteDialog"
    mc:Ignorable="d"
    Title="Trasa" Height="300" Width="300" ShowInTaskbar="False" ResizeMode="NoResize" WindowStartupLocation="CenterOwner">
<Window.DataContext>
    <local:MainWindowViewModel/>
</Window.DataContext>    
<i:Interaction.Triggers>
    <i:EventTrigger EventName="Loaded">
        <i:InvokeCommandAction Command="{Binding VehicleCmdGetList}"/>
        <i:InvokeCommandAction Command="{Binding DriverCmdGetList}"/>
    </i:EventTrigger>
</i:Interaction.Triggers>
<Grid>
    <Grid.ColumnDefinitions>
        <ColumnDefinition/>
        <ColumnDefinition/>
        <ColumnDefinition Width="Auto"/>
    </Grid.ColumnDefinitions>
    <Grid.RowDefinitions>
        <RowDefinition/>
        <RowDefinition/>
        <RowDefinition/>
        <RowDefinition/>
        <RowDefinition/>
        <RowDefinition/>
    </Grid.RowDefinitions>
    <TextBlock Grid.Column="0" Grid.Row="0" Text="numer"/>
    <TextBlock Grid.Column="1" Grid.Row="0" Text="1234"/>
    <TextBlock Grid.Column="0" Grid.Row="1" Text="załadunek"/>
    <DatePicker Grid.Column="1" Grid.Row="1" SelectedDate="{Binding RouteSelected.DataZaladunku}"/>
    <TextBlock Grid.Column="0" Grid.Row="2" Text="dostawa"/>
    <DatePicker Grid.Column="1" Grid.Row="2" SelectedDate="{Binding RouteSelected.DataDostawy}"/>
    <TextBlock Grid.Column="0" Grid.Row="3" Text="pojazd"/>
    <ComboBox Grid.Column="1" Grid.Row="3"
              ItemsSource="{Binding VehicleList}"
              SelectedValuePath="PojazdID" DisplayMemberPath="Nazwa"
              SelectedValue="{Binding RouteSelected.PojazdID}"
              IsSynchronizedWithCurrentItem="True"/>
    <TextBlock Grid.Column="0" Grid.Row="4" Text="kierowca"/>
    <ComboBox Grid.Column="1" Grid.Row="4"
              ItemsSource="{Binding DriverList}"
              SelectedValuePath="KierowcaID" DisplayMemberPath="Nazwisko"
              SelectedValue="{Binding RouteSelected.KierowcaID}"
              IsSynchronizedWithCurrentItem="True"/>
    <TextBlock Grid.Column="0" Grid.Row="5" Text="opis"/>
    <TextBox Grid.Column="1" Grid.Row="5" Text="{Binding RouteSelected.Opis}"/>
    <StackPanel Grid.Column="2" Grid.Row="0" Grid.RowSpan="6">
        <Button Content="✔" IsDefault="True" Click="Ok_Click" Command="{Binding RouteCmdPersist}"/>
        <Button Content="✖" IsCancel="True"/>
    </StackPanel>
</Grid>

所以它应该这样工作:单击“添加”按钮 - 使用默认值创建新项目并将其作为RouteSelected传递,单击“编辑”按钮 - 将DataGrid SelectedItem传递为RouteSelected。接下来,在这两种情况下,使用对话框窗口控件编辑值,并在单击“确认”按钮时保存对数据库的更改。

它有效,但是在使用OpenRouteDialog打开对话框窗口时,我遇到了ComboBox的问题(使用OpenRouteDialogAdd添加新的数据行工作得很好)。两个ComboBox只在第一次窗口加载时显示正确的项目(基于数据行值)。在后续加载时,它们都重置为值“1”,DataGrid反映了这一点。示例:在DataGrid中我选择一些KierowcaID = 4的数据行,单击“编辑”按钮,加载对话框窗口,第二个ComboBox正确显示值为“4”的项目。我关闭窗口(确认保存更改与否 - 结果相同)。我选择相同的数据行(KierowcaID = 4),我点击“编辑”按钮,窗口加载,但这次(和任何后)第二个ComboBox显示值为“1”的项目(DataGrid中KierowcaID的单元格值也更改为“1”)。我不知道为什么会这样,尤其是DatePickers和TextBox每次都显示正确的值。

0 个答案:

没有答案