Skip to main content

Expand and collapse operations

info

This control is available as part of Avalonia Accelerate Business or higher.

When you use a hierarchical TreeDataGrid, your users can expand and collapse rows to navigate parent-child relationships. Avalonia provides methods on HierarchicalTreeDataGridSource<T> that let you control this behavior programmatically, whether you need to expand a single node, expand all nodes at once, or conditionally expand rows that match a filter. You can also subscribe to events that fire before and after each expand or collapse operation.

note

Programmatic expand/collapse and expand/collapse events require the code-behind Source approach with HierarchicalTreeDataGridSource<T>.

Basic expand and collapse operations

You can programmatically expand or collapse rows in a hierarchical TreeDataGrid:

var Source = new HierarchicalTreeDataGridSource<Person>(_people)
.WithHierarchicalExpanderTextColumn(x => x.Name, x => x.Children)
.WithTextColumn(x => x.Age);

// Expand a specific node by index path
Source.Expand(new IndexPath(0)); // Expand first root item

// Collapse a node
Source.Collapse(new IndexPath(0));
info

For more information about IndexPath see Selection modes

Expand all and collapse all

The source provides built-in methods for expanding or collapsing all rows:

// Expand all rows in the tree
Source.ExpandAll();

// Collapse all rows in the tree
Source.CollapseAll();

Expand or collapse based on a condition

You can expand or collapse rows based on a condition:

// Expand all rows where Person.Age > 18
Source.ExpandCollapseRecursive(person => person.Age > 18);

// Collapse all rows
Source.ExpandCollapseRecursive(_ => false);

Responding to expand and collapse events

You can handle expand and collapse events to load data on demand or perform other actions. These events use TreeDataGridRowModelEventArgs:

Source.RowExpanding += (sender, e) =>
{
var person = (Person)e.Row.Model!;
var indexPath = e.Row.ModelIndexPath;
Debug.WriteLine($"Expanding: {person.Name} at {indexPath}");
};

Source.RowExpanded += (sender, e) =>
{
var person = (Person)e.Row.Model!;
var indexPath = e.Row.ModelIndexPath;
Debug.WriteLine($"Expanded: {person.Name} at {indexPath}");
};

Source.RowCollapsing += (sender, e) =>
{
var person = (Person)e.Row.Model!;
Debug.WriteLine($"Collapsing: {person.Name}");
};

Source.RowCollapsed += (sender, e) =>
{
var person = (Person)e.Row.Model!;
Debug.WriteLine($"Collapsed: {person.Name}");
};

Lazy loading data on expand

A common pattern is to load child data on demand when the user expands a row, rather than loading your entire tree upfront. You can use the RowExpanding event to populate children just before a row opens. This keeps initial load times fast, especially for large data sets.

Source.RowExpanding += (sender, e) =>
{
var person = (Person)e.Row.Model!;

if (!person.ChildrenLoaded)
{
var children = MyDataService.LoadChildren(person.Id);
person.Children.Clear();
person.Children.AddRange(children);
person.ChildrenLoaded = true;
}
};

See also