Innovative Full Page Tab Animation

Creative/innovative and responsive full page tab animation with animated content and background SVG animation using HTML, CSS and JS.




In this code snippet, we’ll guide you through creating visually appealing full-page tabs using HTML, CSS, and JavaScript. We’ll start by designing the list items, followed by crafting the content section, and then animating a dynamic background SVG shape using the Anime.js library.

Let’s begin with the list item design.

HTML markup of list items.

<!-- List items -->
<ul class="list">
  <li><a dd-tab="tab1" class="active" href="javascript:void(0);">Design</a></li>
  <li><a dd-tab="tab2" href="javascript:void(0);">Inspiration</a></li>
  <li><a dd-tab="tab3" href="javascript:void(0);">About</a></li>
  <li><a dd-tab="tab4" href="javascript:void(0);">Snippets</a></li>
</ul>

CSS(list item ul/li)

/* List items */
.list {
  display: flex;
  flex-direction: row;
  list-style: none;
  padding: 0;
  margin: 5rem 0;
  transition: all 0.75s cubic-bezier(0.65, 0.05, 0.36, 1);
}
.list li a {
  display: inline-block;
  font-family: var(--title-font);
  font-weight: var(--font-weight);
  font-size: calc(3rem + 2.5vw);
  text-align: center;
  text-decoration: none;
  margin: 1rem;
  -webkit-text-stroke-width: 1.25px;
  -webkit-text-stroke-color: var(--clr-black);
  -webkit-text-fill-color: transparent;
  background-repeat: no-repeat;
  background-clip: text;
  background-image: linear-gradient(
    125deg,
    var(--clr-black),
    var(--clr-black) 50%,
    transparent 50%
  );
  background-size: 0% 100%;
  -webkit-background-clip: text;
  color: transparent;
  transition: all 0.75s;
}
/* Selected/Active tab list item */
.list li a.active {
  background-size: 215% 100%;
}

Next, we will design the tabs and content section.

HTML Structure of Tabs

<div class="tabs">
  <!-- Tab 1 -->
  <div class="tab active" id="tab1">// content</div>
  <div class="tab" id="tab2">// content</div>
  . . .
</div>

CSS of the tabs

/* Tabs */
.tabs .tab {
  display: none;
  transition: transform 0.75s cubic-bezier(0.75, 0.6, 0.3, 1);
}
.tabs .tab.active {
  display: inherit;
}
.tabs .tab.active.animate {
  opacity: 0;
  transform-origin: left;
  transform: translateY(3rem);
}

SVG background shape design and animation

Now, let’s add a visually appealing SVG background shape and animate it. HTML MArkup

<!-- Background SVG(/animation) -->
<svg
  class="bg-blob"
  viewBox="0 0 85 100"
  fill="none"
  xmlns="http://www.w3.org/2000/svg"
>
  <path
    id="svg_path"
    class="blob-path"
    fill-rule="evenodd"
    clip-rule="evenodd"
    d="M32.4059 26.2721C44.6339 9.20485 18.7713 -4.80642 0 2.9239V88.3685C5.38695 97.509 11.5034 91.0179 13.4674 86.3814C33.3711 114.531 40.4022 94.3297 47.5567 84.3943C68.4108 106.317 69.4412 72.6374 58.9198 61.0461C118.885 91.3399 60.4852 -12.9197 32.4059 26.2721Z"
    fill="rgba(0, 0, 0, .5)"
  />
</svg>

CSS

.bg-blob {
  position: fixed;
  height: 100vh;
  left: -30vh;
  top: 0;
  z-index: -1;
}

JavaScript for Tabs and SVG Animation:

Then we apply the javascript to activate and change the content of the tabs dynamically and update the shape of SVG using Anime js

Javascript

// Body Background class list(change dynamically on click)
const bg = ["bg1", "bg2", "bg3", "bg4"];
// SVG path array list
// It is required to have the same number of attributes/values of every SVG paths.
const paths = [
  "M32.4059 26.2721C44.6339 9.20485 18.7713 -4.80642 0 2.9239V88.3685C5.38695 97.509 11.5034 91.0179 13.4674 86.3814C33.3711 114.531 40.4022 94.3297 47.5567 84.3943C68.4108 106.317 69.4412 72.6374 58.9198 61.0461C118.885 91.3399 60.4852 -12.9197 32.4059 26.2721Z",
  "M38.7343 28.916C53.3502 12.8808 14.7319 -19.9663 0 16.6749V87.2576C6.43894 95.8455 16.0974 97.0056 16.0974 85.3907C28.4478 112.978 56.8438 95.1265 56.8438 83.5237C87.3753 97.9451 98.0432 53.3173 63.4995 53.3173C103.817 44.577 72.297 -7.90594 38.7343 28.916Z",
  "M33.0166 24.1626C63.5462 17.9935 23.7262 5.48372 0 0V88.425C5.48847 97.8844 11.7202 91.1668 13.7212 86.3686C30.8726 112.69 41.1635 94.5942 48.4529 84.3122C84.8997 104.362 70.7498 72.1452 60.0301 60.1495C117.916 55.5227 60.7448 33.9305 33.0166 24.1626Z",
  "M32.1191 29.3137C44.2388 13.0652 53.899 -19.5838 0 16.9098V88.4311C5.33927 97.1331 32.1191 107.078 13.3482 86.5393C75.0441 116.638 52.6548 89.6794 52.6548 77.9223C108.213 77.9223 81.299 54.0394 52.6548 54.0394C80.0194 16.9098 59.9498 -7.99797 32.1191 29.3137Z",
];
// Get list item(ul)
const list = document.querySelector(".list");
// Position / Reposition list items
function positionList() {
  let active_item = document.querySelector(".list .active");
  let list_width = list.clientWidth;
  let active_item_width = active_item.offsetWidth;
  // Transform list(x direction)
  let tx = list_width / 2 - active_item.offsetLeft - active_item_width / 2;
  list.style.transform = "translateX(" + tx + "px)";
}
// event: List item click
let list_item = document.querySelectorAll(".list li a");
list_item.forEach((item, key) => {
  item.addEventListener("click", function () {
    // Activate list item
    activeListItem(item, key);
    // Toggle tab content
    toggleTabs(item, key);
  });
});
// Activate list item and animate the svg
function activeListItem(e, key) {
  body.className = bg[key];
  // Call anime lib function timline to animate the SVG
  let timeline = anime({
    duration: 1000,
    targets: ".bg-blob .blob-path",
    d: [
      {
        value: paths[key],
      },
    ],
    easing: "easeOutQuad",
  });

  list_item.forEach((item) => {
    item.classList.remove("active");
  });
  e.classList.add("active");
  // Reposition list
  positionList();
}
// Activate tab(content)
function toggleTabs(item, key) {
  let tab = item.attributes["dd-tab"].value;
  let tabs = document.querySelectorAll(".tabs .tab");
  tabs.forEach((tab) => {
    tab.classList.remove("active");
  });
  let active_tab = document.getElementById(tab);
  active_tab.classList.add("active", "animate");
  setTimeout(() => {
    active_tab.classList.remove("animate");
  }, 250);
}
// Initialize
function init() {
  positionList();
}
// call the function on window resize
window.onresize = positionList;
// call the function on load
window.onload = init;

Feel free to share the code snippets with others if you find them useful!