wpf附加事件
附加事件的作用让一个非UI元素的静态类如Mouse能够定义一种“可以借给任何UI元素使用”的路由事件1、定义附加事件的静态类1定义附加事件下面的代码中 EventManager.RegisterRoutedEvent方法注册路由事件该方法第一个参数是“事件名称”第二个参数是路由策略路由策略分为冒泡、隧道、直接三种第3个参数是委托类型这个委托类型不是固定的RoutedEventHandler是标准的写法第4个参数是事件所在的类。2定义附加属性这里定义一个附加属性IsEnabled附加属性的作用就是启动附加事件在附加属性的回调函数中动态订阅/取消订阅附加事件本文代码中当IsEnabled为true时监听MouseDoubleClick 事件并在监听方法Element_MouseDoubleClick中触发附加事件。publicstaticclassDoubleClickHelper{// 第一部分定义附加事件 publicstaticreadonlyRoutedEventDoubleClickEventEventManager.RegisterRoutedEvent(DoubleClick,RoutingStrategy.Bubble,typeof(RoutedEventHandler),typeof(DoubleClickHelper));publicstaticvoidAddDoubleClickHandler(DependencyObjectobj,RoutedEventHandlerhandler){(objasUIElement)?.AddHandler(DoubleClickEvent,handler);}publicstaticvoidRemoveDoubleClickHandler(DependencyObjectobj,RoutedEventHandlerhandler){(objasUIElement)?.RemoveHandler(DoubleClickEvent,handler);}// 第二部分附加属性来启用功能 publicstaticreadonlyDependencyPropertyIsEnabledPropertyDependencyProperty.RegisterAttached(IsEnabled,// 属性名typeof(bool),// 类型typeof(DoubleClickHelper),// 所属类newPropertyMetadata(false,OnIsEnabledChanged));// 值改变时的回调// 设置 IsEnabled 属性publicstaticvoidSetIsEnabled(DependencyObjectobj,boolvalue){obj.SetValue(IsEnabledProperty,value);}// 获取 IsEnabled 属性publicstaticboolGetIsEnabled(DependencyObjectobj){return(bool)obj.GetValue(IsEnabledProperty);}// 第三部分当启用时监听鼠标双击 privatestaticvoidOnIsEnabledChanged(DependencyObjectobj,DependencyPropertyChangedEventArgse){ControlelementobjasControl;if(elementnull)return;if((bool)e.NewValuetrue){// 启用监听鼠标双击element.MouseDoubleClickElement_MouseDoubleClick;}else{// 禁用取消监听element.MouseDoubleClick-Element_MouseDoubleClick;}}// 第四部分双击发生时触发我们的附加事件 privatestaticvoidElement_MouseDoubleClick(objectsender,MouseButtonEventArgse){UIElementelementsenderasUIElement;if(elementnull)return;// 触发附加事件RoutedEventArgsargsnewRoutedEventArgs(DoubleClickEvent,element);element.RaiseEvent(args);}}2、xaml代码为控件添加附加事件的监控在xaml使用类名.附加事件名StackPanelMargin20local:DoubleClickHelper.IsEnabledTruelocal:DoubleClickHelper.DoubleClickOnDoubleClick!--按钮1启用双击功能--ButtonContent按钮1 - 双击我local:DoubleClickHelper.IsEnabledTruelocal:DoubleClickHelper.DoubleClickOnDoubleClickHeight50Margin0,5/!--按钮2也启用双击功能--ButtonContent按钮2 - 双击我local:DoubleClickHelper.IsEnabledTruelocal:DoubleClickHelper.DoubleClickOnDoubleClickHeight50Margin0,5/!--文本框也支持双击--TextBoxText文本框 - 双击我local:DoubleClickHelper.IsEnabledTruelocal:DoubleClickHelper.DoubleClickOnDoubleClickHeight30Margin0,5/!--状态显示--RichTextBoxNameStatusTextMargin0,20ForegroundRedFontSize12//StackPanel3、逻辑层代码只要附加事件被触发下面的代码就会执行如果判断被双击的是Button则获取Button的Content属性如果被双击的是TextBox则获取它的Text属性。privatevoidOnDoubleClick(objectsender,RoutedEventArgse){// sender 是被双击的那个元素FrameworkElementelementsenderasFrameworkElement;stringelementTypeelement?.GetType().Name??未知;stringcontent;// 获取显示文本if(elementisButtonbtn)contentbtn.Content.ToString();elseif(elementisTextBoxtxt)contenttxt.Text;// 显示提示StatusText.AppendText($双击了{elementType}{content}时间{System.DateTime.Now:T}Environment.NewLine);}4、测试结果1双击按钮1你会发现有richTextbox有两条记录一个是按钮1被双击了一个是StackPanel这是因为附加是冒泡事件当按钮1被双击以后冒泡基制也会导致StackPanel作为按钮1的父控件也可以监听到双击事件。2双击文本框