WPF 无法从 MouseDown 事件中获取触摸位置 [英] WPF could not get touch position from MouseDown event

查看:46
本文介绍了WPF 无法从 MouseDown 事件中获取触摸位置的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我在将触摸支持添加到 .NET (v 4.0) 之前编写了一个 WPF 项目,因此只处理了鼠标事件.我在用手指在触摸屏上测试项目时遇到了这个问题.

I have a WPF project written before touch support was added to .NET (v 4.0), so only the mouse events were handled. I run into this problem when testing the project on a touch screen with fingers.

问题是,位置 (X, Y) 在第一次触摸中被正确检索,但 (X, Y) 值在后续触摸中保持不变,无论我触摸到哪里,即使我触摸了Image,MouseDown 事件被触发,这让它变得更奇怪.

The problem is, the position (X, Y) is correctly retrieved in the first touch, but the (X, Y) values stay the same in subsequent touches, no matter where I touch, and even if I touch out of the Image, the MouseDown event is fired, which makes it more weird.

.NET 3.0/3.5/4.0都可以重现,在Win7/Win8上测试,都是64位.似乎是 MouseDown 事件出现了问题,MouseUp 工作正常.

It can be reproduced with .NET 3.0/3.5/4.0, tested on Win7/Win8, both are 64 bits. And it seems it is MouseDown event that is misbehaving, MouseUp works fine.

更新:

这是一个历史悠久的错误,MS 尚未修复它(即使在 4.5 中),因此如果遇到相同的症状,您必须更新代码 - 从 Touch 事件中获取触摸位置,而不是鼠标事件.幸运的是,这个错误并不微妙,因此只需一点时间即可定位和修复.

重现问题的代码:

XAML:

<Window x:Class="WpfApplication1.MainWindow"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    Title="MainWindow" Height="350" Width="525">
    <Grid>
        <Image Height="60" Width="80" x:Name="Image" MouseDown="Image_MouseDown" 
                Source="/WpfApplication1;component/Images/Desert.jpg" />
    </Grid> 
</Window>

背后的代码:

using System;
using System.Collections.Generic;
using System.Text;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Data;
using System.Windows.Documents;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Imaging;
using System.Windows.Navigation;
using System.Windows.Shapes;

namespace WpfApplication1
{
    /// <summary>
    /// Interaction logic for MainWindow.xaml
    /// </summary>
    public partial class MainWindow : Window
    {
        public MainWindow()
        {
            InitializeComponent();
        }
        private void Image_MouseDown(object sender, MouseButtonEventArgs e)
        {
            Point p = e.GetPosition(Image);
            MessageBox.Show(p.X.ToString() + " " + p.Y.ToString());
        }
    }
}

推荐答案

默认情况下,在 WPF 中,如果控件未处理 Touch 事件,它将被提升为鼠标事件.触摸事件是路由事件,因此当鼠标事件被触发时,它会在可视化树中上下移动(因此即使您触摸图像外部,您的事件处理程序也会被执行).

By default in WPF, if a Touch event is not handled by a control it will be promoted to a Mouse event. Touch events are routed events, so when the Mouse event will be triggered it will go up and down the visual tree (hence your event handler being executed even when you touch outside of the Image).

如果 MouseDown 事件来自提升的触摸事件,您可能可以使用 StylusDevice 获得正确的位置:

If the MouseDown event comes from a promoted touch event, you could probably get the correct position using the StylusDevice:

if (e.StylusDevice != null)
    point = e.StylusDevice.GetPosition(sender as Image);

或者作为替代方案,您可以为需要位置的控件添加 TouchDown 事件的处理程序:

Or as an alternative, you could add a handler for the TouchDown event for the controls where you need the position:

<Image TouchDown="UIElement_OnTouchDown"/>

 private void UIElement_OnTouchDown(object sender, TouchEventArgs e)
 {
      var touchPoint = e.GetTouchPoint(sender as Image);
      // more processing using touchPoint.Position
 }

这篇关于WPF 无法从 MouseDown 事件中获取触摸位置的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆