Reputation: 8594
I have a DataGrid
control in my application:
<DataGrid AutoGenerateColumns="False"
BorderThickness="1"
CanUserDeleteRows="False"
CanUserReorderColumns="False"
CanUserResizeColumns="True"
CanUserResizeRows="False"
CanUserSortColumns="True"
EnableColumnVirtualization="True"
EnableRowVirtualization="True"
FontSize="16"
FontWeight="Bold"
IsReadOnly="True"
Grid.Column="0"
Grid.ColumnSpan="2"
Grid.Row="2"
Margin="5"
Name="PendingRowsGrid"
SelectionUnit="FullRow"
ScrollViewer.CanContentScroll="True"
ScrollViewer.HorizontalScrollBarVisibility="Auto"
ScrollViewer.VerticalScrollBarVisibility="Auto"
ToolTip="Number of rows pending transmission"
Visibility="{Binding Converter={StaticResource BoolToHide}, Path=AdvancedSettings.RunningStandAlone, RelativeSource={RelativeSource AncestorType={x:Type cs:Dashboard}}}">
<DataGrid.Columns>
<cs:ExtendedTextColumn Binding="{Binding Mode=OneWay, Path=Value.DataTypeDisplay}"
Header="Data Type"
Width="*" />
<cs:ExtendedTextColumn Binding="{Binding Converter={StaticResource CountConverter}, ConverterParameter='#,##0', Mode=OneWay, Path=Value.ToEoc}"
Header="To EOC"
HorizontalAlignment="Right"
Width="Auto" />
<cs:ExtendedTextColumn Binding="{Binding Converter={StaticResource CountConverter}, ConverterParameter='#,##0', Mode=OneWay, Path=Value.FromEoc}"
Header="From EOC"
HorizontalAlignment="Right"
Width="Auto" />
</DataGrid.Columns
</DataGrid>
The first column is left aligned, and the last two columns need to be right aligned. In addition, the right most 2 columns need to adjust their widths to fit the widest value in the column.
Here's the code for the ExtendedTextColumn
class:
public class ExtendedTextColumn : DataGridTextColumn {
public static readonly DependencyProperty HorizontalAlignmentProperty =
DependencyProperty.Register( "HorizontalAlignment", typeof( HorizontalAlignment ), typeof( ExtendedTextColumn ),
new PropertyMetadata( HorizontalAlignment.Stretch ) );
public static readonly DependencyProperty VerticalAlignmentProperty =
DependencyProperty.Register( "VerticalAlignment", typeof( VerticalAlignment ), typeof( ExtendedTextColumn ),
new PropertyMetadata( VerticalAlignment.Stretch ) );
public HorizontalAlignment HorizontalAlignment {
get { return (HorizontalAlignment) GetValue( HorizontalAlignmentProperty ); }
set { SetValue( HorizontalAlignmentProperty, value ); }
}
public VerticalAlignment VerticalAlignment {
get { return (VerticalAlignment) GetValue( VerticalAlignmentProperty ); }
set { SetValue( VerticalAlignmentProperty, value ); }
}
protected override FrameworkElement GenerateElement( DataGridCell cell, object dataItem ) {
FrameworkElement element = base.GenerateElement( cell, dataItem );
// Set the FrameworkElement's HorizontalAlignment and VeritcalAligment properties
element.HorizontalAlignment = HorizontalAlignment;
element.VerticalAlignment = VerticalAlignment;
return element;
}
protected override FrameworkElement GenerateEditingElement( DataGridCell cell, object dataItem ) {
TextBox textBox = (TextBox) base.GenerateEditingElement( cell, dataItem );
// Set the TextBox's TextAlignment and VeritcalAligment properties
textBox.TextAlignment = GetTextAlignment();
textBox.VerticalContentAlignment = VerticalAlignment;
return textBox;
}
private TextAlignment GetTextAlignment() {
switch ( HorizontalAlignment ) {
case HorizontalAlignment.Center:
return TextAlignment.Center;
case HorizontalAlignment.Left:
return TextAlignment.Left;
case HorizontalAlignment.Right:
return TextAlignment.Right;
default:
return TextAlignment.Justify;
}
}
}
}
The problem is that the two right most columns are not sized properly with the XAML shown. I've also tried using DataGridTemplateColumns
for the right-most two columns:
<DataGridTemplateColumn Header="To EOC"
HeaderStyle="{StaticResource CenteredHeaderText}"
Width="Auto">
<DataGridTemplateColumn.CellTemplate>
<DataTemplate>
<TextBlock TextAlignment="Right"
Text="{Binding Converter={StaticResource CountConverter}, ConverterParameter='#,##0', Mode=OneWay, Path=Value.ToEoc}"
VerticalAlignment="Center" />
</DataTemplate>
</DataGridTemplateColumn.CellTemplate>
</DataGridTemplateColumn>
<DataGridTemplateColumn Header="From EOC"
HeaderStyle="{StaticResource CenteredHeaderText}"
Width="Auto">
<DataGridTemplateColumn.CellTemplate>
<DataTemplate>
<TextBlock TextAlignment="Right"
Text="{Binding Converter={StaticResource CountConverter}, ConverterParameter='#,##0', Mode=OneWay, Path=Value.FromEoc}"
VerticalAlignment="Center" />
</DataTemplate>
</DataGridTemplateColumn.CellTemplate>
</DataGridTemplateColumn>
But these, also, do not size properly. In both cases, one to one and a half characters get cut off. In the case of the original XAML (using the ExtendedTextColumn
class), it's the left most character that gets cut off; in the second XAML (the DataGridTemplateColumn
case), it's the right most character.
I've tried changing the original XAML so the DataGrid
uses DataGridTextColumns
for the right-most two columns and these do get sized properly. This leads me to believe that there's something the DataGrid
or DataGridTextColumn
class does that isn't being done in the other two cases to determine how wide the column is, yet my ExtendedTextColumn
class descends from DataGridTextColumn
. I'm at a loss.
Does anyone have any suggestions for how I can get this to work properly?
Upvotes: 1
Views: 1080
Reputation: 8594
After playing with the Xaml & the code for most of the day, I've come up with something that almost works.
First, I stopped using my class and I used XAML similar to the following for the right two columns instead:
<DataGridTextColumn Binding="{Binding Value.FromEoc, ConverterParameter=#\,##0, Converter={StaticResource CountConverter}, Mode=OneWay}"
Header="From EOC"
HeaderStyle="{StaticResource CenteredHeaderText}"
MinWidth="80"
Width="*">
<DataGridTextColumn.ElementStyle>
<Style TargetType="{x:Type TextBlock}">
<Setter Property="HorizontalAlignment" Value="Right" />
</Style>
</DataGridTextColumn.ElementStyle>
</DataGridTextColumn>
I figured that since the DataGridTextColumn
resized properly by itself that this would do the trick. Alas, it did not. The Column ended up being 1/2 character too narrow!
So in the end, I punted. The original problem was that the columns were too narrow if the number of digits to be displayed was 8 or greater. I changed the Width
of the first column to Auto
and the Widths
of the last two columns to *
. The columns are now wide enough that I shouldn't have a problem until the number of digits is greater than 12 or so, and we shouldn't have that many digits in a production system.
Upvotes: 1