chenyingying0

效果图

 

 注:值是根据原生select中的值来动态获取并进行分类

index.html

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>index</title>
  <link rel="stylesheet" href="style.css">
</head>
<body>
  <div class="container">
      <div id="wrap">
      <div class="div1">
        <div class="title">自定义select</div>

        <div class="select">
          <select id="select-name">
            <option value="" disabled="true">请选择</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">

              </div>
            </div>
          </div>
        </div>

      </div>
      <div class="outdiv">
        <p id="out"></p>
      </div>

    
      <div class="div2">
        <div class="title">原生select</div>
        <select>
          <option value="1" type="构建工具">Babel</option>
          <option value="2" type="构建工具">Webpack</option>
          <option value="3" type="构建工具">Rollup</option>
          <option value="4" type="前端框架">Vue</option>
          <option value="5" type="前端框架">Angular</option>
          <option value="6" type="前端框架">React</option>
          <option value="7" type="前端框架">Nerv</option>
        </select>
      </div>
    </div>
  </div>
  <script src="index.js"></script>
</body>
</html>

style.css

.container{
    width:100%;
    height:100vh;
    text-align: center;
}
#wrap{
    height:170px;
    position: relative;
    top:50%;
    margin-top:-85px;
    text-align: center;
}
.div1{
    text-align: center;
}
.div2{
    text-align: center;
}
.title{
    color: rgb(75,151,251);
    margin-bottom: 10px;
}
div.select{
    width: 200px;
    position: relative;
    left: 50%;
    margin-left: -100px;
}
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 rgb(75,151,251);
    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: 30px;
    width: 30px;
    right: -1px;
    background: url(./arrow.png) center center no-repeat;
    background-size: 30px auto;
}

div.select-body{
    display: none;
    width: 100%;
    border: solid 1px rgb(75,151,251);
    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-y: auto;
    text-align: left;
    overflow-x: hidden;
}

div.value-body li{
    display: flex;
    height: 24px;
    padding: 5px 5px 5px 30px;
    font-size: 14px;
    align-items: center;
    cursor: pointer;
    position: relative;
}

div.value-body span{
    display: block;
    font-weight: bold;
    font-size: 16px;
    margin:10px;
}

div.value-body span+li{
    margin-top: 14px;
}

div.value-body li:hover,li.active{
    background-color: #F5F6FA;
}

div.value-body li.active{
    background-color: rgb(75,151,251);
    color:white;
}

div.value-body li.none,div.none{
    display: none;
}

div.value-body div{
    text-align: center;
    height: 30px;
    line-height: 30px;
    color: #AAA;
}

index.js

    window.onload = function () {

      //初始化生成DOM元素
      function init(){
        var types=[];
        // 根据原生的select中的每一项提供的类型和值,使用脚本获取,然后进行分类重新显示
        var options=document.querySelectorAll(\'.div2 option\');
        var templates=\'\';//插入到select的总模板
        var se_templates=\'\';//插入到div的总模板
        var tem=\'\';//select 某个分类的总模板
        var se_tem=\'\';//div 某个分类的总模板

        options.forEach( function(element, index) {
            var type=element.getAttribute(\'type\');

            //创建分类
            if (types.indexOf(type)==-1){
              types.push(type)

              tem=`<span>`+type+`</span>`;
              se_tem=`<span>`+type+`</span>`;

              var lis=\'\';//select 某个分类下的项目模板
              var se_lis=\'\';//div 某个分类下的项目模板

              //根据分类创建选项
              options.forEach( function(ele) {
                var value=ele.getAttribute(\'value\');
                var text=ele.innerText;
                if(ele.getAttribute(\'type\')==type){
                  lis+=`<li data-value="`+text+`">`+text+`</li>`;
                  se_lis+=`<option value="`+text+`">`+text+`</option>`;
                }             
              });
              tem+=lis;
              se_tem+=se_lis;
              templates+=tem; 
              se_templates+=se_tem; 
            }
                        
          });
        
        document.querySelector(\'.value-body\').innerHTML=templates;
        document.querySelector(\'#select-name\').innerHTML=se_templates;       
      }
      init();

      var out=document.querySelector(\'#out\');
      var last_out=\'未选择--undefined\';


      //清空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
          out.innerHTML= \'之前的值是:\'+last_out+\'<br>改变后的值是:\'+data_value
          last_out=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\').toLowerCase().indexOf(input_value.toLowerCase()) == -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>li\').classList = \'\'
        }else{
          document.querySelector(\'div.value-body>li\').classList = \'none\'
        }
      }


    };

分类:

技术点:

相关文章: