SHIFT + 滚动以在 ScrollViewer UWP 中水平滚动
SHIFT + Scroll to Scroll Horizontally in ScrollViewer UWP
我想启用在滚动时按住键盘上的 SHIFT 以水平滚动 ScrollViewer
。
我从here that the PointerWheelChanged
event is the one I am looking for. Handling that, however, doesn't work because the ScrollViewer
handles it internally, so my handler is never called. To get around that, I used the AddHandler
method, as described in the "Routed Events Overview"文章中学到了。
这有效...但在 ScrollViewer
运行其内部代码后似乎是 运行 我的代码。结果是 ScrollViewer
内容垂直平移,然后水平平移。它们似乎按此顺序发生,设置 e.Handled = true
不会阻止它。
有没有办法 "intercept" 滚动,这样我就可以用我自己的逻辑来处理它,从而允许 ScrollViewer
在按下 SHIFT 时水平平移?我最近问了一个类似的问题(涉及拦截控件的输入,以便我可以用自己的逻辑处理它),答案涉及处理不同的事件,该事件发生在控制之前 运行 自己的逻辑。我没有看到类似的 "pre stuff happening" 指针滚动事件。
我的代码如下。请注意 ScrollViewer
可以水平和垂直滚动,也可以缩放:
<!-- Contained in Grid in a UserControl, if that's relevant -->
<ScrollViewer Name="MyCanvasScrollViewer"
VerticalScrollBarVisibility="Auto"
HorizontalScrollBarVisibility="Auto"
ZoomMode="Enabled"
ZoomSnapPointsType="Optional"
PointerWheelChanged="MyCanvasScrollViewer_PointerWheelChanged">
<!-- Content to pan -->
</ScrollViewer>
代码隐藏:
// Constructor for the user contol.
public MyControl()
{
// Add the scroll wheel event handler and force it to run.
this.MyCanvasScrollViewer.AddHandler(ScrollViewer.PointerWheelChangedEvent, new PointerEventHandler(this.MyCanvasScrollViewer_PointerWheelChanged), true);
// Other un-related stuff omitted here...
}
// Event handler for the Pointer Wheel Changed event.
private void MyCanvasScrollViewer_PointerWheelChanged(object sender, PointerRoutedEventArgs e)
{
// If SHIFT is pressed...
var keyState = CoreWindow.GetForCurrentThread().GetKeyState(VirtualKey.Shift);
if ((keyState & CoreVirtualKeyStates.Down) == CoreVirtualKeyStates.Down)
{
// Get the amount to scroll.
PointerPoint pointer = e.GetCurrentPoint(this.WallCanvasScrollViewer);
double scrollWheelDelta = pointer.Properties.MouseWheelDelta;
// Change the view in the scroll viewer.
this.MyCanvasScrollViewer.ChangeView(scrollWheelDelta, null, null, true);
// Mark event as handled.
e.Handled = true;
}
}
您可以简单地在 shift
keydown 中禁用 VerticalScrollMode
并在 keyup 中启用它。不需要 pointerwheelchanged
本身。它工作得很好。
Xaml
<ScrollViewer ZoomMode="Enabled" x:Name="MyScrollViewer" HorizontalScrollMode="Enabled" HorizontalScrollBarVisibility="Visible" >
<Image Height="600" Width="500" Source="/Assets/1.jpg"></Image>
</ScrollViewer>
//C#代码
public sealed partial class MainPage : Page
{
public MainPage()
{
this.InitializeComponent();
CoreWindow.GetForCurrentThread().KeyDown += MainPage_KeyDown;
CoreWindow.GetForCurrentThread().KeyUp += MainPage_KeyUp; ;
}
private void MainPage_KeyUp(CoreWindow sender, KeyEventArgs args)
{
if (args.VirtualKey == VirtualKey.Shift)
{
MyScrollViewer.IsScrollInertiaEnabled = true;
MyScrollViewer.VerticalScrollMode = ScrollMode.Enabled;
}
}
private void MainPage_KeyDown(CoreWindow sender, KeyEventArgs args)
{
if (args.VirtualKey == VirtualKey.Shift)
{
MyScrollViewer.IsScrollInertiaEnabled = false;
MyScrollViewer.VerticalScrollMode = ScrollMode.Disabled;
}
}
}
我想启用在滚动时按住键盘上的 SHIFT 以水平滚动 ScrollViewer
。
我从here that the PointerWheelChanged
event is the one I am looking for. Handling that, however, doesn't work because the ScrollViewer
handles it internally, so my handler is never called. To get around that, I used the AddHandler
method, as described in the "Routed Events Overview"文章中学到了。
这有效...但在 ScrollViewer
运行其内部代码后似乎是 运行 我的代码。结果是 ScrollViewer
内容垂直平移,然后水平平移。它们似乎按此顺序发生,设置 e.Handled = true
不会阻止它。
有没有办法 "intercept" 滚动,这样我就可以用我自己的逻辑来处理它,从而允许 ScrollViewer
在按下 SHIFT 时水平平移?我最近问了一个类似的问题(涉及拦截控件的输入,以便我可以用自己的逻辑处理它)
我的代码如下。请注意 ScrollViewer
可以水平和垂直滚动,也可以缩放:
<!-- Contained in Grid in a UserControl, if that's relevant -->
<ScrollViewer Name="MyCanvasScrollViewer"
VerticalScrollBarVisibility="Auto"
HorizontalScrollBarVisibility="Auto"
ZoomMode="Enabled"
ZoomSnapPointsType="Optional"
PointerWheelChanged="MyCanvasScrollViewer_PointerWheelChanged">
<!-- Content to pan -->
</ScrollViewer>
代码隐藏:
// Constructor for the user contol.
public MyControl()
{
// Add the scroll wheel event handler and force it to run.
this.MyCanvasScrollViewer.AddHandler(ScrollViewer.PointerWheelChangedEvent, new PointerEventHandler(this.MyCanvasScrollViewer_PointerWheelChanged), true);
// Other un-related stuff omitted here...
}
// Event handler for the Pointer Wheel Changed event.
private void MyCanvasScrollViewer_PointerWheelChanged(object sender, PointerRoutedEventArgs e)
{
// If SHIFT is pressed...
var keyState = CoreWindow.GetForCurrentThread().GetKeyState(VirtualKey.Shift);
if ((keyState & CoreVirtualKeyStates.Down) == CoreVirtualKeyStates.Down)
{
// Get the amount to scroll.
PointerPoint pointer = e.GetCurrentPoint(this.WallCanvasScrollViewer);
double scrollWheelDelta = pointer.Properties.MouseWheelDelta;
// Change the view in the scroll viewer.
this.MyCanvasScrollViewer.ChangeView(scrollWheelDelta, null, null, true);
// Mark event as handled.
e.Handled = true;
}
}
您可以简单地在 shift
keydown 中禁用 VerticalScrollMode
并在 keyup 中启用它。不需要 pointerwheelchanged
本身。它工作得很好。
Xaml
<ScrollViewer ZoomMode="Enabled" x:Name="MyScrollViewer" HorizontalScrollMode="Enabled" HorizontalScrollBarVisibility="Visible" >
<Image Height="600" Width="500" Source="/Assets/1.jpg"></Image>
</ScrollViewer>
//C#代码
public sealed partial class MainPage : Page
{
public MainPage()
{
this.InitializeComponent();
CoreWindow.GetForCurrentThread().KeyDown += MainPage_KeyDown;
CoreWindow.GetForCurrentThread().KeyUp += MainPage_KeyUp; ;
}
private void MainPage_KeyUp(CoreWindow sender, KeyEventArgs args)
{
if (args.VirtualKey == VirtualKey.Shift)
{
MyScrollViewer.IsScrollInertiaEnabled = true;
MyScrollViewer.VerticalScrollMode = ScrollMode.Enabled;
}
}
private void MainPage_KeyDown(CoreWindow sender, KeyEventArgs args)
{
if (args.VirtualKey == VirtualKey.Shift)
{
MyScrollViewer.IsScrollInertiaEnabled = false;
MyScrollViewer.VerticalScrollMode = ScrollMode.Disabled;
}
}
}