WPF DataGrid Hide RowDetails или Unselect Row
У меня есть DataGrid, для которого RowDetails устанавливается, когда он выбран (RowDetailsVisibilityMode = "VisibleWhenSelected" ). Теперь я хочу избавиться от него! Я установил кнопку закрытия в строках с этим кодом:
private void Button_Click(object sender, RoutedEventArgs e)
{
e.Handled = true;
Button button = sender as Button;
DataGridRow row = button.FindAncestor<DataGridRow>();
row.DetailsVisibility = Visibility.Collapsed;
}
Этот код получает меня на 90%, но после того, как данные строки свернуты для данной строки, он не появится в следующий раз, когда будет выбрана строка.
Ответы
Ответ 1
Я тоже столкнулся с этим. Здесь решение:
Сохраните эту кнопку в RowDetails и немного измените ее код. Вместо того, чтобы сосредоточиться на видимости отдельных строк, установите для свойства DataGrid SelectedIndex значение -1 (ни один не выбран).
DataGrid1.SelectedIndex = -1;
Поскольку ваш RowDetailsVisibilityMode равен VisibleWhenSelected
, DataGrid будет свернуть/скрыть все расширенные RowDetails. Это хорошо работает, когда SelectionMode Single
.
Ответ 2
Вы можете реализовать это со следующим кодом в XAML:
<WpfToolkit:DataGrid Name="dgSysthetic" ItemsSource="{Binding}"
AutoGenerateColumns="True"
SelectionMode="Extended"
RowDetailsVisibilityMode="Collapsed"
CanUserAddRows="False" CanUserDeleteRows="False"
CanUserResizeRows="False" CanUserSortColumns="False"
RowHeaderWidth="20" RowHeight="25">
<WpfToolkit:DataGrid.RowHeaderTemplate>
<DataTemplate>
<Button Name="btnHideRow" Click="btnHideDetails_Click" FontSize="5">></Button>
</DataTemplate>
</WpfToolkit:DataGrid.RowHeaderTemplate>
<WpfToolkit:DataGrid.RowDetailsTemplate>
<DataTemplate>
<WpfToolkit:DataGrid Name="dgAnalytical" ItemsSource="{Binding}" AutoGenerateColumns="True"/>
</DataTemplate>
</WpfToolkit:DataGrid.RowDetailsTemplate>
</WpfToolkit:DataGrid>
См. кнопку внутри RowHeaderTemplate.
В коде С# вы сделаете следующее:
private void btnHideDetails_Click(object sender, RoutedEventArgs e)
{
DependencyObject obj = (DependencyObject)e.OriginalSource;
while (!(obj is DataGridRow) && obj != null) obj = VisualTreeHelper.GetParent(obj);
if (obj is DataGridRow)
{
if ((obj as DataGridRow).DetailsVisibility == Visibility.Visible)
{
(obj as DataGridRow).DetailsVisibility = Visibility.Collapsed;
}
else
{
(obj as DataGridRow).DetailsVisibility = Visibility.Visible;
}
}
}
Это очень сработало для меня.
Ответ 3
вы можете поместить это как событие нажатия кнопок, оно подбирается к дереву, находит datarow и задает детали там, где это необходимо.
DependencyObject dep = (DependencyObject)e.OriginalSource;
while ((dep != null) && !(dep is DataGridRow))
{
dep = VisualTreeHelper.GetParent(dep);
}
if (dep != null && dep is DataGridRow)
{
DataGridRow row = dep as DataGridRow;
if (row.DetailsVisibility == Visibility.Collapsed)
{
row.DetailsVisibility = Visibility.Visible;
}
else
{
row.DetailsVisibility = Visibility.Collapsed;
}
}
Ответ 4
попробуйте добавить row.DetailsVisibility = Visibility.Visible;
в событие RowDetailsVisibilityChanged
.
Ответ 5
Попробуйте установить стиль на кнопке с сеттерами, которые задают свойства Button Command, CommandParameter. Вам нужно создать свой класс, который использует ICommand и включить его как StaticResource в XAML. Здесь я использовал DataGridRowHeader как кнопку, а не кнопку в деталях строки.
<local:DeselectRowCommand x:Key='deselectCommand' />
<Setter Property='Command' Value='{StaticResource deselectCommand}' />
<Setter Property='CommandParameter'
Value='{Binding RelativeSource={RelativeSource Mode=FindAncestor,
AncestorType=wpf:DataGridRow}}' />
В методе Execute команды вы можете получить DataGridRow из параметра команды и применить все необходимые методы.
По крайней мере, таким образом вы можете поделиться этим стилем или использовать другие его функции и повторно использовать ICommand для других ваших DataGrids, а также уменьшить обработку событий.
Вы можете увидеть рабочий пример в этот проект Silverlight-to-WPF DataGrid с открытым исходным кодом.
Ответ 6
Попробуйте это (добавив событие PreviewMouseDown в DataGrid в XAML):
private void UIElement_OnPreviewMouseDown(object sender, MouseButtonEventArgs e)
{
DataGrid grid = sender as DataGrid;
if (grid != null)
{
FrameworkElement element = e.OriginalSource as FrameworkElement;
if (element?.DataContext is FixedIncomeOrder)
{
if (grid.SelectedItem == (FixedIncomeOrder) ((FrameworkElement) e.OriginalSource).DataContext)
{
grid.SelectedIndex = -1;
e.Handled = true;
}
}
}
}
Ответ 7
Убедитесь, что у вашего datagrid есть имя, например
<DataGrid x:Name="dgPrimary"
...>
Поместите кнопку в шаблон строки, например
<DataGrid.RowDetailsTemplate>
<DataTemplate>
<Button Content="X" Click="Button_Click" Width="20"/>
....
Затем в коде просто установите для выделенного индекса datagrid значение -1
private void Button_Click(object sender, RoutedEventArgs e)
{
dgPrimary.SelectedIndex = -1;
}