Используя шаблон MVVM создаю несколько экземпляров модели данных и упаковываю их в List для хранения в ViewModel. Затем по клику на UserControl привязанном к модели, с помощью RelayCommand, в коллекции будет меняться состояние свойства модели (для простоты цвет фона), а задача UserControl отобразить изменения во View.
BorderControl.xaml
<UserControl x:Class="TestWpfApp.BorderControl"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:local="clr-namespace:TestWpfApp"
mc:Ignorable="d">
<UserControl.Resources>
<Style TargetType="{x:Type Border}">
<Setter Property="Width" Value="{Binding Path=Width, RelativeSource={RelativeSource TemplatedParent}}"/>
<Setter Property="Height" Value="{Binding Path=Height, RelativeSource={RelativeSource TemplatedParent}}"/>
<Setter Property="Background" Value="{Binding Path=Background, RelativeSource={RelativeSource TemplatedParent}}"/>
</Style>
<Style TargetType="{x:Type local:BorderControl}">
<Setter Property="Width" Value="100"/>
<Setter Property="Height" Value="100"/>
<Setter Property="Margin" Value="10"/>
<Setter Property="Background" Value="{Binding Path=Background, UpdateSourceTrigger=PropertyChanged}"/>
</Style>
</UserControl.Resources>
<UserControl.Template>
<ControlTemplate>
<Border/>
</ControlTemplate>
</UserControl.Template>
</UserControl>
BorderModel.cs
class BorderModel
{
public SolidColorBrush Background { get; set; } = new SolidColorBrush(Colors.Wheat);
}
ViewModel.cs
class ViewModel
{
private RelayCommand controlClickedCommand;
public List<BorderModel> Models { get; set; } = new List<BorderModel>()
{
{new BorderModel() }, {new BorderModel()}, {new BorderModel()}
};
public RelayCommand ControlClickedCommand => controlClickedCommand ?? new RelayCommand(ControlClicked);
private void ControlClicked(object args)
{
Models[0].Background = new SolidColorBrush(Colors.Red);
}
}
MainWindow.xaml
<Window x:Class="TestWpfApp.MainWindow"
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:TestWpfApp"
mc:Ignorable="d"
Title="MainWindow" Height="450" Width="800">
<Window.DataContext>
<local:ViewModel/>
</Window.DataContext>
<Grid>
<ItemsControl ItemsSource="{Binding Models}">
<ItemsControl.ItemTemplate>
<DataTemplate>
<local:BorderControl/>
</DataTemplate>
</ItemsControl.ItemTemplate>
</ItemsControl>
</Grid>
</Window>
Для того, чтобы привязаться и выполнить команду ControlClickedCommand в ViewModel я могу использовать InputBindings в BorderControl:
<ControlTemplate>
<Border>
<Border.InputBindings>
<MouseBinding Command="{Binding ControlClickedCommand}" MouseAction="LeftClick"/>
</Border.InputBindings>
</Border>
</ControlTemplate>
Но из-за то, что DataContext у Border это BorderModel упакованная в List, не понятно, как привязаться к RelayCommand ControlClickedCommand ViewModel при клике по BorderControl.

BorderModel? Тогда вопрос решится сам собой. – aepot Apr 01 '21 at 11:28BorderModel, можно подробнее? – Dmitry Chudov Apr 01 '21 at 11:34BorderModel, больше ничего не нужно. Ну и вместоModels[0].Background- простоBackground– aepot Apr 01 '21 at 11:39=> controlClickedCommand ??, должно быть=> controlClickedCommand ??=– aepot Apr 01 '21 at 11:41SolidColorBrush Background- цвет, это к чему относится? Это данные, UI или что-то еще? Скорей всего это UI, то есть View слой, верно? Тогда что у вас цвет делает в Model (слой данных)? Ок, предположим это чисто ради примера, но команда, это какой слой? Вот есть 3 слоя: Model - источник данных (база, файл на диске, сервер и др.), View - интерфейс и взаимодействие с пользователем (то, что он видит), и ViewModel - слой, который обрабатывает действия пользователя и делает что-то с Model слоем. Так где должны быть команды? – EvgeniyZ Apr 01 '21 at 11:47SolidColorBrush Backgroundприведён для упрощения примера. А команды - это способ взаимодействия между слоями. – Dmitry Chudov Apr 01 '21 at 12:00А команды - это способ взаимодействия между слоями.вооот, так почему вы ее хотите перенести или как-либо с ней взаимодействовать из Model слоя? Он знать даже не должен что-либо о V и VM слое, а вы его вдруг ответственным за команду сделать хотите. Также мне не понравилосьDataContext у Border это BorderModel- то есть вы изначально проигнорировали существование VM слоя и привязались к Model, может из-за этого тогда у вас все трудности? – EvgeniyZ Apr 01 '21 at 12:14при клике по элементу- в VM слое команда и ее обработчик, который по клику вызывает метод из модели. Сама команда естественно привязана в V слое. Также рядом с командой находится список VM объектов, которые являются оберткой над M объектами, они в себе содержат лишь то, что необходимо для View слоя, для привязок. Далее,перебирать массив объектов- это обычно делают методом в M слое, который возвращает после завершения нужный список обратно.и менять свойства у нужного- подписываетесь на событие обновления коллекции и все изменения переносите в M слой – EvgeniyZ Apr 01 '21 at 12:19Также мне не понравилось DataContext у Border это BorderModel- странно, что у View контекст данных это Model в MVVM, да? Вопрос был в том, как из контекста данных UserControl получить доступ к контексту данных VM. – Dmitry Chudov Apr 05 '21 at 06:58