<ul class="filter mb-30">
    <li class="filter__btn" data-target="all">ALL</li>
    <li class="filter__btn" data-target="red">RED</li>
    <li class="filter__btn" data-target="blue">BLUE</li>
    <li class="filter__btn" data-target="yellow">YELLOW</li>
    <li class="filter__btn" data-target="green">GREEN</li>
</ul>
<ul class="filter__list">
    <li class="filter__item red">item01</li>
    <li class="filter__item blue">item02</li>
    <li class="filter__item red">item03</li>
    <li class="filter__item blue">item04</li>
    <li class="filter__item yellow">item05</li>
    <li class="filter__item green">item06</li>
    <li class="filter__item yellow">item07</li>
    <li class="filter__item green">item08</li>
    <li class="filter__item red">item09</li>
    <li class="filter__item yellow">item10</li>
    <li class="filter__item green">item11</li>
    <li class="filter__item blue">item12</li>
    <li class="filter__item blue">item13</li>
    <li class="filter__item yellow">item14</li>
    <li class="filter__item red">item15</li>
    <li class="filter__item green">item16</li>
</ul>
  • Content:
    .filter > li {
      display: inline-block;
      padding: 8px 12px;
      margin-right: 12px;
      background: #333;
      color: #fff;
      border-radius: 8px;
      cursor: pointer;
    }
    
    .filter__list {
      display: flex;
      flex-wrap: wrap;
      transition: opacity 0.3s;
    }
    
    .filter__item {
      display: flex;
      width: 80px;
      height: 80px;
      line-height: 80px;
      margin: 0 12px 12px 0;
      color: #fff;
      align-items: center;
      justify-content: center;
    }
    
    .filter__item.red {
      background: red;
    }
    
    .filter__item.blue {
      background: blue;
    }
    
    .filter__item.yellow {
      background: yellow;
    }
    
    .filter__item.green {
      background: green;
    }
    
  • URL: /components/raw/filter/filter.css
  • Filesystem Path: src\components\09-filter\filter.css
  • Size: 644 Bytes
  • Content:
    .filter {
      & > li {
        display: inline-block;
        padding: $space_sm $space_md;
        margin-right: $space_md;
        background: $color_main;
        color: $color_opposite;
        border-radius: $radius_md;
        cursor: pointer;
      }
      &__list {
        display: flex;
        flex-wrap: wrap;
        transition: opacity $speed_fast;
      }
      &__item {
        display: flex;
        width: 80px;
        height: 80px;
        line-height: 80px;
        margin: 0 $space_md $space_md 0;
        color: $color_opposite;
        align-items: center;
        justify-content: center;
        &.red {
          background: red;
        }
        &.blue {
          background: blue;
        }
        &.yellow {
          background: yellow;
        }
        &.green {
          background: green;
        }
      }
    }
    
  • URL: /components/raw/filter/filter.scss
  • Filesystem Path: src\components\09-filter\filter.scss
  • Size: 745 Bytes
  • Content:
    (function() {
      const filterBtns = document.querySelectorAll('.filter__btn');
      const filterList = document.querySelector('.filter__list');
      if(!filterList) {return;}
      const filterItems = document.querySelectorAll('.filter__item');
      let filterFlag = false;
      let currentFilter;
      transitionSet();
      filterBtns.forEach(btn => {
        btn.addEventListener('click', () => {
          filterFlag = true;
          currentFilter = btn.dataset.target;
          hideItems();
        });
      });
    
      function itemFilter() {
        filterItems.forEach(item => {
          item.style.display = '';
          // 現在のフィルターと一致しない要素を非表示にする
          if(!item.classList.contains(currentFilter) && currentFilter != 'all') {
            item.style.display = 'none';
          }
        });
        filterFlag = false;
        showItems();
      }
    
      function showItems() {
        filterList.style.opacity = 1;
      }
    
      function hideItems() {
        filterList.style.opacity = 0;
      }
    
      function transitionSet() {
        // ※アイテム要素全体のopacityを変化させて表示・非表示を切り替えることで、transitionendの対象を一つにできる
        filterList.addEventListener('transitionend', () => {
          if(filterFlag) {
            itemFilter();
          }
        })
      }
    }());
    
  • URL: /components/raw/filter/filter.js
  • Filesystem Path: src\components\09-filter\filter.js
  • Size: 1.3 KB