diff --git a/samples/ControlCatalog/Pages/SplitViewPage.xaml b/samples/ControlCatalog/Pages/SplitViewPage.xaml index 7e629db2da..6902b27715 100644 --- a/samples/ControlCatalog/Pages/SplitViewPage.xaml +++ b/samples/ControlCatalog/Pages/SplitViewPage.xaml @@ -58,12 +58,18 @@ + - + + + + + + @@ -76,7 +82,7 @@ - + diff --git a/src/Avalonia.Controls/SplitView.cs b/src/Avalonia.Controls/SplitView.cs index fc3ff51f24..b71858f796 100644 --- a/src/Avalonia.Controls/SplitView.cs +++ b/src/Avalonia.Controls/SplitView.cs @@ -145,7 +145,7 @@ namespace Avalonia.Controls private bool _isPaneOpen; private Panel _pane; - private CompositeDisposable _pointerDisposables; + private IDisposable _pointerDisposable; public SplitView() { @@ -320,37 +320,14 @@ namespace Avalonia.Controls var topLevel = this.VisualRoot; if (topLevel is Window window) { - //Logic adapted from Popup - //Basically if we're using an overlay DisplayMode, close the pane if we don't click on the pane - IDisposable subscribeToEventHandler(T target, TEventHandler handler, - Action subscribe, Action unsubscribe) - { - subscribe(target, handler); - return Disposable.Create((unsubscribe, target, handler), state => state.unsubscribe(state.target, state.handler)); - } - - _pointerDisposables = new CompositeDisposable( - window.AddDisposableHandler(PointerPressedEvent, PointerPressedOutside, RoutingStrategies.Tunnel), - InputManager.Instance?.Process.Subscribe(OnNonClientClick), - subscribeToEventHandler(window, Window_Deactivated, - (x, handler) => x.Deactivated += handler, (x, handler) => x.Deactivated -= handler), - subscribeToEventHandler(window.PlatformImpl, OnWindowLostFocus, - (x, handler) => x.LostFocus += handler, (x, handler) => x.LostFocus -= handler)); + _pointerDisposable = window.AddDisposableHandler(PointerPressedEvent, PointerPressedOutside, RoutingStrategies.Tunnel); } } protected override void OnDetachedFromVisualTree(VisualTreeAttachmentEventArgs e) { base.OnDetachedFromVisualTree(e); - _pointerDisposables?.Dispose(); - } - - private void OnWindowLostFocus() - { - if (IsPaneOpen && ShouldClosePane()) - { - IsPaneOpen = false; - } + _pointerDisposable?.Dispose(); } private void PointerPressedOutside(object sender, PointerPressedEventArgs e) @@ -371,7 +348,12 @@ namespace Avalonia.Controls var src = e.Source as IVisual; while (src != null) { - if (src == _pane) + // Make assumption that if Popup is in visual tree, + // owning control is within pane + // This works because if pane is triggered to close + // when clicked anywhere else in Window, the pane + // would close before the popup is opened + if (src == _pane || src is PopupRoot) { closePane = false; break; @@ -385,31 +367,7 @@ namespace Avalonia.Controls e.Handled = true; } } - - private void OnNonClientClick(RawInputEventArgs obj) - { - if (!IsPaneOpen) - { - return; - } - - var mouse = obj as RawPointerEventArgs; - if (mouse?.Type == RawPointerEventType.NonClientLeftButtonDown) - - { - if (ShouldClosePane()) - IsPaneOpen = false; - } - } - - private void Window_Deactivated(object sender, EventArgs e) - { - if (IsPaneOpen && ShouldClosePane()) - { - IsPaneOpen = false; - } - } - + private bool ShouldClosePane() { return (DisplayMode == SplitViewDisplayMode.CompactOverlay || DisplayMode == SplitViewDisplayMode.Overlay);