65.9K
CodeProject is changing. Read more.
Home

Change Height of ALL Rows in DataGridView Simultaneously

starIconstarIconstarIconstarIconstarIcon

5.00/5 (1 vote)

May 28, 2012

CPOL

2 min read

viewsIcon

29859

This tip describes how to change DataGridView behavior concerning row resizing

Introduction

Most of the grid components I've seen allowed user to resize height of all rows simultaneously: when user dragged row's bottom border with a mouse button pressed and then released the mouse button, all rows changed their height accordingly, not just the one being actually resized with the mouse. This is neither bad nor good: I've just got used to this behavior of grid components.

However, Microsoft DataGridView component (shipped with .NET 2.0 and higher) has another behavior: only the row being actually resized with the mouse changes its height, so after the drag operation completes, we have rows of different heights. This is very annoying for me and my users as well. I wanted to find a way to have the drag-one-resize-all behavior, or - even better - to have a choice of which behavior to use.

All solutions I found in the Internet use one of the following 2 approaches:

  • update DataGridView.RowTemplate.Height property and recreate rows from data source
  • loop through all rows and set height of each row individually

I think I've found a better solution.

Using the Code

Create a control derived from DataGridView. Place the following code into this control's class:

private bool _preserveEqualRowHeights = true;
[DefaultValue(true)]
public bool PreserveEqualRowHeights
{
    get { return _preserveEqualRowHeights; }
    set { _preserveEqualRowHeights = value; }
}

private int _rowHeightByUser = 0;
protected override void OnRowHeightInfoPushed(DataGridViewRowHeightInfoPushedEventArgs e)
{
    base.OnRowHeightInfoPushed(e);
    if (this.PreserveEqualRowHeights)
    {
        _rowHeightByUser = e.Height;
        this.Invalidate();
    }
}
protected override void OnRowHeightInfoNeeded(DataGridViewRowHeightInfoNeededEventArgs e)
{
    base.OnRowHeightInfoNeeded(e);
    if (_preserveEqualRowHeights && _rowHeightByUser > 0 && e.Height != _rowHeightByUser)
    {
        e.Height = _rowHeightByUser;
    }
}

If you do not want to create a derived control, you can simply use events RowHeightInfoPushed and RowHeightInfoNeeded of an existing DataGridView control instead of overriding methods OnRowHeightInfoPushed and OnRowHeightInfoNeeded inside the derived control.

Setting property PreserveEqualRowHeights of the derived control to false provides the default [annoying] row-resizing behavior of the DataGridView control. For my projects, it is convenient to have true as the default value of this property.

Points of Interest

I haven't checked whether this approach demonstrates better performance. Anyway, I like the possibility to not loop through all rows and not rebind to datasource.

History

  • 28-May-2012: Submitted