diff --git a/src/Avalonia.Base/Layout/Layoutable.cs b/src/Avalonia.Base/Layout/Layoutable.cs
index 47f2217816..b2d47ad112 100644
--- a/src/Avalonia.Base/Layout/Layoutable.cs
+++ b/src/Avalonia.Base/Layout/Layoutable.cs
@@ -948,5 +948,17 @@ namespace Avalonia.Layout
{
return new Size(Math.Max(size.Width, 0), Math.Max(size.Height, 0));
}
+
+ internal override void SynchronizeCompositionProperties()
+ {
+ base.SynchronizeCompositionProperties();
+
+ if (CompositionVisual is { } visual)
+ {
+ // If the visual isn't using layout rounding, it's possible that antialiasing renders to pixels
+ // outside the current bounds. Extend the dirty rect by 1px in all directions in this case.
+ visual.ShouldExtendDirtyRect = !UseLayoutRounding;
+ }
+ }
}
}
diff --git a/src/Avalonia.Base/Rendering/Composition/Server/ServerCompositionVisual.cs b/src/Avalonia.Base/Rendering/Composition/Server/ServerCompositionVisual.cs
index 54848d885d..112a817541 100644
--- a/src/Avalonia.Base/Rendering/Composition/Server/ServerCompositionVisual.cs
+++ b/src/Avalonia.Base/Rendering/Composition/Server/ServerCompositionVisual.cs
@@ -254,6 +254,12 @@ namespace Avalonia.Rendering.Composition.Server
{
if (rc == default)
return;
+
+ // If the visual isn't using layout rounding, it's possible that antialiasing renders to pixels
+ // outside the current bounds. Extend the dirty rect by 1px in all directions in this case.
+ if (ShouldExtendDirtyRect && RenderOptions.EdgeMode != EdgeMode.Aliased)
+ rc = rc.Inflate(new Thickness(1));
+
Root?.AddDirtyRect(rc);
}
diff --git a/src/Avalonia.Base/composition-schema.xml b/src/Avalonia.Base/composition-schema.xml
index 6c48c71b51..ce989296b1 100644
--- a/src/Avalonia.Base/composition-schema.xml
+++ b/src/Avalonia.Base/composition-schema.xml
@@ -34,6 +34,7 @@
+