Browse Source

Use the correct flag to determine if extra dirty rect needs to be combined with existing one (#20896)

pull/20912/head
Nikita Tsukanov 1 week ago
committed by GitHub
parent
commit
97f36b9f34
No known key found for this signature in database GPG Key ID: B5690EEEBB952194
  1. 4
      src/Avalonia.Base/Rendering/Composition/Server/ServerCompositionVisual/ServerCompositionVisual.ComputedProperties.cs
  2. 2
      src/Avalonia.Base/Rendering/Composition/Server/ServerCompositionVisual/ServerCompositionVisual.DirtyInputs.cs
  3. 6
      src/Avalonia.Base/Rendering/Composition/Server/ServerCompositionVisual/ServerCompositionVisual.Update.cs
  4. 25
      tests/Avalonia.Base.UnitTests/Rendering/CompositorInvalidationTests.cs

4
src/Avalonia.Base/Rendering/Composition/Server/ServerCompositionVisual/ServerCompositionVisual.ComputedProperties.cs

@ -50,7 +50,7 @@ partial class ServerCompositionVisual
private LtrbRect? _ownClipRect; private LtrbRect? _ownClipRect;
private bool _hasExtraDirtyRect; private bool _needsToAddExtraDirtyRectToDirtyRegion;
private LtrbRect _extraDirtyRect; private LtrbRect _extraDirtyRect;
public virtual LtrbRect? ComputeOwnContentBounds() => null; public virtual LtrbRect? ComputeOwnContentBounds() => null;
@ -107,7 +107,7 @@ partial class ServerCompositionVisual
_isDirtyForRender |= dirtyForRender; _isDirtyForRender |= dirtyForRender;
// If node itself is dirty for render, we don't need to keep track of extra dirty rects // If node itself is dirty for render, we don't need to keep track of extra dirty rects
_hasExtraDirtyRect = !dirtyForRender && (_hasExtraDirtyRect || additionalDirtyRegion); _needsToAddExtraDirtyRectToDirtyRegion = !dirtyForRender && (_needsToAddExtraDirtyRectToDirtyRegion || additionalDirtyRegion);
} }
public void RecomputeOwnProperties() public void RecomputeOwnProperties()

2
src/Avalonia.Base/Rendering/Composition/Server/ServerCompositionVisual/ServerCompositionVisual.DirtyInputs.cs

@ -166,7 +166,7 @@ partial class ServerCompositionVisual
protected void AddExtraDirtyRect(LtrbRect rect) protected void AddExtraDirtyRect(LtrbRect rect)
{ {
_extraDirtyRect = _hasExtraDirtyRect ? _extraDirtyRect.Union(rect) : rect; _extraDirtyRect = _delayPropagateHasExtraDirtyRects ? _extraDirtyRect.Union(rect) : rect;
_delayPropagateHasExtraDirtyRects = true; _delayPropagateHasExtraDirtyRects = true;
EnqueueOwnPropertiesRecompute(); EnqueueOwnPropertiesRecompute();
} }

6
src/Avalonia.Base/Rendering/Composition/Server/ServerCompositionVisual/ServerCompositionVisual.Update.cs

@ -56,7 +56,7 @@ internal partial class ServerCompositionVisual
private bool NeedToPushBoundsAffectingProperties(ServerCompositionVisual node) private bool NeedToPushBoundsAffectingProperties(ServerCompositionVisual node)
{ {
return (node._isDirtyForRenderInSubgraph || node._hasExtraDirtyRect || node._contentChanged); return (node._isDirtyForRenderInSubgraph || node._needsToAddExtraDirtyRectToDirtyRegion || node._contentChanged);
} }
public void PreSubgraph(ServerCompositionVisual node, out bool visitChildren) public void PreSubgraph(ServerCompositionVisual node, out bool visitChildren)
@ -142,7 +142,7 @@ internal partial class ServerCompositionVisual
// specified before the tranform, i.e. in inner space, hence we have to pick them // specified before the tranform, i.e. in inner space, hence we have to pick them
// up before we pop the transform from the transform stack. // up before we pop the transform from the transform stack.
// //
if (node._hasExtraDirtyRect) if (node._needsToAddExtraDirtyRectToDirtyRegion)
{ {
AddToDirtyRegion(node._extraDirtyRect); AddToDirtyRegion(node._extraDirtyRect);
} }
@ -169,7 +169,7 @@ internal partial class ServerCompositionVisual
node._isDirtyForRender = false; node._isDirtyForRender = false;
node._isDirtyForRenderInSubgraph = false; node._isDirtyForRenderInSubgraph = false;
node._needsBoundingBoxUpdate = false; node._needsBoundingBoxUpdate = false;
node._hasExtraDirtyRect = false; node._needsToAddExtraDirtyRectToDirtyRegion = false;
node._contentChanged = false; node._contentChanged = false;
} }

25
tests/Avalonia.Base.UnitTests/Rendering/CompositorInvalidationTests.cs

@ -39,6 +39,31 @@ public class CompositorInvalidationTests : CompositorTestsBase
} }
} }
[Fact]
public void Sibling_Controls_Should_Invalidate_Union_Rect_When_Removed()
{
using (var s = new CompositorCanvas())
{
var control = new Border()
{
Background = Brushes.Red, Width = 20, Height = 10,
[Canvas.LeftProperty] = 30, [Canvas.TopProperty] = 10
};
var control2 = new Border()
{
Background = Brushes.Blue, Width = 20, Height = 10,
[Canvas.LeftProperty] = 30, [Canvas.TopProperty] = 50
};
s.Canvas.Children.Add(control);
s.Canvas.Children.Add(control2);
s.RunJobs();
s.Events.Rects.Clear();
s.Canvas.Children.Remove(control);
s.Canvas.Children.Remove(control2);
s.AssertRects(new Rect(30, 10, 20, 50));
}
}
[Fact] [Fact]
public void Control_Should_Invalidate_Both_Own_Rects_When_Moved() public void Control_Should_Invalidate_Both_Own_Rects_When_Moved()
{ {

Loading…
Cancel
Save