diff --git a/src/Avalonia.Visuals/Rendering/SceneGraph/IVisualNode.cs b/src/Avalonia.Visuals/Rendering/SceneGraph/IVisualNode.cs index 681f00799b0..1668f592ecc 100644 --- a/src/Avalonia.Visuals/Rendering/SceneGraph/IVisualNode.cs +++ b/src/Avalonia.Visuals/Rendering/SceneGraph/IVisualNode.cs @@ -93,5 +93,7 @@ public interface IVisualNode : IDisposable /// to hit test children they must be hit tested manually. /// bool HitTest(Point p); + + bool Disposed { get; } } } diff --git a/src/Avalonia.Visuals/Rendering/SceneGraph/Scene.cs b/src/Avalonia.Visuals/Rendering/SceneGraph/Scene.cs index 352d41d0241..ffa0b0bcc5a 100644 --- a/src/Avalonia.Visuals/Rendering/SceneGraph/Scene.cs +++ b/src/Avalonia.Visuals/Rendering/SceneGraph/Scene.cs @@ -98,7 +98,10 @@ public Scene CloneScene() public void Dispose() { - Root.Dispose(); + foreach (var node in _index.Values) + { + node.Dispose(); + } } /// @@ -137,6 +140,8 @@ public void Remove(IVisualNode node) Contract.Requires(node != null); _index.Remove(node.Visual); + + node.Dispose(); } private VisualNode Clone(VisualNode source, IVisualNode parent, Dictionary index) diff --git a/src/Avalonia.Visuals/Rendering/SceneGraph/VisualNode.cs b/src/Avalonia.Visuals/Rendering/SceneGraph/VisualNode.cs index 427f819200b..3ee689b6d24 100644 --- a/src/Avalonia.Visuals/Rendering/SceneGraph/VisualNode.cs +++ b/src/Avalonia.Visuals/Rendering/SceneGraph/VisualNode.cs @@ -113,6 +113,11 @@ public double Opacity /// The child to add. public void AddChild(IVisualNode child) { + if (child.Disposed) + { + throw new ObjectDisposedException("Visual node for {node.Visual}"); + } + EnsureChildrenCreated(); _children.Add(child); } @@ -135,7 +140,6 @@ public void RemoveChild(IVisualNode child) { EnsureChildrenCreated(); _children.Remove(child); - child.Dispose(); } /// @@ -145,13 +149,13 @@ public void RemoveChild(IVisualNode child) /// The child to add. public void ReplaceChild(int index, IVisualNode node) { - EnsureChildrenCreated(); - var old = _children[index]; - _children[index] = node; - if (node != old) + if (node.Disposed) { - old.Dispose(); + throw new ObjectDisposedException("Visual node for {node.Visual}"); } + + EnsureChildrenCreated(); + _children[index] = node; } /// @@ -332,13 +336,11 @@ private void EnsureDrawOperationsCreated() _drawOperationsCloned = false; } } + + public bool Disposed { get; } public void Dispose() { - foreach (var child in Children) - { - child.Dispose(); - } _drawOperationsRefCounter?.Dispose(); }