• WPF入门(二):初遇RoutedEvent


    先做个简单的东西吧,新建个wpf项目,拖动一个menu控件到窗体里。使用设计器添加几个菜单子项,并双击菜单注册事件,代码如下:
    代码
     1 <Window x:Class="WpfApplication1.WinMain"
     2     xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
     3     xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
     4     Title="WinMain" Height="494" Width="715">
     5     <Grid>
     6         <Grid.ColumnDefinitions>
     7             <ColumnDefinition Width="371*" />
     8             <ColumnDefinition Width="344*" />
     9         </Grid.ColumnDefinitions>
    10         <Menu Height="25" Name="menu1" VerticalAlignment="Top" Grid.ColumnSpan="2">
    11             <MenuItem Header="第一级菜单" Click="MenuItem_Click">
    12                 <MenuItem Header="第二级菜单1" />
    13                 <MenuItem Header="第二级菜单2" />
    14             </MenuItem>
    15         </Menu>
    16     </Grid>
    17 </Window>
    18   
    19 
    20   /// <summary>
    21     /// WinMain.xaml 的交互逻辑
    22     /// </summary>
    23     public partial class WinMain : Window
    24     {
    25         public WinMain()
    26         {
    27             InitializeComponent();
    28         }
    29 
    30         private void MenuItem_Click(object sender, RoutedEventArgs e)
    31         {
    32             object obj = e.Source;
    33             bool handled = e.Handled;
    34 
    35             RoutedEvent routedEvent = e.RoutedEvent;
    36             RoutingStrategy routingStrategy = routedEvent.RoutingStrategy;
    37 
    38 
    39             MessageBox.Show("触发了事件 \r\n 源:" + e.Source.ToString());
    40         }
    41 
    42     }

    我们重点看节点Menu和MenuItem,menu是菜单的根节点。header属性是菜单的标题。(顺便说一句,在winform里这些都是设置属性"Text"的,而在wpf里,大多变成"Content"属性)。而让人惊讶的是 “在代码设计器中,我们只能对一级菜单注册事件”,查看代码第11行里。有句“Click="MenuItem_Click"” 熟悉 html人都能明白这个意思,就是注册一个事件,事件名字是“MenuItem_Click”,而事件的实现代码当然是在"CodeBehind"代码后置文件里找了。这里 “二级菜单1”和“二级菜单2”两个菜单的单击都会触发"MenuItem_Click"。也就是说“子控件里的单击 触发了 父控件里注册的事件”。其实是个 “事件路由(RoutedEvent)”,流程如下:

    1.先触发子控件的click事件,(本示例没有订阅该事件,等下我们做个订阅尝试)。

    2.再触发父控件的click事件。

    3.依次再触发该控件的上一级父控件的事件。

    这里就有了事件 触发策略问题。即事件如何传递。

     我们看下 注册事件的代码 private void MenuItem_Click(object sender, RoutedEventArgs e) ,方法签名里和我们常见的方法签名区别是这个这个参数RoutedEventArgs ,该参数属性有(摘自msdn):

      名称 说明
    Handled 获取或设置一个值,该值指示路由事件在路由过程中的事件处理当前状态。
    OriginalSource 在父类进行任何可能的 Source 调整之前,获取原始报告源(由纯粹命中测试确定)。
    RoutedEvent 获取或设置与此 RoutedEventArgs 实例关联的 RoutedEvent
    Source 获取或设置对引发事件的对象的引用。

    我们在事件中,如果想终止该事件的继续传递,设置e.Handled= true就可以了。

    事件使用的委托的方法签名如下:

    public delegate void RoutedEventHandler(
    	Object sender,
    	RoutedEventArgs e
    )
    实际上一切都是由RoutedEvent 对象来管理的。也就是说。RoutedEvent处理了事件的传递方式。

    名称 说明
    HandlerType 获取路由事件的处理程序类型。
    Name 获取路由事件的标识名称。
    OwnerType 获取路由事件的已注册所有者类型。
    RoutingStrategy 获取路由事件的路由策略。

    public enum RoutingStrategy 路由策略的枚举类型如下:

    成员名称 说明
    Tunnel 路由事件使用隧道策略,以便事件实例通过树向下路由(从根到源元素)。
    Bubble 路由事件使用冒泡策略,以便事件实例通过树向上路由(从事件元素到根)。
    Direct 路由事件不通过元素树路由,但支持其他路由事件功能,例如类处理、EventTriggerEventSetter

    我们可以设置我们RoutedEvent的传递方式,当然这要自己写控件的时候才用得到。

     

    稍候待续...

  • 相关阅读:
    为什么要用全文搜索引擎:全文搜索引擎 VS 数据库管理系统
    大数据学习路线之hive存储格式
    web测试教程之JavaScript中的变量
    Java学习中面向过程与面向对象的优缺点
    Java教程之Java反射
    Python技术基础知识点:OS模块的应用
    软件测试教程——概念解析及常用方法概说
    UI设计师必备技能 网页中的色彩搭配(色彩篇)
    UI技术分享 如何提高自己的设计视野
    JavaScript学习指南分享
  • 原文地址:https://www.cnblogs.com/vir56k/p/1934578.html
Copyright © 2020-2023  润新知