在日常的開(kāi)發(fā)中鼠標(biāo)的事件是我們使用的最多的事件,但是在Silverlight中,只支持以下六種有限的鼠標(biāo)事件:MouseEnter、 MouseLeave、MouseLeftButtonDown、MouseLeftButtonUp、MouseMove、MouseWheel,
Silverlight開(kāi)發(fā)中如何為Silverlight添加雙擊事件
。這給我們的開(kāi)發(fā)造成了不小的麻煩,還好 Silverlight支持強(qiáng)大的附加屬性機(jī)制,這里就指導(dǎo)大家如何通過(guò)附加屬性來(lái)給Silverlight添加鼠標(biāo)的雙擊事件。附加屬性是Silverlight也是WPF中最具創(chuàng)新也是最強(qiáng)大的特性之一,它能夠讓你在不擁有控件的源碼的情況下對(duì)其功能進(jìn)行擴(kuò)展。關(guān)于 附加屬性的強(qiáng)大我就不在這里敘述了,有感興趣的朋友可以去查看WPF控件開(kāi)發(fā)揭秘一書(shū),里面有一張專(zhuān)門(mén)爭(zhēng)對(duì)附加屬性進(jìn)行了介紹,網(wǎng)絡(luò) 上和園子里也早就有許多關(guān)于附加屬性的文章。
這里直接進(jìn)入主題,首先,我們需要對(duì)外提供兩種雙擊事件的處理機(jī)制,一種是常用的事件機(jī)制,使用自帶的 MouseButtonEventHandler;另一種是現(xiàn)在比較流行的Command機(jī)制,使用ICommand接口。兩個(gè)附加屬性的定義如下:
附加屬性的定義
#region MouseDoubleClick
public static MouseButtonEventHandler GetMouseDoubleClick(DependencyObject obj)
{
return (MouseButtonEventHandler)obj.GetValue(MouseDoubleClickProperty);
}
public static void SetMouseDoubleClick(DependencyObject obj, MouseButtonEventHandler value)
{
obj.SetValue(MouseDoubleClickProperty, value);
}
public static readonly DependencyProperty MouseDoubleClickProperty = DependencyProperty.RegisterAttached(
"MouseDoubleClick",
typeof(MouseButtonEventHandler),
typeof(MouseEventHelper),
new PropertyMetadata(new PropertyChangedCallback(OnMouseDoubleClickChanged)));
#endregion
#region MouseDoubleClickCommand
public static ICommand GetMouseDoubleClickCommand(DependencyObject obj)
{
return (ICommand)obj.GetValue(MouseDoubleClickCommandProperty);
}
public static void SetMouseDoubleClickCommand(DependencyObject obj, ICommand value)
{
obj.SetValue(MouseDoubleClickCommandProperty, value);
}
public static readonly DependencyProperty MouseDoubleClickCommandProperty =
DependencyProperty.RegisterAttached("MouseDoubleClickCommand", typeof(ICommand), typeof(MouseEventHelper), new PropertyMetadata(OnMouseDoubleClickChanged));
#endregion
附加屬性在定義上與依賴(lài)屬性的主要區(qū)別就是附加屬性是通過(guò)DependencyProperty.RegisterAttached的方式進(jìn)行注冊(cè)的,而依賴(lài)屬性 是通過(guò)DependencyProperty.Register方法進(jìn)行注冊(cè)的。這里還提供了Get和Set方法,這兩個(gè)方法是提供給在Xaml代碼中進(jìn)行附加屬性注冊(cè) 時(shí)使用的。大家在進(jìn)行附加屬性的定義時(shí),可以通過(guò)輸入propa再按一下Tab鍵進(jìn)行代碼生成。大家可以注意到,在兩個(gè)屬性的定義中我們 都傳入了一個(gè)PropertyChangedCallback,這就是所謂的擴(kuò)展點(diǎn),在這個(gè)回調(diào)中,我們可以根據(jù)自己的邏輯進(jìn)行相應(yīng)的處理,這里我們只是 注冊(cè)了UIElement的MouseLeftButtonDown事件,這樣可以讓我們的附加屬性能夠作用于所有繼承自UIElement的控件(基本上就是全部的控 件了吧~)。
雙擊事件的實(shí)現(xiàn)思路非常簡(jiǎn)單,就是通過(guò)在MouseLeftButtonDown中記錄鼠標(biāo)點(diǎn)擊的時(shí)間,然后用上次的點(diǎn)擊時(shí)間跟這次的點(diǎn)擊時(shí)間進(jìn) 行比較,如果兩次點(diǎn)擊間隔小于200ms則作為一次雙擊處理,觸發(fā)對(duì)應(yīng)的事件和命令,完整的代碼如下:
MouseEventHelper
///
/// Silverlight鼠標(biāo)事件幫助類(lèi)
///
public class MouseEventHelper
{
#region Dependency Properties
#region 模擬鼠標(biāo)雙擊事件
#region MouseDoubleClick
public static MouseButtonEventHandler GetMouseDoubleClick(DependencyObject obj)
{
return (MouseButtonEventHandler)obj.GetValue(MouseDoubleClickProperty);
}
public static void SetMouseDoubleClick(DependencyObject obj, MouseButtonEventHandler value)
{
obj.SetValue(MouseDoubleClickProperty, value);
}
public static readonly DependencyProperty MouseDoubleClickProperty = DependencyProperty.RegisterAttached(
"MouseDoubleClick",
typeof(MouseButtonEventHandler),
typeof(MouseEventHelper),
new PropertyMetadata(new PropertyChangedCallback(OnMouseDoubleClickChanged)));
#endregion
#region MouseDoubleClickCommand
public static ICommand GetMouseDoubleClickCommand(DependencyObject obj)
{
return (ICommand)obj.GetValue(MouseDoubleClickCommandProperty);
}
public static void SetMouseDoubleClickCommand(DependencyObject obj, ICommand value)
{
obj.SetValue(MouseDoubleClickCommandProperty, value);
}
public static readonly DependencyProperty MouseDoubleClickCommandProperty =
DependencyProperty.RegisterAttached("MouseDoubleClickCommand", typeof(ICommand), typeof (MouseEventHelper), new PropertyMetadata(OnMouseDoubleClickChanged));
#endregion
private static DateTime? _lastClickTime = null;
private const int MaxClickInterval = 200;//ms
private static void OnMouseDoubleClickChanged(DependencyObject obj, DependencyPropertyChangedEventArgs e)
{
UIElement element = obj as UIElement;
if (element != null)
{
element.MouseLeftButtonDown += new MouseButtonEventHandler (element_MouseLeftButtonDown);
}
}
///
/// 通過(guò)檢測(cè)兩次鼠標(biāo)單機(jī)的間隔來(lái)模擬鼠標(biāo)雙擊事件
///
/// www.bianceng.cn
///
///
static void element_MouseLeftButtonDown(object sender, MouseButtonEventArgs e)
{
//進(jìn)入雙擊事件
if (_lastClickTime.HasValue && DateTime.Now.Subtract(_lastClickTime.Value).Milliseconds <= MaxClickInterval)
{
//觸發(fā)事件
MouseButtonEventHandler handler = (sender as UIElement).GetValue (MouseDoubleClickProperty) as MouseButtonEventHandler;
if (handler != null)
{
handler(sender, e);
}
ICommand command = (sender as UIElement).GetValue(MouseDoubleClickCommandProperty) as ICommand;
if (command != null)
{
if (command.CanExecute(sender))
{
command.Execute(sender);
}
}
//重新計(jì)時(shí)
_lastClickTime = null;
}
else
{
_lastClickTime = DateTime.Now;
}
}
#endregion
#endregion
}
是不是覺(jué)得很簡(jiǎn)單?按照上面的流程大家就可以盡情的擴(kuò)展Silverlight,幫她加上各種各樣的功能了!~