WPF中,控件的事件分为起泡事件和通道事件。起泡事件从接收到事件的元素开始,逐级触发上层元素的同名事件。通道事件从根元素开始,逐级触发下层元素的同名事件,直到接收事件的元素。要关闭这种事件传递,可以在需要中止传递的元素的处理方法中设置EventArgs的Handled属性为true。经过我的实验,控件的通道事件先于起泡事件执行。也就是说如果同时定义了SomeEvent和PreviewSomeEvent事件,并且为SomeEvent和PreviewSomeEvent事件都写了处理方法X_SomeEvent和X_PreviewSomeEvent。那么,只会执行X_PreviewSomeEvent方法。列如:在本例中,不会执行win_MouseDow,btn_MouseDow,lbl_MouseDow方法。除非,删除对应的Preview方法或者在Preview是空方法。

 

定义一个窗体win,一个按钮btn,一个标签lbl。并设置win内容为btn,btn内容为lbl:

 

private static Window win = new Window();
private static Button btn = new Button();
private static Label lbl = new Label();
lbl.Content = "Click Me";
btn.Content = lbl;
win.Content = btn;

 

为控件添加鼠标单击事件处理方法:

//为个元素添加鼠标按下事件的冒泡事件处理方法

win.MouseDown += win_MouseDown;

btn.MouseDown += btn_MouseDown;

lbl.MouseDown += lbl_MouseDown;

//为各元素添加鼠标按下事件的通道事件处理方法     
       
win.PreviewMouseDown += new System.Windows.Input.MouseButtonEventHandler(win_PreviewMouseDown);

btn.PreviewMouseDown += new System.Windows.Input.MouseButtonEventHandler(btn_PreviewMouseDown);

lbl.PreviewMouseDown += new System.Windows.Input.MouseButtonEventHandler(lbl_PreviewMouseDown);

 

 

事件处理方法:

//Lable标签的鼠标按下事件的通道事件的处理方法
	private static void lbl_PreviewMouseDown(object sender, System.Windows.Input.MouseButtonEventArgs e)
        {
            MessageBox.Show("This is triggered by lbl_PreviewMouseDown");
        }

        //按钮的鼠标按下事件的通道事件处理方法
        private static void btn_PreviewMouseDown(object sender, System.Windows.Input.MouseButtonEventArgs e)
        {
            //e.Handled = true;
            MessageBox.Show("This is triggered by btn_PreviewMouseDown");
        }

        //窗体的鼠标按下事件的通道事件的处理方法
        private static void win_PreviewMouseDown(object sender, System.Windows.Input.MouseButtonEventArgs e)
        {
           MessageBox.Show("This is triggered by win_PreviewMouseDown");
        }

        //Lable标签的鼠标按下事件的起泡事件的处理方法
        private static void lbl_MouseDown(object sender, System.Windows.Input.MouseButtonEventArgs e)
        {
            //e.Handled = true;
            MessageBox.Show("This is triggered by lbl_MouseDown");
        }

        //按钮的鼠标按下事件的起泡事件的处理方法
        public static void btn_MouseDown(object sender, System.Windows.Input.MouseButtonEventArgs e)
        {
            //e.Handled = true;
            MessageBox.Show("This is triggered by btn_MouseDown");
        }

        //窗体的鼠标按下事件的起泡事件处理方法
        private static void win_MouseDown(object sender, System.Windows.Input.MouseButtonEventArgs e)
        {
            MessageBox.Show("This is triggered by win_MouseDown");
        }

 

运行程序,单击窗体上的按钮。弹出对话框依次显示:

“This is triggered by win_PreviewMouseDown”

“This is triggered by btn_PreviewMouseDown”

“This is triggered by lbl_PreviewMouseDown”

 

而“This is triggered by btn_MouseDown”等X_MouseDown事件处理方法中要求显示的信息不会显示,注释掉X_PreviewMouseDown事件处理方法后方能显示(X_PreviewMouseDown事件处理方法为空方法时也会显示,不明白),说明通道事件优先于起泡事件。

 

posted on 2010-07-17 23:55  一直在摸索  阅读(1124)  评论(0编辑  收藏  举报