Ajax 回忆录

说起Ajax,并没有什么特别的感觉,只记得曾经接触过这么几种:

一:Net2.0自带的ICallbackEventHandler

那时候从VS2003刚等到VS2005一出来之际,就看了大量的视频教程,从中也学到了这个ICallback的用法。

我将之用在一个CMMI的课程设计里,做的一个图书管理系统,好像在上传图片的时候,为了不刷新某个东东而特意用的。

 

 

二:Atlas

只记得很久前,2006还是2007之际。

那时的Atlas框架刚出来的时候,我一路追着风。关注的flychen的博客,虽然他的文章多数是翻译。

那时候的Atlas很牛B,特效特牛,随便拖一个都是一个赞,我的毕业设计里几乎用上了所有的Atlas控件,就是这份特效为了毕设和第一份工作带来了自信。

那时候的毕业设计做的是一个QQ空间,实现的功能就是:主页汇总,日志,留言,音乐盒,相册,换肤,加一个聊天室。

那个是一个劲的特效,随便点一个,都忽的一声出来,背景随便就黑屏的那种。什么折叠效果,乱七八糟的,什么音乐盒,还能到处拖。

到了后来升到asp.net Ajax版本之后,就再也没那种激情追求什么特效了,把B还给牛了

 

 

三:Prototype

在我的毕业设计里,有音乐盒这东西,音乐盒的播放器是从网上下载的。里面用到了一个prototype.js来调用播放列表。

于是prototype就成了我的第二个接触的Ajax封装体了,在里面也只是小小用了一下。

 

 

四:XMLHttpRequest

还是2007年,要实现一个用户上传图片时,可以拖拉范围红色框同时会放大用户的图片,

用户在一个框选头像后,确定截图上传。

这时用上XMLHttpRequest了,什么新瓶装旧水的言论也略听一二了。

技术总监说这些Ajax早在N年前他就在用了,原理还是Iframe这东西。
后来很多时一直还是用这个。

 

 

五:Jquery

这东东我本人没有用过,不过随着它的流行,我在以前兼职教师时,给我学生介绍过,也按着文档实际操作过几个例子,多数还是讲原理的东西。

 

 

 

一路走过来,

 

从不懂性能[哪个帅点用哪个]->很牛B

性能优先[哪个性能最好用哪个]->只有牛,没有B

到性能取舍[哪个适合项目用哪个]->没牛也没B

这是一个领悟过程

 
回归是一种自然

 

 

 

下面说下用Net2.0自带的ICallbackEventHandler实现封装的一种应用:省市区的联动实现

 

首先:新建一个PageBase.cs基类,继承自System.Web.UI.Page和ICallbackEventHandler接口,代码如下:

PageBase.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;

///   <summary>
///  PageBase 的摘要说明
///   </summary>
public   class  PageBase:System.Web.UI.Page,ICallbackEventHandler
{
    
#region  ICallbackEventHandler 成员
    
///   <summary>
    
///  Ajax方法时的回调结果
    
///   </summary>
     public   string  ajaxCallBackResult  =   null ;
    
///   <summary>
    
///  注册Ajax方法
    
///  调用方法名:callAjax(arg)
    
///  回调方法名:callBack(result)
    
///   </summary>
     public   void  RegisterAjax()
    {
        RegisterAjax(
this " callAjax " " callBack " );
    }
    
public   void  RegisterAjax(Control ct,  string  functionName,  string  callBackName)
    {
        
if  ( ! ct.Page.ClientScript.IsClientScriptBlockRegistered(functionName))
        {
            
string  callBack  =  ct.Page.ClientScript.GetCallbackEventReference(ct,  " arg " , callBackName,  null );
            
string  clientFunction  =   " function  "   +  functionName  +   " (arg){ "   +  callBack  +   " } " ;
            ct.Page.ClientScript.RegisterClientScriptBlock(ct.Page.GetType(), functionName, clientFunction, 
true );
        }
    }
    
public   string  GetCallbackResult()
    {
        
return  ajaxCallBackResult;
    }
    
public   virtual   void  RaiseCallbackEvent( string  eventArgument)
    {
        
if  (CallAjaxEvenHandle  !=   null )
        {
            CallAjaxEvenHandle(eventArgument);
        }
        
else
        {
            ajaxCallBackResult 
=  eventArgument;
        }
    }
    
public   delegate   void  CallAjaxFunction( string  para);
    
public   event  CallAjaxFunction CallAjaxEvenHandle;
    
#endregion
}

说明:

上面的基类中封装了一些基础的注册方法,下面演示如何调用。

 

简单测试调用:

普通页面后台.cs代码,继承自PageBase

public   partial   class  _Default :PageBase
{
    
protected   void  Page_Load( object  sender, EventArgs e)
    {
        RegisterAjax();
    }
}

 

接着页面html代码如下:

< html  xmlns ="http://www.w3.org/1999/xhtml"   >
< body >
    
< form  id ="form1"  runat ="server" >
< input  type ="button"  value ="pages"  onclick ="callAjax('hello')"   />
< script > function  callBack(result){alert(result);} </ script >
    
</ form >
</ body >
</ html >

 

OK,点击就可以出现hello了。

 

扩展应用:很多时候,我们需要在用户控件里实现Ajax调用。

 

这里,也做一个简单调用示例:

控件cs代码:

控件CS代码
public   partial   class  Controls_Head : System.Web.UI.UserControl,ICallbackEventHandler
{
    
string  callbackResult;
    
protected   void  Page_Load( object  sender, EventArgs e)
    {
        ((PageBase)
this .Page).RegisterAjax( this " callAjaxControl " " callbackControl " );
    }
    
#region  ICallbackEventHandler 成员
    
public   string  GetCallbackResult()
    {
        
return  callbackResult;
    }
    
public   void  RaiseCallbackEvent( string  eventArgument)
    {
        callbackResult 
=  eventArgument;
    }

    
#endregion
}

 

用户控件html代码:

控件html代码
<% @ Control Language = " C# "  AutoEventWireup = " true "  CodeFile = " Head.ascx.cs "  Inherits = " Controls_Head "   %>
< input  type ="button"  value ="control"  onclick ="callAjaxControl('helloControl')"   />
< script > function  callbackControl(result){alert(result);} </ script >

 

OK,点击结果也同样出来了。

 

以下进一步示范怎么实现联动:

 

过程:

1:默认先绑定一个省

2:选择省时Ajax请求(发送ID到后台

3:后台查询数据库,把省下的市按规则组合发回前台

4:前台js按规则拆分字符串
5:js清空市并连动区与县的下拉框(或者说叫复位)

6:js创建下拉的项option,并添加到市下拉里

重复一下就是几级联动了,最后完成

 

 

这里的js会做很多事件:发送ajax请求->接收result->分隔字符->复位下拉框->创建下拉option并添加

 

这里先添加一个AreaCity.js,把上面的东西都实现,代码如下:

 AreaCity代码[点下面的一条框出来]


function  GetSonData(parentID,sonDropDownID)

   
if (parentID == " 请选择 "   ||   ! parentID)
   {
        SetDropDownToInit(sonDropDownID);
   }
   
else
   {
        callAjax(parentID
+ " , " + sonDropDownID);
   }
}
function  callBack(result)

    
if (result  &&  String(result).indexOf( ' & ' ) >- 1 )
    {
        
var  listString = result.split( ' & ' )[ 0 ];
        
var  dropDownID = result.split( ' & ' )[ 1 ];
        
if ( ! listString){SetDropDownToInit(dropDownID)}
        
else {createNode(listString,dropDownID);}
    }
}
function  createNode(listString ,dropDownID)
{  
    
var  dropDown = $(dropDownID);
    
if ( ! dropDown){ return ;}
    InitDropDown(dropDown);
    
if (listString)
    {
        
var  strValues  =  listString.split( ' | ' );
        
for ( var  i = 0 ;i < strValues.length;i ++ )
        {
            
var  val  =  strValues[i].split( ' , ' )[ 0 ];
            
var  txt  =  strValues[i].split( ' , ' )[ 1 ];
            
            
var  optionObj  =  document.createElement( " option " );
            optionObj.value 
=  val;
            optionObj.innerText 
=  txt;
            dropDown.appendChild(optionObj);
        }
        dropDown.selectedIndex
= 1 ;
    }
}
function  InitDropDown(dropDown)
{
    
while (dropDown.length > 0 )
    {
        dropDown.removeChild(dropDown.firstChild);
    }
    
var  optionObj  =  document.createElement( " option " );
        optionObj.value 
=   '' ;
        optionObj.innerText 
=   ' 请选择 ' ;
        dropDown.appendChild(optionObj);
}
function  SetDropDownToInit(dropDownID)
{
    InitDropDown($(dropDownID));
    
switch (dropDownID)
    {
        
case   " ddlID_City " :
            InitDropDown($(
' ddlID_County ' ));
            InitDropDown($(
' ddlID_Town ' ));
            
break ;
            
case   " ddlID_County " :
            InitDropDown($(
' ddlID_Town ' ));
            
break ;
    }
}
function  $(id){ return  document.getElementById(id);}

 

好,我们先看html代码:引入areacity.cs并拉几个下拉控件上去:

html代码
< html  xmlns ="http://www.w3.org/1999/xhtml" >
< head  runat ="server" >
    
< script  src ="js/AreaCity.js" ></ script >
</ head >
< body >
    
< form  id ="form1"  runat ="server" >
        省:
        
< asp:DropDownList  ID ="ddlID_Province"  runat ="server"  onchange ="GetSonData(this.value,'ddlID_City')" >
        
</ asp:DropDownList >< br  />
        市:
        
< asp:DropDownList  ID ="ddlID_City"  runat ="server"  onchange ="GetSonData(this.value,'ddlID_County')" >
        
< asp:ListItem  Text ="请选择" ></ asp:ListItem ></ asp:DropDownList >< br  />
        区:
        
< asp:DropDownList  ID ="ddlID_County"  runat ="server"  onchange ="GetSonData(this.value,'ddlID_Town')" >
        
< asp:ListItem  Text ="请选择" ></ asp:ListItem ></ asp:DropDownList >< br  />
        镇:
        
< asp:DropDownList  ID ="ddlID_Town"  runat ="server" >
        
< asp:ListItem  Text ="请选择" ></ asp:ListItem >
        
</ asp:DropDownList >
    
</ form >
</ body >
</ html >

 

现在看一下后台代码cs,这里不用数据库,临时用Dic字典组合充当数据:

 

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;
using  System.Collections.Generic;
using  System.Collections;
public   partial   class  ProvinceCity : PageBase
{
    
protected   void  Page_Load( object  sender, EventArgs e)
    {
        
if  ( ! IsPostBack)
        {

            RegisterAjax();
            
// 一开始绑定省
            ddlID_Province.DataSource  =  GetChild( 0 );
            ddlID_Province.DataValueField 
=   " key " ;
            ddlID_Province.DataTextField 
=   " value " ;
            ddlID_Province.DataBind();
            ddlID_Province.Items.Insert(
0 " 请选择 " );
        }
    }
    
public   override   void  RaiseCallbackEvent( string  eventArgument)
    {
        
if  (eventArgument.Contains( " , " ))
        {
            
string  parentID  =  eventArgument.Split( ' , ' )[ 0 ];
            
// 根据ID查数据库
            Dictionary < int string >  items  =  GetChild( int .Parse(parentID));
            
if  (items.Count  >   0 )
            {
                
foreach  (KeyValuePair < int string >  itemPair  in  items)
                {
                    ajaxCallBackResult 
+=  itemPair.Key  +   " , "   +  itemPair.Value  +   " | " ;
                }
                ajaxCallBackResult 
=  ajaxCallBackResult.TrimEnd( ' | ' );
            }

            ajaxCallBackResult 
+=   " & "   +  eventArgument.Split( ' , ' )[ 1 ]; // 附加回去下拉列表控件ID
        }
    }
    
#region  假设这里为数据库查询
    
protected  Dictionary < int string >  GetChild( int  parentID)
    {
        Dictionary
< int string >  items  =   new  Dictionary < int string > ();
        
switch  (parentID)
        {
            
case   0 :
                items.Add(
1 " 广东省 " );
                items.Add(
2 " 广西省 " );
                
break ;
            
case   1 :
                items.Add(
11 " 汕尾市 " );
                items.Add(
12 " 广州市 " );
                
break ;
            
case   2 :
                items.Add(
21 " 桂林市 " );
                items.Add(
22 " 南宁市 " );
                
break ;
            
case   11 :
                items.Add(
111 " 海丰县 " );
                
break ;
            
case   12 :
                items.Add(
121 " 天河区 " );
                
break ;

            
case   111 :
                items.Add(
1111 " 城东 " );
                items.Add(
1112 " 城西 " );
                
break ;

        }
        
return  items;
    }
    
#endregion
}

 

至此,下拉效果就出来了。

 

示例代码下载:ProvinceCity.rar

 

你可能感兴趣的:(Ajax 回忆录)