jquery 模拟类搜索框自动完成搜索提示功能(改进)


Posted in Javascript onMay 24, 2010

autopoint.js代码:

/* 
* @date: 2010-5-22 21:42:15 
* @author: 胡灵伟 
* Depends: 
* jquery.js 
* 
* function:类似GOOGLE搜索框提示功能 
*/ 
(function($) { 
$.fn.autopoint = function (options) { 
defaults = { 
url:options.url, 
keyLeft : 37,//向左方向键 
keyUp : 38,//向上方向键 
keyRight : 39,//向右方向键 
keyDown : 40,//向下方向键 
keyEnter : 13,//回车键 
listHoverCSS : 'jhover',//提示框列表鼠标悬浮的样式 
tpl : '<div class="list"><div class="word">{word}</div><div class="view">约{view}条记录</div></div>', 
topoffset:options.topoffset||5 
}; 
var options = $.extend(defaults, options); 
var dropDiv = $('<div></div>').addClass('dropDiv').appendTo('body'); 
var isOver = false; 
dropDiv.hover(function(){ 
isOver = true; 
}, function(){ 
isOver = false; 
}); 
return this.each(function(){ 
var pa = $(this); 
$(this).bind('keydown', function(event){ 
if (dropDiv.css('display') != 'none') {//当提示层显示时才对键盘事件处理 
var currentList = dropDiv.find('.' + options.listHoverCSS); 
if (event.keyCode == options.keyDown) {//如果按的是向下方向键 
if (currentList.length == 0) { 
//如果提示列表没有一个被选中,则将列表第一个选中 
$(this).val(getPointWord(dropDiv.find('.list:first') 
.mouseover())); 
} else if (currentList.next().length == 0) { 
//如果是最后一个被选中,则取消选中,即可认为是输入框被选中 
unHoverAll(); 
} else { 
unHoverAll(); 
//将原先选中列的下一列选中 
if (currentList.next().length != 0) 
$(this).val(getPointWord(currentList.next() 
.mouseover())); 
} 
return false; 
} else if (event.keyCode == options.keyUp) {//如果按的是向上方向键 
if (currentList.length == 0) { 
$(this).val(getPointWord(dropDiv.find('.list:last') 
.mouseover())); 
} else if (currentList.prev().length == 0) { 
unHoverAll(); 
} else { 
unHoverAll(); 
if (currentList.prev().length != 0) 
$(this).val(getPointWord(currentList.prev() 
.mouseover())); 
} 
return false; 
}else if(event.keyCode == options.keyEnter) dropDiv.empty().hide(); 
} 
//当按下键之前记录输入框值,以方便查看键弹起时值有没有变 
$(this).attr('alt', $(this).val()); 
}).bind('keyup', function(event){ 
//如果弹起的键是向上或向下方向键则返回 
if(event.keyCode == options.keyDown||event.keyCode == options.keyUp) return; 
if($(this).val() == ''){ 
dropDiv.empty().hide(); 
return; 
} 
//若输入框值没有改变或变为空则返回 
if ($(this).val() == $(this).attr('alt')) 
return; 
getData(pa, $(this).val()); 
}).bind('blur', function(){ 
if(isOver&&dropDiv.find('.' + options.listHoverCSS)!=0) return; 
//文本输入框失去焦点则清空并隐藏提示层 
dropDiv.empty().hide(); 
}); 
/**处理ajax返回成功的方法**/ 
handleResponse = function(parent, json) { 
var isEmpty = true; 
for(var o in json){ 
if(o == 'data') isEmpty = false; 
} 
if(isEmpty) { 
showError("返回数据格式错误,请检查请求URL是否正确!"); 
return; 
} 
if(json['data'].length == 0) { 
//返回数据为空 
return; 
} 
refreshDropDiv(parent, json); 
dropDiv.show(); 
} 
/**处理ajax失败的方法**/ 
handleError = function(error) { 
//showError("由于url错误或超时请求失败!"); 
} 
showError = function(error){ 
alert(error); 
} 
/**通过ajax返回json格式数据生成用来创建dom的字符串**/ 
render = function(parent, json) { 
var res = json['data'] || json; 
var appendStr = ''; 
//用json对象中内容替换模版字符串中匹配/\{([a-z]+)\}/ig的内容,如{word},{view} 
for ( var i = 0; i < res.length; i+=1) { 
appendStr += options.tpl.replace(/\{([a-z]+)\}/ig, function(m, n) { 
return res[i][n]; 
}); 
} 
jebind(parent, appendStr); 
} 
/**将新建dom对象插入到提示框中,并重新绑定mouseover事件监听**/ 
jebind = function(parent, a) { 
dropDiv.append(a); 
dropDiv.find('.list').each(function() { 
$(this).unbind('mouseover').mouseover(function() { 
unHoverAll(); 
$(this).addClass(options.listHoverCSS); 
}).unbind('click').click(function(){ 
parent.val(getPointWord($(this))); 
dropDiv.empty().hide(); 
parent.focus(); 
}); 
}); 
} 
/**将提示框中所有列的hover样式去掉**/ 
unHoverAll = function() { 
dropDiv.find('.list').each(function() { 
$(this).removeClass(options.listHoverCSS); 
}); 
} 
/**在提示框中取得当前选中的提示关键字**/ 
getPointWord = function(p) { 
return p.find('div:first').text() 
} 
/**刷新提示框,并设定样式**/ 
refreshDropDiv = function(parent, json) { 
var left = parent.offset().left; 
var height = parent.height(); 
var top = parent.offset().top + options.topoffset + height; 
var width = options.width || parent.width() + 'px'; 
dropDiv.empty(); 
dropDiv.css( { 
'border' : '1px solid #FE00DF', 
'left' : left, 
'top' : top, 
'width' : width 
}); 
render(parent, json); 
//防止ajax返回之前输入框失去焦点导致提示框不消失 
parent.focus(); 
} 
/**通过ajax向服务器请求数据**/ 
getData = function(parent, word) { 
$.ajax( { 
type : 'GET', 
data : "word="+ word, 
url : options.url, 
dataType : 'json', 
timeout : 1000, 
success : function(json){handleResponse(parent, json);}, 
error : handleError 
}); 
} 
}); 
} 
})(jQuery);

网页上主要样式:
<style type="text/css"> 
.dropDiv { 
position: absolute; 
z-index: 10; 
display: none; 
cursor: hand; 
} 
.dropDiv .jhover { 
background-color: #00FEDF; 
} 
.dropDiv .list { 
float:left; 
width:100%; 
} 
.dropDiv .word { 
float:left; 
} 
.dropDiv .view { 
float:right; 
color: gray; 
text-align: right; 
font-size: 10pt; 
} 
</style>

调用方法:
<script type="text/javascript" src="../js/jquery-1.4.2.min.js"></script> 
<script type="text/javascript" src="../js/autopoint-1.0.1.js"></script> 
<script type="text/javascript"> 
$(function(){ 
$("input").autopoint({url:'http://localhost/xun/ajax.svl?method=getsearchhelp'}); 
}); 
</script> 
<body> 

<input type="text" size="50" /> 

<input type="text" size="50" /> 
</body>

servlet主要部分:
response.setContentType("text/html"); 
response.setHeader("Cache-Control", "no-cache"); 
response.setCharacterEncoding("UTF-8"); 
String word = request.getParameter("word"); 
if(Utils.isBlank(word)) return; 
JSONObject json = new JSONObject(); 
JSONArray array = new JSONArray(); 
Map<String, Object> map1 = new HashMap<String, Object>(); 
map1.put("word", word + "a1"); 
map1.put("view", 10); 
Map<String, Object> map2 = new HashMap<String, Object>(); 
map2.put("word", word + "a2"); 
map2.put("view", 15); 
Map<String, Object> map3 = new HashMap<String, Object>(); 
map3.put("word", word + "a3"); 
map3.put("view", 2); 
array.add(JSONObject.fromObject(map1)); 
array.add(JSONObject.fromObject(map2)); 
array.add(JSONObject.fromObject(map3)); 
json.put("data", array); 
PrintWriter out = response.getWriter(); 
out.print(json.toString()); 
out.close();

其中JSONObject和JSONArray类来自json-lib.jar,为了测试方便,是直接返回数据的,实际应用中可以替换为
从数据源查取数据.
Javascript 相关文章推荐
用正则xmlHttp实现的偷(转)
Jan 22 Javascript
JavaScript DOM学习第六章 表单实例
Feb 19 Javascript
Jquery事件的连接使用示例
Jun 18 Javascript
JS数组的赋值介绍
Mar 10 Javascript
jquery $(document).ready()和window.onload的区别浅析
Feb 04 Javascript
node.js下LDAP查询实例分享
Sep 30 Javascript
jQuery zTree加载树形菜单功能
Feb 25 Javascript
JavaScript面向对象继承原理与实现方法分析
Aug 09 Javascript
Vue.js获取被选择的option的value和text值方法
Aug 24 Javascript
vue组件之间通信方式实例总结【8种方式】
Feb 22 Javascript
React.js组件实现拖拽排序组件功能过程解析
Apr 27 Javascript
Ant Design的Table组件去除
Oct 24 Javascript
mysql输出数据赋给js变量报unterminated string literal错误原因
May 22 #Javascript
让mayfish支持mysqli数据库驱动的实现方法
May 22 #Javascript
JavaScript 笔记二 Array和Date对象方法
May 22 #Javascript
Javascript笔记一 js以及json基础使用说明
May 22 #Javascript
javascript Array数组对象的扩展函数代码
May 22 #Javascript
javascript 正则替换 replace(regExp, function)用法
May 22 #Javascript
JQuery 文本框使用小结
May 22 #Javascript
You might like
PHP根据IP判断地区名信息的示例代码
2014/03/03 PHP
php中in_array函数用法探究
2014/11/25 PHP
PHP实现的redis主从数据库状态检测功能示例
2017/07/20 PHP
setTimeout和setInterval的浏览器兼容性分析
2007/02/27 Javascript
jQuery前台数据获取实现代码
2011/03/16 Javascript
jQuery的.live()和.die() 使用介绍
2011/09/10 Javascript
动态的改变IFrame的高度实现IFrame自动伸展适应高度
2012/12/28 Javascript
两种常用的javascript数组去重方法思路及代码
2013/03/26 Javascript
jquery ajax 局部无刷新更新数据的实现案例
2014/02/08 Javascript
jQuery中width()方法用法实例
2014/12/24 Javascript
JavaScript实现的圆形浮动标签云效果实例
2015/08/06 Javascript
JS+CSS实现电子商务网站导航模板效果代码
2015/09/10 Javascript
AngularJS基础教程之简单介绍
2015/09/27 Javascript
jquery实现网页的页面平滑滚动效果代码
2015/11/02 Javascript
JavaScript判断输入是否为数字类型的方法总结
2017/09/28 Javascript
EasyUI的DataGrid绑定Json数据源的示例代码
2017/12/16 Javascript
javascript实现超好看的3D烟花特效
2020/01/01 Javascript
[01:10]为家乡而战!完美世界城市挑战赛全国总决赛花絮
2019/07/25 DOTA
Python中的数据对象持久化存储模块pickle的使用示例
2016/03/03 Python
Python、PyCharm安装及使用方法(Mac版)详解
2017/04/28 Python
解决Django模板无法使用perms变量问题的方法
2017/09/10 Python
速记Python布尔值
2017/11/09 Python
详解Python如何生成词云的方法
2018/06/01 Python
python logging模块的使用总结
2019/07/09 Python
提升python处理速度原理及方法实例
2019/12/25 Python
Python 支持向量机分类器的实现
2020/01/15 Python
Python自动登录QQ的实现示例
2020/08/28 Python
Python学习之time模块的基本使用
2021/01/17 Python
Skyscanner加拿大:全球旅行搜索平台
2018/11/19 全球购物
《和我们一样享受春天》教学反思
2014/02/07 职场文书
股权转让意向书
2014/04/01 职场文书
理想演讲稿范文
2014/05/21 职场文书
敬老院院长事迹材料
2014/05/21 职场文书
幼儿园个人总结
2015/02/28 职场文书
《女娲补天》教学反思
2016/02/20 职场文书
Django中celery的使用项目实例
2022/07/07 Python