博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
搜索框键入提示并回显准确信息
阅读量:5901 次
发布时间:2019-06-19

本文共 23090 字,大约阅读时间需要 76 分钟。

类似百度这种,大家应该也都清楚这个东西

我提供一个网上大家都在用的一个方法,整理了一下分享出来。

 

1.文本框和设置一个div,class=parentCls ,  搜索框的class设置:class=“inputElem”   , 为文本框设置一个oninput的属性。

 

 

在返回数据之前,我们先创建一个接受返回的json值的变量。

var resultData;

2.编写JS。

1   /**  2      * JS 模糊查询  3      * @param 1.当前的input add targetCls  4      * 2. 隐藏域里面统一增加同类名 叫 hiddenCls  5      * 3. 在各个父级元素上 添加类名 parentCls  6      */  7     function AutoComplete(options) {  8         this.config = {  9             targetCls: '.inputElem',          // 输入框目标元素 10             parentCls: '.parentCls',          // 父级类 11             hiddenCls: '.hiddenCls',          // 隐藏域input 12             searchForm: '.jqtransformdone',     //form表单 13             hoverBg: 'hoverBg',             // 鼠标移上去的背景 14             outBg: 'outBg',               // 鼠标移下拉的背景 15             isSelectHide: true,                 // 点击下拉框 是否隐藏 16             url: 'search',                    // url接口 17             height: 0,                     // 默认为0 不设置的话 那么高度自适应 18             manySelect: false,                 // 输入框是否多选 默认false 单选 19             renderHTMLCallback: null,                  // keyup时 渲染数据后的回调函数 20             callback: null,                  // 点击某一项 提供回调 21             closedCallback: null                   // 点击输入框某一项x按钮时 回调函数 22         }; 23  24         this.cache = { 25             currentIndex: -1, 26             oldIndex: -1, 27             inputArrs: []                 // 多选时候 输入框值放到数组里面去 28         }; 29         this.init(options); 30     } 31  32     AutoComplete.prototype = { 33  34         constructor: AutoComplete, 35         init: function (options) { 36  37             this.config = $.extend(this.config, options || {}); 38             var self = this, 39                 _config = self.config, 40                 _cache = self.cache; 41  42             // 鼠标点击输入框时候 43             $(_config.targetCls).each(function (index, item) { 44  45                 /* 46                  *  禁止 ctrl+v 和 黏贴事件 47                  */ 48                 $(item).unbind('paste'); 49                 $(item).bind('paste', function (e) { 50                     e.preventDefault(); 51                     var target = e.target, 52                         targetParent = $(target).closest(_config.parentCls); 53                     $(this).val(''); 54                     $(_config.hiddenCls, targetParent) && $(_config.hiddenCls, targetParent).val(''); 55                 }); 56  57                 $(item).keyup(function (e) { 58                     _cache.inputArrs = []; 59                     var targetVal = $.trim($(this).val()), 60                         keyCode = e.keyCode, 61                         elemHeight = $(this).outerHeight(), 62                         elemWidth = $(this).outerWidth(); 63  64                     // 如果输入框值为空的话 那么隐藏域的value清空掉 65                     if (targetVal == '') { 66                         var curParents = $(this).closest(_config.parentCls); 67                         $(_config.hiddenCls, curParents).val(''); 68                     } 69                     var targetParent = $(this).parent(); 70                     $(targetParent).css({'position': 'relative'}); 71  72                     if ($('.auto-tips', targetParent).length == 0) { 73                         // 初始化时候 动态创建下拉框容器 74                         $(targetParent).append($('
')); 75 $('.auto-tips', targetParent).css({ 76 'position': 'absolute', 77 'top': elemHeight, 78 'left': '0px', 79 'margin-left': '383px', 80 'z-index': 999, 81 'width': elemWidth, 82 'border': '1px solid #ccc' 83 }); 84 } 85 86 87 var curIndex = self._keyCode(keyCode); 88 if (curIndex > -1) { 89 self._keyUpAndDown(targetVal, e, targetParent); 90 } else { 91 if (targetVal != '') { 92 self._doPostAction(targetVal, targetParent); 93 } 94 95 } 96 }); 97 98 // 失去焦点时 如果没有点击 或者上下移时候 直接输入 那么当前输入框值情况 隐藏域值情况 99 $(item).blur(function (e) {100 var target = e.target,101 targetParent = $(target).closest(_config.parentCls);102 if ($(this).attr('up') || $(this).attr('down')) {103 return;104 } else {105 $(this).val('');106 $(_config.hiddenCls, targetParent).val('');107 }108 });109 110 });111 112 // 阻止form表单默认enter键提交113 $(_config.searchForm).each(function (index, item) {114 $(item).keydown(function (e) {115 var keyCode = e.keyCode;116 if (keyCode == 13) {117 return false;118 }119 });120 });121 122 // 点击文档123 $(document).click(function (e) {124 e.stopPropagation();125 var target = e.target,126 tagParent = $(target).parent(),127 attr = $(target, tagParent).closest('.auto-tips');128 129 var tagCls = _config.targetCls.replace(/^\./, '');130 131 if (attr.length > 0 || $(target, tagParent).hasClass(tagCls)) {132 return;133 } else {134 $('.auto-tips').each(function (index, item) {135 !$(item, tagParent).hasClass('hidden') && $(item, tagParent).addClass('hidden');136 });137 138 }139 });140 141 var stylesheet = '.auto-tips { margin: 0 1px; list-style: none;height:auto !important;padding: 0px;position:absolute; border:1px solid #ccc; top:27px; left:0; z-index:999; width:100%;background:#fff !important;}' +142 '.auto-tips p {overflow: hidden;margin: 1px 0;padding: 5px 5px;text-align:left;color: #666;text-decoration: none;line-height: 23px;white-space: nowrap;cursor: pointer;zoom: 1;}' +143 '.auto-tips p img{ vertical-align:middle;float:left;}' +144 '.auto-tips p.hoverBg {background-color: #669cb6;color: #fff;cursor: pointer;}' +145 '.hidden {display:none;}';146 147 this._addStyleSheet(stylesheet);148 149 },150 /**151 * 键盘上下键操作152 */153 _keyUpAndDown: function (targetVal, e, targetParent) {154 var self = this,155 _cache = self.cache,156 _config = self.config;157 158 // 如果请求成功后 返回了数据(根据元素的长度来判断) 执行以下操作159 if ($('.auto-tips p', targetParent) && $('.auto-tips p', targetParent).length > 0) {160 161 var plen = $('.auto-tips p', targetParent).length,162 keyCode = e.keyCode;163 _cache.oldIndex = _cache.currentIndex;164 165 // 上移操作166 if (keyCode == 38) {167 if (_cache.currentIndex == -1) {168 _cache.currentIndex = plen - 1;169 } else {170 _cache.currentIndex = _cache.currentIndex - 1;171 if (_cache.currentIndex < 0) {172 _cache.currentIndex = plen - 1;173 }174 }175 if (_cache.currentIndex !== -1) {176 177 !$('.auto-tips .p-index' + _cache.currentIndex, targetParent).hasClass(_config.hoverBg) &&178 $('.auto-tips .p-index' + _cache.currentIndex, targetParent).addClass(_config.hoverBg).siblings().removeClass(_config.hoverBg);179 var curAttr = $('.auto-tips .p-index' + _cache.currentIndex, targetParent).attr('data-html');180 // embId = $('.auto-tips .p-index'+_cache.currentIndex,targetParent).attr('embId');181 182 // 判断是否是多选操作 多选操作 暂留接口183 if (_config.manySelect) {184 _cache.inputArrs.push(curAttr);185 _cache.inputArrs = self._unique(_cache.inputArrs);186 self._manySelect(targetParent);187 } else {188 $(_config.targetCls, targetParent).val(curAttr);189 // 上移操作增加一个属性 当失去焦点时候 判断有没有这个属性190 if (!$(_config.targetCls, targetParent).attr('up')) {191 $(_config.targetCls, targetParent).attr('up', 'true');192 }193 194 self._createDiv(targetParent, curAttr);195 // hover196 self._hover(targetParent);197 }198 199 }200 201 } else if (keyCode == 40) { //下移操作202 if (_cache.currentIndex == plen - 1) {203 _cache.currentIndex = 0;204 } else {205 _cache.currentIndex++;206 if (_cache.currentIndex > plen - 1) {207 _cache.currentIndex = 0;208 }209 }210 if (_cache.currentIndex !== -1) {211 212 !$('.auto-tips .p-index' + _cache.currentIndex, targetParent).hasClass(_config.hoverBg) &&213 $('.auto-tips .p-index' + _cache.currentIndex, targetParent).addClass(_config.hoverBg).siblings().removeClass(_config.hoverBg);214 var curAttr = $('.auto-tips .p-index' + _cache.currentIndex, targetParent).attr('data-html');215 // embId = $('.auto-tips .p-index'+_cache.currentIndex,targetParent).attr('embId');216 217 218 // 判断是否是多选操作 多选操作 暂留接口219 if (_config.manySelect) {220 _cache.inputArrs.push(curAttr);221 _cache.inputArrs = self._unique(_cache.inputArrs);222 self._manySelect(targetParent);223 } else {224 $(_config.targetCls, targetParent).val(curAttr);225 226 // 下移操作增加一个属性 当失去焦点时候 判断有没有这个属性227 if (!$(_config.targetCls, targetParent).attr('down')) {228 $(_config.targetCls, targetParent).attr('down', 'true');229 }230 231 var pCls = $(_config.targetCls, targetParent).closest(_config.parentCls);232 // $(_config.hiddenCls,pCls).val(embId);233 self._createDiv(targetParent, curAttr);234 self._closed(targetParent);235 // hover236 self._hover(targetParent);237 }238 239 }240 } else if (keyCode == 13) { //回车操作241 var curVal = $('.auto-tips .p-index' + _cache.oldIndex, targetParent).attr('data-html');242 $(_config.targetCls, targetParent).val(curVal);243 /*244 if(_config.isSelectHide) {245 !$(".auto-tips",targetParent).hasClass('hidden') && $(".auto-tips",targetParent).addClass('hidden');246 }247 */248 249 _cache.currentIndex = -1;250 _cache.oldIndex = -1;251 252 }253 }254 },255 // 键码判断256 _keyCode: function (code) {257 var arrs = ['17', '18', '38', '40', '37', '39', '33', '34', '35', '46', '36', '13', '45', '44', '145', '19', '20', '9'];258 for (var i = 0, ilen = arrs.length; i < ilen; i++) {259 if (code == arrs[i]) {260 return i;261 }262 }263 return -1;264 },265 _doPostAction: function (targetVal, targetParent) {266 267 var self = this,268 _cache = self.cache,269 _config = self.config,270 url = _config.url;271 272 // 假如返回的数据如下:273 if (resultData != null) {274 var result = JSON.parse(resultData);275 if (result.length > 0) {276 var results = result;277 self._renderHTML(results, targetParent);278 self._executeClick(results, targetParent);279 } else {280 !$('.auto-tips', targetParent).hasClass('hidden') && $('.auto-tips', targetParent).addClass("hidden");281 $('.auto-tips', targetParent).html('');282 }283 }284 },285 286 /*287 $.get(url+"?keyword="+targetVal+"&timestamp="+new Date().getTime(),function(data){288 var ret = $.parseJSON(data.content),289 results = ret.results;290 if(results.length > 0) {291 self._renderHTML(results,targetParent);292 self._executeClick(results,targetParent);293 }else {294 !$('.auto-tips',targetParent).hasClass('hidden') && $('.auto-tips',targetParent).addClass("hidden");295 $('.auto-tips',targetParent).html('');296 297 }298 });*/299 _renderHTML: function (ret, targetParent) {300 var self = this,301 _config = self.config,302 _cache = self.cache,303 html = '';304 305 for (var i = 0, ilen = ret.length; i < ilen; i += 1) {306 html += '

' +307 '' + ret[i].appname + '' +308 '

';309 }310 // 渲染值到下拉框里面去311 $('.auto-tips', targetParent).html(html);312 $('.auto-tips', targetParent).hasClass('hidden') && $('.auto-tips', targetParent).removeClass('hidden');313 $('.auto-tips p:last', targetParent).css({"border-bottom": 'none'});314 315 316 // 出现滚动条 计算p的长度 * 一项p的高度 是否大于 设置的高度 如是的话 出现滚动条 反之317 var plen = $('.auto-tips p', targetParent).length,318 pheight = $('.auto-tips p', targetParent).height();319 320 if (_config.height > 0) {321 if (plen * pheight > _config.height) {322 $('.auto-tips', targetParent).css({'height': _config.height, 'overflow': 'auto'});323 } else {324 $('.auto-tips', targetParent).css({'height': 'auto', 'overflow': 'auto'});325 }326 }327 }328 ,329 /**330 * 当数据相同的时 点击对应的项时 返回数据331 */332 _executeClick: function (ret, targetParent) {333 var self = this,334 _config = self.config,335 _cache = self.cache;336 $('.auto-tips p', targetParent).unbind('click');337 $('.auto-tips p', targetParent).bind('click', function (e) {338 var dataAttr = $(this).attr('data-html');339 // embId = $(this).attr('embId');340 341 // 判断是否多选342 if (_config.manySelect) {343 _cache.inputArrs.push(dataAttr);344 _cache.inputArrs = self._unique(_cache.inputArrs);345 self._manySelect(targetParent);346 } else {347 $(_config.targetCls, targetParent).val(dataAttr);348 var parentCls = $(_config.targetCls, targetParent).closest(_config.parentCls),349 hiddenCls = $(_config.hiddenCls, parentCls);350 // $(hiddenCls).val(embId);351 self._createDiv(targetParent, dataAttr);352 353 // hover354 self._hover(targetParent);355 356 // !$(_config.targetCls,targetParent).hasClass('hidden') && $(_config.targetCls,targetParent).addClass('hidden');357 }358 self._closed(targetParent);359 if (_config.isSelectHide) {360 !$('.auto-tips', targetParent).hasClass('hidden') && $('.auto-tips', targetParent).addClass('hidden');361 }362 _config.callback && $.isFunction(_config.callback) && _config.callback();363 });364 365 // 鼠标移上效果366 $('.auto-tips p', targetParent).hover(function (e) {367 !$(this, targetParent).hasClass(_config.hoverBg) &&368 $(this, targetParent).addClass(_config.hoverBg).siblings().removeClass(_config.hoverBg);369 });370 }371 ,372 _hover: function (targetParent) {373 $('.create-input span', targetParent).hover(function () {374 $(this).css({"background": '#ccc', 'padding-left': '0px'});375 }, function () {376 $(this).css({"background": ''});377 });378 }379 ,380 // 动态的创建div标签 遮住input输入框381 _createDiv: function (targetParent, dataAttr) {382 var self = this,383 _config = self.config;384 var iscreate = $('.create-input', targetParent);385 386 // 确保只创建一次div387 if (iscreate.length > 0) {388 $('.create-input', targetParent).remove();389 }390 $(_config.targetCls, targetParent).val(dataAttr);391 $('.alink', targetParent).css({'float': 'left', 'background': 'none'});392 }393 ,394 // X 关闭事件395 _closed: function (targetParent) {396 var self = this,397 _config = self.config;398 /*399 * 点击X 关闭按钮400 * 判断当前输入框有没有up和down属性 有的话 删除掉 否则 什么都不做401 */402 $('.alink', targetParent).click(function () {403 $('.create-input', targetParent) && $('.create-input', targetParent).remove();404 $(_config.targetCls, targetParent) && $(_config.targetCls, targetParent).hasClass('hidden') &&405 $(_config.targetCls, targetParent).removeClass('hidden');406 $(_config.targetCls, targetParent).val('');407 //清空隐藏域的值408 var curParent = $(_config.targetCls, targetParent).closest(_config.parentCls);409 $(_config.hiddenCls, curParent).val('');410 411 var targetInput = $(_config.targetCls, targetParent);412 if ($(targetInput).attr('up') || $(targetInput).attr('down')) {413 $(targetInput).attr('up') && $(targetInput).removeAttr('up');414 $(targetInput).attr('down') && $(targetInput).removeAttr('down');415 }416 _config.closedCallback && $.isFunction(_config.closedCallback) && _config.closedCallback();417 });418 }419 ,420 /*421 * 数组去重复422 */423 _unique: function (arrs) {424 var obj = {},425 newArrs = [];426 for (var i = 0, ilen = arrs.length; i < ilen; i++) {427 if (obj[arrs[i]] != 1) {428 newArrs.push(arrs[i]);429 obj[arrs[i]] = 1;430 }431 }432 return newArrs;433 }434 ,435 /*436 * 输入框多选操作437 */438 _manySelect: function (targetParent) {439 var self = this,440 _config = self.config,441 _cache = self.cache;442 if (_cache.inputArrs.length > 0) {443 $(_config.targetCls, targetParent).val(_cache.inputArrs.join(','));444 }445 }446 ,447 /*448 * 判断是否是string449 */450 _isString: function (str) {451 return Object.prototype.toString.apply(str) === '[object String]';452 }453 ,454 /*455 * JS 动态添加css样式456 */457 _addStyleSheet: function (refWin, cssText, id) {458 459 var self = this;460 if (self._isString(refWin)) {461 id = cssText;462 cssText = refWin;463 refWin = window;464 }465 refWin = $(refWin);466 var doc = document;467 var elem;468 469 if (id && (id = id.replace('#', ''))) {470 elem = $('#' + id, doc);471 }472 473 // 仅添加一次,不重复添加474 if (elem) {475 return;476 }477 //elem = $(''); 不能这样创建 IE8有bug478 elem = document.createElement("style");479 // 先添加到 DOM 树中,再给 cssText 赋值,否则 css hack 会失效480 $('head', doc).append(elem);481 482 if (elem.styleSheet) { // IE483 elem.styleSheet.cssText = cssText;484 } else { // W3C485 elem.appendChild(doc.createTextNode(cssText));486 }487 }488 ,489 /*490 * 销毁操作 释放内存491 */492 destory: function () {493 var self = this,494 _config = self.config,495 _cache = self.cache;496 _cache.ret = [];497 _cache.currentIndex = 0;498 _cache.oldIndex = 0;499 _cache.inputArrs = [];500 _config.targetCls = null;501 }502 };503 // 初始化504 $(function () {505 var auto = new AutoComplete({});506 });507

 

 

73行-83行,我手动设置了下他的位置,让他加载生成到我的搜索框下面。正好对准。

 

3:编写ajax:

  如果监测到搜索框内容改变 就请求action

function onChange(value) {        var textValue = $("#inputName").val(); //文本框的值        if ($.trim(textValue) == "") {  //判断文本框的值是否为空            return;        }        $.ajax({            dataType: "text",            type: "POST",            url: "/search", //请求地址            data: {
"search": textValue}, //附带参数 success: function (result) {  //返回结果 var result = JSON.parse(result);  //将一个json字符串转换成对象 if (result.status == 1) { //判断返回值 resultData = result.data;  //将返回的json信息,赋值给我们上面定义好的变量resultData } } }); }

 

4.返回:resutData:

将返回的resultData,传给我们上面编写的js里面。(在273行有体现

 

效果: 

 

 我的sql :

select 搜索词 from 表名 where 搜索词 like  CONCAT('','${搜索词}','%' ) GROUP BY 搜索词 LIMIT 5 我是以匹配以什么内容开头去查询的信息, limit 5 是控制显示条数。

转载于:https://www.cnblogs.com/wdnnccey/p/6431317.html

你可能感兴趣的文章
minio 并发数_MinIO 参数解析与限制
查看>>
flash back mysql_mysqlbinlog flashback 使用最佳实践
查看>>
mysql存储引擎模式_MySQL存储引擎
查看>>
java 重写system.out_重写System.out.println(String x)方法
查看>>
配置ORACLE 11g绿色版客户端和PLSQL远程连接环境
查看>>
ASP.NET中 DataList(数据列表)的使用前台绑定
查看>>
Linux学习之CentOS(八)--Linux系统的分区概念
查看>>
System.Func<>与System.Action<>
查看>>
asp.net开源CMS推荐
查看>>
csharp skype send message in winform
查看>>
MMORPG 游戏服务器端设计--转载
查看>>
HDFS dfsclient写文件过程 源码分析
查看>>
ubuntu下安装libxml2
查看>>
nginx_lua_waf安装测试
查看>>
WinForm窗体缩放动画
查看>>
JQuery入门(2)
查看>>
linux文件描述符
查看>>
传值引用和调用引用的区别
查看>>
hyper-v 无线网连接
查看>>
Python3.7.1学习(六)RabbitMQ在Windows环境下的安装
查看>>