文章出處

  上接”委托與事件——委托“,為了維護程序的封裝性,事件不得不出場。

  關鍵字event,用來聲明事件對象,允許一個類或對象提供通知的成員,他必須是委托類型。

  事件是類和對象向外界發出的消息,事件的執行是通過事件委托的方式,事件的類型是委托類型。調用我們所準備好的處理方法,要響應某些事件并針對某些事件執行我們指定的方法,需要做到以下幾步:

1、聲明事件委托。

2、聲明事件。—————————怎么聲明事件

3、添加事件的觸發方法。——————這個事件在什么情況下會被觸發

4、添加事件的處理程序(響應事件的方法)。————————怎么處理這個事件

5、將指定的事件處理程序綁定到要處理的事件上(訂閱事件)。—————誰來處理

6、用戶信息操作,并觸發事件(調用事件的觸發方法)。

7、通過事件委托的回調,執行我們需要的事件處理程序。

所以要想讓事件能夠正常運轉,我的程序中必須存在以下三者:

      事件發送者、事件接收者、事件本身

  只能對事件進行“+=”和“-=”操作,不可以對事件進行賦值“=”操作。所以引用事件的目的,就是為了封裝。

  在我們進行winform編程的時候,我們經常用到按鈕Button的重要事件:Click,

        //處理事件的方法,被定義成委托
        public delegate void EventHandler(object sender, EventArgs e);
        //單機按鈕的時候發生的事件
        public event EventHandler Click;
        
        //訂閱事件,將事件處理程序綁定到要處理的事件上
        btn.Click += new EventHandler(btn_MyClick);

        //這個是我們點擊的按鈕之后,所執行的方法
        private void btn_MyClick(object sender, EventArgs e)
        {
            Button btn = sender as Button;
            MessageBox.Show("你點擊了" + btn.Text);
        }

  下面我們來編寫程序,自己定義一個事件,然后觸發這個事件,再進行處理

  這是一個監聽鍵盤按鍵的事件,會把我們按下的鍵的字符顯示出來。

  1 /*TestEventSource類。他就相當于windows控件類一樣,是事件的源,里面包含有事件的聲明,
  2  * 以及存儲調用參數的事件參數類,以及事件的觸發方法。      
  3 
  4 TestEventListener類。他提供了事件處理程序,并實現了事件處理程序和事件對象的邦定,
  5  * 當然時間處理程序可以放在別處, 跟邦定程序(訂閱事件)放在一起便于理解和調用
  6 
  7 Test 類,實例化自定義事件的事件源對象,并調用 TestEventListener類中的Subscribe(es);
  8  * 方法進行事件對象和事件處理程序的邦定(訂閱事件),調用 TestEventSource類中的
  9  * RaiseEvent(char keyToRaiseEvent)引發對象,并有對象所指定的委托回調處理事件。
 10  * 完成整個自定義事件。
 11 
 12 其中   RaiseEvent(char keyToRaiseEvent)      就相當于main()一樣是自定義事件的執行入口,      
 13  * 從這個法開始---〉調用事件委托----〉查找訂閱事件程序找到事件所封裝的方法集----〉
 14  * 由委托回調事件處理程序并傳遞參數---〉執行事件處理程序。
 15  */
 16 namespace event事件
 17 {
 18     //發布事件的類
 19     public class TestEventSource 
 20     {
 21         //定義事件參數類
 22         public class TestEventArgs : EventArgs 
 23         {
 24             public readonly char KeyToRaiseEvent;
 25             public TestEventArgs(char keyToRaiseEvent) 
 26             {
 27                 KeyToRaiseEvent = keyToRaiseEvent;
 28             }
 29         }
 30 
 31         //定義delegate
 32         public delegate void TestEventHandler(object sender, TestEventArgs e);
 33 
 34         //用event關鍵字聲明事件對象
 35         public event TestEventHandler TestEvent;
 36 
 37         //事件觸發方法
 38         protected virtual void OnTestEvent(TestEventArgs e) 
 39         {
 40             if (TestEvent != null)
 41             {
 42                 TestEvent(this, e);
 43             }
 44         }
 45 
 46         //引發事件
 47         public void RaiseEvent(char keyToRaiseEvent) 
 48         {
 49             TestEventArgs e = new TestEventArgs(keyToRaiseEvent);
 50             OnTestEvent(e);
 51         }
 52     }
 53 
 54     //監聽事件的類
 55     public class TestEeventListener 
 56     {
 57         //定義處理事件的方法,它與聲明事件的delegate具有相同的參數和返回值類型
 58         public void keyPressed(object sender, TestEventSource.TestEventArgs e) 
 59         {
 60             Console.WriteLine("發送者:{0},所按的鍵為:{1}",sender,e.KeyToRaiseEvent);
 61         }
 62 
 63         //訂閱事件
 64         public void Subscribe(TestEventSource eventSource) 
 65         {
 66             eventSource.TestEvent += new TestEventSource.TestEventHandler(keyPressed);
 67         }
 68 
 69         //取消訂閱事件
 70         public void UnSubscribe(TestEventSource eventSource)
 71         {
 72             eventSource.TestEvent -= new TestEventSource.TestEventHandler(keyPressed);
 73         }
 74     }
 75 
 76     class Program 
 77     {
 78         public static void Main() 
 79         {
 80             //創建事件源對象
 81             TestEventSource es = new TestEventSource();
 82 
 83             //創建監聽對象
 84             TestEeventListener el = new TestEeventListener();
 85 
 86             //訂閱事件
 87             Console.WriteLine("訂閱事件\n");
 88             el.Subscribe(es);
 89 
 90             //引發事件
 91             Console.WriteLine("輸入一個字符,再按enter鍵");
 92             string s = Console.ReadLine();
 93             es.RaiseEvent(s.ToCharArray()[0]);
 94 
 95             //取消訂閱事件
 96             Console.WriteLine("\n取消訂閱事件\n");
 97             el.UnSubscribe(es);
 98 
 99             //引發事件
100             Console.WriteLine("輸入一個字符,再按enter鍵");
101             s = Console.ReadLine();
102             es.RaiseEvent(s.ToCharArray()[0]);
103         }
104     }
View Code

  當我們取消訂閱事件后,再來引發事件,就不會再執行處理事件的方法了。


文章列表


不含病毒。www.avast.com
全站熱搜
創作者介紹
創作者 大師兄 的頭像
大師兄

IT工程師數位筆記本

大師兄 發表在 痞客邦 留言(0) 人氣()