GridControl: Hierarchy of tables linked with data relation

The Wpf GridControl provides numerous data binding features and supports creation of any hierarchies with simple tools. A new feature – bulding a hierarchy with DataRelation. This feature is based on conditional data binding used in the grid.

Wpf GridControl data relations

A grid can be bound to a data table that may have relations with other tables. DataRow objects in the data table have DataRow.GetChildRows(DataRelation) method that returns children collection based on DataRelation. Therefore, to build a hierarchy it is necessary to tell the grid that added rows are linked with children rows via DataRelation. This should be done during data binding. The example below shows how to do it with simple tools using conditional data binding:

Create a DataSet with two tables and a data relation:

public static DataSet CreateDataSet()
{
// create a DataSet with one table, two columns
DataSet dataSet = new DataSet();

// create the 'Customers' table
DataTable table = new DataTable("Customers");
dataSet.Tables.Add(table);
table.Columns.Add("customerId", typeof(int)).AutoIncrement = true;
table.Columns.Add("name", typeof(string));
table.PrimaryKey = new DataColumn[] { table.Columns["customerId"] };

// create the 'Orders' table
table = new DataTable("Orders");
dataSet.Tables.Add(table);
table.Columns.Add("orderId", typeof(int)).AutoIncrement = true;
table.Columns.Add("customerId", typeof(int));
table.Columns.Add("amount", typeof(double));
table.PrimaryKey = new DataColumn[] { table.Columns["orderId"] };

// create a data relation
dataSet.Relations.Add("myrelation",
dataSet.Tables["Customers"].Columns["customerId"],
dataSet.Tables["Orders"].Columns["customerId"]);

Random r = new Random();

// populate the 'Customers' table
int orderId = 1;
const int customerCount = 10;
const int ordersPerCustomer = 5;
for (int customerId = 1; customerId <= customerCount; customerId++)
{
// add a new customer
dataSet.Tables["Customers"].Rows.Add(new object[] { customerId, string.Format("customer{0}", customerId) });
}

// populate the 'Orders' table
for (int order = 1; order <= customerCount * ordersPerCustomer; order++)
{
// add an order
dataSet.Tables["Orders"].Rows.Add(new object[] { orderId++, 1 + r.Next() % customerCount, (10 + r.Next() % 10) });
}

return dataSet;
}

Wpf GridControl declaration:

<!--Declaration of the grid-->
<df:GridControl x:Name="grid">
<df:GridControl.Headers>
<df:Header ScrollType="Stretch">
<df:Header.Columns>
<df:Column Id="customerId" Title="CustomerId" CellHorizontalAlignment="Left" />
<df:Column Id="name" Title="Costomer name" CellHorizontalAlignment="Left" />
</df:Header.Columns>
</df:Header>
<df:Header ScrollType="Stretch">
<df:Header.Columns>
<df:Column Id="orderId" Title="orderId" CellHorizontalAlignment="Left" />
<df:Column Id="amount" Title="amount" CellHorizontalAlignment="Left" />
</df:Header.Columns>
</df:Header>
</df:GridControl.Headers>
</df:GridControl>

Populate the Wpf GridControl with customers and orders:

void OnGridControl_Initialize()
{
//Add an event handler to handle data relation at adding time
grid.RowAdding += delegate(object sender, GridControlRowAddingEventArgs e)
{
//The object is adding on the root level
if (e.ParentRow == null)
{
e.InsertionType = InsertionType.AsDataRelation;
e.DataObject = "myrelation";
}
};


grid.ItemsSource = CreateDataSet().Tables["Customers"];
}

Back to Wpf GridControl features