Progress bar

by htduy262

HTML

<script src="//code.jquery.com/jquery-3.3.1.slim.min.js"></script>
<link rel="stylesheet" href="//stackpath.bootstrapcdn.com/bootstrap/4.1.0/css/bootstrap.min.css">
<script src="//cdnjs.cloudflare.com/ajax/libs/popper.js/1.14.0/umd/popper.min.js"></script>
<script src="//stackpath.bootstrapcdn.com/bootstrap/4.1.0/js/bootstrap.min.js"></script>
<link rel="stylesheet" href="https://use.fontawesome.com/releases/v5.3.1/css/all.css">
<script src="https://cdnjs.cloudflare.com/ajax/libs/knockout/3.4.2/knockout-min.js"></script>
<script src="https://github.com/SteveSanderson/knockout-projections/blob/master/dist/knockout-projections.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/lodash.js/1.2.1/lodash.min.js"></script>
<script src="https://cdn.jsdelivr.net/npm/[email protected]/slick/slick.min.js"></script>
<link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/slick-carousel/1.9.0/slick.css">
<link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/slick-carousel/1.9.0/slick-theme.min.css">
<script src="https://cdnjs.cloudflare.com/ajax/libs/slick-carousel/1.9.0/slick-theme.min.css.map"></script>
<link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/slick-carousel/1.9.0/slick.min.css">
<!-- Dynamic -->
<div class="d-flex align-items-center justify-content-between">
  <div class="div-side"></div>
  <div class="progress align-items-center justify-content-between" data-bind="foreach: { data: items, as: 'item' }">
    <div class="step">
      <i class="top-icon fa fa-home" data-bind="css: { active: isActive }"></i>
      <div class="step-main" role="button" data-bind="attr: { id: item.name },
                      click: $parent.stepClick.bind($parent, item),
                      css: { 'first-type': isFirstOfType, 'last-type': isLastOfType,
                      'active': isActive, 'first': isFirstActive, 'last': isLastActive, 'only': isOnly }
                      ">
        <i class="step-icon far"...

SCSS

$background-color-lightyellow: lightyellow;

.max-lines-2 {
  overflow: hidden;
   text-overflow: ellipsis;
   display: -webkit-box;
   line-height: 16px;     /* fallback */
   max-height: 32px;      /* fallback */
   -webkit-line-clamp: 2; /* number of lines to show */
   -webkit-box-orient: vertical;
}

.progress{
  //width: 100%;
  min-width: 768px;
  min-height: 150px;
  background: $background-color-lightyellow;
  overflow-x: scroll;
}

.div-side{
  width: 20px;
  height: 100px;
  background: lightgreen;
}

.horizontal-line{
  height: 10px;
  width: 100%;
  //border-bottom: 10px solid red;
  border-top-left-radius: 60px;
  border-bottom-left-radius: 60px;
  border-top-right-radius: 60px;
  border-bottom-right-radius: 60px;
  padding-left: 10px;
  padding-right: 10px;
  background: red;
  position: absolute;
}

.step {
  width: 100%;
  text-align: center;
  //display: block;
  flex-direction: column;
  align-items: center;
}

.step-main {
  //width: 100%;
  //background-color: lightyellow;
  text-align: center;
  position: relative;
  display: flex;
  justify-content: center;
  list-style: none;
}

.step-main:before,
.step-main:after{
  content: "";
  //width: 500%;
  top: 50%;
  z-index: 1;
  border: 2px solid lightgrey;
  position: absolute;
  //-webkit-transition: width 2s, height 4s; /* For Safari 3.1 to 6.0 */
  //transition: width 2s, height 4s;
}

.step-main.active:before {
  content: "";
  //width: 500%;
  top: 50%;
  z-index: 2;
  border: 2px solid red;
  position: absolute;
  //-webkit-transition: width 2s, height 4s; /* For Safari 3.1 to 6.0 */
  //transition: width 2s, height 4s;
}

.step-main:before {
  left: 0;
  right: 50%;
}

.step-main:after {
  left: 50%;
  right: 0;
}

.step-main.active:before {
  left: 0;
  right: 50%;
}

.step-main.first-type:before {
  border: none !important;
}

.step-main.last-type:after {
  border: none !important;
}

.step-main.active.first:before {
  border: 2px solid lightgrey;
}

.step-main.active.last:after {
 ...

JavaScript

function myModel() {
  var that = this;
  that.items = ko.observableArray([{
      index: 0,
      name: "item1",
      isFirstOfType: ko.observable(true),
      isLastOfType: ko.observable(false),
      isActive: ko.observable(false),
      isFirstActive: ko.observable(false),
      isLastActive: ko.observable(false),
      isOnly: ko.observable(false)
    },
    {
      index: 1,
      name: "item2",
      isFirstOfType: ko.observable(false),
      isLastOfType: ko.observable(false),
      isActive: ko.observable(true),
      isFirstActive: ko.observable(true),
      isLastActive: ko.observable(false),
      isOnly: ko.observable(false)
    },
    {
      index: 2,
      name: "item3",
      isFirstOfType: ko.observable(false),
      isLastOfType: ko.observable(false),
      isActive: ko.observable(true),
      isFirstActive: ko.observable(false),
      isLastActive: ko.observable(false),
      isOnly: ko.observable(false)
    },
    {
      index: 3,
      name: "item4",
      isFirstOfType: ko.observable(false),
      isLastOfType: ko.observable(false),
      isActive: ko.observable(true),
      isFirstActive: ko.observable(false),
      isLastActive: ko.observable(true),
      isOnly: ko.observable(false)
    },
    {
      index: 4,
      name: "item5",
      isFirstOfType: ko.observable(false),
      isLastOfType: ko.observable(false),
      isActive: ko.observable(false),
      isFirstActive: ko.observable(false),
      isLastActive: ko.observable(false),
      isOnly: ko.observable(false)
    },
    {
      index: 5,
      name: "item6",
      isFirstOfType: ko.observable(false),
      isLastOfType: ko.observable(true),
      isActive: ko.observable(false),
      isFirstActive: ko.observable(false),
      isLastActive: ko.observable(false),
      isOnly: ko.observable(false)
    }
  ]);
  that.itemsLength = ko.computed(() => {
    return that.items().length;
  });
  that.activeItems = ko.computed(() => {
    var activeItems = that.items().filter((x) =>...