大家使用百度谷歌的时候都会有输入自动提示的功能,心血来潮自己用Ajax模拟了一个,和大家分享分享。
下面让我们先看下效果:
输入自动提示
键盘上下移动选取
鼠标选取同样支持
支持中文匹配
JSP前台:
<%@ page language="java" import="java.util.*" pageEncoding="UTF-8"%>
<%
String path = request.getContextPath();
String basePath = request.getScheme() + "://"
+ request.getServerName() + ":" + request.getServerPort()
+ path + "/";
%>
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">
<html>
<head>
<base href="<%=basePath%>">
<title>文本自动提示补全功能</title>
<meta http-equiv="pragma" content="no-cache">
<meta http-equiv="cache-control" content="no-cache">
<meta http-equiv="expires" content="0">
<meta http-equiv="keywords" content="keyword1,keyword2,keyword3">
<meta http-equiv="description" content="This is my page">
<link rel="stylesheet" type="text/css"
href="<%=basePath%>css/styles.css">
<script type="text/javascript" language="javascript" charset="gb2312"
src="<%=basePath%>js/jquery.js">
</script>
<script type="text/javascript" language="javascript" charset="gb2312"
src="<%=basePath%>js/autopromot.js">
</script>
</head>
<body>
自动提示:
<!-- autocomplete防止一些浏览器的自动提示完成功能 -->
<input type="text" name="content" id="content" autocomplete="off" />
<input type="button" id="button" name="button" value="提交" οnclick="" />
<div id="auto">
</div>
<br />
<p>
药家鑫案死者丈夫称坚持死刑并非全为以命抵命
</p>
</body>
</html>
核心AJAX:
//高亮索引 var highlightindex=-1; //设置文本框的内容 function setContent(con,index){ var context=con.eq(index).text(); $("#content").val(context); } //设置背景颜色 function setBkColor(con,index,color){ con.eq(index).css("background-color",color); } $(document).ready( function(){ //获得输入框节点 var inputItem=$("#content"); var inputOffset=inputItem.offset(); var autonode=$("#auto"); //设置提示框隐藏 autonode.hide().css("border","1px black solid").css("position","absolute") .css("top",inputOffset.top+inputItem.height()+5+"px") .css("left",inputOffset.left+"px").width(inputItem.width()+"px"); //当键盘抬起时触发事件执行访问服务器业务 $("#content").keyup( function(event){ var myevent=event||window.event; var mykeyCode=myevent.keyCode; //字母,退格,删除,空格 if(mykeyCode>=65&&mykeyCode<=90||mykeyCode==8||mykeyCode==46||mykeyCode==32){ //清除上一次的内容 autonode.html(" "); //获得文本框内容 var word=$("#content").val(); var timeDelay; if(word!=""){ //取消上次提交 window.clearTimeout(timeDelay); //延迟提交,这边设置的为400ms timeDelay=window.setTimeout( //将文本框的内容发到服务器 $.post("Autocomplete",{wordtext:encodeURI(word)}, function(data){ //将返回数据转换为JQuery对象 var jqObj=$(data); //找到所有的word节点 var wordNodes=jqObj.find("word"); wordNodes.each( function(i){ //获得返回的单词内容 var wordNode=$(this); var newNode=$("<div>").html(wordNode.text()).attr("id",i).addClass("pro"); //将返回内容附加到页面 newNode.appendTo(autonode); //处理鼠标事件 var con=$("#auto").children("div"); //鼠标经过 newNode.mouseover( function(){ if(highlightindex!=-1){ setBkColor(con,highlightindex,"white"); } highlightindex=$(this).attr("id"); $(this).css("background-color","#ADD8E6"); setContent(con,highlightindex); } ); //鼠标离开 newNode.mouseout( function(){ $(this).css("background-color","white"); } ); //鼠标点击 newNode.click( function(){ setContent(con,highlightindex); highlightindex=-1; autonode.hide(); } ); } ); //each //当返回的数据长度大于0才显示 if(wordNodes.length>0){ autonode.show(); }else{ autonode.hide(); } } ,"xml") //post ,400); //settimeout }else{ autonode.hide(); highlightindex=-1; } }else{ //获得返回框中的值 var rvalue=$("#auto").children("div"); //上下键 if(mykeyCode==38||mykeyCode==40){ //向上 if(mykeyCode==38){ if(highlightindex!=-1){ setBkColor(rvalue,highlightindex,"white"); highlightindex--; } if(highlightindex==-1){ setBkColor(rvalue,highlightindex,"white"); highlightindex=rvalue.length-1; } setBkColor(rvalue,highlightindex,"#ADD8E6"); setContent(rvalue,highlightindex); } //向下 if(mykeyCode==40){ if(highlightindex!=rvalue.length){ setBkColor(rvalue,highlightindex,"white"); highlightindex++; } if(highlightindex==rvalue.length){ setBkColor(rvalue,highlightindex,"white"); highlightindex=0; } setBkColor(rvalue,highlightindex,"#ADD8E6"); setContent(rvalue,highlightindex); } } //回车键 if(mykeyCode==13){ if(highlightindex!=-1){ setContent(rvalue,highlightindex); highlightindex=-1; autonode.hide(); }else{ alert($("#content").val()); } } } } );//键盘抬起 //当文本框失去焦点时的做法 inputItem.focusout( function(){ //隐藏提示框 autonode.hide(); } ); } );//reday
后台Servlet:
/**
* @author :LYL
*@date:2011-4-21,下午11:15:29
*/
package com.lyl.service;
import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.io.PrintWriter;
import java.net.URLDecoder;
import java.net.URLEncoder;
import java.util.ArrayList;
import java.util.Iterator;
import java.util.List;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.xml.parsers.DocumentBuilder;
import javax.xml.parsers.DocumentBuilderFactory;
import javax.xml.parsers.ParserConfigurationException;
import javax.xml.transform.OutputKeys;
import javax.xml.transform.Transformer;
import javax.xml.transform.TransformerConfigurationException;
import javax.xml.transform.TransformerException;
import javax.xml.transform.TransformerFactory;
import javax.xml.transform.dom.DOMSource;
import javax.xml.transform.stream.StreamResult;
import org.w3c.dom.Document;
import org.w3c.dom.Element;
import org.w3c.dom.Node;
import org.w3c.dom.NodeList;
import org.w3c.dom.Text;
import org.xml.sax.SAXException;
public class Autocomplete extends HttpServlet {
public void doPost(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
response.setContentType("text/xml");
response.setCharacterEncoding("utf-8");
PrintWriter out = response.getWriter();
String path = request.getContextPath();
String basePath = request.getScheme()+"://"+request.getServerName()+":"+request.getServerPort()+path+"/";
String userword=URLDecoder.decode(request.getParameter("wordtext"),"utf-8");
String datas=getXml(userword,basePath);
out.println(datas);
out.flush();
out.close();
}
/**
* 获得匹配的字母,返回List类型
* @return
*/
private static List<String> getResultList(String userword,String path){
DocumentBuilderFactory dbf=DocumentBuilderFactory.newInstance();
List<String> resultlist=new ArrayList<String>();
try {
DocumentBuilder db=dbf.newDocumentBuilder();
Document document=db.parse(path+"/Words.xml");
NodeList words=document.getElementsByTagName("word");
int length=words.getLength();
for(int i=0;i<length;i++){
Node node=words.item(i);
//获得字母
String result=node.getFirstChild().getNodeValue();
//这边进行一些逻辑处理,字符串的匹配,(后续工作)
if(result.contains(userword)){
resultlist.add(result);
}
}
} catch (ParserConfigurationException e) {
e.printStackTrace();
} catch (SAXException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
return resultlist;
}
/**
* 返回结果的XML字符串
* @return
*/
private static String getXml(String userword,String path){
List<String> list=getResultList(userword,path);
Iterator<String> iterator=list.iterator();
DocumentBuilderFactory dbf=DocumentBuilderFactory.newInstance();
DocumentBuilder db=null;
Document document=null;
try {
db=dbf.newDocumentBuilder();
document=db.newDocument();
//创建根节点
Element root=document.createElement("words");
//根节点添加到dom树上
document.appendChild(root);
while(iterator.hasNext()){
String content=iterator.next();
//创建文本节点
Text word=document.createTextNode(content);
//创建word节点
Element child=document.createElement("word");
child.appendChild(word);
root.appendChild(child);
}
} catch (ParserConfigurationException e) {
e.printStackTrace();
}
return doc2Xml(document);
}
private static String doc2Xml(Document document){
//创建一个DOM转换器
TransformerFactory transformerFactory = TransformerFactory.newInstance();
ByteArrayOutputStream outputStream=null;
try {
Transformer transformer = transformerFactory.newTransformer();
transformer.setOutputProperty(OutputKeys.ENCODING,"GB2312");
transformer.setOutputProperty(OutputKeys.INDENT,"yes");
outputStream = new ByteArrayOutputStream();
transformer.transform(new DOMSource(document), new StreamResult(outputStream));
} catch (TransformerConfigurationException e) {
e.printStackTrace();
} catch (TransformerException e) {
e.printStackTrace();
}
return outputStream.toString();
}
}
CSS:
@CHARSET "UTF-8";
* {
font-size: 18px;
}
#content {
width: 300px;
height: 30px;
padding: 0px auto;
}
#button {
width: 100px;
height: 30px;
}
.pro {
cursor: default;
}
#auto {
background-color: white;
}
好了,大家有什么建议或疑问可以留言哦。
源码见附件。