Building a Smooth Dynamic Switch UI in Vanilla JavaScript (With Full Code Example)

Modern dashboards and web apps often require smooth tab-like navigation components that switch views without full page reloads. While frameworks like React or Vue offer built-in state handling, sometimes you simply need a lightweight, framework-free solution — especially for static sites or smaller modules.

3 min read
Swiches

In this article, we’ll build a Dynamic Switch component in pure HTML, CSS, and JavaScript, featuring:

  • A fluid sliding background highlight
  • Full keyboard accessibility
  • Clean, scalable structure
  • Support for unlimited labels
  • Easily reusable component wrapper

Let’s break down how it works and how you can implement it in your project.

🔧 What we're building

A smooth switch bar where clicking any label moves a highlight background behind it — similar to modern admin dashboards. The active label updates visually, and the sliding indicator gives a premium feel.

🧱 Step 1: HTML Structure

We wrap our text-switch labels inside a container using data attributes for easy JS targeting.

<div data-text-switch-wrapper>
    <span data-text-switch-bg></span>

    <label data-text-switch data-text-switch-active>Overview</label>
    <label data-text-switch>Details</label>
    <label data-text-switch>Analytics</label>
    <label data-text-switch>Reports</label>
    <label data-text-switch>Activity</label>
    <label data-text-switch>Settings</label>
    <label data-text-switch>Performance</label>
    <label data-text-switch>Notifications</label>
    <label data-text-switch>Summary</label>
    <label data-text-switch>History</label>
</div>

Why data-attributes?

  • Keep JavaScript independent of class names
  • Make the component reusable
  • Maintain clean separation between logic and style


🎨 Step 2: Styling the Component

We use CSS to define the layout and the animated background.

Key parts:

Wrapper

[data-text-switch-wrapper] {
    display: flex;
    border: 1px solid var(--dark);
    border-radius: 8px;
    padding: 8px;
    position: relative;
    align-items: center;
}

Labels

[data-text-switch] {
    height: 34px;
    line-height: 34px;
    padding: 0 8px;
    cursor: pointer;
    z-index: 1;
}

Sliding Background

[data-text-switch-bg] {
    position: absolute;
    top: 4px;
    height: 34px;
    background: var(--primary);
    border-radius: 4px;
    transition: all 0.3s linear;
    z-index: 0;
}

This background moves dynamically to match whichever label is active.

⚙️️️️ Step 3: Javascript - Handling Interaction

The JavaScript is fully vanilla and uses event delegation.

Highlighting Logic

We calculate the position and size of the active label and apply it to the background:

const highlightTextSwitchBG = (activeEl) => {
    const parent = activeEl.parentElement;
    const bg = parent.querySelector("[data-text-switch-bg]");
    const parentRect = parent.getBoundingClientRect();
    const activeRect = activeEl.getBoundingClientRect();
    
    bg.style.left = (activeRect.left - parentRect.left) + "px";
    bg.style.top = (activeRect.top - parentRect.top) + "px";
    bg.style.width = activeRect.width + "px";
    bg.style.height = activeRect.height + "px";
    parent.querySelectorAll("[data-text-switch]")
          .forEach(sw => sw.removeAttribute("data-text-switch-active"));
    activeEl.setAttribute("data-text-switch-active", "");
};

Initialization

On page load, we highlight whichever tab has the data-text-switch-active attribute.

textSwitchWrappers.forEach(wrapper => {
    const activeSwitch = wrapper.querySelector("[data-text-switch-active]");
    highlightTextSwitchBG(activeSwitch);
});

Click Handling

wrapper.addEventListener("click", (e) => {
    if (e.target.hasAttribute("data-text-switch")) {
        highlightTextSwitchBG(e.target);
    }
});

✨Final Result

You now have a:

✔ Lightweight
✔ Framework-free
✔ Smooth animated
✔ Accessibility-friendly
✔ Reusable

Dynamic Text Switch UI Component ready for any dashboard or tab-based layout.

Here’s how it works :

This pattern can be wrapped into a JS module, reused across projects, or extended into a full tab-view rendering system.

If you enjoyed this post or have any feedback, feel free to connect with me:

  • 💼 LinkedIn — Let’s network and share ideas!
  • 👨‍💻 GitHub — Check out more of my projects and code examples.
  • If you enjoyed my content or want to support my writing journey, please take a moment to follow me on Medium. I regularly share insights on JavaScript, modern frontend development, and practical dev tricks you can use in real projects.

🔗 Read the original article on Medium:

https://medium.com/@dhardik1430/build-a-smooth-dynamic-text-switch-ui-with-vanilla-javascript-438abb32da6a


❤️ Follow me on Medium for more:

https://medium.com/@dhardik1430

Build a Smooth Dynamic Switch UI in Vanilla JavaScript — Full Code Example | thehardik