zoukankan      html  css  js  c++  java
  • 下拉列表实现模糊匹配选择

    最近在做一个在文本框输入关键字, 文本框下动态显示加载相关内容的下拉列表的效果, 就是类似于百度和淘宝搜索框这种效果.

    不断的研究加上尝试, 得到两种方案解决这个需求, 特意记录一下, 以免下次用的时候忘记.

    方法一: HTML5新增的datalist标签

    HTML5作为当下最为热门的 Web 技术, 已经在互联网行业得到了普遍应用, 基于HTML5的浏览器和Web引擎为用户带来了感知体验上的巨大飞跃, 并将Web应用带入了一个新的发展阶段, 可以预见HTML5会有更广泛的使用及更好的发展. HTML5相较于HTML4.01增加了好多实用的语义化标签和属性, 关于其中datalist标签的详细使用介绍可以参考datalist标签 | 菜鸟教程.

    1.HTML部分代码

    <input id="userName" type="text" autocomplete="off" list="userNameList" placeholder=" 请输入用户名" onblur="checkUserName(this)" onfocus="findAllUsers()">
    <datalist id="userNameList"></datalist>
    <label>双击文本框进行选择</label>
    <input type="hidden" name="userId" />

    显示效果如图所示

    这里写图片描述

    2.JS部分代码

    // "用户名"模糊匹配查询_jquery Ajax实现
    $(document).ready(function() {
        $('#userName').keyup(function() {
            $("#userNameList option").remove();
            $.ajaxSetup({async: true}); 
            $.get(webUrl+"/sys/userRole/fuzzySearchUser.action", {'username' : $("#userName").val() == "" ? null : $("#userName").val()}, function(data) {
                for(var i in data) {
                    /* $("#userNameList").append("<option value=data[i].username data-userId=data[i].id ></option>"); */
                    var html = "";
                    html += "<option value='" + data[i].username + "' data-userId='" + data[i].id + "'></option>";
                    $("#userNameList").append(html); 
                    /* console.log(html); */
                }
            }, "json")
        })
    })

    当每次在文本框输入文字并按下键盘后, ajax将本文框中的文字传到后台处理, 并将查到的数据以json格式返回, 再通过拼接字符串将标签加到中, 显示如下效果. 
    这里写图片描述

    注意事项:

    1. 上图是在forfox下的显示效果, 如果查询出的结果比较多的话, 会自动添加滚动条; 而chrome则不会出现滚动条, 会显示所有查询结果, 我也没用css修改好, 有时间再试试; 在IE和Edge上, 每次输入内容后都无法直接显示出下拉列表, 需要按一下”Backspace”才能显示, 查看HTML源码发现datalist标签下有相应的option内容…..也许是HTML5还太年轻, 各个浏览器显示效果都不同, 折腾好久快要炸了…..

    2. HTML data-* 属性也是HTML5新增的属性, 用于存储私有页面后应用的自定义数据. 其中jquery有个相应的方法data()方法用于在指定的元素上存取数据, 返回设置值. 注意: 自定义属性前缀 “data-” 会被客户端忽略.

    3. dataList下的option标签选中的时候没法选中当前的对象, 并获取id值, 这里我采用的方式是在提交表单的时候, 将搜索框中的内容和后台返回的值进行对比, 将匹配的值的id传到设置的隐藏域中, 最后传到后台. 代码如下:

    var userInfo = $("#userName").val();
    var getUserId = $("option[value='" + userInfo + "']").data("userid");
    $("input[name='userId']").val(getUserId);

    3. 后台Java部分代码

    项目后台是用的SSM框架编写.

    @ResponseBody
    @RequestMapping("/fuzzySearchUser")
    public List<SysUser> fuzzySearchUser(SysUser user) {
        return userRoleService.findUsersByName(user);
    }

    至此, 用datalist标签基本上能实现要求的功能, 不过在不同浏览器显示效果不同的问题还是没有完美的解决方案, 为了不耽误项目进度, 我采用了下列方法二.

    方法二 jQuery Autocomplete插件

    jQuery Autocomplete 插件根据用户输入值进行搜索和过滤,让用户快速找到并从预设值列表中选择。 

    该插件现在是 jQuery UI 的一部分,独立的版本不会再更新了。 

    jQuery UI 实例 - 自动完成(Autocomplete) 

    jQuery UI API - 自动完成部件(Autocomplete Widget)

    1.HTML部分代码

    <input id="rolename" type="text" autocomplete="off" list="roleNameList" placeholder=" 请输入角色名" >
    <label>双击文本框进行选择</label>
    <input type="hidden" name="roleId" />

    2.JS部分代码

    // "角色名"模糊匹配查询
    $(document).ready(function(){
        $('#rolename').keyup(function(){
            $("#roleNameList option").remove();
            $.ajax({
                async: true,
                url: webUrl+"/sys/userRole/fuzzySearchRole.action",
                type: 'get',
                dataType: 'json',
                data: {
                    'name' : $("#rolename").val() == "" ? null : $("#rolename").val(),
                },
                success:function(data) {
                    var arr = [];
                    for(var i in data){
                        /* var html = "";
                        html += "<option value='" + data[i].name + "' data-roleId='" + data[i].id + "'></option>";
                        $("#roleNameList").append(html);  */
                        var one = {};
                        one.label = data[i].name;
                        one.value = data[i].id;
                        arr[i] = one;
                        /* console.log(one); */
                    }
                    console.log(arr);
                    $("#rolename").autocomplete({
                        source : arr,  // 数据源
                        delay: 0,  // 多久后显示, 单位ms
                         320,
                        max: 5,  // 为什么不起作用?
                        highlight: false,
                        multiple: true,
                        multipleSeparator: "",
                        scroll: true,
                        scrollHeight: 300,
                        select: function(event, ui){
                            // 这里的this指向当前输入框的DOM元素
                            // event参数是事件对象
                            // ui对象只有一个item属性,对应数据源中被选中的对象
                            alert("123");
                           /*  $(this).value = ui.item.label; */
                           $( "#rolename" ).val( ui.item.label );
                            $("input[name='roleId']").val(ui.item.value );
                            // 必须阻止事件的默认行为,否则autocomplete默认会把ui.item.value设为输入框的value值
                            event.preventDefault();     
                        }
                    });
                }
            })
        })
    })

    后台java代码同上, 就不贴了.

    Appache开源项目Lucene

    Appache有个全文检索引擎架构的项目叫”Lucene”, 可以用来做搜索, 改天有空再更.

     

    方案二:

     

    在网上有很多可输入及模糊查询的select下拉插件,功能也很强大,比如select、chosen等,做这个的方法也是有很多的,适用自己就好,下面是我自己的一个方法,希望适合大家


    CSS代码

    在网上有很多可输入及模糊查询的select下拉插件,功能也很强大,比如select、chosen等,做这个的方法也是有很多的,适用自己就好,下面是我自己的一个方法,希望适合大家

    .second select {
         11%;
        height: 106px;
        margin: 0px;
        outline: none;
        border: 1px solid #999;
        margin-top: 31px;
    }
    .second input {
         167px;
        top: 9px;
        outline: none;
        border: 0pt;
        position: absolute;
        line-height: 30px;
        left: 8px;
        height: 30px;
        border: 1px solid #999;
    }
    .second ul {
        position: absolute;
        top: 27px;
        border: 1px solid #999;
        left: 8px;
         125px;
        line-height: 16px;
    }
    .ul li{
        list-style: none;
         161px;
        /* left: 15px; */
        margin-left: -40px;
        font-family: 微软雅黑;
        padding-left: 4px;
    }
    .blue { 
        background:#1e91ff; 
    }

    JS代码

    var TempArr=[];//存储option
     
    $(function(){
        /*先将数据存入数组*/
        $("#typenum option").each(function(index, el) {
            TempArr[index] = $(this).text();
        });
        $(document).bind('click', function(e) {  
            var e = e || window.event; //浏览器兼容性   
            var elem = e.target || e.srcElement;  
            while (elem) { //循环判断至跟节点,防止点击的是div子元素   
                if (elem.id && (elem.id == 'typenum' || elem.id == "makeupCo")) {  
                    return;  
                }  
                elem = elem.parentNode;  
            }  
            $('#typenum').css('display', 'none'); //点击的不是div或其子元素   
        });  
    })
     
    function changeF(this_) {
        $(this_).prev("input").val($(this_).find("option:selected").text());
        $("#typenum").css({"display":"none"});
    }
    function setfocus(this_){
        $("#typenum").css({"display":""});
        var select = $("#typenum");
        for(i=0;i<TempArr.length;i++){
            var option = $("<option></option>").text(TempArr[i]);
            select.append(option);
        } 
    }
     
    function setinput(this_){
        var select = $("#typenum");
        select.html("");
        for(i=0;i<TempArr.length;i++){
            //若找到以txt的内容开头的,添option
            if(TempArr[i].substring(0,this_.value.length).indexOf(this_.value)==0){
                var option = $("<option></option>").text(TempArr[i]);
                select.append(option);
            }
        }
    }

    页面代码

    <span class="second">
        <input type="text" name="makeupCo" id="makeupCo" class="makeinp" onfocus="setfocus(this)" oninput="setinput(this);" placeholder="请选择或输入"/>
        <select name="makeupCoSe" id="typenum" onchange="changeF(this)" size="10" style="display:none;">
            <option value="">1</option>
            <option value="">2</option>
            <option value="">12323</option>
            <option value="">31</option>
            <option value="">1332</option>
            <option value="">412</option>
            <option value="">42</option>
            <option value="">11</option>
        </select>
    </span>

    搜索框模糊匹配下拉显示

     版权声明:本文为博主原创文章,未经博主允许不得转载。 https://blog.csdn.net/zym2999/article/details/78266779

    最近在做一个在文本框输入关键字, 文本框下动态显示加载相关内容的下拉列表的效果, 就是类似于百度和淘宝搜索框这种效果.

    这里写图片描述

    不断的研究加上尝试, 得到两种方案解决这个需求, 特意记录一下, 以免下次用的时候忘记.

    方法一: HTML5新增的datalist标签

    HTML5作为当下最为热门的 Web 技术, 已经在互联网行业得到了普遍应用, 基于HTML5的浏览器和Web引擎为用户带来了感知体验上的巨大飞跃, 并将Web应用带入了一个新的发展阶段, 可以预见HTML5会有更广泛的使用及更好的发展. HTML5相较于HTML4.01增加了好多实用的语义化标签和属性, 关于其中datalist标签的详细使用介绍可以参考datalist标签 | 菜鸟教程.

    1.HTML部分代码

    <input id="userName" type="text" autocomplete="off" list="userNameList" placeholder=" 请输入用户名" onblur="checkUserName(this)" onfocus="findAllUsers()">
    <datalist id="userNameList"></datalist>
    <label>双击文本框进行选择</label>
    <input type="hidden" name="userId" />
    • 1
    • 2
    • 3
    • 4

    显示效果如图所示

    这里写图片描述

    2.JS部分代码

    // "用户名"模糊匹配查询_jquery Ajax实现
    $(document).ready(function() {
        $('#userName').keyup(function() {
            $("#userNameList option").remove();
            $.ajaxSetup({async: true}); 
            $.get(webUrl+"/sys/userRole/fuzzySearchUser.action", {'username' : $("#userName").val() == "" ? null : $("#userName").val()}, function(data) {
                for(var i in data) {
                    /* $("#userNameList").append("<option value=data[i].username data-userId=data[i].id ></option>"); */
                    var html = "";
                    html += "<option value='" + data[i].username + "' data-userId='" + data[i].id + "'></option>";
                    $("#userNameList").append(html); 
                    /* console.log(html); */
                }
            }, "json")
        })
    })
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16

    当每次在文本框输入文字并按下键盘后, ajax将本文框中的文字传到后台处理, 并将查到的数据以json格式返回, 再通过拼接字符串将标签加到中, 显示如下效果. 
    这里写图片描述

    注意事项:

    1. 上图是在forfox下的显示效果, 如果查询出的结果比较多的话, 会自动添加滚动条; 而chrome则不会出现滚动条, 会显示所有查询结果, 我也没用css修改好, 有时间再试试; 在IE和Edge上, 每次输入内容后都无法直接显示出下拉列表, 需要按一下”Backspace”才能显示, 查看HTML源码发现datalist标签下有相应的option内容…..也许是HTML5还太年轻, 各个浏览器显示效果都不同, 折腾好久快要炸了…..

    这里写图片描述

    2. HTML data-* 属性也是HTML5新增的属性, 用于存储私有页面后应用的自定义数据. 其中jquery有个相应的方法data()方法用于在指定的元素上存取数据, 返回设置值. 注意: 自定义属性前缀 “data-” 会被客户端忽略.

    3. dataList下的option标签选中的时候没法选中当前的对象, 并获取id值, 这里我采用的方式是在提交表单的时候, 将搜索框中的内容和后台返回的值进行对比, 将匹配的值的id传到设置的隐藏域中, 最后传到后台. 代码如下:

    var userInfo = $("#userName").val();
    var getUserId = $("option[value='" + userInfo + "']").data("userid");
    $("input[name='userId']").val(getUserId);
    • 1
    • 2
    • 3

    3. 后台Java部分代码

    项目后台是用的SSM框架编写.

    @ResponseBody
    @RequestMapping("/fuzzySearchUser")
    public List<SysUser> fuzzySearchUser(SysUser user) {
        return userRoleService.findUsersByName(user);
    }
    • 1
    • 2
    • 3
    • 4
    • 5

    至此, 用datalist标签基本上能实现要求的功能, 不过在不同浏览器显示效果不同的问题还是没有完美的解决方案, 为了不耽误项目进度, 我采用了下列方法二.

    方法二 jQuery Autocomplete插件

    jQuery Autocomplete 插件根据用户输入值进行搜索和过滤,让用户快速找到并从预设值列表中选择。 
    该插件现在是 jQuery UI 的一部分,独立的版本不会再更新了。 
    jQuery UI 实例 - 自动完成(Autocomplete) 
    jQuery UI API - 自动完成部件(Autocomplete Widget)

    1.HTML部分代码

    <input id="rolename" type="text" autocomplete="off" list="roleNameList" placeholder=" 请输入角色名" >
    <label>双击文本框进行选择</label>
    <input type="hidden" name="roleId" />
    • 1
    • 2
    • 3

    2.JS部分代码

    // "角色名"模糊匹配查询
    $(document).ready(function(){
        $('#rolename').keyup(function(){
            $("#roleNameList option").remove();
            $.ajax({
                async: true,
                url: webUrl+"/sys/userRole/fuzzySearchRole.action",
                type: 'get',
                dataType: 'json',
                data: {
                    'name' : $("#rolename").val() == "" ? null : $("#rolename").val(),
                },
                success:function(data) {
                    var arr = [];
                    for(var i in data){
                        /* var html = "";
                        html += "<option value='" + data[i].name + "' data-roleId='" + data[i].id + "'></option>";
                        $("#roleNameList").append(html);  */
                        var one = {};
                        one.label = data[i].name;
                        one.value = data[i].id;
                        arr[i] = one;
                        /* console.log(one); */
                    }
                    console.log(arr);
                    $("#rolename").autocomplete({
                        source : arr,  // 数据源
                        delay: 0,  // 多久后显示, 单位ms
                         320,
                        max: 5,  // 为什么不起作用?
                        highlight: false,
                        multiple: true,
                        multipleSeparator: "",
                        scroll: true,
                        scrollHeight: 300,
                        select: function(event, ui){
                            // 这里的this指向当前输入框的DOM元素
                            // event参数是事件对象
                            // ui对象只有一个item属性,对应数据源中被选中的对象
                            alert("123");
                           /*  $(this).value = ui.item.label; */
                           $( "#rolename" ).val( ui.item.label );
                            $("input[name='roleId']").val(ui.item.value );
                            // 必须阻止事件的默认行为,否则autocomplete默认会把ui.item.value设为输入框的value值
                            event.preventDefault();     
                        }
                    });
                }
            })
        })
    })
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35
    • 36
    • 37
    • 38
    • 39
    • 40
    • 41
    • 42
    • 43
    • 44
    • 45
    • 46
    • 47
    • 48
    • 49
    • 50
    • 51

    后台java代码同上, 就不贴了.

    Appache开源项目Lucene

    Appache有个全文检索引擎架构的项目叫”Lucene”, 可以用来做搜索, 改天有空再更.

  • 相关阅读:
    WPF Get jiayuan outbox list(send mail box)
    Python中列表的各种方法
    Python中字符串拼接的三种方式
    Python2中input()、raw_input()和Python3中input()
    Python 中for...esle和while...else语法
    第 20 章 设置应用程序的样式并对其进行部署
    第 19 章 用户帐号
    第 18 章 Django 入门
    第 17 章 使用API
    安装requests
  • 原文地址:https://www.cnblogs.com/zp-uestc/p/10347522.html
Copyright © 2011-2022 走看看