原生JS模拟Bootstrap中的折叠(Collapse)插件

 

来源:https://github.com/HelloLeeChan/Exercise-Demo/tree/master/Collapse%20By%20Native%20JS

 

<!doctype html>
<html>
<head>
<meta charset="UTF-8">
<title>Collapse By Native JS</title>
<style>
* {
  box-sizing: border-box;
  -webkit-box-sizing: border-box;
}

body {
  font-family: "Helvetica Neue", Helvetica, Arial, sans-serif;
  font-size: 14px;
  line-height: 1.42857143;
  color: #333;
  background-color: #fff;
  margin: 2px;
}

a {
  text-decoration: underline;
  color: #666666;
}

a:hover {
  text-decoration: none;
}

.collapseDiv {
  color: #333;
  border-radius: 4px;
  background-color: #f5f5f5;
  border: 1px solid transparent;
  border-color: #ddd;
  box-shadow: 0 1px 1px rgba(0, 0, 0, .05);
  margin-top: 5px;
  margin-bottom: 0;
}

.collapseDiv h3 {
  font-size: 14px;
  font-weight: bold;
  color: #333;
  border-color: #ddd;
  padding-top: 5px;
  padding-right: 15px;
  padding-bottom: 5px;
  padding-left: 15px;
  background-color: #f5f5f5;
  margin: 0;
}

.collapse_body {
  background-color: #fff;
  position: relative;
  height: 0;
  overflow: hidden;
  -webkit-transition-timing-function: ease;
  -o-transition-timing-function: ease;
  transition-timing-function: ease;
  -webkit-transition-duration: .35s;
  -o-transition-duration: .35s;
  transition-duration: .35s;
  -webkit-transition-property: height, visibility;
  -o-transition-property: height, visibility;
  transition-property: height, visibility
}

.collapse_content {
  border-top: 1px solid #ddd;
  background-color: #fff;
  padding: 15px;
}
</style>
</head>

<body>
<div class="collapseDiv"> 
	  <h3>Title1</h3> 	  
	 <div class="collapse_body">
        <div class="collapse_content">
             content1<br />content1<br />content1<br />content1<br />
            </div>
       </div>
	</div>

	<div class="collapseDiv"> 
	  <h3>Title2</h3> 
	 <div class="collapse_body">
       <div class="collapse_content">
            content2<br />content2<br />content2<br />content2<br />
            </div>
       </div>
	</div>

	<div class="collapseDiv"> 
	  <h3>Title3</h3> 
	 <div class="collapse_body">
       <div class="collapse_content">
           content3<br />content3<br />content3<br />content3
           </div>
       </div>
	</div>

	<div class="collapseDiv"> 
	  <h3>Title4</h3> 
	 <div class="collapse_body">
         <div class="collapse_content">
          content4<br />content4<br />content4<br />content4<br />content4<br />
           </div>
       </div>
	</div>

</body>
<script>

//接受三个参数,分别是折叠菜单的外包div名称,是否关闭之前的折叠,默认开启的折叠内容
        function Collapse(className,close_prev,default_open){        
        this._elements = [];
        this._className = String(className);
        this._previous = Boolean(close_prev)
        this._default = typeof(default_open)==="number" ? default_open: -1
        this.getCurrent  
        this.init();
    }

    //收集所有折叠菜单的div
    Collapse.prototype.collectElementbyClass = function(){
        this._elements = [];
        var allelements = document.getElementsByTagName("div");

        for(var i=0;i<allelements.length;i++){
            var collapse_div = allelements[i];
            if (typeof collapse_div.className === "string" && collapse_div.className === this._className){

                var h3s = collapse_div.getElementsByTagName("h3");
                var collapse_body = collapse_div.getElementsByClassName("collapse_body");
                if(h3s.length === 1 && collapse_body.length === 1){
                    h3s[0].style.cursor = "pointer";    
                    
                    if(this._default === this._elements.length){
                        collapse_body[0].style.visibility = "visible";
                      collapse_body[0].style.height = collapse_body[0].scrollHeight+"px"
                    }else{
                        collapse_body[0].style.height = "0px";
                      collapse_body[0].style.visibility = "hidden";    
                    }
                    this._elements[this._elements.length] = collapse_div;
                }                
            }
        }
    }
    Collapse.prototype.open = function(elm){
        elm.style.visibility = "visible";
        elm.style.height = elm.scrollHeight + "px"
        
    }
    Collapse.prototype.close = function(elm){
      elm.style.height = "0px";
      elm.style.visibility = "hidden";
    }
    Collapse.prototype.isOpen = function(elm){    
    
      return elm.style.visibility === "visible"
    }
    
    Collapse.prototype.getCurrent = function(header){
        var cur ;
        if(window.addEventListener){
            cur = header.parentNode
        }else{
            cur = header.parentElement
        }
        return cur.getElementsByClassName("collapse_body")[0]
        }
    
    Collapse.prototype.toggleDisplay = function(header){
        
        var cur = this.getCurrent(header)
        //console.log(cur)
        if(this.isOpen(cur)){
            this.close(cur);
        }else{
            this.open(cur);
        }        
        if(this._previous){
            for(var i=0;i<this._elements.length;i++){
                if(this._elements[i] !== (cur.parentNode||cur.parentElement)){                
                    var collapse_body = this._elements[i].getElementsByClassName("collapse_body");
                    collapse_body[0].style.height = "0px";
                    collapse_body[0].style.visibility = "hidden";
                            
                }
            }
        }
    }    
    
    Collapse.prototype.init = function(){        
        var instance = this;
        this.collectElementbyClass();
        if(this._elements.length === 0){
            return;
        }
        
        for(var i=0;i<this._elements.length;i++){
            var h3s = this._elements[i].getElementsByTagName("h3");            
            if(window.addEventListener){
                h3s[0].addEventListener("click",function(){ instance.toggleDisplay(this);},false); 
            }else{
                h3s[0].onclick = function(){instance.toggleDisplay(this);}
            }
        }
    }
    
//传参
 var myCollapse = new Collapse("collapseDiv",true);
 
</script>
</html>