11using System ;
22using System . Collections . Generic ;
3+ using System . Linq ;
34using System . IO ;
45using System . Threading . Tasks ;
56using Avalonia ;
1112using Avalonia . Media ;
1213using Avalonia . Platform . Storage ;
1314using Avalonia . VisualTree ;
15+ using SourceGit . ViewModels ;
1416
1517namespace SourceGit . Views
1618{
@@ -132,7 +134,7 @@ protected override async void OnKeyDown(KeyEventArgs e)
132134
133135 await App . CopyTextAsync ( path ) ;
134136 e . Handled = true ;
135- }
137+ }
136138 }
137139 else if ( node . Backend is { Type : Models . ObjectType . Blob } file &&
138140 e . Key == Key . S &&
@@ -295,6 +297,17 @@ protected override async void OnPropertyChanged(AvaloniaPropertyChangedEventArgs
295297
296298 if ( change . Property == RevisionProperty )
297299 {
300+ var selectedNode = _revisionFileRowsListBox ? . SelectedItem as RevisionFileTreeNode ;
301+
302+ var expandedObjects = new List < Models . Object > ( ) ;
303+ foreach ( var node in _rows )
304+ {
305+ if ( node . IsExpanded )
306+ {
307+ expandedObjects . Add ( node . Backend ) ;
308+ }
309+ }
310+
298311 _tree . Clear ( ) ;
299312 _searchResult . Clear ( ) ;
300313
@@ -324,10 +337,51 @@ protected override async void OnPropertyChanged(AvaloniaPropertyChangedEventArgs
324337
325338 Rows . Clear ( ) ;
326339 Rows . AddRange ( topTree ) ;
340+
341+ _revisionFileRowsListBox ??= this . Find < RevisionFileRowsListBox > ( "RevisionFileRowsListBox" ) ;
342+
343+ if ( _revisionFileRowsListBox is { IsArrangeValid : true } )
344+ {
345+ RestoreTreeState ( expandedObjects , selectedNode ) ;
346+ }
347+
327348 GC . Collect ( ) ;
328349 }
329350 }
330351
352+ private void RestoreTreeState ( List < Models . Object > expandedObjects , RevisionFileTreeNode selectedNode )
353+ {
354+ for ( int i = 0 ; i < _rows . Count ; i ++ )
355+ {
356+ var revisionFileTreeNode = _rows [ i ] ;
357+
358+ if ( ! revisionFileTreeNode . IsFolder )
359+ continue ;
360+
361+ if ( expandedObjects . FirstOrDefault ( o => o . SHA == revisionFileTreeNode . Backend . SHA || o . Path == revisionFileTreeNode . Backend . Path ) != null )
362+ {
363+ ToggleNodeIsExpanded ( revisionFileTreeNode ) ;
364+ }
365+ }
366+
367+ if ( selectedNode != null )
368+ {
369+ foreach ( var node in _rows )
370+ {
371+ if ( node . Backend . SHA != selectedNode . Backend . SHA && node . Backend . Path != selectedNode . Backend . Path )
372+ continue ;
373+
374+ selectedNode = node ;
375+ break ;
376+ }
377+ }
378+
379+ if ( _revisionFileRowsListBox != null )
380+ {
381+ _revisionFileRowsListBox . SelectedItem = selectedNode ;
382+ }
383+ }
384+
331385 private void OnTreeNodeContextRequested ( object sender , ContextRequestedEventArgs e )
332386 {
333387 if ( DataContext is ViewModels . CommitDetail { Repository : ViewModels . Repository repo , Commit : Models . Commit commit } vm &&
@@ -339,7 +393,7 @@ private void OnTreeNodeContextRequested(object sender, ContextRequestedEventArgs
339393 _ => CreateRevisionFileContextMenu ( repo , vm , commit , obj ) ,
340394 } ;
341395 menu . Open ( grid ) ;
342- }
396+ }
343397
344398 e . Handled = true ;
345399 }
@@ -363,9 +417,9 @@ private async void OnRowsSelectionChanged(object sender, SelectionChangedEventAr
363417
364418 if ( sender is ListBox { SelectedItem : ViewModels . RevisionFileTreeNode { IsFolder : false } node } )
365419 await vm . ViewRevisionFileAsync ( node . Backend ) ;
366- else
420+ else
367421 await vm . ViewRevisionFileAsync ( null ) ;
368- }
422+ }
369423
370424 private async Task < List < ViewModels . RevisionFileTreeNode > > GetChildrenOfTreeNodeAsync ( ViewModels . RevisionFileTreeNode node )
371425 {
@@ -671,5 +725,6 @@ public ContextMenu CreateRevisionFileContextMenu(ViewModels.Repository repo, Vie
671725 private List < ViewModels . RevisionFileTreeNode > _tree = [ ] ;
672726 private bool _disableSelectionChangingEvent = false ;
673727 private List < ViewModels . RevisionFileTreeNode > _searchResult = [ ] ;
728+ private RevisionFileRowsListBox _revisionFileRowsListBox ;
674729 }
675730}
0 commit comments