diff --git a/src/Avalonia.Controls.DataGrid/DataGridColumnHeader.cs b/src/Avalonia.Controls.DataGrid/DataGridColumnHeader.cs index 4c77c8b5ae..d1651b2d09 100644 --- a/src/Avalonia.Controls.DataGrid/DataGridColumnHeader.cs +++ b/src/Avalonia.Controls.DataGrid/DataGridColumnHeader.cs @@ -468,7 +468,7 @@ namespace Avalonia.Controls private void DataGridColumnHeader_PointerReleased(object sender, PointerReleasedEventArgs e) { - if (OwningColumn == null || e.Handled || !IsEnabled || e.MouseButton != MouseButton.Left) + if (OwningColumn == null || e.Handled || !IsEnabled || e.InitialPressMouseButton != MouseButton.Left) { return; } diff --git a/src/Avalonia.Controls/Button.cs b/src/Avalonia.Controls/Button.cs index d39ea73828..78d02e200f 100644 --- a/src/Avalonia.Controls/Button.cs +++ b/src/Avalonia.Controls/Button.cs @@ -294,7 +294,7 @@ namespace Avalonia.Controls { base.OnPointerReleased(e); - if (IsPressed && e.MouseButton == MouseButton.Left) + if (IsPressed && e.InitialPressMouseButton == MouseButton.Left) { IsPressed = false; e.Handled = true; diff --git a/src/Avalonia.Controls/Calendar/Calendar.cs b/src/Avalonia.Controls/Calendar/Calendar.cs index 89b375996b..beafab3edf 100644 --- a/src/Avalonia.Controls/Calendar/Calendar.cs +++ b/src/Avalonia.Controls/Calendar/Calendar.cs @@ -1565,7 +1565,7 @@ namespace Avalonia.Controls protected override void OnPointerReleased(PointerReleasedEventArgs e) { base.OnPointerReleased(e); - if (!HasFocusInternal && e.MouseButton == MouseButton.Left) + if (!HasFocusInternal && e.InitialPressMouseButton == MouseButton.Left) { FocusManager.Instance.Focus(this); } diff --git a/src/Avalonia.Controls/Calendar/CalendarButton.cs b/src/Avalonia.Controls/Calendar/CalendarButton.cs index 53852defb3..a273e68d56 100644 --- a/src/Avalonia.Controls/Calendar/CalendarButton.cs +++ b/src/Avalonia.Controls/Calendar/CalendarButton.cs @@ -173,7 +173,7 @@ namespace Avalonia.Controls.Primitives protected override void OnPointerReleased(PointerReleasedEventArgs e) { base.OnPointerReleased(e); - if (e.MouseButton == MouseButton.Left) + if (e.InitialPressMouseButton == MouseButton.Left) CalendarLeftMouseButtonUp?.Invoke(this, e); } } diff --git a/src/Avalonia.Controls/Calendar/CalendarDayButton.cs b/src/Avalonia.Controls/Calendar/CalendarDayButton.cs index cb2a98e5ca..e62a1ce1f4 100644 --- a/src/Avalonia.Controls/Calendar/CalendarDayButton.cs +++ b/src/Avalonia.Controls/Calendar/CalendarDayButton.cs @@ -231,7 +231,7 @@ namespace Avalonia.Controls.Primitives { base.OnPointerReleased(e); - if (e.MouseButton == MouseButton.Left) + if (e.InitialPressMouseButton == MouseButton.Left) CalendarDayButtonMouseUp?.Invoke(this, e); } } diff --git a/src/Avalonia.Controls/ContextMenu.cs b/src/Avalonia.Controls/ContextMenu.cs index a5025df82d..5dfa5863f5 100644 --- a/src/Avalonia.Controls/ContextMenu.cs +++ b/src/Avalonia.Controls/ContextMenu.cs @@ -192,7 +192,7 @@ namespace Avalonia.Controls e.Handled = true; } - if (e.MouseButton == MouseButton.Right) + if (e.InitialPressMouseButton == MouseButton.Right) { if (contextMenu.CancelOpening()) return; diff --git a/src/Avalonia.Controls/MenuItem.cs b/src/Avalonia.Controls/MenuItem.cs index 8c82fed58d..3ba0007f6b 100644 --- a/src/Avalonia.Controls/MenuItem.cs +++ b/src/Avalonia.Controls/MenuItem.cs @@ -337,7 +337,7 @@ namespace Avalonia.Controls { base.OnPointerEnter(e); - var point = e.GetPointerPoint(null); + var point = e.GetCurrentPoint(null); RaiseEvent(new PointerEventArgs(PointerEnterItemEvent, this, e.Pointer, this.VisualRoot, point.Position, e.Timestamp, point.Properties, e.KeyModifiers)); } @@ -347,7 +347,7 @@ namespace Avalonia.Controls { base.OnPointerLeave(e); - var point = e.GetPointerPoint(null); + var point = e.GetCurrentPoint(null); RaiseEvent(new PointerEventArgs(PointerLeaveItemEvent, this, e.Pointer, this.VisualRoot, point.Position, e.Timestamp, point.Properties, e.KeyModifiers)); } diff --git a/src/Avalonia.Controls/Platform/DefaultMenuInteractionHandler.cs b/src/Avalonia.Controls/Platform/DefaultMenuInteractionHandler.cs index 98f925cd0c..b5dbd1e668 100644 --- a/src/Avalonia.Controls/Platform/DefaultMenuInteractionHandler.cs +++ b/src/Avalonia.Controls/Platform/DefaultMenuInteractionHandler.cs @@ -356,7 +356,7 @@ namespace Avalonia.Controls.Platform { var item = GetMenuItem(e.Source as IControl); - if (e.MouseButton == MouseButton.Left && item?.HasSubMenu == false) + if (e.InitialPressMouseButton == MouseButton.Left && item?.HasSubMenu == false) { Click(item); e.Handled = true; diff --git a/src/Avalonia.Controls/RepeatButton.cs b/src/Avalonia.Controls/RepeatButton.cs index 07a1e82638..a982a0970c 100644 --- a/src/Avalonia.Controls/RepeatButton.cs +++ b/src/Avalonia.Controls/RepeatButton.cs @@ -98,10 +98,10 @@ namespace Avalonia.Controls { base.OnPointerReleased(e); - if (e.MouseButton == MouseButton.Left) + if (e.InitialPressMouseButton == MouseButton.Left) { StopTimer(); } } } -} \ No newline at end of file +} diff --git a/src/Avalonia.Controls/TabControl.cs b/src/Avalonia.Controls/TabControl.cs index 50bcb034ac..61ac0822b0 100644 --- a/src/Avalonia.Controls/TabControl.cs +++ b/src/Avalonia.Controls/TabControl.cs @@ -196,7 +196,7 @@ namespace Avalonia.Controls protected override void OnPointerReleased(PointerReleasedEventArgs e) { - if (e.MouseButton == MouseButton.Left && e.Pointer.Type != PointerType.Mouse) + if (e.InitialPressMouseButton == MouseButton.Left && e.Pointer.Type != PointerType.Mouse) { var container = GetContainerFromEventSource(e.Source); if (container != null diff --git a/src/Avalonia.Controls/Utils/SelectingItemsControlSelectionAdapter.cs b/src/Avalonia.Controls/Utils/SelectingItemsControlSelectionAdapter.cs index 4d814170c6..78361fcc8f 100644 --- a/src/Avalonia.Controls/Utils/SelectingItemsControlSelectionAdapter.cs +++ b/src/Avalonia.Controls/Utils/SelectingItemsControlSelectionAdapter.cs @@ -178,7 +178,7 @@ namespace Avalonia.Controls.Utils /// The event data. private void OnSelectorPointerReleased(object sender, PointerReleasedEventArgs e) { - if (e.MouseButton == MouseButton.Left) + if (e.InitialPressMouseButton == MouseButton.Left) { OnCommit(); } diff --git a/src/Avalonia.Input/Gestures.cs b/src/Avalonia.Input/Gestures.cs index 6b06151773..a5bd4feb64 100644 --- a/src/Avalonia.Input/Gestures.cs +++ b/src/Avalonia.Input/Gestures.cs @@ -97,7 +97,7 @@ namespace Avalonia.Input if (s_lastPress.TryGetTarget(out var target) && target == e.Source) { - var et = e.MouseButton != MouseButton.Right ? TappedEvent : RightTappedEvent; + var et = e.InitialPressMouseButton != MouseButton.Right ? TappedEvent : RightTappedEvent; e.Source.RaiseEvent(new RoutedEventArgs(et)); } } diff --git a/src/Avalonia.Input/MouseDevice.cs b/src/Avalonia.Input/MouseDevice.cs index 0d5471f790..c84596b913 100644 --- a/src/Avalonia.Input/MouseDevice.cs +++ b/src/Avalonia.Input/MouseDevice.cs @@ -221,7 +221,7 @@ namespace Avalonia.Input _lastClickTime = timestamp; _lastClickRect = new Rect(p, new Size()) .Inflate(new Thickness(settings.DoubleClickSize.Width / 2, settings.DoubleClickSize.Height / 2)); - _lastMouseDownButton = properties.GetObsoleteMouseButton(); + _lastMouseDownButton = properties.PointerUpdateKind.GetMouseButton(); var e = new PointerPressedEventArgs(source, _pointer, root, p, timestamp, properties, inputModifiers, _clickCount); source.RaiseEvent(e); return e.Handled; @@ -267,7 +267,8 @@ namespace Avalonia.Input if (hit != null) { var source = GetSource(hit); - var e = new PointerReleasedEventArgs(source, _pointer, root, p, timestamp, props, inputModifiers); + var e = new PointerReleasedEventArgs(source, _pointer, root, p, timestamp, props, inputModifiers, + _lastMouseDownButton); source?.RaiseEvent(e); _pointer.Capture(null); diff --git a/src/Avalonia.Input/PointerEventArgs.cs b/src/Avalonia.Input/PointerEventArgs.cs index 5b3c43e4df..e12a20f7a2 100644 --- a/src/Avalonia.Input/PointerEventArgs.cs +++ b/src/Avalonia.Input/PointerEventArgs.cs @@ -88,9 +88,20 @@ namespace Avalonia.Input return _rootVisualPosition * _rootVisual.TransformToVisual(relativeTo) ?? default; } - public PointerPoint GetPointerPoint(IVisual relativeTo) + [Obsolete("Use GetCurrentPoint")] + public PointerPoint GetPointerPoint(IVisual relativeTo) => GetCurrentPoint(relativeTo); + + /// + /// Returns the PointerPoint associated with the current event + /// + /// The visual which coordinate system to use. Pass null for toplevel coordinate system + /// + public PointerPoint GetCurrentPoint(IVisual relativeTo) => new PointerPoint(Pointer, GetPosition(relativeTo), _properties); + /// + /// Returns the current pointer point properties + /// protected PointerPointProperties Properties => _properties; } @@ -124,7 +135,7 @@ namespace Avalonia.Input public int ClickCount => _obsoleteClickCount; [Obsolete("Use PointerUpdateKind")] - public MouseButton MouseButton => Properties.GetObsoleteMouseButton(); + public MouseButton MouseButton => Properties.PointerUpdateKind.GetMouseButton(); } public class PointerReleasedEventArgs : PointerEventArgs @@ -132,15 +143,21 @@ namespace Avalonia.Input public PointerReleasedEventArgs( IInteractive source, IPointer pointer, IVisual rootVisual, Point rootVisualPosition, ulong timestamp, - PointerPointProperties properties, KeyModifiers modifiers) + PointerPointProperties properties, KeyModifiers modifiers, + MouseButton initialPressMouseButton) : base(InputElement.PointerReleasedEvent, source, pointer, rootVisual, rootVisualPosition, timestamp, properties, modifiers) { - + InitialPressMouseButton = initialPressMouseButton; } - [Obsolete("Use PointerUpdateKind")] - public MouseButton MouseButton => Properties.GetObsoleteMouseButton(); + /// + /// Gets the mouse button that triggered the corresponding PointerPressed event + /// + public MouseButton InitialPressMouseButton { get; } + + [Obsolete("Either use GetCurrentPoint(this).Properties.PointerUpdateKind or InitialPressMouseButton, see https://github.com/AvaloniaUI/Avalonia/wiki/Pointer-events-in-0.9 for more details", true)] + public MouseButton MouseButton => InitialPressMouseButton; } public class PointerCaptureLostEventArgs : RoutedEventArgs diff --git a/src/Avalonia.Input/PointerPoint.cs b/src/Avalonia.Input/PointerPoint.cs index d823a78090..e9f3c02b7f 100644 --- a/src/Avalonia.Input/PointerPoint.cs +++ b/src/Avalonia.Input/PointerPoint.cs @@ -49,17 +49,6 @@ namespace Avalonia.Input } public static PointerPointProperties None { get; } = new PointerPointProperties(); - - public MouseButton GetObsoleteMouseButton() - { - if (PointerUpdateKind == PointerUpdateKind.LeftButtonPressed || PointerUpdateKind == PointerUpdateKind.LeftButtonReleased) - return MouseButton.Left; - if (PointerUpdateKind == PointerUpdateKind.MiddleButtonPressed || PointerUpdateKind == PointerUpdateKind.MiddleButtonReleased) - return MouseButton.Middle; - if (PointerUpdateKind == PointerUpdateKind.RightButtonPressed || PointerUpdateKind == PointerUpdateKind.RightButtonReleased) - return MouseButton.Right; - return MouseButton.None; - } } public enum PointerUpdateKind @@ -72,4 +61,18 @@ namespace Avalonia.Input RightButtonReleased, Other } + + public static class PointerUpdateKindExtensions + { + public static MouseButton GetMouseButton(this PointerUpdateKind kind) + { + if (kind == PointerUpdateKind.LeftButtonPressed || kind == PointerUpdateKind.LeftButtonReleased) + return MouseButton.Left; + if (kind == PointerUpdateKind.MiddleButtonPressed || kind == PointerUpdateKind.MiddleButtonReleased) + return MouseButton.Middle; + if (kind == PointerUpdateKind.RightButtonPressed || kind == PointerUpdateKind.RightButtonReleased) + return MouseButton.Right; + return MouseButton.None; + } + } } diff --git a/src/Avalonia.Input/TouchDevice.cs b/src/Avalonia.Input/TouchDevice.cs index 765e02848f..b231c9fff4 100644 --- a/src/Avalonia.Input/TouchDevice.cs +++ b/src/Avalonia.Input/TouchDevice.cs @@ -60,7 +60,7 @@ namespace Avalonia.Input args.Root, args.Position, ev.Timestamp, new PointerPointProperties(GetModifiers(args.InputModifiers, false), PointerUpdateKind.LeftButtonReleased), - GetKeyModifiers(args.InputModifiers))); + GetKeyModifiers(args.InputModifiers), MouseButton.Left)); } } diff --git a/tests/Avalonia.Controls.UnitTests/Platform/DefaultMenuInteractionHandlerTests.cs b/tests/Avalonia.Controls.UnitTests/Platform/DefaultMenuInteractionHandlerTests.cs index ff11bc513d..989bd744a6 100644 --- a/tests/Avalonia.Controls.UnitTests/Platform/DefaultMenuInteractionHandlerTests.cs +++ b/tests/Avalonia.Controls.UnitTests/Platform/DefaultMenuInteractionHandlerTests.cs @@ -18,7 +18,9 @@ namespace Avalonia.Controls.UnitTests.Platform default); static PointerReleasedEventArgs CreateReleased(IInteractive source) => new PointerReleasedEventArgs(source, - new FakePointer(), (IVisual)source, default,0, new PointerPointProperties(RawInputModifiers.None, PointerUpdateKind.LeftButtonReleased), default); + new FakePointer(), (IVisual)source, default,0, + new PointerPointProperties(RawInputModifiers.None, PointerUpdateKind.LeftButtonReleased), + default, MouseButton.Left); public class TopLevel { diff --git a/tests/Avalonia.UnitTests/MouseTestHelper.cs b/tests/Avalonia.UnitTests/MouseTestHelper.cs index d6e64936c7..48c4d73471 100644 --- a/tests/Avalonia.UnitTests/MouseTestHelper.cs +++ b/tests/Avalonia.UnitTests/MouseTestHelper.cs @@ -86,8 +86,7 @@ namespace Avalonia.UnitTests { _pointer.Capture(null); target.RaiseEvent(new PointerReleasedEventArgs(source, _pointer, (IVisual)target, position, - Timestamp(), props, - GetModifiers(modifiers))); + Timestamp(), props, GetModifiers(modifiers), _pressedButton)); } else Move(target, source, position);