我正在创建一个WinUI 3用户控件,为了简单起见,可以将其描述为美化的滑块:
- 每当用户按下其左键(
PointerPressed
事件)时,指针移动开始被跟踪。 - 每当用户释放其左击(
PointerReleased
事件)时,此跟踪就会停止。
示例XAML
<UserControl [...] >
<Border Name="MainArea"
PointerPressed="StartCapturing"
PointerReleased="StopCapturing"
PointerMoved="CaptureCoords"
[...] >
<!-- [...] -->
</Border>
</UserControl>
示例C#
bool _isCapturing = false;
private void CalculateCoords(PointerRoutedEventArgs args){
// max distance is [w,h]. min distance is [0,0]
var h = MainArea.ActualHeight;
var w = MainArea.ActualWidth;
// Coordinates relative to the MainArea element;
var pos = args.GetCurrentPoint(MainArea).Position;
var (x, y) = (pos.X, pos.Y);
// clip 0% - 100%
x = x < 0 ? 0 : (x > w ? w : x);
y = y < 0 ? 0 : (y > h ? h : y);
// convert to percentages
var (x_perc, y_perc) = (x/w, y/h);
// Do stuff with the two percentages
}
public void StartCapturing(object? sender, PointerRoutedEventArgs args){
_isCapturing = true;
CalculateCoords(args);
}
public void CaptureCoords(object? sender, PointerRoutedEventArgs args){
if (!_isCapturing) return;
CalculateCoords(args);
}
public void StopCapturing(object? sender, PointerRoutedEventArgs args){
_isCapturing = false;
CalculateCoords(args);
}
当光标在控件内部时,这种方法可以正常工作。当光标离开元素时,问题就出现了:移动跟踪停止,并且如果在边界框外释放单击,则即使没有按下单击,一旦鼠标重新进入边界框,捕获也将继续。
这些问题是可以预料到的。为了消除这些问题,我想到过但不知道如何实施的唯一可能的解决方案是:
- 强制捕获鼠标事件,即使指针退出控件
- 将鼠标移动限制在控件的边界框内
有办法做到这两件事吗?
1条答案
按热度按时间6ioyuze21#
您可以在
StartCapturing
中使用CapturePointer。您通常会捕获指针,因为您希望当前指针操作启动应用中的行为。在这种情况下,您通常不希望其他元素处理来自该指针操作的任何其他事件,直到您的行为完成或通过释放指针捕获取消为止。如果捕获了指针,则只有具有捕获的元素才会获取指针的输入事件。和其他元素不会激发事件,即使指针移动到它们的边界内。例如,考虑具有两个相邻元素的UI。**通常,如果您将指针从一个元素移动到另一个元素,您将首先从第一个元素获取PointerMoved事件,然后从第二个元素获取。但如果第一个元素已捕获指针,则第一个元素继续接收PointerMoved事件,即使捕获的指针离开其边界。**此外,当捕获的指针进入第二个元素时,第二个元素不会为捕获的指针触发PointerEntered事件。