C# - WPF -禁止滚动此元素,但允许滚动父元素

zfycwa2u  于 2023-05-01  发布在  C#
关注(0)|答案(1)|浏览(176)

后台

我需要防止ComboBox滚动(使用滚轮),当它是focused
但是,我需要它的父UIElement仍然滚动。
我从这个问题中得到了以下代码,它可以防止 * 任何 * 滚动,包括父UIElement的滚动。

代码

<ComboBox comboBox:NoScrollingBehaviour.Enabled="True"
          IsEditable="True" 
          IsTextSearchEnabled="True" 
          IsTextSearchCaseSensitive="False" 
          StaysOpenOnEdit="True"
          Text="{Binding MyTextProperty}"
          ItemsSource="{Binding DataContext.MySourceProperty, ElementName=MyElementName}"/>
using System.Windows;
using System.Windows.Input;

namespace AE.UI.ComboBox
{
    public static class NoScrollingBehaviour
    {
        public static readonly DependencyProperty EnabledProperty =
            DependencyProperty.RegisterAttached("Enabled", typeof(bool), typeof(NoScrollingBehaviour),
                                                new UIPropertyMetadata(false, OnEnabledChanged));

        public static bool GetEnabled(System.Windows.Controls.ComboBox comboBox) => (bool)comboBox.GetValue(EnabledProperty);

        public static void SetEnabled(System.Windows.Controls.ComboBox comboBox, bool value) => comboBox.SetValue(EnabledProperty, value);

        private static void OnEnabledChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
        {
            var comboBox = (System.Windows.Controls.ComboBox)d;
            if (GetEnabled(comboBox))
                comboBox.PreviewMouseWheel += OnPreviewMouseWheel;
        }

        private static void OnPreviewMouseWheel(object sender, MouseWheelEventArgs e)
        {
            var comboBox = (System.Windows.Controls.ComboBox)sender;
            if (!GetEnabled(comboBox))
                return;
            
            if (comboBox.IsDropDownOpen)
                return;

            e.Handled = true;
        }
    }
}

问题

如何允许父UIElement滚动,同时仍然阻止ComboBox滚动?

ego6inou

ego6inou1#

我可以使用下面的代码来传播它

private static void OnPreviewMouseWheel(object sender, MouseWheelEventArgs e)
        {
            var comboBox = (System.Windows.Controls.ComboBox)sender;
            if (!GetEnabled(comboBox))
                return;

            if (comboBox.IsDropDownOpen)
                return;

            e.Handled = true;
            
            var parentScrollViewer = comboBox.GetVisualParent<ScrollViewer>();
            parentScrollViewer?.ScrollToVerticalOffset(parentScrollViewer.VerticalOffset - e.Delta * 0.4);
        }

 public static T GetVisualParent<T>(this DependencyObject child) where T : Visual
        {
            while ((child != null) && !(child is T))
            {
                child = VisualTreeHelper.GetParent(child);
            }
            return child as T;
        }

注意:您可能需要缩放e.Delta(我要求缩放0.4,但我不确定这是否在任何地方都相同)

相关问题