StackPanel child visibility change handler
This commit is contained in:
@@ -9,10 +9,10 @@ namespace TerminalUI.Controls;
|
|||||||
|
|
||||||
public class Grid<T> : ChildContainerView<T>, IVisibilityChangeHandler
|
public class Grid<T> : ChildContainerView<T>, IVisibilityChangeHandler
|
||||||
{
|
{
|
||||||
|
private readonly List<IView> _forceRerenderChildren = new();
|
||||||
|
private readonly object _forceRerenderChildrenLock = new();
|
||||||
private List<RowDefinition> _rowDefinitions = new() {RowDefinition.Star(1)};
|
private List<RowDefinition> _rowDefinitions = new() {RowDefinition.Star(1)};
|
||||||
private List<ColumnDefinition> _columnDefinitions = new() {ColumnDefinition.Star(1)};
|
private List<ColumnDefinition> _columnDefinitions = new() {ColumnDefinition.Star(1)};
|
||||||
private List<IView> _forceRerenderChildren = new();
|
|
||||||
private readonly object _forceRerenderChildrenLock = new();
|
|
||||||
private ILogger<Grid<T>>? Logger => ApplicationContext?.LoggerFactory?.CreateLogger<Grid<T>>();
|
private ILogger<Grid<T>>? Logger => ApplicationContext?.LoggerFactory?.CreateLogger<Grid<T>>();
|
||||||
|
|
||||||
private delegate void WithSizes(RenderContext renderContext, ReadOnlySpan<int> widths, ReadOnlySpan<int> heights);
|
private delegate void WithSizes(RenderContext renderContext, ReadOnlySpan<int> widths, ReadOnlySpan<int> heights);
|
||||||
@@ -156,7 +156,7 @@ public class Grid<T> : ChildContainerView<T>, IVisibilityChangeHandler
|
|||||||
IReadOnlyList<IView> forceRerenderChildren;
|
IReadOnlyList<IView> forceRerenderChildren;
|
||||||
lock (_forceRerenderChildrenLock)
|
lock (_forceRerenderChildrenLock)
|
||||||
{
|
{
|
||||||
forceRerenderChildren = _forceRerenderChildren;
|
forceRerenderChildren = _forceRerenderChildren.ToList();
|
||||||
_forceRerenderChildren.Clear();
|
_forceRerenderChildren.Clear();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -1,11 +1,13 @@
|
|||||||
using System.Collections.ObjectModel;
|
using PropertyChanged.SourceGenerator;
|
||||||
using PropertyChanged.SourceGenerator;
|
|
||||||
using TerminalUI.Models;
|
using TerminalUI.Models;
|
||||||
|
using TerminalUI.Traits;
|
||||||
|
|
||||||
namespace TerminalUI.Controls;
|
namespace TerminalUI.Controls;
|
||||||
|
|
||||||
public partial class StackPanel<T> : ChildContainerView<T>
|
public partial class StackPanel<T> : ChildContainerView<T>, IVisibilityChangeHandler
|
||||||
{
|
{
|
||||||
|
private readonly List<IView> _forceRerenderChildren = new();
|
||||||
|
private readonly object _forceRerenderChildrenLock = new();
|
||||||
private readonly Dictionary<IView, Size> _requestedSizes = new();
|
private readonly Dictionary<IView, Size> _requestedSizes = new();
|
||||||
[Notify] private Orientation _orientation = Orientation.Vertical;
|
[Notify] private Orientation _orientation = Orientation.Vertical;
|
||||||
|
|
||||||
@@ -41,12 +43,29 @@ public partial class StackPanel<T> : ChildContainerView<T>
|
|||||||
{
|
{
|
||||||
var delta = 0;
|
var delta = 0;
|
||||||
var neededRerender = false;
|
var neededRerender = false;
|
||||||
|
IReadOnlyList<IView> forceRerenderChildren;
|
||||||
|
lock (_forceRerenderChildrenLock)
|
||||||
|
{
|
||||||
|
forceRerenderChildren = _forceRerenderChildren.ToList();
|
||||||
|
_forceRerenderChildren.Clear();
|
||||||
|
}
|
||||||
|
|
||||||
foreach (var child in Children)
|
foreach (var child in Children)
|
||||||
{
|
{
|
||||||
if (!child.IsVisible) continue;
|
if (!child.IsVisible) continue;
|
||||||
|
|
||||||
if (!_requestedSizes.TryGetValue(child, out var childSize)) throw new Exception("Child size not found");
|
if (!_requestedSizes.TryGetValue(child, out var childSize)) throw new Exception("Child size not found");
|
||||||
|
|
||||||
|
if (forceRerenderChildren.Contains(child))
|
||||||
|
{
|
||||||
|
renderContext = new RenderContext(
|
||||||
|
renderContext.ConsoleDriver,
|
||||||
|
true,
|
||||||
|
renderContext.Foreground,
|
||||||
|
renderContext.Background
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
var childPosition = Orientation == Orientation.Vertical
|
var childPosition = Orientation == Orientation.Vertical
|
||||||
? position with {Y = position.Y + delta}
|
? position with {Y = position.Y + delta}
|
||||||
: position with {X = position.X + delta};
|
: position with {X = position.X + delta};
|
||||||
@@ -74,4 +93,20 @@ public partial class StackPanel<T> : ChildContainerView<T>
|
|||||||
|
|
||||||
return neededRerender;
|
return neededRerender;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public void ChildVisibilityChanged(IView child)
|
||||||
|
{
|
||||||
|
var viewToForceRerender = child;
|
||||||
|
while (viewToForceRerender.VisualParent != null && viewToForceRerender.VisualParent != this)
|
||||||
|
{
|
||||||
|
viewToForceRerender = viewToForceRerender.VisualParent;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (viewToForceRerender.VisualParent != this) return;
|
||||||
|
|
||||||
|
lock (_forceRerenderChildrenLock)
|
||||||
|
{
|
||||||
|
_forceRerenderChildren.Add(viewToForceRerender);
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
Reference in New Issue
Block a user