Язык программирования C#9 и платформа .NET5 - Троелсен Эндрю
new Car { Id = 1, Color = "Blue", Make = "Chevy", PetName = "Kit", IsChanged = false }); Cars.Add( new Car { Id = 2, Color = "Red", Make = "Ford", PetName = "Red Rider", IsChanged = false });}Далее переместите весь код, относящийся к командам, из файла отделенного кода окна в модель представления, заменив ссылку на переменную
_carsCars// Для краткости остальной код не показанprivate void DeleteCar(Car car){ Cars.Remove(car);}Обновление кода и разметки MainWindow
Из файла
MainWindow.xaml.csItemsSourceInitializeComponent()public MainWindow(){ InitializeComponent();}Добавьте в начало файла следующий оператор
usingusing WpfViewModel.ViewModels;Создайте строго типизированное свойство для хранения экземпляра модели представления:
public MainWindowViewModel ViewModel { get; set; } = new MainWindowViewModel();Добавьте свойство
DataContextDataContext="{Binding ViewModel, RelativeSource={RelativeSource Self}}"Обновление разметки элементов управления
Теперь, когда свойство
DataContextWindowItemsSource<ComboBox Name="cboCars" Grid.Column="1" DisplayMemberPath="PetName" ItemsSource="{Binding Cars}" />Прием работает, т.к. контекстом данных для
WindowMainWindowViewModelCarsButtonDataContext<Button x:Name="btnAddCar" Content="Add Car" Margin="5,0,5,0" Padding="4, 2" Command="{Binding Path=<b>DataContext.AddCarCmd</b>, RelativeSource={RelativeSource Mode=FindAncestor, AncestorType={x:Type Window}}}" CommandParameter="{Binding ElementName=cboCars, Path=ItemsSource}"/><Button x:Name="btnDeleteCar" Content="Delete Car" Margin="5,0,5,0" Padding="4, 2" Command="{Binding Path=<b>DataContext.DeleteCarCmd</b>, RelativeSource={RelativeSource Mode=FindAncestor, AncestorType={x:Type Window}}}" CommandParameter="{Binding ElementName=cboCars, Path=SelectedItem}" /><Button x:Name="btnChangeColor" Content="Change Color" Margin="5,0,5,0" Padding="4, 2" Command="{Binding Path=<b>DataContext.ChangeColorCmd</b>, RelativeSource={RelativeSource Mode=FindAncestor, AncestorType={x:Type Window}}}" CommandParameter="{Binding ElementName=cboCars, Path=SelectedItem}"/>Итоговые сведения о моделях представлений
Верите или нет, но вы только что закончили построение первого WPF-приложения MWM. Вы можете подумать: "Это не реалистичное приложение. Как насчет данных? Данные в примере жестко закодированы". И вы будете совершенно правы. Это не реальное приложение, а лишь демонстрация. Однако в ней легко оценить всю прелесть паттерна MWM. Представлению ничего не известно о том, откуда поступают данные; оно просто привязывается к свойству модели представления. Реализации модели представления можно менять, скажем, использовать версию с жестко закодированными данными во время тестирования и версию, обращающуюся к базе данных, в производственной среде.
Можно было бы обсудить еще немало вопросов, в том числе разнообразные инфраструктуры с открытым кодом, паттерн "Локатор модели представления" (View Model Locator) и множество разных мнений на предмет того, как лучше реализовывать паттерн MWM. В том и заключается достоинство паттернов проектирования программного обеспечения — обычно существует много правильных способов их реализации, и вам необходимо лишь отыскать стиль, который наилучшим образом подходит к имеющимся требованиям.
Обновление проекта AutoLot.Dal для MWM
Если вы хотите обновить проект
AutoLot.DalCarAutoLot.Dal.ModelsBaseEntity