Component

Segmented Tabs

iOS-style segmented control with a sliding indicator that animates between segments. Used for switching time ranges and compact view modes.

  • Component
  • Tailwind
  • HTML
  • MIT

What it does

Capabilities

  • Sliding indicator
  • Smooth animation
  • Compact control
  • Arrow-key navigation
  • Resize-aware

Preview

Live component

Interactive preview
Open preview
9:41 100%
devsnips.site/library/tailwind/components/tabs/segmented-tabs/
fluid · no fixed width 100%
No dependencies Production-ready

Install

Add to your project

terminal
npx devsnips add Tailwind/Components/Tabs/segmented-tabs
registry path: Tailwind/Components/Tabs/segmented-tabs

Source

Implementation

code.html
<div class="w-full max-w-md">
  <div role="tablist" aria-label="View mode" class="relative inline-flex items-center gap-1 p-1 bg-gray-100 rounded-xl">
    <span class="seg-indicator absolute top-1 bottom-1 left-1 w-[calc(33.333%-0.25rem)] bg-white rounded-lg shadow-sm transition-transform duration-300 ease-out" aria-hidden="true"></span>
    <button role="tab" id="gtab-day" aria-selected="true" aria-controls="gpanel-day" tabindex="0"
      class="relative z-10 flex-1 px-4 py-1.5 text-sm font-medium text-gray-900 transition-colors focus:outline-none focus-visible:ring-2 focus-visible:ring-blue-500 rounded-lg">
      Day
    </button>
    <button role="tab" id="gtab-week" aria-selected="false" aria-controls="gpanel-week" tabindex="-1"
      class="relative z-10 flex-1 px-4 py-1.5 text-sm font-medium text-gray-500 hover:text-gray-800 transition-colors focus:outline-none focus-visible:ring-2 focus-visible:ring-blue-500 rounded-lg">
      Week
    </button>
    <button role="tab" id="gtab-month" aria-selected="false" aria-controls="gpanel-month" tabindex="-1"
      class="relative z-10 flex-1 px-4 py-1.5 text-sm font-medium text-gray-500 hover:text-gray-800 transition-colors focus:outline-none focus-visible:ring-2 focus-visible:ring-blue-500 rounded-lg">
      Month
    </button>
  </div>

  <div class="mt-5">
    <div role="tabpanel" id="gpanel-day" aria-labelledby="gtab-day" tabindex="0" class="rounded-xl border border-gray-200 p-4 focus:outline-none">
      <p class="text-xs font-medium text-gray-500">Today, Aug 4</p>
      <p class="mt-1 text-lg font-semibold text-gray-900">2h 14m focused</p>
      <div class="mt-3 flex h-2 rounded-full overflow-hidden bg-gray-100">
        <div class="bg-blue-500" style="width:42%"></div><div class="bg-blue-300" style="width:28%"></div><div class="bg-gray-300" style="width:30%"></div>
      </div>
    </div>
    <div role="tabpanel" id="gpanel-week" aria-labelledby="gtab-week" tabindex="0" class="hidden rounded-xl border border-gray-200 p-4 focus:outline-none">
      <p class="text-xs font-medium text-gray-500">This week</p>
      <p class="mt-1 text-lg font-semibold text-gray-900">14h 02m focused</p>
      <div class="mt-3 flex items-end gap-1.5 h-16">
        <div class="flex-1 bg-blue-500 rounded-t" style="height:60%"></div><div class="flex-1 bg-blue-500 rounded-t" style="height:80%"></div><div class="flex-1 bg-blue-500 rounded-t" style="height:45%"></div><div class="flex-1 bg-blue-500 rounded-t" style="height:70%"></div><div class="flex-1 bg-blue-500 rounded-t" style="height:90%"></div><div class="flex-1 bg-blue-400 rounded-t" style="height:55%"></div><div class="flex-1 bg-blue-400 rounded-t" style="height:40%"></div>
      </div>
    </div>
    <div role="tabpanel" id="gpanel-month" aria-labelledby="gtab-month" tabindex="0" class="hidden rounded-xl border border-gray-200 p-4 focus:outline-none">
      <p class="text-xs font-medium text-gray-500">August</p>
      <p class="mt-1 text-lg font-semibold text-gray-900">62h 30m focused</p>
      <p class="mt-2 text-xs text-emerald-600 font-medium">▲ 18% vs last month</p>
    </div>
  </div>
</div>

<script>
  (function () {
    var list = document.querySelector('[aria-label="View mode"]');
    if (!list) return;
    var tabs = Array.prototype.slice.call(list.querySelectorAll('[role="tab"]'));
    var panels = tabs.map(function (t) { return document.getElementById(t.getAttribute('aria-controls')); });
    var indicator = list.querySelector('.seg-indicator');
    function moveIndicator(tab) {
      if (!indicator) return;
      var pad = 4;
      indicator.style.left = (tab.offsetLeft + pad) + 'px';
      indicator.style.width = (tab.offsetWidth - pad * 2) + 'px';
      indicator.style.top = pad + 'px';
      indicator.style.height = (list.offsetHeight - pad * 2) + 'px';
    }
    function activate(tab) {
      tabs.forEach(function (t) {
        var s = t === tab;
        t.setAttribute('aria-selected', s); t.tabIndex = s ? 0 : -1;
        t.classList.toggle('text-gray-900', s); t.classList.toggle('text-gray-500', !s);
      });
      moveIndicator(tab);
      panels.forEach(function (p) { if (p) p.classList.add('hidden'); });
      var panel = document.getElementById(tab.getAttribute('aria-controls'));
      if (panel) panel.classList.remove('hidden');
    }
    tabs.forEach(function (tab, i) {
      tab.addEventListener('click', function () { activate(tab); });
      tab.addEventListener('keydown', function (e) {
        var idx = null;
        if (e.key === 'ArrowRight') idx = (i + 1) % tabs.length;
        if (e.key === 'ArrowLeft') idx = (i - 1 + tabs.length) % tabs.length;
        if (idx !== null) { e.preventDefault(); tabs[idx].focus(); activate(tabs[idx]); }
      });
    });
    moveIndicator(tabs[0]);
    window.addEventListener('resize', function () {
      var active = list.querySelector('[aria-selected="true"]') || tabs[0];
      moveIndicator(active);
    });
  })();
</script>
82 lines UTF-8 · LF · Spaces: 2
DevSnips AI ready Claude · Cursor · Windsurf

Agent skill & Model Context Protocol

Pass this component straight into your AI workflow. DevSnips exposes each resource as a structured, addressable registry entry, so your agent installs the real files instead of approximating them.

devsnips://components/tabs/segmented-tabs
Prompt instruction
I want to use this DevSnips resource in production:

Page:
https://devsnips.site/library/tailwind/components/tabs/segmented-tabs/

Install: npx devsnips add
Tailwind/Components/Tabs/segmented-tabs

This is the Segmented Tabs — iOS-style segmented control with a sliding indicator that animates between segments. Used for switching time ranges and compact view modes.

Use this DevSnips resource as the starting point for my project.
Adapt it to my project's stack and conventions, fix any issues,
and make it production-ready while preserving its intended design
and behavior.

Paste into ChatGPT, Claude or your agent — it already carries the page URL and the exact install path.

Resource URI
devsnips://components/tabs/segmented-tabs