wpf scrollviewer mousewheel无法使用stackpanel

时间:2014-08-18 15:23:00

标签: c# scrollviewer mousewheel stackpanel wpf-4.0

我有一个用scrollviewer包装的stackpanel。在stackpanel里面,我有一些网格,在网格内部再次有堆叠面板,一些瓷砖由MahApps Metro控制。

如果我拖动滚动条,则scrollviewer正常工作。但是鼠标轮不工作。可能是一些控制是窃取鼠标轮动作但我不能指出哪一个。我专注于滚动条时试图滚动鼠标滚轮。但它仍然没有用。

<ScrollViewer x:Name="TS" Grid.Row="1" HorizontalAlignment="Stretch" HorizontalScrollBarVisibility="Auto" VerticalScrollBarVisibility="Disabled" CanContentScroll="True" PanningMode="HorizontalOnly" SnapsToDevicePixels="True" Background="Transparent">
    <StackPanel x:Name="TilesPanel" VerticalAlignment="Top" HorizontalAlignment="Stretch" Orientation="Horizontal">
        <StackPanel.Resources>
            <Style TargetType="{x:Type Grid}">
                <Setter Property="Margin" Value="0,50,0,0"/>
            </Style>
        </StackPanel.Resources>
        <Separator Background="{x:Null}" Width="110"></Separator>
        <Grid>
            <StackPanel>
                <StackPanel Orientation="Horizontal">
                    <StackPanel.Resources>
                        <Style TargetType="{x:Type Grid}">
                            <Setter Property="Margin" Value="10,0,0,0"/>
                        </Style>
                    </StackPanel.Resources>
                    <Grid Height="260">
                        <StackPanel>
                            <StackPanel.Resources>
                                <Style TargetType="{x:Type StackPanel}">
                                    <Setter Property="Margin" Value="0,0,0,10"/>
                                </Style>
                            </StackPanel.Resources>
                        <StackPanel Width="247" Height="119">
                            <Custom:Tile x:Name="Mail" Margin="0" Width="auto" d:LayoutOverrides="Height">
                                <Image Stretch="Fill" Source="Res/AppTiles/Mail.png"/>
                            </Custom:Tile>
                        </StackPanel>

                        //and it goes on like this//

                        </grid>
                      </stackpanel>
                <Separator Background="{x:Null}" Width="50"/>
            </Grid>
    </StackPanel>
    </ScrollViewer>

网格是否会挡路?或者在Horizo​​ntal Scrollviewer中有没有其他方法可以使用鼠标滚轮?我只是想不通。 请帮忙。

2 个答案:

答案 0 :(得分:4)

通常鼠标只有一个滚轮,分配给垂直滚动。我假设你的情况一样。

根据您的代码,您似乎想要通过鼠标滚轮执行水平滚动。

我建议使用Attached properties

的解决方案

示例xaml

<ScrollViewer x:Name="TS"
              Grid.Row="1"
              HorizontalAlignment="Stretch"
              HorizontalScrollBarVisibility="Auto"
              VerticalScrollBarVisibility="Disabled"
              CanContentScroll="False"
              PanningMode="HorizontalOnly"
              SnapsToDevicePixels="True"
              Background="Transparent"
              l:ScrollViewerExtensions.IsHorizontalScrollOnWheelEnabled="true">

我已将ScrollViewerExtensions.IsHorizontalScrollOnWheelEnabled附加到滚动查看器,这将启用通过鼠标滚轮进行水平滚动。还记得设置CanContentScroll="False",在你的情况下需要它。

ScrollViewerExtensions类

namespace CSharpWPF
{
    class ScrollViewerExtensions : DependencyObject
    {
        public static bool GetIsHorizontalScrollOnWheelEnabled(DependencyObject obj)
        {
            return (bool)obj.GetValue(IsHorizontalScrollOnWheelEnabledProperty);
        }

        public static void SetIsHorizontalScrollOnWheelEnabled(DependencyObject obj, bool value)
        {
            obj.SetValue(IsHorizontalScrollOnWheelEnabledProperty, value);
        }

        // Using a DependencyProperty as the backing store for IsHorizontalScrollOnWheelEnabled.  This enables animation, styling, binding, etc...
        public static readonly DependencyProperty IsHorizontalScrollOnWheelEnabledProperty =
            DependencyProperty.RegisterAttached("IsHorizontalScrollOnWheelEnabled", typeof(bool), typeof(ScrollViewerExtensions), new PropertyMetadata(false, OnIsHorizontalScrollOnWheelEnabledChanged));

        private static void OnIsHorizontalScrollOnWheelEnabledChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
        {
            ScrollViewer sv = d as ScrollViewer;
            if ((bool)e.NewValue)
                sv.PreviewMouseWheel += sv_PreviewMouseWheel;
            else
                sv.PreviewMouseWheel -= sv_PreviewMouseWheel;
        }

        static void sv_PreviewMouseWheel(object sender, MouseWheelEventArgs e)
        {
            ScrollViewer scrollviewer = sender as ScrollViewer;
            if (e.Delta > 0)
                scrollviewer.LineLeft();
            else
                scrollviewer.LineRight();
            e.Handled = true;
        }
    }
}

整个想法是听取鼠标滚轮并根据滚轮三角形(旋转)向左或向右滚动

答案 1 :(得分:3)

是的,我想出来了。并以最小的方式解决了这个问题。

<ScrollViewer x:Name="TS" Grid.Row="1" HorizontalAlignment="Stretch" HorizontalScrollBarVisibility="Auto" VerticalScrollBarVisibility="Disabled" CanContentScroll="True" PanningMode="HorizontalOnly" SnapsToDevicePixels="True" Background="Transparent" PreviewMouseWheel="TS_PreviewMouseWheel">

添加了PreviewMouseWheel =&#34; TS_PreviewMouseWheel&#34;

并在后面的代码中,

private void TS_PreviewMouseWheel(object sender, MouseWheelEventArgs e)
    {
        TS.HorizontalScrollBarVisibility = ScrollBarVisibility.Visible;
        ScrollViewer scrollviewer = sender as ScrollViewer;
        if (e.Delta > 0)
        {
            scrollviewer.LineLeft();
        }
        else
        {
            scrollviewer.LineRight();
        }
        e.Handled = true;
 }
无论如何,谢谢。