国产探花免费观看_亚洲丰满少妇自慰呻吟_97日韩有码在线_资源在线日韩欧美_一区二区精品毛片,辰东完美世界有声小说,欢乐颂第一季,yy玄幻小说排行榜完本

首頁 > 開發 > 綜合 > 正文

淺析C#的事件處理和自定義事件

2024-07-21 02:19:56
字體:
來源:轉載
供稿:網友
一、了解c#中的預定義事件處理機制

在寫代碼前我們先來熟悉.net框架中和事件有關的類和委托,了解c#中預定義事件的處理。

eventargs是包含事件數據的類的基類,用于傳遞事件的細節。

eventhandler是一個委托聲明如下

public delegate void eventhandler( object sender , eventargs e )

注意這里的參數,前者是一個對象(其實這里傳遞的是對象的引用,如果是button1的click事件則sender就是button1),后面是包含事件數據的類的基類。

下面我們研究一下button類看看其中的事件聲明(使用wincv工具查看),以click事件為例。

public event eventhandler click;

這里定義了一個eventhandler類型的事件click

前面的內容都是c#在類庫中已經為我們定義好了的。下面我們來看編程時產生的代碼。

private void button1_click(object sender, system.eventargs e)
{
...
}

這是我們和button1_click事件所對應的方法。注意方法的參數符合委托中的簽名(既參數列表)。那我們怎么把這個方法和事件聯系起來呢,請看下面的代碼。

this.button1.click += new system.eventhandler(this.button1_click);

把this.button1_click方法綁定到this.button1.click事件。

下面我們研究一下c#事件處理的工作流程,首先系統會在為我們創建一個在后臺監聽事件的對象(如果是button1的事件那么監聽事件的就是button1),這個對象用來產生事件,如果有某個用戶事件發生則產生對應的應用程序事件,然后執行訂閱了事件的所有方法。

二、簡單的自定義事件(1)

首先我們需要定義一個類來監聽客戶端事件,這里我們監聽鍵盤的輸入。

定義一個委托。

public delegate void userrequest(object sender,eventargs e);

前面的object用來傳遞事件的發生者,后面的eventargs用來傳遞事件的細節,現在暫時沒什么用處,一會后面的例子中將使用。

下面定義一個此委托類型類型的事件

public event userrequest onuserrequest;

下面我們來做一個死循環

public void run() { bool finished=false; do { if (console.readline()=="h") { onuserrequest(this,new eventargs()); } }while(!finished); }

此代碼不斷的要求用戶輸入字符,如果輸入的結果是h,則觸發onuserrequest事件,事件的觸發者是本身(this),事件細節無(沒有傳遞任何參數的eventargs實例)。我們給這個類取名為userinputmonitor。

下面我們要做的是定義客戶端的類
首先得實例化userinputmonitor類
userinputmonitor monitor=new userinputmonitor();

然后我們定義一個方法。

private void showmessage(object sender,eventargs e)
{
console.writeline("haha!!");
}

最后要做的是把這個方法和事件聯系起來(訂閱事件),我們把它寫到庫戶端類的構造函數里。

client(userinputmonitor m)
{
m.onuserrequest+=new userinputmonitor.userrequest(this.showmessage);
//m.onuserrequest+=new m.userrequest(this.showmessage);

//注意這種寫法是錯誤的,因為委托是靜態的

}

下面創建客戶端的實例。

new client(monitor);

對了,別忘了讓monitor開始監聽事件。

monitor.run();

大功告成,代碼如下:

using system;class userinputmonitor{ public delegate void userrequest(object sender,eventargs e); //定義委托 public event userrequest onuserrequest; //此委托類型類型的事件 public void run() { bool finished=false; do { if (console.readline()=="h") { onuserrequest(this,new eventargs()); } }while(!finished); }}

public class client{ public static void main() { userinputmonitor monitor=new userinputmonitor(); new client(monitor); monitor.run(); } private void showmessage(object sender,eventargs e) { console.writeline("haha!!"); } client(userinputmonitor m) { m.onuserrequest+=new userinputmonitor.userrequest(this.showmessage); //m.onuserrequest+=new m.userrequest(this.showmessage); //注意這種寫法是錯誤的,因為委托是靜態的 }}
三、進一步研究c#中的預定義事件處理機制

可能大家發現在c#中有些事件和前面的似乎不太一樣。例如

private void textbox1_keypress(object sender, system.windows.forms.keypresseventargs e)
{

}

this.textbox1.keypress+=newsystem.windows.forms.keypresseventhandler(this.textbox1_keypress);

這里使用了keypresseventargs而不是eventargs作為參數。這里使用了keyeventhandler委托,而不是eventhandler委托。

keypresseventargs是eventargs的派生類,而keyeventhandler的聲明如下

public delegate void keyeventhandler( object sender , keyeventargs e );

是參數為keyeventargs的委托。那為什么keypress事件要這么做呢,我們可以從兩個類的構造函數來找答案。

public eventargs();

public keypresseventargs(char keychar);

這里的keydata是什么,是用來傳遞我們按下了哪個鍵的,哈。

我在keyeventargs中又發現了屬性

public char keychar { get; }

進一步證明了我的理論。下面我們來做一個類似的例子來幫助理解。

四、簡單的自定義事件(2)

拿我們上面做的例子來改。

我們也定義一個eventargs(類似keyeventargs)取名myeventargs,定義一個構造函數public myeventargs(char keychar),同樣我們也設置相應的屬性。代碼如下

using system;class mymyeventargs:eventargs{ private char keychar; public mymyeventargs(char keychar) { this.keychar=keychar; } public char keychar { get { return keychar; } }}

因為現在要監聽多個鍵了,我們得改寫監聽器的類中的do...while部分。改寫委托,改寫客戶端傳遞的參數。好了最終代碼如下,好累

using system;class myeventargs:eventargs{ private char keychar; public myeventargs(char keychar) { this.keychar=keychar; } public char keychar { get { return keychar; } }}

class userinputmonitor{ public delegate void userrequest(object sender,myeventargs e); //定義委托 public event userrequest onuserrequest; //此委托類型類型的事件 public void run() { bool finished=false; do { string inputstring= console.readline(); if (inputstring!="") onuserrequest(this,new myeventargs(inputstring[0])); }while(!finished); }}

public class client{ public static void main() { userinputmonitor monitor=new userinputmonitor(); new client(monitor); monitor.run(); } private void showmessage(object sender,myeventargs e) { console.writeline("捕捉到:{0}",e.keychar); } client(userinputmonitor m) { m.onuserrequest+=new userinputmonitor.userrequest(this.showmessage); //m.onuserrequest+=new m.userrequest(this.showmessage); //注意這種寫法是錯誤的,因為委托是靜態的 }}




收集最實用的網頁特效代碼!

發表評論 共有條評論
用戶名: 密碼:
驗證碼: 匿名發表
主站蜘蛛池模板: 尼木县| 土默特右旗| 凤阳县| 稻城县| 稷山县| 上栗县| 陇川县| 德阳市| 长汀县| 辽源市| 白沙| 巴南区| 香港 | 莒南县| 江达县| 大渡口区| 绥化市| 琼海市| 沁水县| 聊城市| 郎溪县| 团风县| 屏山县| 思茅市| 容城县| 东乡| 湄潭县| 清原| 赫章县| 平阴县| 颍上县| 定边县| 蒙城县| 东莞市| 太原市| 海门市| 日照市| 汉川市| 高青县| 佛学| 伽师县|