前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >专栏 >WPF 单击与双击操作区分

WPF 单击与双击操作区分

作者头像
jgrass
发布于 2024-12-25 10:26:23
发布于 2024-12-25 10:26:23
30800
代码可运行
举报
文章被收录于专栏:蔻丁杂记蔻丁杂记
运行总次数:0
代码可运行

背景

如果不需要严格区分单击与双击操作,可以直接通过 MouseButtonEventArgs 中的 ClickCount 属性来进行判断。

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
private void MyMouseDownHandler(object sender, MouseButtonEventArgs e){    if (e.ClickCount == 2)    {        // Handle double-click    }}

但上述写法有个问题是,如果我需要在单击和双击时执行不同的操作,则无法满足需求。 因为用户双击时,会首先触发一次 e.ClickCount == 1 的单击。

mouseevent - Distinguish between mouse doubleclick and mouse click in wpf - Stack Overflow

实现

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
using System;using System.Windows.Input;using System.Windows.Threading;
namespace xxx.xxx;
/// <summary>/// 通过延迟判断来区分鼠标单击和双击操作,/// 对于需要严格区分单击和双击的场景使用。/// 影响:单击的响应会有延迟,延迟 220 ms/// </summary>internal class MouseDoubleClickHelper{    private static readonly TimeSpan DoubleClickCheckTime = TimeSpan.FromMilliseconds(220); // ms
    private DateTime _lastClickTime = DateTime.MinValue;
    private readonly DispatcherTimer _timer;
    /// <summary>    /// 单击时的动作    /// </summary>    public Action<object, MouseButtonEventArgs>? ClickAction { get; set; }
    /// <summary>    /// 双击时的动作    /// </summary>    public Action<object, MouseButtonEventArgs>? DoubleClickAction { get; set; }
    public MouseDoubleClickHelper(Dispatcher dispatcher)    {        _timer = new DispatcherTimer(DoubleClickCheckTime, DispatcherPriority.Input, TimerCallback, dispatcher);    }
    private void TimerCallback(object? _, EventArgs __)    {        // ReSharper disable once UsePatternMatching        var args = _timer.Tag as (object sender, MouseButtonEventArgs e)?;
        if (args != null)        {            // 计时器到,没有出现第二次点击,则认为是单击动作,执行单击操作            ClickAction?.Invoke(args.Value.sender, args.Value.e);            _timer.Tag = null;        }    }
    /// <summary>    /// 鼠标点击时调用    /// </summary>    public void OnMouseDown(object sender, MouseButtonEventArgs e)    {        var now = DateTime.Now;        var span = now - _lastClickTime;
        if (span > DoubleClickCheckTime)        {            // 首次点击,不立即执行,启动计时器,延迟执行            _timer.Tag = (sender, e);            _timer.Start();        }        else if (span <= DoubleClickCheckTime)        {            // 停掉单击的执行            _timer.Tag = null;            _timer.Stop();            if (e.ClickCount == 2)            {                // 执行双击动作                DoubleClickAction?.Invoke(sender, e);            }        }
        _lastClickTime = now;    }}

通过延迟判断,来过滤掉双击时,第一次鼠标点击的触发。

带来的问题是,正常的单击操作,会被延迟触发。

如果你期望使用更精确的 DoubleClickCheckTime,可以使用 System.Windows.Forms.SystemInformation.DoubleClickTime

SystemInformation.DoubleClickTime 属性 (System.Windows.Forms) | Microsoft Learn

在 WPF 中,需要先添加 WindowForms 的引用。

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
<Project Sdk="Microsoft.NET.Sdk">  <PropertyGroup>    <TargetFramework>net8.0-windows</TargetFramework>    <ImplicitUsings>enable</ImplicitUsings>    <Nullable>enable</Nullable>    <UseWPF>true</UseWPF>    <UseWindowsForms>true</UseWindowsForms>  </PropertyGroup></Project>

其它

在 WinForm 下区分单击和双击: 如何区分单击和双击 - Windows Forms .NET | Microsoft Learn

原文链接: https://cloud.tencent.com/developer/article/2481575

本作品采用 「署名 4.0 国际」 许可协议进行许可,欢迎转载,但未经作者同意必须保留此段声明,且在文章页面明显位置给出原文链接。

本文参与 腾讯云自媒体同步曝光计划,分享自作者个人站点/博客。
原始发表:2024年9月25日 ,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档
本文部分代码块支持一键运行,欢迎体验
本文部分代码块支持一键运行,欢迎体验