• 1.实现的效果
  • 2.实现说明
  • 3.完整代码

一、实现的效果:


二、实现说明:

1.由于无法修改原生select中的option样式,因此自己通过ul,li实现下拉列表,用input实现回显框;
input实现select回显注意2个地方:
1)使用 readonly=“readonly” 让input框无法实现输入 ,不获取焦点;

<input type="text" readonly="readonly" class="ec-input__value" placeholder="业务类型" value="" id="yewu-value">

2)当需要input框可以输入时,使用autocomplete=“new-password” 避免input框获取焦点时自动以下拉的方式弹出以前输入过的值,导致覆盖真正需要展示的下拉列表

 <input type="text" autocomplete="new-password" class="ec-input__value" placeholder="请选择国家地区" value="" id="area-value" oninput="enterSearch(this)">

2.下拉框的弹出与隐藏
1)没有显示时点击input部分弹出(同时右侧三角箭头改变,朝上),当弹出框以及显示点击隐藏下拉弹出框(三角箭头方向恢复,朝下)
实现弹出下拉列表代码如下:

   //自定义下拉框弹出事件function openValue(obj, e){e.stopPropagation(); //阻止冒泡//阻止默认浏览器动作(W3C)if ( e && e.preventDefault ){e.preventDefault();} else{window.event.returnValue = false;}if ($(".dropdown-menus").is(":visible")) {$('.dropdown-menus').hide();$('.ec-input').removeClass('ec-input__open');}else{$(obj).addClass('ec-input__open');$(obj).next().show();}}

右侧三角箭头

 .caret{display: inline-block;width: 0;height: 0;margin-left: 2px;vertical-align: middle;border-top: 4px dashed;border-top: 4px solid;border-right: 4px solid transparent;border-left: 4px solid transparent;}.ec-input .caret {position: absolute;top: 50%;right: 12px;margin-top: -2px;vertical-align: middle;}.ec-input__open .caret{transform: rotate(180deg);}

2)选中下拉框的某一个值之后,值回显,弹出框隐藏;
注意:由于使用事件委托的方式,当点击某一个选项时,有可能点击的target不是li节点,而是li的子节点,此时可以取其父节点

 // 点击的地方可能是li,也可能是li的子节点if(e.target && e.target.nodeName == "LI"){selectedDom = e.target;}else{selectedDom = $(e.target).parent();}

事件的完整代码如下:

   //点击某个下拉菜单的值之后的事件处理function getValue(obj, e){e.stopPropagation(); //阻止冒泡var selectedDom;// 点击的地方可能是li,也可能是li的子节点if(e.target && e.target.nodeName == "LI"){selectedDom = e.target;}else{selectedDom = $(e.target).parent();}var selectedValue = $(selectedDom).data('value');var selectedLable = $(selectedDom).data('label');var operId = $(obj).data('id');$(selectedDom).siblings().removeClass('ec-active')$(selectedDom).addClass('ec-active');$('#'+operId+'-value').val(selectedLable);$('#'+operId+'-label').val(selectedValue);$('.ec-input').removeClass('ec-input__open');$(obj).parent().hide();}

3)当下拉弹出框显示时,点击下拉组件以外的部分,弹出框隐藏,代码如下:

 // 自定义下拉框:点击其他部分收起下拉事件document.addEventListener("click", (e) => {if ($(".dropdown-menus").is(":visible")) {$('.dropdown-menus').hide();$('.ec-input').removeClass('ec-input__open');}});

3.带搜索的下拉框,当中文输入法输入中文时,让其回显中文时实现搜索,而非输入每次输入都执行一次搜索操作,代码如下:

   // 中文输入法$('.ec-input__value').on('compositionstart',function(event) {isChinese = true;})//  输入中文之后$('.ec-input__value').on('compositionend',function() {isChinese = false;enterSearch(this)})

三、完整代码:

<!DOCTYPE html>
<html lang="en">
<head><meta charset="UTF-8"><meta http-equiv="X-UA-Compatible" content="IE=edge"><meta name="viewport" content="width=device-width, initial-scale=1.0"><title>自定义下拉组件</title>
</head>
<style>body, p{margin:0;padding:0;}.container{margin:100px;}.askForm{margin:20px;display: flex;display: -webkit-flex;background: #fff;border:1px solid #e1e1e1;border-radius: 6px;height: 34px;}.select-left{flex:2;}.select-right{flex: 3;padding-right: 10px;}.ec-select{height: 34px;}.select-online{width: 20px;margin-right: 10px;height: 20px;margin-top:7px;border-right: 1px solid #e1e1e1;}.ec-input{width: 100%;height: 34px;line-height: 34px;padding-left: 10px;position: relative;}.ec-input .ec-input__value{border: none;outline: none;width: 90%;cursor: pointer;}.caret{display: inline-block;width: 0;height: 0;margin-left: 2px;vertical-align: middle;border-top: 4px dashed;border-top: 4px solid;border-right: 4px solid transparent;border-left: 4px solid transparent;}.ec-input .caret {position: absolute;top: 50%;right: 12px;margin-top: -2px;vertical-align: middle;}.ec-input__open .caret{transform: rotate(180deg);}.dropdown-menus{position: relative;max-height: 200px;width: 100%;display: none;border: 1px solid rgba(0,0,0,.15);border-radius: 4px;-webkit-box-shadow: 0 6px 12px rgb(0 0 0 / 18%);box-shadow: 0 6px 12px rgb(0 0 0 / 18%);overflow-y: scroll;overflow: auto;min-height: 42px;}.dropdown-menu{padding:6px 0;margin:0;list-style: none;}.menu-item{height: 30px;cursor: pointer;line-height: 30px;padding-left: 10px;}.menu-item:hover{outline: 0;color:#FF9500;background: rgba(255, 149, 0, 0.1);}.select-ok{position: absolute;display: inline-block;right: 15px;margin-top: 8px;}.ec-active .select-ok{width: 14px;height: 6px;display: inline-block;border: 1px solid #FF9500;border-width: 0 0 2px 2px;transform: rotate(-45deg);-ms-transform: rotate(-45deg);-moz-transform: rotate(-45deg);-webkit-transform: rotate(-45deg);-o-transform: rotate(-45deg);vertical-align: baseline;}.no-result{padding: 8px;}
</style>
<body><div class="container"><div class="askForm"><div class="select-container select-left"><div class="ec-input" onclick="openValue(this,event)"><input type="hidden" value="" id="yewu-label"><input type="text" readonly="readonly" class="ec-input__value" placeholder="业务类型" value="" id="yewu-value"><span class="caret"></span></div><div class="dropdown-menus"><ul class="dropdown-menu" onclick="getValue(this, event)" data-id="yewu"><li class="menu-item" data-value="0" data-label="专线"><span class="text">专线</span><span class="select-ok"></span></li><li class="menu-item ec-active" data-value="1" data-label="系统通知"><span class="text">系统通知</span><span class="select-ok"></span></li><li class="menu-item" data-value="2" data-label="版本发布"><span class="text">版本发布</span><span class="select-ok"></span></li></ul></div></div><div class="select-online"></div><div class="select-container select-right"><div class="ec-input" onclick="openValue(this,event)"><input type="hidden" value="" id="area-label"><input type="text" class="ec-input__value" autocomplete="new-password" placeholder="请选择国家地区" value="" id="area-value" oninput="enterSearch(this)"><span class="caret"></span></div><div class="dropdown-menus area-menus"></div></div></div></div>
</body>
<script src="http://cdn.staticfile.org/jquery/2.1.1/jquery.min.js" type="text/javascript"></script>
<script>var earaData = [{name:'中国'},{name:'泰国'},{name:'美国'},{name:'英国'},{name:'日本'},{name:'澳大利亚'},{name:'韩国'},{name:'印度尼西亚'},];var filterArea = [];var isChinese = false;searchArea('');//初始化国家地区dom//自定义下拉框弹出事件function openValue(obj, e){e.stopPropagation(); //阻止冒泡//阻止默认浏览器动作(W3C)if ( e && e.preventDefault ){e.preventDefault();} else{window.event.returnValue = false;}if ($(".dropdown-menus").is(":visible")) {$('.dropdown-menus').hide();$('.ec-input').removeClass('ec-input__open');}else{$(obj).addClass('ec-input__open');$(obj).next().show();}}//点击某个下拉菜单的值之后的事件处理function getValue(obj, e){e.stopPropagation(); //阻止冒泡var selectedDom;// 点击的地方可能是li,也可能是li的子节点if(e.target && e.target.nodeName == "LI"){selectedDom = e.target;}else{selectedDom = $(e.target).parent();}var selectedValue = $(selectedDom).data('value');var selectedLable = $(selectedDom).data('label');var operId = $(obj).data('id');$(selectedDom).siblings().removeClass('ec-active')$(selectedDom).addClass('ec-active');$('#'+operId+'-value').val(selectedLable);$('#'+operId+'-label').val(selectedValue);$('.ec-input').removeClass('ec-input__open');$(obj).parent().hide();}//国家地区搜索框输入事件function enterSearch(obj){if(!isChinese){var key = $(obj).val();searchArea(key);}}// 下拉搜索框搜索事件function searchArea(key){filterArea = [];for(var j = 0,len=earaData.length;j<len;j++){if(earaData[j].name.match(key)){filterArea.push(earaData[j].name)}}appendSelectArea(key);}// 中文输入法$('.ec-input__value').on('compositionstart',function(event) {isChinese = true;})//  输入中文之后$('.ec-input__value').on('compositionend',function() {isChinese = false;enterSearch(this)})// 将搜索到的结果重新渲染到下拉框中function appendSelectArea(key){var areasHtml = '';if(filterArea && filterArea.length>0){areasHtml = '<ul class="dropdown-menu" οnclick="getValue(this, event)" data-id="area">';for(var i = 0,len = filterArea.length ;i<len;i++){areasHtml+='<li class="menu-item" data-value='+filterArea[i]+' data-label='+filterArea[i]+'><span class="text">'+filterArea[i]+'</span><span class="select-ok"></span></li>'}areasHtml+='</ul>';}else{areasHtml = '<div class="dropdown-menu no-result" data-id="area"> 很抱歉没有找到“'+key+'”相关结果!</div>';}$('.area-menus').html(areasHtml);}// 自定义下拉框:点击其他部分收起下拉事件document.addEventListener("click", (e) => {if ($(".dropdown-menus").is(":visible")) {$('.dropdown-menus').hide();$('.ec-input').removeClass('ec-input__open');}});
</script>
</html>

如何实现自定义下拉组件,select下拉框样式自定义,带搜索的select下拉框相关推荐

  1. html搜索框如何加下拉框,js实现带搜索功能的下拉框

    本文实例为大家分享了js实现带搜索功能的下拉框,供大家参考,具体内容如下 1.介绍 在实现下拉框的时候,如果用select+option可以在满足pc端的需求,但如果需应用到手机端,由于select的 ...

  2. 【技巧】带搜索的城市下拉

    [技巧]带搜索的城市下拉 <!doctype html> <html> <head> <meta http-equiv="Content-Type& ...

  3. vue自定义音频播放组件_易于创建Vue的自定义音频播放器组件

    vue自定义音频播放组件 音频更好 (vue-audio-better) Easy to create custom audio player components for Vue.js. 易于为Vu ...

  4. Android 几种弹框样式 自定义Dialog PopupWindow的使用

    1.弹框的波浪线是动态的 和小度弹框样式相似 用到PopWindow 和自定义View . 2.这个弹框是动态的 用于网络加载时候  用到自定义Dialog 3.这就是一简单通用的弹框样式 第一种弹框 ...

  5. 微信小程序自定义导航栏组件(完美适配所有手机),可自定义实现任何你想要的功能

    背景 在做小程序时,关于默认导航栏,我们遇到了以下的问题: Android.IOS 手机对于页面 title 的展示不一致,安卓 title 的显示不居中 页面的 title 只支持纯文本级别的样式控 ...

  6. html select 修改默认箭头样式,自定义select标签箭头样式

    select::-ms-expand{ display: none; }//ie样式清除 select{ appearance:none; -moz-appearance:none; -webkit- ...

  7. layui下拉选择框开启搜索功能后,文本框会将Nbsp显示出来的解决办法

    layui下拉选择框直接在select标签添加lay-search,即可开启搜索功能 <select id="selectCategory" lay-filter=" ...

  8. Vue(组件间通信:props、自定义事件、全局事件总线、消息订阅与发布)

    一.props props不仅可以实现父给子传递信息,还可以进行子给父传递信息 1.父给子传递信息: 父组件中给子组件实例传递信息 子组件利用props进行接收组件传递信息(接收方式有三种:数组.对象 ...

  9. UI组件库Form表单_数字类型验证之坑实现数字框

    目录 Input 输入框 实现数字框封装使用 项目需求 : 使用的饿了么组件库的 input 框 , 但是想要 实现用户只能输入 数字 的功能 , So 看到了数字类型的验证 (缺点 :不能阻止用户输 ...

最新文章

  1. linux下文件系统的启动过程
  2. 万字长文带你一览ICLR2020最新Transformers进展(下)
  3. thinkphp中表有前缀名的时候申明模板的方法
  4. 开箱即用Bumblebee独立部署搭建webapi网关详解
  5. php中双引号的区别,PHP中单引号和双引号的区别
  6. python sftp_python中实现sftp
  7. Linux下小型web服务器boa的使用
  8. 如何搭建python框架_从0到1告诉你搭建完整Python+requests接口自动化测试框架!
  9. 计算机网络习题集_主打选择填空
  10. K8S 还没用,K9S 又是什么鬼?
  11. 机器学习算法工程师面试考点汇总
  12. 华为重启交换机命令_华为交换机常用命令
  13. Java 实现局域网聊天室功能(私聊,群聊)
  14. 云栖大会马总演讲:《未来属于善于拥抱未来的人》
  15. ipv6如何测试服务器已经是ipv6协议,怎么测试域名是否支持ipv6
  16. 输入数独题目,程序输出数独的唯一解。保证所有已知数据的格式都是合法的,并且题目有唯一的解。
  17. SCPC :普普通通的DP(位运算)
  18. qt 频谱 音乐播放器
  19. 将两个ISO文件挂载至同一个虚拟光驱
  20. android google 登录登出接入

热门文章

  1. 那一年,我喜欢过的女孩
  2. FFmpeg命令行实现两路/多路视频拼接 合并 合成 同时播放
  3. 第四届汽车 ADAS 与自动驾驶论坛
  4. Robomaster基于传统算法的视觉识别教程
  5. 微信公众号接入第三方管理平台和创建微官网
  6. Vue cli3配置生产环境,开发环境,和测试环境
  7. Spring配置文件中关于约束配置详解
  8. 立方体盒子翻转特效图文展示素材PR视频模板
  9. AirPods的自动连接配对原理
  10. 技术动态 | ChatGPT 下的知识图谱审视:一次关于必然影响、未来方向的讨论实录与总结...