上一篇:Asp.net技巧:创建自定义验证控件(1)
\n开发环境VS2008+SQL2005
\n本篇将写一个比较复杂的自定义控件,AjaxValidator(AJAX自定义验证控件)。AjaxValidator控件用于创建一个服务器端的自定义验证函数。AjaxValidator可以在浏览器调用自定义的验证方法(即客户端脚本直接调用服务器端方法)。
\nAjaxValidator控件使用AJAX从客户端调用服务器端验证方法,使用AJAX优势在于用户不用显示地回传服务器端。
\n大家在创建一个注册表单,并且需要验证用户名字段,以确认用户输入的用户名在数据库中并不存在。本篇就利用AjaxValidator写了一个这样的DEMO。AjaxValidator控件可以在客户端调用服务端的验证方法来检查用户名在数据库中是否唯一。
\nAjaxValidator类的代码如下
\nCode
\n<!–
Code highlighting produced by Actipro CodeHighlighter (freeware)
\nhttp://www.CodeHighlighter.com/
\n–>using System;
\nusing System.Collections.Generic;
\nusing System.Linq;
\nusing System.Web;
using System.Web.UI;
\nusing System.Web.UI.WebControls;
\n//引用上述2个命名空间
namespace validatorControls
\n{
\n/// <summary>
\n///AjaxValidator 的摘要说明
\n///可以让你自定义对客户端和服务端的验证
\n///by mFrog
\n///2008 12,4
\n/// </summary>
public class AjaxValidator : BaseValidator, ICallbackEventHandler
\n{
\npublic AjaxValidator()
\n{
\n//
\n//TOD 在此处添加构造函数逻辑
\n//
\n}
//定一个ServerValidateEventHandler委托的事件
\npublic event ServerValidateEventHandler ServerValidate;
string _controlToValidateValue;
\nprotected override void OnPreRender(EventArgs e)
\n{
\nString evenRef = Page.ClientScript.GetCallbackEventReference(this, “”, “”, “”);
//注册要导入的脚本文件
\nString includeScript = Page.ResolveClientUrl(“~/ClientScripts/AjaxValidator.js”);
\nPage.ClientScript.RegisterClientScriptInclude(“AjaxValidator”, includeScript);
//注册启动脚本
\nString startupScript = String.Format(“document.getElementById(‘{0}’).evaluationfunction = ‘AjaxValidatorEvaluateIsValid’;”, this.ClientID);
\nPage.ClientScript.RegisterStartupScript(this.GetType(), “AjaxValidator”, startupScript, true);
base.OnPreRender(e);
\n}
/// <summary>
\n///浏览器对AJAX技术的支持
\n/// </summary>
\nprotected override bool DetermineRenderUplevel()
\n{
\nreturn Context.Request.Browser.SupportsCallback;
\n}
/// <summary>
\n/// 客户端ajax调用服务器端方法
\n/// </summary>
\n/// <returns></returns>
\npublic string GetCallbackResult()
\n{
\nreturn ExecuteValidationFunction(_controlToValidateValue).ToString();
\n}
/// <summary>
\n/// 回调返回结果到客户端
\n/// </summary>
\n/// <param name=”eventArgument”></param>
\npublic void RaiseCallbackEvent(string eventArgument)
\n{
\n_controlToValidateValue = eventArgument;
\n}
/// <summary>
\n/// 服务器端的方法验证
\n/// </summary>
\n/// <returns></returns>
\nprotected override bool EvaluateIsValid()
\n{
\nString controlToValidateValue = this.GetControlValidationValue(this.ControlToValidate);
\nreturn ExecuteValidationFunction(controlToValidateValue);
\n}
/// <summary>
\n/// 在服务器端和客户端都执行验证
\n/// </summary>
\n/// <param name=”controlToValidateValue”></param>
\n/// <returns></returns>
\nprivate bool ExecuteValidationFunction(String controlToValidateValue)
\n{
\nServerValidateEventArgs args = new ServerValidateEventArgs(controlToValidateValue,this.IsValid);
\nif (ServerValidate != null)
\n{
\nServerValidate(this,args);
\n}
\nreturn args.IsValid;
\n}
\n}
\n}
AjaxValidato控件继承BaseValidator,并实现了ICallbackEventHandler接口。ICallbackEventHandler接口定义了两个方法,当客户端发出AJAX请求时,这两个方法在服务器端调用。
\n在OnPreRender()方法中,注册了一个内嵌JAVASCRIPT文件和启动脚本。内嵌JAVASCRIPT文件包含了AjaxValidato控件在客户端验证表单字段时调用的客户端函数。启动脚本把客户端的AjaxValidatorEvaluateIsValid()方法和AjaxValidato控件关联起来。执行验证时,客户端验证框架自动调用这个JAVASCRIPT方法。
\n下面是AjaxValidato控件使用的JAVASCRIPT方法
\n
\n//AJAX请求执行回服务器
\nfunction AjaxValidatorEvaluateIsValid(val) {
\nvar value = ValidatorGetValue(val.controltovalidate);
\nWebForm_DoCallback(val.id, value, AjaxValidatorResult, val, AjaxValidatorError, true);
\nreturn true;
\n}
//从服务器返回结果
\nfunction AjaxValidatorResult(returnValue, context) {
\nif (returnValue == ‘True’)
\n{
\ncontext.isvalid = true;
\n}
\nelse
\n{
\ncontext.isvalid = false;
\n}
\nValidatorUpdateDisplay(context);
\n}
//显示错误
\nfunction AjaxValidatorError(message)
\n{
\nalert(‘Error:’+message);
\n}
\nJAVASCRIPT方法AjaxValidatorEvaluateIsValid()通过调用WebForm_DoCallback()方法初始化一个AJAX调用。该方法调用AjaxValidator控件关联的服务器端验证方法。当AJAX调用完成时,再调用AjaxValidatorResult()方法。这个方法在客户端更新验证控件的显示。
\n页面代码:
\nCode
\n<!–\n
Code highlighting produced by Actipro CodeHighlighter (freeware)
\nhttp://www.CodeHighlighter.com/
\n–><%@ Page Language=”C#” AutoEventWireup=”true” CodeFile=”Default.aspx.cs” Inherits=”_Default” %>
\n<%@ Register TagPrefix=”mFrog” Namespace=”validatorControls” %>
\n<!DOCTYPE html PUBLIC “-//W3C//DTD XHTML 1.0 Transitional//EN” “http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd”>
\n<html xmlns=”http://www.w3.org/1999/xhtml”>
\n<head runat=”server”>
\n<title>AjaxValidatorDEMO</title>
\n</head>
\n<body>
\n<form id=”form1″ runat=”server”>
\n<div>
<asp:Label ID=”lblUserName” runat=”server” AssociatedControlID=”txtUserName”>用户名</asp:Label>
\n<asp:TextBox ID=”txtUserName” runat=”server”></asp:TextBox>
\n<mFrog:AjaxValidator ID=”avUserName” ControlToValidate=”txtUserName”
\nrunat=”server” Text=”此用户名已经存在”
\nonservervalidate=”avUserName_ServerValidate” Display=”Dynamic”></mFrog:AjaxValidator>
\n<asp:RequiredFieldValidator ID=”rfvUserName” runat=”server”
\nControlToValidate=”txtUserName” Display=”Dynamic” ErrorMessage=”用户名不能为空”></asp:RequiredFieldValidator>
\n<br />
\n<br />
\n<asp:Label ID=”Label1″ runat=”server” Text=”密码”></asp:Label>
\n<asp:TextBox ID=”txtUserPwd” runat=”server”></asp:TextBox>
\n<asp:RequiredFieldValidator ID=”rfvUserPwd” runat=”server”
\nControlToValidate=”txtUserPwd” ErrorMessage=”密码不能为空”></asp:RequiredFieldValidator>
\n<br />
\n<br />
\n<asp:Button ID=”btnSubmit” runat=”server” Text=”提交” onclick=”btnSubmit_Click” />
\n</div>
\n</form>
\n</body>
\n</html>
\n后台CS代码:
\nCode
\n<!–
Code highlighting produced by Actipro CodeHighlighter (freeware)
\nhttp://www.CodeHighlighter.com/
\n–>using System;
\nusing System.Collections.Generic;
\nusing System.Linq;
\nusing System.Web;
\nusing System.Web.UI;
\nusing System.Web.UI.WebControls;
\nusing System.Data.SqlClient;
\nusing System.Web.Configuration;
public partial class _Default : System.Web.UI.Page
\n{
\n/// <summary>
\n/// 返回true时,用户名已存在
\n/// </summary>
\n/// <param name=”username”></param>
\n/// <returns></returns>
\nprivate bool UserNameExists(string username)
\n{
\nstring conString= WebConfigurationManager.ConnectionStrings["ConnectionString"].ConnectionString;
\nstring selectString=”select count(*) from User_Info where UserName=@UserName”;
\nSqlConnection conn = new SqlConnection(conString);
\nSqlCommand cmd = new SqlCommand(selectString, conn);
\ncmd.Parameters.AddWithValue(“@UserName”, username);
\nbool result = false;
\nusing (conn)
\n{
\nconn.Open();
\nint count = (int)cmd.ExecuteScalar();
\nif (count > 0)
\n{
\nresult = true;
\n}
\n}
return result;
\n}
protected void Page_Load(object sender, EventArgs e)
\n{
}
\nprotected void avUserName_ServerValidate(object source, ServerValidateEventArgs args)
\n{
\nif (UserNameExists(args.Value))
\n{
\nargs.IsValid = false;
\n}
\nelse
\n{
\nargs.IsValid = true;
\n}
\n}
/// <summary>
\n/// 插入数据到数据库中
\n/// </summary>
\n/// <param name=”sender”></param>
\n/// <param name=”e”></param>
\nprotected void btnSubmit_Click(object sender, EventArgs e)
\n{
\nstring conString = WebConfigurationManager.ConnectionStrings["ConnectionString"].ConnectionString;
\nstring insertString = “insert into User_Info(UserName,UserPwd) values(@UserName,@UserPwd)”;
\nSqlConnection conn = new SqlConnection(conString);
\nSqlCommand cmd = new SqlCommand(insertString,conn);
\ncmd.Parameters.AddWithValue(“@UserName”,txtUserName.Text);
\ncmd.Parameters.AddWithValue(“@UserPwd”, txtUserPwd.Text);
\nusing (conn)
\n{
\nconn.Open();
\ncmd.ExecuteNonQuery();
\n}
\ntxtUserName.Text = string.Empty;
\ntxtUserPwd.Text = string.Empty;
\n}
\n}
这个页面演示了如何使用AjaxValidator控件。页面处理AjaxValidator控件的ServerValidate事件以后将一个自定义验证方法关联到控件上。
\n页面输入用户名和密码以后,提交表单这些字段的值就会插入到数据库User_Info中。
\n在后台代码,验证方法检查用户名在数据库中是否已经存在,如果输入的用户名已经存在,就会显示一个验证错误。提交表单返回到服务端之前,这个信息就会显示在浏览器中。
\nAjaxValidator可以关联任何服务器端验证方法。
\n数据库建表语句
Code
\n<!–
Code highlighting produced by Actipro CodeHighlighter (freeware)
\nhttp://www.CodeHighlighter.com/
\n–>SET ANSI_NULLS ON
\nGO
\nSET QUOTED_IDENTIFIER ON
\nGO
\nSET ANSI_PADDING ON
\nGO
\nCREATE TABLE [dbo].[User_Info](
\n[id] [int] IDENTITY(1,1) NOT NULL,
\n[UserName] [varchar](50) NOT NULL,
\n[UserPwd] [varchar](50) NOT NULL
\n) ON [PRIMARY]
GO
\nSET ANSI_PADDING OFF
\n效果截图: