0
votes

I am binding an ObservableCollection to a Datagrid. Everything is working besides this row height issue I've been fighting for a while now.

The Issue is the row heights are storing the largest cell's height and not changing from that.

If I have a collection of 5 objects. In ASC order,Row 1 height is 100 and row 5 height is 20. If I resort the same column to DESC then row 1 height is now 100 and row 5 height is 100 as well.

I've tried wrapping the Datagrid in a Scrollviewer and changed DataGridTextColumn to DataGridTemplateColumn with a vertical aligned text box. Silverlight doesn't have ViewCollectionSource so I couldn't try that one.

How can I get it to recalculate the height after a sort?

XAML

        SelectedItem="{Binding SelectedComment, Mode=TwoWay}"
        VerticalAlignment="Top"
        Width="1000"
        Height="Auto"
        >
         <sdk:DataGrid.Columns>
                <sdk:DataGridTemplateColumn Header ="Comment" Width="4*" IsReadOnly="True" SortMemberPath="Commentstr" CanUserSort="True">
                    <sdk:DataGridTemplateColumn.CellTemplate>
                        <DataTemplate>
                            <TextBlock Text="{Binding Commentstr}" TextWrapping="Wrap" VerticalAlignment="Top"></TextBlock>
                        </DataTemplate>
                    </sdk:DataGridTemplateColumn.CellTemplate>
                </sdk:DataGridTemplateColumn>

            </sdk:DataGrid.Columns>
        </sdk:DataGrid>

Code-Behind

 private ObservableCollection<Comment> commentCollection = new ObservableCollection<Comment>();
    public ObservableCollection<Comment> CommentCollection
    {
        get { return commentCollection; }
        set
        {
            commentCollection = value;
        }
    }
    public Main()
    {
        InitializeComponent();
        this.Loaded += new RoutedEventHandler(CustomScreenTemplate_Loaded);

        CommentGrid.ItemsSource = CommentCollection;
    }
1

1 Answers

0
votes

Finally got the row height issue resolved. Posting what worked for me here in case anyone else has the same problem.

Creat an Override Class for DataGrid

public class FixedDataGrid : DataGrid
{
    /// <summary>
    /// Overrides OnLoadingRow
    /// </summary>
    protected override void OnLoadingRow(DataGridRowEventArgs e)
    {
        if (double.IsNaN(this.RowHeight))
        {
            e.Row.Loaded += Row_Loaded;
        }

        base.OnLoadingRow(e);
    }

    private void Row_Loaded(object sender, RoutedEventArgs e)
    {
        var row = (DataGridRow)sender;
        row.Loaded -= Row_Loaded;

        for (int col = 0; col < this.Columns.Count; col++)
        {
            var cellElement = this.Columns[col].GetCellContent(row);
            if (cellElement != null)
            {
                cellElement.SizeChanged += CellElement_SizeChanged;
            }
        }
    }

    private static void CellElement_SizeChanged(object sender, SizeChangedEventArgs e)
    {
        //Fix issue: DataGrid Row Auto-Resize only grows row height but won't shrink
        var dataGrid = GetParentOf<DataGrid>((FrameworkElement)sender);
        if (dataGrid != null && double.IsNaN(dataGrid.RowHeight))
        {
            var row = DataGridRow.GetRowContainingElement((FrameworkElement)sender);

            //Fore recalculating row height
            try
            {
                dataGrid.RowHeight = 0;
                row.InvalidateMeasure();
                row.Measure(row.RenderSize);
            }
            finally
            {
                //Restore RowHeight
                dataGrid.RowHeight = double.NaN;
            }
        }
    }

    private static T GetParentOf<T>(FrameworkElement element) where T : FrameworkElement
    {
        while (element != null)
        {
            T item = element as T;
            if (item != null)
            {
                return item;
            }

            element = (FrameworkElement)VisualTreeHelper.GetParent(element);
        }

        return null;
    }
}

Use the override class as your Datagrid

xmlns:fixed="clr-namespace:MyNameSpace

<fixed:FixedDataGrid x:Name="BetterGrid"  ... />