效果展示
功能描述
如效果所见,它可以实现一般的select功能的同时,还附加搜索功能,输入关键词即可快捷搜索。
为了使其可以应用于实际,我还给他同步写了一个普通select,当此自定义select框的值修改时,普通select也跟着修改,可以满足表单提交的需求。
接下来听听我的思路吧!
思路解析
- 普通select写出后隐藏,做表单提交之用
- 用div模仿select的功能写出一个复制体
- 给div的value-body限制高度使其自动出现滚动条
- 用input的oninput事件实时搜索条件,不符的值隐藏
代码参考
-
准备图片三张
-
代码
本人粗浅,代码出现不兼容状况实属常事,不过本人已测试火狐、Chrome、QQ浏览器最新版本兼容其功能。
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Document</title>
<style type="text/css">
*{
padding: 0;
margin: 0;
}
body{
width: 100vw;
height: calc(100vh - 20px);
}
div.select select{
display: none;
}
div.select-box{
width: 200px;
margin: 20px 20px;
}
div.select-head{
position: relative;
height: 30px;
width: 100%;
display: flex;
border: solid 1px #000;
align-items: center;
cursor: pointer;
}
div.select-head span{
font-size: 16px;
margin-left: 5px;
color: #AAA;
}
div.select-head span.fill{
color: #000;
}
div.select-head i{
position: absolute;
height: 16px;
width: 16px;
right: 5px;
background-image: url(./arrow.png);
background-size: 16px auto;
}
div.select-body{
display: none;
width: 100%;
border: solid 1px #000;
border-top: none;
}
div.search-input{
position: relative;
height: 40px;
}
div.search-input input{
height: 30px;
width: 150px;
margin: 5px 8px;
text-indent: 10px;
padding-right: 30px;
}
div.search-input i{
position: absolute;
display: block;
height: 20px;
width: 20px;
top: 12px;
right: 15px;
background-image: url(./search-normal.png);
background-size: 20px 20px;
cursor: pointer;
}
div.search-input i:hover{
background-image: url(./search-active.png);
}
div.value-body{
max-height: 150px;
overflow: auto;
}
div.value-body li{
display: flex;
height: 24px;
padding: 5px 5px;
font-size: 14px;
align-items: center;
cursor: pointer;
}
div.value-body li:hover,li.active{
background-color: #F5F6FA;
}
div.value-body li.none,div.none{
display: none;
}
div.value-body div{
text-align: center;
height: 30px;
line-height: 30px;
color: #AAA;
}
</style>
<script type="text/javascript">
window.onload = function () {
//清空select的value
document.querySelector('div.select>select').value = ''
/**
* 点击自定义的select框开启或收回选择框
*/
document.querySelector('div.select-head').onclick = function () {
//清空输入框内容
document.querySelector('div.search-input>input').value = ''
document.querySelectorAll('div.value-body>li').forEach( function(element, index) {
if (element.classList.contains('active')) {
element.classList = 'active'
}else {
element.classList = ''
}
});
document.querySelector('div.value-body>div').classList = 'none'
var select_body = document.querySelector('div.select-body')
if (select_body.style.display == 'block')
select_body.style.display = 'none'
else
select_body.style.display = 'block'
};
/**
* 点击空白处关闭select框
*/
document.onclick = function (argument) {
if(!argument.target.classList.contains('s')){
var select_body = document.querySelector('div.select-body')
if (select_body.style.display == 'block')
select_body.style.display = 'none'
}
}
/**
* 自定义的select的选值功能
*/
document.querySelectorAll('div.value-body>li').forEach( function(element, index) {
element.onclick = function () {
//初始化下样式
document.querySelectorAll('div.value-body>li').forEach( function(element, index) {
element.classList = ''
});
element.classList = 'active'
//更新select框的value和自定义的select框的value
var data_value = element.getAttribute('data-value')
var select_head_span = document.querySelector('div.select-head>span')
document.querySelector('div.select>select').value = data_value
select_head_span.innerHTML = data_value
if(!select_head_span.classList.contains('fill'))
select_head_span.classList = 'fill'
//关闭select-body
document.querySelector('div.select-body').style.display = 'none'
}
});
/**
* 搜素功能实现
*/
document.querySelector('div.search-input>input').oninput = function () {
var input_value = document.querySelector('div.search-input>input').value
if(input_value == '') {
document.querySelectorAll('div.value-body>li').forEach( function(element, index) {
if (element.classList.contains('active')) {
element.classList = 'active'
}else {
element.classList = ''
}
});
}else{
document.querySelectorAll('div.value-body>li').forEach( function(element, index) {
if(element.getAttribute('data-value').indexOf(input_value) == -1){
if (element.classList.contains('active')) {
element.classList += ' none'
}else {
element.classList = 'none'
}
}else {
if(element.classList.contains('none')) {
document.querySelectorAll('div.value-body>li').forEach( function(element, index) {
if (element.classList.contains('active')) {
element.classList = 'active'
}else {
element.classList = ''
}
});
}
}
});
}
//记一下结果数量
var length = 0
document.querySelectorAll('div.value-body>li').forEach( function(element, index) {
if (!element.classList.contains('none')) length++
});
if (length == 0) {
document.querySelector('div.value-body>div').classList = ''
}else{
document.querySelector('div.value-body>div').classList = 'none'
}
}
};
</script>
</head>
<body>
<div class="select">
<select name="select-name">
<option value="" disabled="true">请选择</option>
<option value="选择1">选择1</option>
<option value="选择2">选择2</option>
<option value="选择3">选择3</option>
<option value="选择4">选择4</option>
<option value="选择5">选择5</option>
<option value="选择6">选择6</option>
<option value="选择7">选择7</option>
<option value="选择8">选择8</option>
<option value="选择9">选择9</option>
<option value="选择10">选择10</option>
</select>
<div class="s select-box">
<div class="s select-head">
<span class="s">请选择</span>
<i class="s"></i>
</div>
<div class="s select-body">
<div class="s search-input">
<input class="s" type="text" placeholder="搜索">
<i class="s"></i>
</div>
<div class="s value-body">
<li data-value="选择1">选择1</li>
<li data-value="选择2">选择2</li>
<li data-value="选择3">选择3</li>
<li data-value="选择4">选择4</li>
<li data-value="选择5">选择5</li>
<li data-value="选择6">选择6</li>
<li data-value="选择7">选择7</li>
<li data-value="选择8">选择8</li>
<li data-value="选择9">选择9</li>
<li data-value="选择10">选择10</li>
<div class="none">暂无匹配选项</div>
</div>
</div>
</div>
</div>
</body>
</html>