Почему метод срабатывает, и выбранный элемент действительно передаётся, но в итоге в список для второго Datagrid он не добавляется?

Рейтинг: 1Ответов: 0Опубликовано: 28.05.2023

Логика функциональности следующая. У меня есть есть 2 Datagrid'a, один изначально имеет какие-либо значения (в моём случае это товары). Второй — пустой. Грубо говоря, я выбираю товары из 1-ого Datagrid, и они добавляются во второй, который является своего рода чеком, что выбрал пользователь при заказе:

Скрин Datagrid

Вот как должно работать:

Пример

Я делаю MVVM-структуру в своём приложении, поэтому делаю всё через привязки и команды, так что для меня в первый раз сделать это является довольно проблематичным.

Сначала создаются 2 ViewModel, первая отвечает за первый Datagrid, вторая — за второй соответственно.

Код ViewModel для первого Datagrid:

internal class BW_FirstDataGridViewModel : PropertyChangedHelper
{
    #region Properties
    private FabricFromCheck selectedFabric = new FabricFromCheck();
    public FabricFromCheck SelectedFabric
    {
        get { return selectedFabric; }
        set
        {
            selectedFabric = value;
            OnPropertyChanged();
            AddFabric();
        }
    }

    private ObservableCollection<FabricFromCheck> _firstDataGridItems;
    public ObservableCollection<FabricFromCheck> FirstDataGridItems
    {
        get { return _firstDataGridItems; }
        set
        {
            _firstDataGridItems = value;
            OnPropertyChanged();
        }
    }
    #endregion

    /*// Команда для добавления элемента во второй датагрид
    public AddSelectedItemCommand<FabricFromCheck> AddItemCommand { get; }*/

    public ICommand AddItemCommand { get; set; }

    public BW_FirstDataGridViewModel()
    {
        /*AddItemCommand = new AddSelectedItemCommand<FabricFromCheck>(BW_SecondDataGridViewModel.Instance);*/
        AddItemCommand = new RelayCommand(AddFabric);

        FirstDataGridItems = new ObservableCollection<FabricFromCheck>()
        {
            new FabricFromCheck("Стол", "500", 15),
            new FabricFromCheck("Комод", "500", 35),
            new FabricFromCheck("Стул", "500", 25),
            new FabricFromCheck("Табурет", "543", 15),
            new FabricFromCheck("Шкаф", "345", 10),
            new FabricFromCheck("Диван", "565", 4),
            new FabricFromCheck("Столешница", "3545", 7)
        };
    }

    public void AddFabric()
    {
        if (SelectedFabric == null)
        {
            MessageBox.Show("Товар не выбран");
            return;
        }
        FabricToCheck item = new FabricToCheck(SelectedFabric);
        BW_SecondDataGridViewModel.Instance.SecondDataGridItems.Add(item);
    }
}

Вторая ViewModel:

internal class BW_SecondDataGridViewModel : PropertyChangedHelper
{
    private ObservableCollection<FabricToCheck> _secondDataGridItems;
    public ObservableCollection<FabricToCheck> SecondDataGridItems
    {
        get { return _secondDataGridItems; }
        set
        {
            _secondDataGridItems = value;
            OnPropertyChanged();
        }
    }

    // Создаем единственный экземпляр модели представления (Singleton)
    public static BW_SecondDataGridViewModel Instance { get; } = new BW_SecondDataGridViewModel();

    public BW_SecondDataGridViewModel()
    {
        SecondDataGridItems = new ObservableCollection<FabricToCheck>();
    }
}

Класс, который наследую для OnPropertyChanged():

public class PropertyChangedHelper : INotifyPropertyChanged
{
    ////////////////////////////////////////////////////////////////////
    public event PropertyChangedEventHandler PropertyChanged;
    protected void OnPropertyChanged([CallerMemberName] string propertyName = null)
    {
        PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(propertyName));
    }
}

Классы, использованные в ViewModels (FabricFromCheck && FabricToCheck):

internal class FabricFromCheck
{
    public string Name { get; set; }
    public string Size { get; set; }
    public int Amount { get; set; }
    public FabricFromCheck(string name, string size, int amount)
    {
        Name = name;
        Size = size;
        Amount = amount;
    }
    public FabricFromCheck() { }
}


internal class FabricToCheck
{
    public string Name { get; set; }
    public string Size { get; set; }
    public FabricToCheck(string name, string size)
    {
        Name = name;
        Size = size;
    }
    public FabricToCheck(FabricFromCheck selected)
    {
        Name = selected.Name;
        Size = selected.Size;
    }
}

По идее, метод срабатывает, и на строчке ниже выбранный элемент действительно передаётся, но в итоге в список для Второго Datagrid он не добавляется:

BW_SecondDataGridViewModel.Instance.SecondDataGridItems.Add(item);

XAML:

<DataGrid SelectedItem="{Binding SelectedFabric}" ItemsSource="{Binding FirstDataGridItems}" x:Name="AllFabrics_DataGrid" Grid.Row="1" Margin="7,0,0,0" IsReadOnly="True" AutoGenerateColumns="False" SelectionChanged="AllFabrics_DataGrid_SelectionChanged">
    <i:Interaction.Triggers>
        <i:EventTrigger EventName="SelectionChanged">
            <i:InvokeCommandAction Command="{Binding AddItemCommand}" />
        </i:EventTrigger>
    </i:Interaction.Triggers>

    <DataGrid.Columns>
        <DataGridTextColumn Header="Название" Binding="{Binding Name}"/>
        <DataGridTextColumn Header="Размер" Binding="{Binding Size}"/>
        <DataGridTextColumn Header="Количество" Binding="{Binding Amount}"/>
    </DataGrid.Columns>
</DataGrid>

<DataGrid ItemsSource="{Binding SecondDataGridItems}" x:Name="Fabrics_InCheck_DataGrid" Grid.Row="1" Grid.Column="2" Margin="0,0,7,0"  IsReadOnly="True" AutoGenerateColumns="False" >
    <DataGrid.Columns>
        <DataGridTextColumn Header="Название"/>
        <DataGridTextColumn Header="Размер"/>
    </DataGrid.Columns>
</DataGrid>

Я в привязках и командах новичок, было бы очень приятно получить ответ от людей знающих. Долго промучался, всё равно не работает. Что-то делаю не так, только вот что?

Ответы

Ответов пока нет.