最终,没有收到与计时器无关的解决方案建议(我也没有找到任何建议),因此这里提供一个简单的示例,说明如何在双击发生时防止单击。
Xaml:
<Window x:Class="StackOverflow.DoubleClickExample.MainWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
Height="100" Width="150"
MouseDown="RootElement_OnMouseDown">
</Window>
后台代码:
namespace StackOverflow.DoubleClickExample
{
using System;
using System.Diagnostics;
using System.Runtime.InteropServices;
using System.Threading.Tasks;
using System.Windows;
using System.Windows.Input;
public partial class MainWindow : Window
{
[DllImport("user32.dll")]
public static extern uint GetDoubleClickTime();
public MainWindow()
{
this.InitializeComponent();
}
private Guid lastGuid = Guid.Empty;
private void RootElement_OnMouseDown(object sender, MouseButtonEventArgs e)
{
if (e.ClickCount == 1)
{
var guid = Guid.NewGuid();
this.lastGuid = guid;
Task.Run(async () =>
{
await Task.Delay((int)GetDoubleClickTime());
if (guid == this.lastGuid)
{
Trace.WriteLine("Single-click occured");
}
});
return;
}
this.lastGuid = Guid.NewGuid();
Trace.WriteLine("Double-click occured");
}
}
}
为了测试,请在窗口区域内单击,并跟踪编写到Visual Studio输出窗口中的消息(菜单视图 -> 输出)。
另一种方法是使用CancellationTokenSource
,并在发生双击时触发其Cancel
方法。只需替换lastGuid
字段和RootElement_OnMouseDown
方法:
private CancellationTokenSource cancellationTokenSource;
private void RootElement_OnMouseDown(object sender, MouseButtonEventArgs e)
{
if (e.ClickCount == 1)
{
try
{
this.cancellationTokenSource = new CancellationTokenSource();
var token = this.cancellationTokenSource.Token;
Task.Run(async () =>
{
await Task.Delay((int)GetDoubleClickTime(), token);
Trace.WriteLine("Single-click occured");
}, token);
}
catch (OperationCanceledException)
{
}
return;
}
if (this.cancellationTokenSource != null)
{
this.cancellationTokenSource.Cancel();
}
Trace.WriteLine("Double-click occured");
}