Skip to content

Commit

Permalink
Speed up reassigning items.
Browse files Browse the repository at this point in the history
Previously reassigning hierarchical items was expensive as the flattened list was being recalculated with each row disposal. Ignore collection changes while the rows are being disposed and recalculate the flattened rows at the end.
  • Loading branch information
grokys committed Mar 8, 2024
1 parent bbfa905 commit ffd6e29
Show file tree
Hide file tree
Showing 2 changed files with 23 additions and 21 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,7 @@ public class HierarchicalRows<TModel> : ReadOnlyListBase<HierarchicalRow<TModel>
private readonly IExpanderColumn<TModel> _expanderColumn;
private readonly List<HierarchicalRow<TModel>> _flattenedRows;
private Comparison<TModel>? _comparison;
private bool _isExpandingCollapsing;
private bool _ignoreCollectionChanges;

public HierarchicalRows(
IExpanderRowController<TModel> controller,
Expand Down Expand Up @@ -90,10 +90,10 @@ static void Expand(IReadOnlyList<HierarchicalRow<TModel>> rows, Func<TModel, boo
}
}

_isExpandingCollapsing = true;
_ignoreCollectionChanges = true;

try { Expand(_roots, filter); }
finally { _isExpandingCollapsing = false; }
finally { _ignoreCollectionChanges = false; }

_flattenedRows.Clear();
InitializeRows();
Expand Down Expand Up @@ -147,7 +147,14 @@ public ICell RealizeCell(IColumn column, int columnIndex, int rowIndex)

public void SetItems(TreeDataGridItemsSourceView<TModel> items)
{
_roots.SetItems(items);
_ignoreCollectionChanges = true;

try {_roots.SetItems(items); }
finally { _ignoreCollectionChanges = false; }

_flattenedRows.Clear();
InitializeRows();
CollectionChanged?.Invoke(this, CollectionExtensions.ResetEvent);
}

public void Sort(Comparison<TModel>? comparison)
Expand Down Expand Up @@ -214,6 +221,9 @@ void IExpanderRowController<TModel>.OnChildCollectionChanged(
IExpanderRow<TModel> row,
NotifyCollectionChangedEventArgs e)
{
if (_ignoreCollectionChanges)
return;

if (row is HierarchicalRow<TModel> h)
OnCollectionChanged(h.ModelIndexPath, e);
else
Expand Down Expand Up @@ -269,7 +279,7 @@ private int AddRowsAndDescendants(int index, HierarchicalRow<TModel> row)

private void OnCollectionChanged(in IndexPath parentIndex, NotifyCollectionChangedEventArgs e)
{
if (_isExpandingCollapsing)
if (_ignoreCollectionChanges)
return;

void Add(int index, IEnumerable? items, bool raise)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -727,24 +727,20 @@ public void Can_Reassign_Items(bool sorted)
{
var data = CreateData();
var target = CreateTarget(data, sorted);
var rowsAddedRaised = 0;
var rowsRemovedRaised = 0;
var raised = 0;

Assert.Equal(5, target.Rows.Count);

target.Rows.CollectionChanged += (s, e) =>
{
if (e.Action == NotifyCollectionChangedAction.Add)
rowsAddedRaised += e.NewItems!.Count;
else if (e.Action == NotifyCollectionChangedAction.Remove)
rowsRemovedRaised += e.OldItems!.Count;
Assert.Equal(NotifyCollectionChangedAction.Reset, e.Action);
++raised;
};

target.Items = CreateData(10);

Assert.Equal(10, target.Rows.Count);
Assert.Equal(5, rowsRemovedRaised);
Assert.Equal(10, rowsAddedRaised);
Assert.Equal(1, raised);
}

[AvaloniaTheory(Timeout = 10000)]
Expand All @@ -754,25 +750,21 @@ public void Can_Reassign_Items_With_Expanded_Node(bool sorted)
{
var data = CreateData();
var target = CreateTarget(data, sorted);
var rowsAddedRaised = 0;
var rowsRemovedRaised = 0;
var raised = 0;

target.Expand(0);
Assert.Equal(10, target.Rows.Count);

target.Rows.CollectionChanged += (s, e) =>
{
if (e.Action == NotifyCollectionChangedAction.Add)
rowsAddedRaised += e.NewItems!.Count;
else if (e.Action == NotifyCollectionChangedAction.Remove)
rowsRemovedRaised += e.OldItems!.Count;
Assert.Equal(NotifyCollectionChangedAction.Reset, e.Action);
++raised;
};

target.Items = CreateData(12);

Assert.Equal(12, target.Rows.Count);
Assert.Equal(10, rowsRemovedRaised);
Assert.Equal(12, rowsAddedRaised);
Assert.Equal(1, raised);
}

[AvaloniaTheory(Timeout = 10000)]
Expand Down

0 comments on commit ffd6e29

Please sign in to comment.