ASP.NET 2.0 開發無重新整理頁面(已試)

來源:互聯網
上載者:User

 

        在已經發布的 ASP.NET2.0 中,無重新整理頁面開發相關部分同 beta2 有不少改動。而且在越來越多的 Ajax 開發包被開發出來的情況下, ASP.NET2.0 內建的無重新整理頁面技術沒有被很多人瞭解,甚至不少人認為該功能有些“雞肋”。但如果我們僅僅是在程式中加入很少部分的 Ajax 特性 、Atlas 、Ajax.Net 等就顯得有些“殺雞用牛刀”的感覺了。而且,我認為使用 ASP.NET2.0 提供的方法進行開發並不很複雜,相反,使用很少的代碼就可以做出來很棒的效果!
   下面我來一步一步的帶大家開發無重新整理的頁面!

 第一步:實現 ICallbackEventHandler 介面

   ICallbackEventHandler介面位於System.Web.UI命名空間下。在beta2時,ICallbackEventHandler只包含一個RaiseCallbackEvent方法,即處理回調事件,又返回處理結果。在正式版中,它變成了包含GetCallbackResult和RaiseCallbackEvent兩個成員方法,第一個用來返回回調事件的結果,第二個用來出來回調事件。這個變化主要是為了編寫Web控制項而做的改動,具體可以看一下GridView等控制項中的實現代碼。

建立一個 Web 網站,我們來修改 default.aspx.cs 檔案:

using System;
using System.Data;
using System.Configuration;
using System.Collections;
using System.Web;
using System.Web.Security;
using System.Web.UI;
using System.Web.UI.WebControls;
using System.Web.UI.WebControls.WebParts;
using System.Web.UI.HtmlControls;

 

public partial class _Default: System.Web.UI.Page, ICallbackEventHandler
{
    protected void Page_Load(object sender, EventArgs e)
    {

    }

    private string str;

    public void RaiseCallbackEvent(string eventArgument)
    {
        //可以根據傳遞的參數不同,調用不同的處理邏輯
        str = "從伺服器端返回的內容:" + eventArgument;
    }

    public string GetCallbackResult()
    {
        return str;
    }
}

  第二步:註冊回調方法

   我們在 default.aspx 頁面中添加一個 TextBox ,一個 Label 和一個 Html 控制項 Button ,並給 Button 添加 onclick 事件:

<%@ Page Language="C#" AutoEventWireup="true" CodeFile="Default.aspx.cs" Inherits="_Default" %>

<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">

<html xmlns="http://www.w3.org/1999/xhtml" >
<head runat="server">
    <title>無標題頁</title>
<script type="text/javascript">
<!--
     //由button調用
    function CallServer(inputcontrol,context)
    {
        context.innerHTML = "Loading";
        arg = inputcontrol.value;
        //註冊回調方法
        <%= ClientScript.GetCallbackEventReference(this, "arg", "ReceiveServerData", "context")%>;
    }
    //在回調方法中註冊的接收返回結果的函數
    function ReceiveServerData(result,context)
    {
        context.innerHTML = result;
    }
// -->
</script>
</head>
<body>
    <form id="form1" runat="server">
    <div>
        <asp:TextBox ID="TextBox1" runat="server"></asp:TextBox>
        <br />
        <input id="Button1" type="button" value="button" language="javascript" onclick="CallServer(TextBox1, Label1)" /><br />
        <asp:Label ID="Label1" runat="server" Text="Label"></asp:Label></div>
    </form>
</body>
</html>

   好了,一個無重新整理的頁面就開發完了,它可以將你在 TextBox 中輸入的文字,通過伺服器代碼寫回到頁面的 Label 中。是不是很簡單?你可以運行一下你的程式看看效果啦!

   下面我們來分析一下這些代碼。

   首先,我們看<%= ClientScript.GetCallbackEventReference(this, "arg", "ReceiveServerData", "context")%>;

   ClientScript是System.Web.UI.Page對象的一個屬性,它是System.Web.UI.ClientScriptManager對象。用於管理用戶端指令碼,GetCallbackEventReference方法用於註冊一個伺服器端事件的用戶端回調。它的第四個參數“Context”非常重要,但在MSDN中並沒有相關的例子和詳細的說明。在我上面給的代碼中可以看到,調用CallServer方法時,傳遞的Context參數就是Label1,而ReceiveServerData的第二個參數“Context”就是被傳遞過來的Label1。在我的例子中,Context被我用於設定一個用來顯示服務端返回結果的控制項。其實,你可以將任意的對象賦值給Context,它都會被傳遞給本地端處理回調返回結果的函數,這樣,你就可以根據調用前指定的“上下文”靈活的操作返回結果了!

在下面給出的完整例子中,你可以看到一個使用Context做的無重新整理顯示GridView的例子。
   在這裡我要說個題外話,Context這麼重要的參數在MSDN中不但沒有詳細的說明,而且VS2005中文正式版MSDN中關於回調的例子竟然還是beta2時的實現!這個版本的MSDN可以說是我用過的版本中品質最差的。不過現在的MSND可以用“相當”龐大來形容,出錯也是在所難免的,希望下個版本的MSND會好一些。

   OK,在ASP.NET 2.0中開發具有Ajax特性的東東不難吧!其實就是兩步:

1、在Server端實現ICallbackEventHandler介面,在介面包含的方法中根據傳遞的參數分別調用不同的處理方法,然後返回結果;

2、在Client端註冊回呼函數(當然你也可以在Server端註冊),然後實現處理回調結果的函數。其中,如果對Context能幹靈活運行,你就可以做出非常好的效果了。

.ASPX代碼

<%@ Page Language="C#" AutoEventWireup="true"  CodeFile="Default.aspx.cs" Inherits="_Default" %>

<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">

<html xmlns="http://www.w3.org/1999/xhtml" >
<head runat="server">
    <title>ASP.NET 2.0 頁面提交無重新整理示範</title>
    <script type="text/javascript">
       function CallServer1(inputcontrol, context)
       {
            context.innerHTML = "<IMG SRC='images/pie.gif' />Loading";
            arg = 'ServerMethod1|' + inputcontrol.value;
            <%= ClientScript.GetCallbackEventReference(this, "arg", "ReceiveServerData1", "context")%>;
        }
      
        function ReceiveServerData1(result, context)
        {
            context.innerHTML = context.id + ":" + result;
        }
      
        function CallServer2(obj)
        {
            context = gridspan;
            context.innerHTML = "<IMG SRC='images/pie.gif' />資料載入中";
            arg = "ServerMethod2|" + obj.value;
            <%= ClientScript.GetCallbackEventReference(this, "arg", "ReceiveServerData2", "context")%>;
        }
      
        function ReceiveServerData2(result, context)
        {
            context.innerHTML = result;
        }
      
    </script>
</head>
<body>
    <form id="form1" runat="server">
    <div>
        <h1>Demo1:html按鈕提交資料</h1><br />
        <asp:TextBox ID="TextBox1" runat="server"></asp:TextBox>
        <input id="Button1" type="button" value="提交到Label1" onclick="CallServer1(TextBox1, Label1)"/>
        <input id="Button2" type="button" value="提交到Label2" onclick="CallServer1(TextBox1, Label2)"/>
        <br />
        <asp:Label ID="Label1" runat="server" Text="Label1:"></asp:Label>
        <br />
        <asp:Label ID="Label2" runat="server" Text="Label2:"></asp:Label>
    </div>
    <hr />
    <div>
        <h1>Demo2:伺服器按鈕提交資料</h1><br />
        <asp:TextBox ID="TextBox2" runat="server"></asp:TextBox>
        <asp:Button ID="Button3" runat="server" Text="Button" /><br />
        <asp:Label ID="Label3" runat="server" Text="Label3:"></asp:Label></div>  
    <hr />
    <div>
        <h1>Demo3:下拉式清單方塊和gridview綁定資料</h1><br />
        <asp:SqlDataSource ID="SqlDataSource1" runat="server" ConnectionString="<%$ connectionStrings:test %>"
            SelectCommand="select distinct(country) from customers"></asp:SqlDataSource>
        <asp:SqlDataSource ID="SqlDataSource2" runat="server" ConnectionString="<%$ connectionStrings:test %>"
            SelectCommand="select customerid, companyname, country from customers where country=@Country">
            <SelectParameters>
                <asp:ControlParameter Name="Country" ControlID="DropDownList1" PropertyName="SelectedValue" />
            </SelectParameters>
        </asp:SqlDataSource>
        <div>
            <asp:DropDownList ID="DropDownList1" runat="server" Width="239px"
                DataSourceID="SqlDataSource1" DataTextField="Country" DataValueField="Country">
            </asp:DropDownList>
        </div>
        <br />
        <span id="gridspan">
            <asp:GridView ID="GridView1" runat="server" DataSourceID="SqlDataSource2">
            </asp:GridView>
        </span>
    </div>
    </form>
</body>
</html>

.CS代碼

using System;
using System.Data;
using System.Configuration;
using System.Web;
using System.Web.Security;
using System.Web.UI;
using System.Web.UI.WebControls;
using System.Web.UI.WebControls.WebParts;
using System.Web.UI.HtmlControls;
using System.IO;
using System.Globalization;

public partial class _Default : System.Web.UI.Page,ICallbackEventHandler
{
    protected void Page_Load(object sender, EventArgs e)
    {
        //註冊用戶端事件處理方法
        Button3.Attributes.Add("onclick", "CallServer1(TextBox2, Label3);return false;");
        DropDownList1.Attributes.Add("onchange", "CallServer2(this)");
    }

    private string serverReturn;

    public string GetCallbackResult()
    {
        //為便於查看載入效果,添加延時
        System.Threading.Thread.Sleep(2000);

        string[] parts = serverReturn.Split('|');
        //根據傳遞的方法名進行調用,並傳遞相應的參數,目前只支援一個參數
        return (string)GetType().GetMethod(parts[0]).Invoke(this, new object[] { parts[1] });
    }

    public void RaiseCallbackEvent(string eventArgument)
    {
        serverReturn = eventArgument;
    }

    //根據從用戶端傳來的英文國家名或縮寫,翻譯成相應的中文國家名
    public string ServerMethod1(string arg)
    {
        string s;
        switch (arg.ToLower())
        {
            case "cn":
            case "china":
                s = "中國";
                break;
            case "us":
                s = "美國";
                break;
            default:
                s = "未知國家";
                break;
        }
        return s;
    }

    //根據從用戶端傳來的值,對GridView的內容進行更新,並將更新後的GridView的html返回
    public string ServerMethod2(string arg)
    {
        DropDownList1.SelectedValue = arg;
        GridView1.DataBind();

        return RenderControl(GridView1);
    }

    private string RenderControl(Control control)
    {
        StringWriter writer1 = new StringWriter(CultureInfo.InvariantCulture);
        HtmlTextWriter writer2 = new HtmlTextWriter(writer1);

        control.RenderControl(writer2);
        writer2.Flush();
        writer2.Close();

        return writer1.ToString();
    }
}

 

Web.config

 

<configuration>
 <appSettings/>
  <connectionStrings>
    <add name="test" connectionString="server=(local);Integrated security=true;database=pubs"/>
  </connectionStrings>
 <system.web>
  <compilation debug="true"/>
 </system.web>
</configuration>

 

customers.sql

 

use pubs
go

create table customers
(
 customerid int identity(1,1) primary key, --主鍵 自動成長
 companyname varchar(20) not null,  --公司名稱
 country  varchar(20) not null  --所屬國家
)

insert into customers values ('中國公司','cn')
insert into customers values ('中國公司','china')
insert into customers values ('美國公司','us')
insert into customers values ('韓國公司','corea')
insert into customers values ('新加坡公司','singapore')

select * from customers

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.