Nano Hash - криптовалюты, майнинг, программирование

WPF Xaml GridView SelectionChanged Behavior

Я работаю с представлением WPF с Prism.MVVM, которое позволяет нашим пользователям редактировать записи. Изначально запись для редактирования выбиралась через ComboBox.

<ComboBox IsSynchronizedWithCurrentItem="True" 
          ItemsSource="{Binding Records}"                 
          SelectedItem="{Binding SelectedRecord}"/>

Это сработало, но пользователям нужен был более эффективный способ определения того, какие записи содержат поля, требующие обновления, поэтому мы добавили DataGrid только для чтения, который они могут сортировать и визуально определять, какие записи их интересуют. Затем они хотят выбрать запись для редактирования. вне сетки (но сохраните поле со списком). Здесь что-то идет не так.

В идеале поведение, которое мы ищем:

  • Если пользователь выбирает запись из поля со списком:

    1. The selected record is loaded in the form
    2. Выбранная запись отображается как выбранная в поле со списком.
    3. Выбранная запись отображается как выбранная в сетке.
  • Если пользователь выбирает запись в сетке

    1. single click to select record.
    2. Выбранная запись загружается в форму
    3. Выбранная запись отображается как выбранная в поле со списком
    4. Выбранная запись отображается как выбранная в сетке.

Самая успешная попытка

Запуск команды при событии SelectionChanged DataGrid

<DataGrid x:Name="TheDataGrid"
          ItemsSource="{Binding Source={StaticResource GridRecords}}"
          SelectedItem="DataContext.SelectedRecord, ElementName=LayoutRoot, Mode=OneWay}">
...
<i:Interaction.Triggers>
    <i:EventTrigger EventName="SelectionChanged">
        <i:InvokeCommandAction CommandParameter="{Binding SelectedItem, ElementName=TheDataGrid}"
                               Command="{Binding DataContext.SelectRecordFromGridCommand, ElementName=LayoutRoot}"/>
    </i:EventTrigger>
</i:Interaction.Triggers>

Команда делегата:

Public ReadOnly Property SelectRecordFromGridCommand As DelegateCommand(Of TheRecordType) = new DelegateCommand(Of TheRecordType)(Sub(r) SelectedRecord = r)

Это было предпринято с различными вариантами режима привязки SelectedItem. Если привязка DataGrid SelectedItem удалена, мы получим 1,2,4,5,6 и 7. но выбор записи из поля со списком не покажет запись, выбранную в сетке.

Если для привязки DataGrid SelectedItem установлено значение OneWay, выбор записи с помощью поля со списком прерывается: настройка SelectedRecord запускает событие SelectionChanged в DataGrid, которое использует значение до события и эффективно возвращает все к исходному значению.

Это можно исправить, введя контрольный элемент в набор свойств в модели представления.

Private _selectedRecord As TheRecordType
Private _enableRecordSelection As Boolean = true
Public Property SelectedRecord As TheRecordType
    Get
        Return _selectedRecord 
    End Get
    Set(value As TheRecordType)
        If _enableRecordSelection 
            _enableRecordSelection = false
            SetProperty(_selectedRecord , value)
            _enableRecordSelection = true
        End If            
    End Set
End Property

Это действительно работает, и мы придумали это, когда писали вопрос, но кажется ужасно хакерским. Моя интуиция подсказывает мне, что должен быть лучший способ, поэтому я все еще спрашиваю:

Есть ли чистый (желательно только xaml) способ настроить это?

Другие наиболее успешные вещи, которые мы пробовали:

Прямая конфигурация XAML для DataGrid с двусторонней привязкой

<DataGrid x:Name="TheDataGrid"
          ItemsSource="{Binding Source={StaticResource GridRecords}}"
          SelectedItem="DataContext.SelectedRecord, ElementName=LayoutRoot, Mode=TwoWay}"/>

При этом мы удовлетворяем требованиям с 1 по 6; однако при выборе записи через сетку всегда выделяется предыдущая запись вместо текущей.

DataGrid.InputBindings

<DataGrid.InputBindings>
    <MouseBinding Gesture="LeftClick"
                  CommandParameter="{Binding SelectedItem, ElementName=TheDataGrid}"
                  Command="{Binding DataContext.SelectRecordFromGridCommand, ElementName=LayoutRoot}"/>
</DataGrid.InputBindings>

Без привязки SelectedItem это ведет себя так же, как без привязки InteractionTrigger к SelectionChanged, за исключением того, что пользователь должен выполнить несколько действий с мышью. Первый щелчок выделяет строку в сетке (фактическое выделение жирным синим цветом). Второй щелчок запускает команду.

С привязкой OneWay к SelectedItem это ведет себя аналогично прямой конфигурации xaml, опять же, за исключением необходимости многократного щелчка.

Еще раз, чтобы повторить вопрос: есть ли более чистый способ выполнить 7 требований, чем прибегать к контрольному значению в установщике свойств?

12.08.2016

Ответы:


1

Судя по вашему запросу, я понимаю, что вы хотите синхронизировать выбранный элемент в Datagrid и ComboBox. На вашем месте я бы использовал эти два элемента управления, связывающие один и тот же объект (SelectedRecord). Я знаком только с C#, поэтому код пишу на C#. Надеюсь, это поможет вам.

Для XAML:

<DataGrid ItemsSource="{Binding Records}"
          SelectedValue="{Binding SelectedRecord}" />
<ComboBox Grid.Column="1" ItemsSource="{Binding Records}"
          DisplayMemberPath="Id"
          SelectedValue="{Binding SelectedRecord}" />

Для ViewModel:

public ObservableCollection<Record> Records { get; } = new ObservableCollection<Record>();

public Record SelectedRecord
{
    get { return _selectedRecord; }
    set
    {
        _selectedRecord = value;
        OnPropertyChanged();
    }
}

public event PropertyChangedEventHandler PropertyChanged;

[NotifyPropertyChangedInvocator]
protected virtual void OnPropertyChanged([CallerMemberName] string propertyName = null)
{
    PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(propertyName));
}
public class Record
{
    private static int id = 0;
    public Record()
    {
        Id = ++id;
    }

    public int Id { get; set; }
}
16.08.2016
  • Спасибо, что обратили мое внимание на SelectedValue, однако это ведет себя идентично разделу Прямая конфигурация xaml для DataGrid с двусторонней привязкой в моем вопросе. При выборе записи из сетки строка, отображаемая как выбранная, всегда отстает на один щелчок. Если Z изначально выбран, и я нажимаю Y, Z по-прежнему отображается как выбранный в сетке, везде на странице обновляется до Y. Если я затем нажимаю X, Y отображается как выбранный в сетке и везде на странице. страница обновлена ​​до X. 16.08.2016
  • @Mr.Mindor, я думаю, что двусторонняя привязка не должна быть причиной выбранной проблемы с задержкой. Используете ли вы другой триггер или команду, влияющую на это? В моем тесте я не могу воспроизвести вашу проблему. 17.08.2016
  • Новые материалы

    Кластеризация: более глубокий взгляд
    Кластеризация — это метод обучения без учителя, в котором мы пытаемся найти группы в наборе данных на основе некоторых известных или неизвестных свойств, которые могут существовать. Независимо от..

    Как написать эффективное резюме
    Предложения по дизайну и макету, чтобы представить себя профессионально Вам не позвонили на собеседование после того, как вы несколько раз подали заявку на работу своей мечты? У вас может..

    Частный метод Python: улучшение инкапсуляции и безопасности
    Введение Python — универсальный и мощный язык программирования, известный своей простотой и удобством использования. Одной из ключевых особенностей, отличающих Python от других языков, является..

    Как я автоматизирую тестирование с помощью Jest
    Шутка для победы, когда дело касается автоматизации тестирования Одной очень важной частью разработки программного обеспечения является автоматизация тестирования, поскольку она создает..

    Работа с векторными символическими архитектурами, часть 4 (искусственный интеллект)
    Hyperseed: неконтролируемое обучение с векторными символическими архитектурами (arXiv) Автор: Евгений Осипов , Сачин Кахавала , Диланта Хапутантри , Тимал Кемпития , Дасвин Де Сильва ,..

    Понимание расстояния Вассерштейна: мощная метрика в машинном обучении
    В обширной области машинного обучения часто возникает необходимость сравнивать и измерять различия между распределениями вероятностей. Традиционные метрики расстояния, такие как евклидово..

    Обеспечение масштабируемости LLM: облачный анализ с помощью AWS Fargate и Copilot
    В динамичной области искусственного интеллекта все большее распространение получают модели больших языков (LLM). Они жизненно важны для различных приложений, таких как интеллектуальные..