From 8f6467715249cee1eee871aaaae6643c3c921bf8 Mon Sep 17 00:00:00 2001 From: Mike Goatly <4577868+mikegoatly@users.noreply.github.com> Date: Sun, 19 Apr 2026 12:30:13 +0100 Subject: [PATCH] Fixes/windows back requested (#21207) * feat: Add test verifyig BackRequested not working * fix: Use InputRoot not this when checking for back requested --- src/Avalonia.Controls/TopLevel.cs | 2 +- .../TopLevelTests.cs | 30 +++++++++++++++++++ 2 files changed, 31 insertions(+), 1 deletion(-) diff --git a/src/Avalonia.Controls/TopLevel.cs b/src/Avalonia.Controls/TopLevel.cs index 44b82c886f..7a9cfa4abb 100644 --- a/src/Avalonia.Controls/TopLevel.cs +++ b/src/Avalonia.Controls/TopLevel.cs @@ -286,7 +286,7 @@ namespace Avalonia.Controls _backGestureSubscription = _inputManager?.PreProcess.Subscribe(e => { - if (e.Root != this) + if (e.Root != InputRoot) return; bool backRequested = false; diff --git a/tests/Avalonia.Controls.UnitTests/TopLevelTests.cs b/tests/Avalonia.Controls.UnitTests/TopLevelTests.cs index 470030ef0b..15c1f650da 100644 --- a/tests/Avalonia.Controls.UnitTests/TopLevelTests.cs +++ b/tests/Avalonia.Controls.UnitTests/TopLevelTests.cs @@ -253,6 +253,36 @@ namespace Avalonia.Controls.UnitTests } } + [Fact] + public void XButton1Down_Should_Raise_BackRequested() + { + // Regression test: prior to this fix, the PreProcess subscription compared + // e.Root against 'this' (the TopLevel/Window), but e.Root is set to the + // PresentationSource (the IInputRoot), not the Window itself. The comparison + // always failed so BackRequested was never raised for XButton1Down. + var services = TestServices.StyledWindow.With(inputManager: new InputManager()); + + using (UnitTestApplication.Start(services)) + { + var impl = CreateMockTopLevelImpl(true); + var target = new TestTopLevel(impl.Object); + + var raised = false; + target.BackRequested += (_, _) => raised = true; + + var mouseDevice = new MouseDevice(new Pointer(0, PointerType.Mouse, true)); + impl.Object.Input!(new RawPointerEventArgs( + mouseDevice, + timestamp: 0, + target.InputRoot, + RawPointerEventType.XButton1Down, + new RawPointerPoint { Position = default }, + RawInputModifiers.None)); + + Assert.True(raised); + } + } + [Fact] public void TopLevel_Should_Unfocus_When_Impl_Focus_Is_Lost() {