Ribbon menu

by lukindo mbuli

HTML

<h1>JavaScript ribbon animation</h1>

<img src="http://www.gaea21.org/site-ges/wp-content/themes/theme-ges/assets/images/ges.png" / style="max-width:160px">
<div class="back-ribbon">
  <div id="ribbon-part-1"></div>
</div>
<div class="front-ribbon">
  <div id="ribbon-part-2"></div>
</div>
<div class="back-ribbon">
  <div id="ribbon-part-3"></div>
</div>
<div class="front-ribbon">
  <div id="ribbon-part-4"></div>
</div>

<svg id="end-ribbon">
  <path d="M-6 17 L35 24 L24 10 Z" />
</svg>

<br>
<br>
<br>
<button onclick="move()">Click Me</button>

CSS

* {
  box-sizing: border-box;
}

.front-ribbon {
  position: relative;
  height: 23px;
  width: 160px;
  z-index: 1;
  transform: skewY(-11deg);
}

.back-ribbon {
  position: relative;
  height: 23px;
  width: 160px;
  transform: skewY(4.7deg);
  z-index: -1;
}

#ribbon-part-1 {
  background-color: rgb(70, 125, 76);
  height: 23px;
  width: 0%;
}

#ribbon-part-2 {
  background-color: rgb(89, 166, 101);
  height: 23px;
  width: 0%;
}


/*Including the code below will allow for a reverse progressive bar*/

.front-ribbon #ribbon-part-2 {
  display: block;
  float: right;
}

#ribbon-part-3 {
  background-color: rgb(70, 125, 76);
  height: 23px;
  width: 0%;
}

#ribbon-part-4 {
  background-color: rgb(89, 166, 101);
  height: 23px;
  width: 0%;
}


/*Including the code below will allow for a reverse progressive bar*/

.front-ribbon #ribbon-part-4 {
  display: block;
  float: right;
}

#end-ribbon {
  fill: rgb(70, 125, 76);
  width: 0%;
}

img {
  position: relative;
  top: 27px;
  z-index: 1;
}

JavaScript

function prepare(elems, width) {
    var width = 0;
    var elem = elems.shift();
    return function frame() {
      if (width >= 100) {
        elem = elems.shift();
        if (!elem) return;
        width = 0;
      } else {
        width += 5;
        elem.style.width = width + '%';
      };
      setTimeout(frame, 5);
    }
  }

  function move() {
    var elements = ['ribbon-part-1', 'ribbon-part-2', 'ribbon-part-3', 'ribbon-part-4', 'end-ribbon'].map(function(id) {
      return document.getElementById(id);
    });
    setTimeout(prepare(elements), 300);
  }