最近开始学习Ajax了,正好复习一下有些遗忘的JavaScript。因为Ajax涉及到其他的一些技术,例如JS, CSS, DHTML等等,刚好一起复习了。
Ajax以前听说过一点,不过从来没有碰过。听说功能很强大,因为它的无刷新技术。简单地说,就是在WEB应用中,在客户端和服务器端之间增加了一层来处理部分用户请求,用户就不用非得等服务器处理好再返回结果。这样可以减轻服务器的负担,同时能让用户感觉浏览速度的加快(因为不用等服务器的反应,也就是不用等整个页面的刷新)。其中,XMLHttpRequest是Ajax技术中的关键技术。它是自IE5.0引入的。具体的Ajax技术还得找专门的资料。我这个例子对于有点入门的朋友来说应该能看懂。开始看例子吧。
环境需求:jdk 5.0, Tomcat5.5, Eclipse3.2(就这么多,比框架的少多了,哈哈)。注意,我的浏览器是6.0的。因为浏览器版本会稍微影响代码,后面会说明的。
首先编写一个test.jsp:
<%@ page language="java" contentType="text/html; charset=ISO-8859-1"
pageEncoding="ISO-8859-1"%>
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">
<html>
<head>
<meta. http-equiv="Content-Type" content="text/html; charset=ISO-8859-1">
<title>Test Page</title>
<script>
var xmlHttp = new ActiveXObject("Microsoft.XMLHTTP");
function checkUsername(){
var username = document.getElementById("username").value;
var queryString = "username=" + username;
var url = "CheckUsername";
xmlHttp.open("POST", url, true);
xmlHttp.onreadystatechange = handleChange;
xmlHttp.setRequestHeader("Content-type", "application/x-www-form-urlencoded;");
xmlHttp.send(queryString);
}
function checkPassword(){
var password = document.getElementById("password").value;
var queryString = "password=" + password;
var url = "CheckPassword";
xmlHttp.open("POST", url, true);
xmlHttp.onreadystatechange = handleChange;
xmlHttp.setRequestHeader("Content-type", "application/x-www-form-urlencoded;");
xmlHttp.send(queryString);
}
function handleChange(){
if(xmlHttp.readyState == 4) {
if(xmlHttp.status == 200) {
var valid = xmlHttp.responseXML.getElementsByTagName("valid")[0].firstChild.data;
var message = xmlHttp.responseXML.getElementsByTagName("message")[0].firstChild.data;
var resultName = xmlHttp.responseXML.getElementsByTagName("divid")[0].firstChild.data;
parseResult(message, valid, resultName);
}
}
}
function parseResult(message, valid, resultName){
var result = document.getElementById(resultName);
var fontColor = "green";
if(valid == "false") {
fontColor = "red";
}
result.innerHTML = "<font color=" + fontColor + ">" + message + "</font>";
}
</script>
</head>
<body>
<center>
<form. action="#">
<table>
<tr>
<td>Username*<input type="text" id="username" nblur="checkUsername();" /></td>
<td><div id="usernameResponse"></div></td>
</tr>
<tr>
<td>Password*<input type="text" id="password" nblur="checkPassword();" /></td>
<td><div id="passwordResponse"></div></td>
</tr>
</table>
</form><br/>
</center>
</body>
</html>
这个例子就是做一个简单的判断,即Username和Password不能为空。
第一要做的是,创建一个XMLHttpRequest对象。因为浏览器不同,创建的语句也不同。我这里用的是var xmlHttp = new ActiveXObject("Microsoft.XMLHTTP");还有一种就是var xmlHttp = new XMLHttpRequest()。
然后,在checkUsername函数中,首先我们要得到username的值,于是调用了document.getElementById这个函数。然后写一个queryString = "username=" + username。这和我们平时见到的url带的参数相同,是名/值对,如果有多个参数就用&来连接。接着就是需要处理这个请求的servlet名字,这里是CheckUsername。然后调用open方法,传参数的时候用的是POST,这就要求我们在用send()函数的时候需要将参数也就是queryString传过去。当然,之前我们还要设置,如果请求状态有变化就交由handleChange这个函数来处理。这就要用到xmlHttp的onreadystatechange属性了。设置后,只要请求状态有改变,就会调用handleChange函数。
我们接下来先看CheckUsername.java:
package src;
import java.io.IOException;
import java.io.PrintWriter;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
/**
* Servlet implementation class for Servlet: CheckUsername
*
*/
public class CheckUsername extends javax.servlet.http.HttpServlet implements javax.servlet.Servlet {
/* (non-Java-doc)
* @see javax.servlet.http.HttpServlet#HttpServlet()
*/
public CheckUsername() {
super();
}
/* (non-Java-doc)
* @see javax.servlet.http.HttpServlet#doGet(HttpServletRequest request, HttpServletResponse response)
*/
protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
// TODO Auto-generated method stub
doPost(request, response);
}
/* (non-Java-doc)
* @see javax.servlet.http.HttpServlet#doPost(HttpServletRequest request, HttpServletResponse response)
*/
protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
// TODO Auto-generated method stub
response.setContentType("text/xml");
response.setHeader("Cache-Control", "no-cache");
String resultName = "usernameResponse";
String isValid = "true";
String message = "Passed";
String username = request.getParameter("username").trim();
if(username == null || username.length() == 0 || username.equals("")){
isValid = "false";
message = "Can't be null";
}
PrintWriter ut = response.getWriter();
out.println("<result>");
out.println("<message>" + message + "</message>");
out.println("<valid>" + isValid +"</valid>");
out.println("<divid>" + resultName + "</divid>");
out.println("</result>");
out.close();
}
}
因为我们之前用的是POST方法来传递参数的,所以,在这个servlet中,我们主要写doPost方法。这里面,isValid是用来表示需要输入的是否为空,message则是验证情况的提示信息,而resultName就是提示信息在test.jsp中,<div />标签的id。因为username和password是两个不同的输入要求,所以要在两个不同的地方显示提示信息。这里,username通过request.getParameter方法得到,然后判断是否为空。如果不为空,显示绿色的Passed,否则显示红色的Can't be null。然后通过写一个XML文件来将结果传回去。
特别注意!最后写XML的时候要注意括号是否写了,因为这里少写一个不会报错,但是会导致无法读取这个xml文件。我犯过这个错误,找了好久才发现少写了一个“>”...
然后我们回到test.jsp看handleChange这个函数。两个if是用来判断请求的状态的,当请求完成后就执行里面的代码。具体的请求状态属性可以参考Ajax的资料。这里面,因为servlet返回了一个xml文件,因此,我们通过xmlHttp的responseXML属性来获取其中的内容。xml文件可以是用DOM的方法,所以比较方便。这里我们就获取了message, valid和resultName三个参数。同时调用parseResult()函数。
parseResult()函数就是用来显示相应的信息的。通过resultName,先得到对应resultName的div元素,因为信息要显示在这里。然后再判断valid是true还是false,根据这个设置信息的颜色。接着就是在div里面显示信息了。
checkPassword函数可以完全参考checkUsername函数。
最后,在<body>里面,就一个form和两个input以及相应的div元素。id一定要设置正确,否则找不到相应的请求参数。在input里面我通过onblur事件来触发相应的函数,也可以改为onchange。好了,例子完成,可以试试效果了。
特别注意:这个博客保存的时候好像有点问题,test.jsp里面,<form. action>的form后面老是有一个点;第二个程序里面的PrintWriter out 这里,保存后总是变成ut。改了几次都没改回来,大家注意下。