tengo una cuadrícula de datos, junto con filas hackeado grupo subtotal en uno de mis proyectos. No nos preocuparon algunos de los problemas que presenta, como ocultar y clasificar columnas, así que no estoy seguro de si puede ampliarse. También me doy cuenta de que podría haber problemas de rendimiento que pueden ser un problema con Conjuntos grandes (mi ventana está funcionando con 32 DataGrids separados - ouch). Pero es una dirección diferente de otras soluciones que he visto, así que pensé en tirarla aquí y ver si te ayuda.
Mi la solución consiste de 2 componentes principales:
1. Las filas de subtotal no son filas en el DataGrid principal, sino que son DataGrids independientes. De hecho, tengo 2 cuadrículas adicionales en cada grupo: 1 en el encabezado que solo se muestra cuando el grupo está colapsado, y una debajo de ItemsPresenter. ItemsSource para el subtotal DataGrids proviene de un convertidor que toma los elementos en el grupo y devuelve un modelo de vista agregado.Las columnas de las cuadrículas subtotales son exactamente las mismas que las de la grilla principal (completadas en DataGrid_Loaded, aunque estoy seguro de que también se pueden hacer en xaml).
<GroupStyle>
<GroupStyle.ContainerStyle>
<Style TargetType="{x:Type GroupItem}">
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="{x:Type GroupItem}">
<Expander Background="Gray" HorizontalAlignment="Left" IsExpanded="True"
ScrollViewer.CanContentScroll="True">
<Expander.Header>
<DataGrid Name="HeaderGrid" ItemsSource="{Binding Path=., Converter={StaticResource SumConverter}}"
Loaded="DataGrid_Loaded" HeadersVisibility="Row"
Margin="25 0 0 0" PreviewMouseDown="HeaderGrid_PreviewMouseDown">
<DataGrid.Style>
<Style TargetType="DataGrid">
<Style.Triggers>
<DataTrigger Binding="{Binding RelativeSource={RelativeSource AncestorType=Expander}, Path=IsExpanded}"
Value="True">
<Setter Property="Visibility" Value="Collapsed"/>
</DataTrigger>
</Style.Triggers>
</Style>
</DataGrid.Style>
</DataGrid>
</Expander.Header>
<StackPanel>
<ItemsPresenter/>
<DataGrid Name="FooterGrid" ItemsSource="{Binding ElementName=HeaderGrid, Path=ItemsSource, Mode=OneWay}"
Loaded="DataGrid_Loaded" HeadersVisibility="Row"
Margin="50 0 0 0">
<DataGrid.Style>
<Style TargetType="DataGrid">
<Style.Triggers>
<DataTrigger Binding="{Binding RelativeSource={RelativeSource AncestorType=Expander}, Path=IsExpanded}"
Value="False">
<Setter Property="Visibility" Value="Collapsed"/>
</DataTrigger>
</Style.Triggers>
</Style>
</DataGrid>
</StackPanel>
</Expander>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
</GroupStyle.ContainerStyle>
</GroupStyle>
2. A continuación, la cuestión es cómo conseguir que todos los DataGrids se comporten como si fueran una sola rejilla. Lo he manejado subclasificando DataGridTextColumn
(solo tenemos texto en este caso, pero otros tipos de columna deberían funcionar también) en una clase llamada DataGridSharedSizeTextColumn
que imita el comportamiento SharedSizeGroup de la clase Grid. Tiene una propiedad de dependencia de cadena con un nombre de grupo y realiza un seguimiento de todas las columnas en el mismo grupo. Cuando Width.DesiredValue
cambia en una columna, actualizo MinWidth en todas las otras columnas y fuerzo una actualización con DataGridOwner.UpdateLayout()
. Esta clase también cubre el reordenamiento de columna y realiza una actualización en todo el grupo cada vez que cambia DisplayIndex. Creo que este método también funcionaría con cualquier otra propiedad de columna, siempre que tenga un setter.
Hubo otras cosas molestas para trabajar con la selección, copia, etc. Pero resultó ser muy fácil de manejar con los eventos MouseEntered y MouseLeave y mediante el uso de un comando Copiar personalizado.
¿Encontró alguna forma de responder a esta necesidad? Aquí está mi pregunta SO (que marqué como duplicado): https://stackoverflow.com/questions/46206673/wpf-datagrid-grouping-and-totales – Simon