方法一:直接使用<%=%>調用(ASPX頁面)
前台JS,代碼如下:
<script type="text/javascript"> var methodStr = "<%=BehindMethod() %>"; alert(methodStr); </script>
後台方法,代碼如下:
public static string BehindMethod() { return "這是一個後台的方法"; }
說明:
1)BehindMethod()方法前的public訪問修飾符不要忘了;
2)此法有局限性——BehindMethod()只會在ASPX頁面加載或者回發的時候自動調用,不能人為控制調用。
方法二:用ajax調用
前台JS/jQuery,代碼如下:
<script type="text/javascript"> var params = {ext:"p9hp"}; //參數,注意參數名要注意和後台方法參數名要一致 $(function(){ $("#btnOk").click(function(){ $.ajax({ type:"POST", //請求方式 url:"AjaxDemo.aspx/GetImg", //請求路徑:頁面/方法名字 data: params, //參數 dataType:"text", contentType:"application/json; charset=utf-8", beforeSend:function(XMLHttpRequest){ $("#tips").text("開始調用後頭方法獲取圖片路徑,請等待"); $("#imgFood").attr("src","image/loading.gif"); }, success:function(msg){ //成功 $("#imgFood").attr("src",eval("("+msg+")").d); $("#tips").text("調用方法結束"); }, error:function(obj, msg, e){ //異常 alert("OH,NO"); } }); }); }); </script>
頁面HTML,代碼如下:
<body> <form id="form1" runat="server"> <div> <label id="tips"></label> <img id="imgFood" /> <input value="點擊我,給你看一張圖片" type="button" width="35px" id="btnOk" /> </div> </form> </body>
ASPX後台方法,代碼如下:
[System.Web.Services.WebMethod] public static string GetImg(string ext) { System.Threading.Thread.Sleep(5000);//為了有點等待的效果,延遲5秒 StringComparer sc = StringComparer.OrdinalIgnoreCase; string[] extArr = new string[] { "php", "asp", "aspx", "txt", "bmp" }; bool f = extArr.Any(s=>sc.Equals(s,ext)); //判斷傳入的後綴名是否存在 if (f) { return "image/54222860.jpg"; } return "image/star1.jpg"; }
說明:
1)後台方法前的[System.Web.Services.WebMethod]不能少;
2)還有一種形式的ajax,與上述很類似,不同之處在於:使用.ashx一般處理程序,將上述前台JS/jQuery代碼中url更改為請求的一般處理程序路徑/[地址欄參數](地址欄參數根據實際需要決定是否添加),如url:"AjaxDemo.ashx"。然後在AjaxDemo.ashx.cs的public void ProcessRequest(HttpContext context){...}中編寫相關代碼,最後以context.Response.Write("返回值")的形式返回返回值。
方法三:AjaxPro或者Ajax庫(也是ajax)
第一步:下載AjaxPro.dll(或者Ajax.dll),並且添加引用到項目
第二步:修改Web.config,在 <system.web> 節點下添加以下代碼。這裡的Ajax.dll和Ajaxpro.dll引用方法是不一樣的,一定要注意。
<configuration> <system.web> <httpHandlers> <!-- Ajax.dll的配置文件寫法為,我下載到的是這個 --> <add verb="POST,GET" path="ajax/*.ashx" type="Ajax.PageHandlerFactory, Ajax" /> <!-- AjaxPro.dll的配置文件寫法為,根據你下載到的DLL文件選擇不同的配置語句--> <add verb="*" path="ajaxpro/*.ashx" type="AjaxPro.AjaxHandlerFactory, AjaxPro"/> </httpHandlers> </system.web> </configuration>
如果是IIS7,則需要在<system.webServer></system.webServer>裡加上<add name="ajax" verb="POST,GET" path="ajax/*.ashx" type="Ajax.PageHandlerFactory, Ajax" />
第三步:對AjaxPro用到的頁(如AjaxDemo.aspx)Page_Load事件中進行運行時注冊。如:
protected void Page_Load(object sender, EventArgs e) { Ajax.Utility.RegisterTypeForAjax(typeof(AjaxDemo));//是Ajax.dll的 AjaxPro.Utility.RegisterTypeForAjax(typeof(AjaxDemo));//Ajaxpro.dll的 }
對RegisterTypeForAjax方法的調用在頁面產生如下的javascript代碼(另外一種選擇,你也可以人工在頁面上添加如下的javascript代碼):
<script type="text/javascript" src="ajax/common.ashx"></script> <script type="text/javascript" src="ajax/NAMESPACE.CLASS,ASSEMBLYNAME.ashx"></script>
上面這段代碼的粗體部分NAMESPACE.PAGECLASS,ASSEMBLYNAME含義如下
NAMESPACE.CLASS
命名空間和類
ASSEMBLYNAME
程序集的名稱
Ajax也可以支持自定義類,但是需要這個類是可以被序列化的,即要在自定義類如User前加上[Serializable()]
[Serializable()] public class User { private int _userId; private string _firstName; private string _lastName; public int userId { get { return _userId; } } public string FirstName { get { return _firstName; } } public string LastName { get { return _lastName; } } public User(int _userId, string _firstName, string _lastName) { this._userId = _userId; this._firstName = _firstName; this._lastName = _lastName; } public User(){} [Ajax.AjaxMethod()]或者是[AjaxPro.AjaxMethod()] public User GetUser(int userId) { //Replace this with a DB hit or something :) return new User(userId,"Michael", "Schwarz"); } [Ajax.AjaxMethod()]或者是[AjaxPro.AjaxMethod()] public DataSet GetUserList(paramType1 param1, paramType2 param2, ...) { //Replace this with a DB hit or something :) return a DataSet;
} [Ajax.AjaxMethod()]或者是[AjaxPro.AjaxMethod()] public DataTable GetUserList(paramType1 param1, paramType2 param2, ...) { //Replace this with a DB hit or something :) return a DataTable;
} }
那麼,在調用頁面用RegisterTypeForAjax向服務器注冊代理類的代碼也要相應變更,代理類的名字不再是頁面類,而是我們自定義的類,代碼如下:
protected void Page_Load(object sender, EventArgs e) { Ajax.Utility.RegisterTypeForAjax(typeof(User));//是Ajax.dll的 AjaxPro.Utility.RegisterTypeForAjax(typeof(User));//Ajaxpro.dll的 }
第四步:編寫服務端方法,並且用[Ajax.AjaxMethod]標注
注意:
1)方法要寫成public,否則在JS裡調用的時候會提示"不支持此屬性或方法";
2)在服務端函數,如果需要處理Session信息,此時必須在想支持Session的服務端函數的Ajax.AjaxMethod屬性上傳遞一個參數,如[Ajax.AjaxMethod(HttpSessionStateRequirement.Read)]。當然了,還可以是Write或ReadWrite,這個參數我們可以根據實際需求自行選擇。
在下面這個例子中,我們有一個文檔管理系統,當一個用戶對文檔進行編輯的時候會給這個文檔加鎖,其他用戶需要等到這個文檔可用時才能修改。不使用Ajax,用戶需要不斷等待刷新,因為不得不不斷的去檢查文檔的狀態是否為可用,這當然不是一個很好的方案。用ajax的sessionstate支持,這就比較容易了。
我們首先Document類中寫一個函數,這個函數通過遍歷文檔ID找到用戶需要的文檔,存儲到session裡,並返回沒有占用的文檔:
[Ajax.AjaxMethod(HttpSessionStateRequirement.Read)] public ArrayList DocumentReleased() { if (HttpContext.Current.Session["DocumentsWaiting"] == null) { return null; } ArrayList readyDocuments = new ArrayList(); int[] documents = (int[])HttpContext.Current.Session["DocumentsWaiting"]; for (int i = 0; i < documents.Length; ++i) { Document document = Document.GetDocumentById(documents[i]); if (document != null && document.Status == DocumentStatus.Ready) { readyDocuments.Add(document); } } return readyDocuments; }
我們在屬性參數中指明了HttpSessionStateRequirement.Read,下面寫javascript函數來使用這個方法帶來的結果:
<script type="text/javascript"> function DocumentsReady_CallBack(response) { if (response.error != null) { alert(response.error); return; } if (response.value != null && response.value.length > 0) { var div = document.getElementById("status"); div.innerHTML = "The following documents are ready!<br />"; for (var i = 0; i < response.value.length; ++i) { div.innerHTML += "<a href=\"edit.aspx?documentId=" + response.value[i].DocumentId + "\">" + response.value[i].Name + "</a><br />"; } } } </script> <body onload="setTimeout('Document.DocumentReleased(DocumentsReady_CallBack)', 10000);">
頁面加載後每10秒鐘向服務器函數請求一次。如果有返回,則callback函數檢查response,並把最新的結果顯示出來。
第五步:前台JS,調用User類的GetUser函數。Ajax封裝類會創建一個javascript函數,形式與服務端GetUser函數相似,帶一個參數,我們以"類名.函數名"的方式調用(如果是AjaxPor.dll,則以"命名空間.類名.函數名"的方式調用)。
作為Ajax最基本的功能,我們所需要做的只是調用這個方法並且傳遞參數,然後獲取返回值進行後續處理,代碼如下:
<script type="text/javascript"> var response = User.GetUser(168); alert(response.value); </script>
Ajax還有更強大的功能,這就是為什麼所有的客戶端代理(如User.GetUser)同時帶有一個額外的定制屬性。這個屬性用來處理服務器響應的回調函數:
<script type="text/javascript"> function getUser(userId) { User.GetUser(userId, GetUser_CallBack); } function GetUser_CallBack(response) { if (response != null && response.value != null) { var user = response.value; if (typeof(user) == "object") { alert(user.FirstName + " " + user.LastName); } } } getUser(1); </script>
從上面的代碼中可以看出,我們為GetUser函數增加了一個額外參數GetUser_CallBack,這個參數就是用來處理服務器端響應的客戶端函數。這個CallBack函數接受一個帶有四個關鍵屬性的response對象:
value
服務器端函數執行的返回值(可能是一個字符串、自定義對象或者dataset)
error
如果發生錯誤,則返回錯誤信息.
request
原始的xmlHttpRequest請求
context
一個上下文對象
我們首先應該檢查是否有錯誤發生,你可以通過在服務器端函數拋出異常來實現這個error屬性。在上面這個例子中,我們簡單的alert了一個值,就是value屬性;request屬性可以用來取得額外的信息(更多的關於XmlHttpRequest的知識)。
說明:
返回值同服務器端對象一樣有三個屬性(FirstName, LastName and UserId)。
實例中我們在服務端函數返回了一個User類對象,那麼Ajax還支持哪些返回類型呢?
Ajax可以支持除了我們上面GetUser函數返回的User類類型以外的很多類型。它可以直接支持integer, string, double, boolean, DateTime, DataSet 和 DataTable,也支持簡單的自定義類型和數組。其他的類型通過其ToString方式來返回字符串。
返回DataSet就像真正的.net Dataset。假設頁面中有個id為userinfo的table標簽,我們可以通過下面的方法在客戶端顯示:
<script type="text/javascript"> function getUserList(userId) { User.GetUserList(param1, param2, ..., GetUserList_CallBack); } function GetUserList_CallBack(response) { var ds = response.value; if (ds != null && typeof(ds) == "object" && ds.Tables != null) { $("#userinfo").empty(); var rowsLength = ds.Tables[0].Rows.length; if(rowsLength > 0) { for(var i = 0; i < rowsLength; i++) { var UserRow = ds.Tables[0].Rows[i]; $("#userinfo").append('<tr>'); $("#userinfo").append('<td>[Ajax.AjaxMethod()] public string Test1(string name, string email, string comment) { string html = ""; html += "Hello " + name + "<br>"; html += "Thank you for your comment <b>"; html += System.Web.HttpUtility.HtmlEncode(comment); html += "</b>."; return html; }
代理的工作機制:
Ajax.PageHandlerFactory是通過反射來取得有定制屬性的函數的細節。Handler尋找帶有AjaxMethod定制屬性的函數,取得他們的特征(返回類型、名稱、參數)並依據這些信息創建客戶端代理。特別的,ajax創建一個與服務端函數類型相同的JavaScript對象作為代理。
Ajax技術可以給客戶端提供豐富的客戶體驗,而ajax.net為您容易的實現這樣強大的功能提供了可能,你可以通過下面的鏈接查看ajax.net的最新文檔:
Keep a close eye on the AJAX .Net wrapper website:http://ajax.schwarz-interactive.de/
For a good hands-on sample, check out the following demo application:http://ajax.schwarz-interactive.de/download/ajaxsample.zip
參考鏈接①:http://www.cnblogs.com/U2USoft/articles/332439.html
參考鏈接②:http://www.jb51.net/article/42176.htm