ajax java 实现自动完成功能


Posted in Javascript onDecember 19, 2012

百度建议给了我们极大的方便,就像我们跟人说话的时候,你点头他知尾,不用多费唇舌,这样我们与之相处久轻松愉悦。

都知道百度建议是用ajax做的,想要做的快速稳定,可复制可移植就不容易了。网上找了半天,好多都是asp或者php的,还有使用jquery的,但说明性文档太少,花时间研究还不如自己来写。根据一个pdf文档提供的资料,用了小半天时间,终于实现了。在此与大家分享。
原理流程图如下:
ajax java 实现自动完成功能 
流程图很明白了,没什么要说的,以下帖代码。
Javascript代码:

var xmlHttpRequest; 
var table; 
var tbody; 
var div; 
var input; 
var curIndex; 
var size; 
var r_userId; 
function createXMLHttpRequest(){ 
if(window.ActiveXObject){ 
xmlHttpRequest = new ActiveXObject("Microsoft.XMLHTTP"); 
}else if(window.XMLHttpRequest){ 
xmlHttpRequest = new XMLHttpRequest(); 
} 
} 
//发送请求 
function findNames(){ 
if(event.keyCode==38||event.keyCode==40){ 
}else{ 
if(input.value.length>0){ 
createXMLHttpRequest(); 
var url = encodeURI(encodeURI("/jforum.html?module=posts&action=findDept&names="+input.value)); 
xmlHttpRequest.open("GET",url,true); 
xmlHttpRequest.onreadystatechange=processMatchResponse; 
xmlHttpRequest.send(null); 
}else{ 
clearNames(); 
} 
} } 
function processMatchResponse(){ 
if(xmlHttpRequest.readyState==4){ 
if(xmlHttpRequest.status==200){ 
//alert(xmlHttpRequest.status); 
//var id = xmlHttpRequest.responseXML.getElementsByTagName("id"); 
var dept = xmlHttpRequest.responseXML.getElementsByTagName("dept"); 
var id = xmlHttpRequest.responseXML.getElementsByTagName("id"); 
setNames(dept,id); 
}else{ 
window.alert("您所请求的页面有异常!"); 
} 
} 
} 
function setNames(depts,ids){ 
clearNames(); 
size = depts.length; 
if(size>0){ 
div.style.visibility = "visible"; 
var row,col1,col2,span; 
for(var i = 0;i < size;i++){ 
row = document.createElement("tr"); 
col1 = document.createElement("td"); 
col1.innerText = depts[i].firstChild.data; 
col2 = document.createElement("td"); 
col2.setAttribute("align","right"); 
col2.setAttribute("id","col2"); 
col2.setAttribute("width","5%"); 
span = document.createElement("span"); 
span.innerText = ids[i].firstChild.data; 
span.style.display = "none"; 
col2.appendChild(span); 

row.appendChild(col1); 
row.appendChild(col2); 
row.onmouseout = function(){ 
this.className = 'mouseOut'; 
} 
row.onmouseover = function(){ 
clearSelected(); 
this.className = 'mouseOver'; 
curIndex = this.rowIndex; 
} 
row.onclick = function(){ 
input.value = this.cells[0].innerText; 
r_userId.value = table.rows[curIndex].cells[1].innerText; 
clearNames(); 
}; 
tbody.appendChild(row); 
} 
row = document.createElement("tr"); 
col2 = document.createElement("td"); 
col1 = document.createElement("td"); 
col2.setAttribute("align","right"); 
link = document.createElement("a"); 
link.href = "javascript:clearNames();"; 
link.innerHTML = "关闭"; 
col1.appendChild(link); 
row.appendChild(col1); 
row.appendChild(col2); 
tbody.appendChild(row); 
} 
} 
function setPosition(){ 
input = document.getElementById("names"); 
r_userId = document.getElementById("r_userId"); 
table = document.getElementById("table"); 
div = document.getElementById("div"); 
tbody = document.getElementById("tbody"); 
div.style.width = input.offsetWidth-2; 
div.style.border = "gray 1px solid"; 
div.style.left = getLeft(input); 
div.style.top = getTop(input)+input.offsetHeight+6; 
curIndex = -1; 
input.focus();//div.style.left+","+div.style.top 
} 
function clearNames(){ 
var ind = tbody.childNodes.length; 
for(i=ind-1;i>=0;i--){ 
tbody.removeChild(tbody.childNodes[i]); 
} 
div.style.visibility="hidden"; 
curIndex = -1; 
} 
function clearSelected(){ 
var ind = tbody.childNodes.length; 
for(var i = ind-1;i>=0;i--){ 
tbody.childNodes[i].className = "mouseOut"; 
} 
} 
function keyDown(){ 
if(div.style.visibility=="visible"){ 
if(event.keyCode ==38){ 
if(curIndex>=0){ 
table.rows[curIndex].className='mouseOut'; 
curIndex = curIndex-1; 
if(curIndex>=0){ 
table.rows[curIndex].className = 'mouseOver'; 
input.value = table.rows[curIndex].cells[0].innerText; 
r_userId.value = table.rows[curIndex].cells[1].innerText; 
} 
} 
} 
if(event.keyCode==40){ 
if(curIndex<size-1){ 
if(curIndex>=0){ 
table.rows[curIndex].className = 'mouseOut'; 
} 
curIndex = curIndex+1; 
table.rows[curIndex].className = 'mouseOver'; 
input.value = table.rows[curIndex].cells[0].innerText; 
r_userId.value = table.rows[curIndex].cells[1].innerText; 
}else{ 
table.rows[curIndex].className = 'mouseOut'; 
curIndex = -1; 
} 
} 
} 
} 
//获取元素的纵坐标 
function getTop(e){ 
var offset=e.offsetTop; 
if(e.offsetParent!=null) offset+=getTop(e.offsetParent); 
return offset; 
} 
//获取元素的横坐标 
function getLeft(e){ 
var offset=e.offsetLeft; 
if(e.offsetParent!=null) offset+=getLeft(e.offsetParent); 
return offset; 
}

代码太多,有点乱,没使用jquery,但更能显示作者的功底。以下分点阐述:
1,setPosition()是用来初始化全局所需要的各个变量,所以在页面加载的时候就要先调用喽,比如在body的onload方法,或者其他方式都可以。
2,findNames()是操作ajax的方法,熟悉ajax的人都可以看明白,里面最主要的是要对参数进行二次编码encodeURI(),相应的在后台要进行解码。
3,processMatchResponse()是回调函数,用来处理从后台返回的数据,这里交给了setNames()来处理。
4,setNames中采用table方式显示提示的内容。这里更多的是JS和node方面的知识。
5,getTop和getLeft方法是获得文本框的绝对位置,相对于浏览器左上角的。
后台java代码如下:
public void findDept() throws IOException{ 
String partDeptName = this.request.getParameter("names"); 
partDeptName = java.net.URLDecoder.decode(partDeptName, "UTF-8"); 
Map<String,String> userMap = DataAccessDriver.getInstance().newUserDAO().getDeptByPart("%" + partDeptName + "%"); this.response.setContentType("text/xml;charset=UTF-8"); 
this.response.setHeader("Cache-Control", "no-cache"); 

ServletOutputStream pw = this.response.getOutputStream(); 
OutputStreamWriter out = new OutputStreamWriter(pw,"UTF-8"); 
out.write("<res>"); 
Iterator<Map.Entry<String, String>> it = userMap.entrySet().iterator(); 
while(it.hasNext()){ 
Map.Entry<String, String> entry=(Map.Entry<String,String>)it.next(); 
out.write("<id>"+entry.getKey()+"</id>"); 
out.write("<dept>"+entry.getValue()+"</dept>"); 
} 
out.write("</res>"); 
out.flush(); 
out.close(); 
}

要点
1,注意对参数进行解码。
2,查询时根据情况进行模糊匹配。
3,返回数据这里采用了xml方式,也可以采用json方式。
4,返回的方式这里采用了
ServletOutputStream pw = this.response.getOutputStream(); 
OutputStreamWriter out = new OutputStreamWriter(pw,"UTF-8");

这样的流是受本系统框架的限制,如果使用单纯的servlet,可以采用PrintWriter out = response.getWriter();当然out的方法是println(),也可以根据自己框架的情况灵活改变。
Javascript 相关文章推荐
js 变量类型转换常用函数与代码[比较全]
Dec 01 Javascript
javascript时间自动刷新实现原理与步骤
Jan 06 Javascript
点击隐藏页面左栏或右栏实现js代码
Apr 01 Javascript
JS保留两位小数 四舍五入函数的小例子
Nov 20 Javascript
JavaScript插件化开发教程(六)
Feb 01 Javascript
JavaScript 对象深入学习总结(经典)
Sep 29 Javascript
微信小程序 二维码canvas绘制实例详解
Jan 06 Javascript
jquery ajaxfileupload异步上传插件使用详解
Feb 08 Javascript
基于JQuery和原生JavaScript实现网页定位导航特效
Apr 03 jQuery
JS实现DOM节点插入操作之子节点与兄弟节点插入操作示例
Jul 30 Javascript
node.js express框架实现文件上传与下载功能实例详解
Oct 15 Javascript
JavaScript对象属性操作实例解析
Feb 04 Javascript
JavaScript字符串String和Array操作的有趣方法
Dec 18 #Javascript
学习js在线html(富文本,所见即所得)编辑器
Dec 18 #Javascript
javascript jscroll模拟html元素滚动条
Dec 18 #Javascript
Android中资源文件(非代码部分)的使用概览
Dec 18 #Javascript
js获取单选框或复选框值及操作
Dec 18 #Javascript
JQuery触发radio或checkbox的change事件
Dec 18 #Javascript
Jquery为单选框checkbox绑定单击click事件
Dec 18 #Javascript
You might like
基于php(Thinkphp)+jquery 实现ajax多选反选不选删除数据功能
2017/02/24 PHP
Yii2实现自定义独立验证器的方法
2017/05/05 PHP
PHP基于正则批量替换Img中src内容实现获取缩略图的功能示例
2017/06/07 PHP
php-beanstalkd消息队列类实例分享
2017/07/19 PHP
ASP中用Join和Array,可以加快字符连接速度的代码
2007/08/22 Javascript
JQuery中上下文选择器实现方法
2015/05/18 Javascript
用js控件div的滚动条,让它在内容更新时自动滚到底部的实现方法
2016/10/27 Javascript
文件上传的几个示例分享【推荐】
2016/12/16 Javascript
详解React 在服务端渲染的实现
2017/11/16 Javascript
GOJS+VUE实现流程图效果
2018/12/01 Javascript
JQuery获取元素尺寸、位置及页面滚动事件应用示例
2019/05/14 jQuery
vue+elementui 对话框取消 表单验证重置示例
2019/10/29 Javascript
详解Node.js使用token进行认证的简单示例
2020/05/25 Javascript
让Vue响应Map或Set的变化操作
2020/11/11 Javascript
Python格式化css文件的方法
2015/03/10 Python
Python实现telnet服务器的方法
2015/07/10 Python
pandas 取出表中一列数据所有的值并转换为array类型的方法
2018/04/11 Python
python实现基于信息增益的决策树归纳
2018/12/18 Python
python 如何去除字符串头尾的多余符号
2019/11/19 Python
python装饰器原理与用法深入详解
2019/12/19 Python
Python能做什么
2020/06/02 Python
Elasticsearch py客户端库安装及使用方法解析
2020/09/14 Python
纯CSS3实现鼠标滑过按钮动画第二节
2020/07/16 HTML / CSS
Html5之svg可缩放矢量图形_动力节点Java学院整理
2017/07/17 HTML / CSS
Spartoo芬兰:欧洲最大的网上鞋店
2016/08/28 全球购物
复古斯堪的纳维亚儿童服装:Baby go Retro
2017/09/09 全球购物
印度服装购物网站:Limeroad
2018/09/26 全球购物
实习评语
2013/12/16 职场文书
保证书格式范文
2014/04/28 职场文书
检讨书大全
2015/01/27 职场文书
2015年办公室工作总结范文
2015/03/31 职场文书
工程部岗位职责范本
2015/04/11 职场文书
简单实现一个手持弹幕功能+文字抖动特效
2021/03/31 HTML / CSS
Java生成日期时间存入Mysql数据库的实现方法
2022/03/03 Java/Android
改造DE1103三步曲
2022/04/07 无线电
用Python仅20行代码编写一个简单的端口扫描器
2022/04/08 Python