探讨微软ASP.NET AJAX控件开发技术(服务器端)
一、簡介
到目前為止,我們已經討論了開發Ajax控件所涉及的客戶端相關技術。現在,讓我們來討論此過程中與服務器端相關的一些技術。
需要說明的是,在【客戶端】篇中我們的舉例本質上僅是使用ASP.NET AJAX框架提供的面向對象JavaScript技術來增強了一個客戶端圖像組件,而沒有明顯涉及到AJAX技術(除了ScriptManager在后臺以AJAX方式下載并管理客戶端腳本代碼外)。所以,這個例子是簡單的,僅憑客戶端相關知識就可以使用這個增強控件。
但是,在實際開發中,當要增強的客戶端控件涉及到AJAX技術時,或者干脆是想增強服務器端組件(如UpdatePanel控件)時,我們必須進行相關的服務器端編程,而這要求我們必須對Ajax控件開發中所涉及的服務器端相關聯的類有所了解。而且,還要以ASP.NET 2.0服務器控件開發相關知識為基本前提,特別是在開發復雜的Ajax控件時。
在本篇中,我們要重新構造一個增強的圖像按鈕控件MySrvImageButton,此控件將以ASP.NET 2.0服務器控件ImageButton為基礎。
二、AJAX控件開發服務器端相關技術
首先,讓我們來看一下AJAX控件開發服務器端相關組件及其關系,這些類之間的繼承關系圖如下圖1所示。
| 圖1:控件開發涉及的主要服務器端類之間層次結構圖 |
上圖展示了組件、控件和擴展器之間的繼承關系。如你所見,為了開發一個控件(注意,Component和Extender不在本文討論范圍之內),我們有兩個選擇:其一,創建一個派生自ScriptControl的類;其二,創建一個實現IScriptControl接口的類。但是,如果你想使你的控件從WebControl派生,那么,ScriptControl應該是一個更好的選擇—因為它正是派生自WebControl控件本身。但是,如果你想從頭開發創建你的控件,并且不要求實現WebControl所具備的任何內在特征,那么,實現IScriptControl則更為恰當。此外,當你想在一個現有控件(例如本文中的MySrvImageButton)中添加Ajax特征時選擇使用接口IScriptControl也會是你的選擇。但是這兩種方法都要求重載下列兩個方法:①、GetScriptDescriptors;②、GetScriptReferences。
三、GetScriptDescriptors
這個方法負責在客戶端以自動方式生成$create語句(而在上篇中是使用手工方式)。它使用了一個特殊類ScriptDescriptor來生成它。在繼續往下討論前,首先讓我們來瀏覽一下ScriptDescriptor類中的繼承層次圖(如圖2所示):
| 圖2:ScriptDescriptor類中的繼承層次圖 |
顯然,每一種具體類型的組件都存在其單獨的描述符。如果你在開發一個常規組件,那么,這個方法會返回一個ScriptComponentDescriptor的實例。對于擴展器而言,該方法返回的是一個ScriptBehaviorDescriptor實例;而對于一個控件,則返回ScriptControlDescriptor類的實例。該描述符中提供了一些特定的方法用于創建服務器端與客戶端的“連接”。下面,還是讓我們來分析一個有關$Create語句是如何在服務器端“注入”的簡短示例:
//上篇中從客戶端以手工方式使用$create {'hoverImageUrl':'Images/updateh.gif'}, {'click':buttonClicked}, null, $get('cliBtn')); new ScriptControlDescriptor("AjaxImageButtonLib.MySrvImageButton", |
在上面的代碼中,我們在構造器中傳遞客戶端類型(盡管客戶端和服務器端具有相同的類型名)和DOM元素ID。這一步將填充$Create語句的第一個和最后一個參數。此后,我們設置hoverImageUrl屬性,它對應于$Create語句的屬性部分。最后,通過設置Click事件處理器,我們填充$Create語句的事件部分。下面是腳本描述符中暴露的幾個重要的方法:
1)AddProperty()
這個方法能夠在客戶端添加一個屬性。第一個參數相應于屬性名,第二個參數對應該參數的取值。
2)AddEvent()
這個方法在客戶端添加一個事件。第一個參數相應于事件名,第二個參數對應你想綁定的函數的名稱。
3)AddScriptProperty()
這個方法能夠把JavaScript代碼指定為屬性的一個值。對于復雜的屬性賦值通常都要求這樣的操作。
4)AddElementProperty()
這個方法在客戶端添加一個屬性,但是其與AddProperty方法間的區別在于,該值作為一個參數傳遞給$get方法。
5)AddComponentProperty()
這個方法負責在$Create語句的Component部分添加一個組件引用。該值將被用于$find語句中實現屬性的賦值。這個方法的第一個參數相應于屬性名,第二個參數對應該組件的id。
四、GetScriptReferences
這個方法負責在ScriptManager中注冊JavaScript文件。在這個方法中,針對每一個要求的JavaScript文件,我們都需要創建一個相應的ScriptReference實例。例如,在圖像按鈕例子中,我們按如下方式注冊JavaScript文件:
| IEnumerable<ScriptReference> IScriptControl.GetScriptReferences() { return new ScriptReference(Page.ResolveUrl("~/SrvImageButton.js")); } |
此外,我們還可以以嵌入式資源方式注冊JavaScript文件。為此,我們必須首先在Visual Studio的解決方案資源管理器中把一個JavaScript文件標記為一種嵌入式資源。然后,我們必須添加上WebResource屬性以便利用Asp.Net 2.0 Web資源處理器。下列代碼展示了如何把一個JavaScript文件注冊為一個嵌入式資源:
[assembly: WebResource("MyControls.SubControl.Script1.js", "text/javascript")] |
此外,如果我們想實現IScriptControl接口而不是從ScriptControl中繼承的話,我們還必須重載OnPreRender與Render方法。這樣將能確保ScriptManger識別出該服務器控件是一個支持Ajax功能的控件。
下列代碼展示了開發基于ASP.NET 2.0服務器端控件的AJAX控件時必須在服務器端實現的最少代碼:
using System; |
上面代碼中,我們在OnPreRender方法中實現注冊控件,而在Render方法中注冊腳本描述符部分。當然,如果頁面上不存在ScriptManager控件的話,我們必須拋出一個錯誤提示。但是,如果你正在開發非基于ASP.NETAJAX框架的控件的話,你完全可以從頁面中刪除ScriptManager控件。
五、創建基于ASP.NET服務器端控件的增強AJAX圖像控件
(一)創建示例AJAX網站
啟動Visual Studio 2005,選擇“文件→新建網站…”,然后選擇“ASP.NET AJAX-Enabled Web Site”模板,命名工程為“AjaxServCtrlTest”,并選擇C#作為內置支持語言,最后點擊“確定”。
(二)創建AJAX技術支持的增強服務器控件
點擊菜單“文件→添加→新建項目…”,在“添加新項目”對話框中,從左邊選擇“項目類型”為“Visual C#→Windows”,從右邊選擇“模板類型”為“Web控件庫”,輸入控件庫的名字為AjaxImageButtonLib,選擇目標目錄為前面創建的網站根目錄,最后點擊“確定”。
接下來,根據我們前面的分析,把類庫源WebCustomControl1.cs文件的內容更改為以下形式:
//…………(省略命名空間引用部分) System.Web.UI.WebControls.ImageButton, IScriptControl return (value == null) ? string.Empty : (string)value; ("ScriptManager required on the page."); new ScriptControlDescriptor("AjaxImageButtonLib.MySrvImageButton", ClientID); |
首先,我們注意到我們要創建的新控件MySrvImageButton繼承自ASP.NET服務器控件ImageButton,并繼承了接口IScriptControl。
有了前面的理論描述,在此,我們省略對于其中幾個常規方法的描述。
接下來,我們要構建這個控件庫(即程序集)。右擊此庫工程,并點擊“生成”命令以生成程序集AjaxImageButtonLib.dll,此庫文件中即包含了我們的服務器控件。
(三)創建客戶端JavaScript代碼
這里創建的客戶端控件類相應的JavaScript文件ImageButton.js在內容上完全相同,只不過為了區別起見,我們進行了某些地方的重新命名罷了。在此不再贅述。
(四)在示例網頁中應用構建的新控件
以鼠標右擊前面網站AjaxServCtrlTest,把它設置為“啟動項目”。事實上,因為這個網站工程與前面的類庫工程創建于同一個方案下,所以,在前面生成程序集AjaxImageButtonLib.dll的一結束,新建的服務器控件就被自動添加到Visual Studio 2005工具欄中,如下圖3所示。于是,我們可以直接把這個控件拖動到示例網頁Default.aspx中。
| 圖3:拖動新建的服務器控件到示例網頁中 |
根據前面的控件代碼實現,不出所料,點擊上圖3中的圖形按鈕控件,即可在其相應的“屬性”對話框中設置這個控件的hoverImageUrl屬性,而且指定其ClientClickFunction方法(其實正是此控件的click事件處理器函數指針)。
注意,因為控件代碼中的方法GetScriptReferences已經為我們自動生成了前面提到的$create方法,所以我們不需要再在ScriptManager中注冊在本篇中創建的JavaScript文件—SrvImageButton.js了。
(五)運行及性能簡析
現在,請按F5鍵運行此頁面并移動鼠標到圖像按鈕上觀察,你會注意到結果與上篇中的效果一致(即在鼠標移動切換新圖像時,這些動作都發生于客戶瀏覽器端而不再與服務器端相關)。下圖4相應于此示例頁面運行時刻快照。
| 圖4:示例網頁運行時刻屏幕快照 |
通過以鼠標右擊網頁并選擇彈出菜單中的“查看源文件”觀察上、下篇中示例頁面相應的源碼,我們會注意到其內容基本是一致的。另外,通過使用Fiddler觀察這兩個示例頁面下載到客戶端時各模塊的大小,你也會注意到基本一致,如下面圖5所示。
| 圖5:兩個示例頁面下載到客戶端時各模塊大小比較 |
因為本文兩個例子極為簡單,所以其性能基本平衡。但隨著服務端編程的復雜化,本篇中基于服務器端控件的擴展方案應該有較大的性能損耗。但應該仍具有令人滿意的效果,這也正是AJAX Control Toolkit控件數量急劇增加的重要原因之一。而上篇中的方案基于“純粹”(相對而言)的客戶端,即使性能上與本篇中方案相差無幾,但是卻明顯多出了跨越服務器端平臺的優勢,這也正是上篇中方案吸引人的主要原因。
六、總結
雖然以上、下兩個篇幅形成此文,但是這也僅能通過簡短的例子向你闡述了開發ASP.NETAJAX框架中的Ajax控件所涉及的主要技術。盡管目前的ASP.NET AJAX框架已經形成正規的1.0版本,而且這個框架為基于AJAX技術開發以ASP.NET 2.0為主的Web應用提供了全方位支持,但是這個框架仍然在許多方面有待改進。事實上,我們可以進一步沿著ASP.NET AJAX客戶端與服務器端架構層次關系圖進一步擴展其底層。當然,在此框架與Visual Studio整合方面也存在相當的挖掘潛力。
如今,隨著微軟Silverlight技術的推出,ASP.NET AJAX框架的重要性日顯突出。自然,與此框架相關的控件開發也必將在這一大環境中占居著重要的位置。
轉載于:https://www.cnblogs.com/xujiaci/archive/2007/09/13/891417.html
總結
以上是生活随笔為你收集整理的探讨微软ASP.NET AJAX控件开发技术(服务器端)的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 假如没有手机
- 下一篇: 深入剖析微软ASP.NET Ajax中的