How to Find Control and Its Value From DataGrid in WPF

I want to implement GridView functionally in WPF. I have done that in may websites and decided to write an article about it.

For implementing GridView functionally in WPF, there are two approaches; they are:

  1. GridView using ListView.
  2. DataGrid.

In this article, I am using a DataGrid with the WPFToolkit.dll.

First you need to download the WPFToolkit.dll.

You can download these DLLs from the following site:

http://wpf.codeplex.com/releases/view/40535

Create a new WPF project and add the WPFToolkit.dll reference to it.

Find the control and its value on button click event.

I have a DataGrid containing a button and a label control. Now I want to find this label and its values on the button click event (i.e. btnUserId_Click).

You can use the following code to find the label control and its values.

XAML Code

<my:DataGrid Name="GridView1" ItemsSource="{Binding}" AutoGenerateColumns="False" >

    <my:DataGrid.Columns>

        <my:DataGridTemplateColumn Header="Vehicle Reg. No." Width="SizeToCells">

            <my:DataGridTemplateColumn.CellTemplate>

                <DataTemplate>

                    <Button Name="btnUserId" Cursor="Hand" Tag="{Binding Path=source_address }"  Click="btnUserId_Click" Content="{Binding Path=VehicleReg }" Style="{StaticResource LinkButton}"></Button>

                </DataTemplate>

            </my:DataGridTemplateColumn.CellTemplate>

        </my:DataGridTemplateColumn>

        <my:DataGridTemplateColumn Header="source_address" Width="SizeToCells" Visibility="Hidden">

            <my:DataGridTemplateColumn.CellTemplate>

                <DataTemplate>

                    <Label x:Name="lblsource_address" Content="{Binding Path=source_address}" />

                </DataTemplate>

            </my:DataGridTemplateColumn.CellTemplate>

        </my:DataGridTemplateColumn>

    </my:DataGrid.Columns>

</my:DataGrid>

 

 

private void btnUserId_Click(object sender, RoutedEventArgs e)

{            

 

    //Find the DataRowView for DataGrid.

    DataRowView Grdrow = ((FrameworkElement)sender).DataContext as DataRowView;

 

    //Fidn the DataGrid row index

    int rowIndex = GridView1.Items.IndexOf(Grdrow);

 

    //Find the DataGridCell

    DataGridCell cell = GetCell(rowIndex, 1); //Pass the row and column

 

    //Find the "lblVehicleName" lable.

    Label lblsource_address = GetVisualChild<Label>(cell); // pass the DataGridCell as a parameter to GetVisualChild

 

    string _value = lblsource_address.Content;

   

}

 

public DataGridCell GetCell(int row, int column)

{

    DataGridRow rowContainer = GetRow(row);

    if (rowContainer != null)

    {

        DataGridCellsPresenter presenter = GetVisualChild<DataGridCellsPresenter>(rowContainer);

        if (presenter == null)

        {

            GridView1.ScrollIntoView(rowContainer, GridView1.Columns[column]);

            presenter = GetVisualChild<DataGridCellsPresenter>(rowContainer);

        }

        DataGridCell cell = (DataGridCell)presenter.ItemContainerGenerator.ContainerFromIndex(column);

        return cell;

    }

    return null;

}

 

public DataGridRow GetRow(int index)

{

    DataGridRow row = (DataGridRow)GridView1.ItemContainerGenerator.ContainerFromIndex(index);

    if (row == null)

    {

        GridView1.UpdateLayout();

        GridView1.ScrollIntoView(GridView1.Items[index]);

        row = (DataGridRow)GridView1.ItemContainerGenerator.ContainerFromIndex(index);

    }

    return row;

}

 

public static T GetVisualChild<T>(Visual parent) where T : Visual

{

    T child = default(T);

    int numVisuals = VisualTreeHelper.GetChildrenCount(parent);

    for (int i = 0; i < numVisuals; i++)

    {

        Visual v = (Visual)VisualTreeHelper.GetChild(parent, i);

        child = v as T;

        if (child == null)

        {

            child = GetVisualChild<T>

            (v);

        }

        if (child != null)

        {

            break;

        }

    }

    return child;

}

Description

  1. First you need to find the "DataRowView" from the button click event:

    DataRowView Grdrow = ((FrameworkElement)sender).DataContextas DataRowView;

     

  2. Then you need to find the row index of the "DataGrid" row index:

    int rowIndex = GridView1.Items.IndexOf(Grdrow);
     

  3. You need to use the GetCell() method to get the required cell. The GetCell() method will take two arguments. One is the row and another is the column. I have passed the row index as the row and 1 as my column because my "lblsource_address" label is present in the first column.

    DataGridCell cell = GetCell(rowIndex, 1);
     

  4. GetVisualChild() will help to find the control and its values.

    Label
    lblsource_address = GetVisualChild<Label>(cell);
    string _value = lblsource_address.Content;