tailwind-css-data-visualization-patterns

star 40

Tailwind CSS configurations and patterns for building data-dense financial dashboard UIs

C00ldudeNoonan By C00ldudeNoonan schedule Updated 5/13/2026

name: Tailwind CSS Data Visualization Patterns description: Tailwind CSS configurations and patterns for building data-dense financial dashboard UIs version: 1.0.0 tags: [tailwind, css, dashboard, data-visualization, dark-mode]

Tailwind CSS Data Visualization Patterns

Configuration

// tailwind.config.ts
import type { Config } from 'tailwindcss';

const config: Config = {
  content: ['./src/**/*.{js,ts,jsx,tsx,mdx}'],
  darkMode: 'class',
  theme: {
    extend: {
      colors: {
        gain: { 500: '#10b981', 600: '#059669', 700: '#047857' },
        loss: { 500: '#ef4444', 600: '#dc2626', 700: '#b91c1c' },
        dashboard: {
          bg: '#f8fafc', 'bg-dark': '#0f172a',
          card: '#ffffff', 'card-dark': '#1e293b',
          border: '#e2e8f0', 'border-dark': '#334155',
        },
        chart: { primary: '#1e40af', grid: '#f3f4f6', 'grid-dark': '#1e293b' },
      },
      fontSize: {
        'metric-xs': ['0.75rem', { lineHeight: '1rem' }],
        'metric-sm': ['0.875rem', { lineHeight: '1.25rem' }],
        'kpi': ['1.5rem', { lineHeight: '2rem', fontWeight: '600' }],
        'kpi-lg': ['2rem', { lineHeight: '2.5rem', fontWeight: '700' }],
      },
      spacing: { card: '1rem', 'card-lg': '1.5rem', section: '2rem' },
      gridTemplateColumns: {
        sidebar: 'minmax(200px, 260px) 1fr',
        metrics: 'repeat(auto-fit, minmax(200px, 1fr))',
      },
      animation: {
        'flash-gain': 'flashGain 600ms ease-out',
        'flash-loss': 'flashLoss 600ms ease-out',
      },
      keyframes: {
        flashGain: { '0%': { backgroundColor: 'rgba(16, 185, 129, 0.25)' }, '100%': { backgroundColor: 'transparent' } },
        flashLoss: { '0%': { backgroundColor: 'rgba(239, 68, 68, 0.25)' }, '100%': { backgroundColor: 'transparent' } },
      },
      boxShadow: {
        card: '0 1px 3px 0 rgba(0, 0, 0, 0.08)',
        'card-hover': '0 4px 12px 0 rgba(0, 0, 0, 0.1)',
      },
    },
  },
};
export default config;

Dashboard Layout

<div class="grid grid-cols-sidebar min-h-screen bg-dashboard-bg dark:bg-dashboard-bg-dark">
  <aside class="sticky top-0 h-screen overflow-y-auto bg-white dark:bg-dashboard-card-dark 
                border-r border-dashboard-border dark:border-dashboard-border-dark">
    <nav class="p-4 space-y-1"><!-- Nav --></nav>
  </aside>
  <main class="min-h-screen">
    <header class="sticky top-0 z-20 bg-white/90 dark:bg-dashboard-card-dark/90 backdrop-blur-sm
                   border-b border-dashboard-border dark:border-dashboard-border-dark px-6 py-4">
      <h1 class="text-xl font-semibold text-gray-900 dark:text-white">Dashboard</h1>
    </header>
    <div class="p-section"><!-- Content --></div>
  </main>
</div>

KPI Card

<div class="bg-white dark:bg-dashboard-card-dark rounded-lg border border-dashboard-border 
            dark:border-dashboard-border-dark p-card-lg hover:shadow-card-hover transition-shadow">
  <div class="flex items-start justify-between">
    <div>
      <p class="text-metric-xs font-medium text-gray-500 dark:text-gray-400 uppercase tracking-wider">
        Total Revenue
      </p>
      <p class="text-kpi-lg text-gray-900 dark:text-white tabular-nums lining-nums mt-1">
        $2,847,293
      </p>
    </div>
    <div class="p-2 rounded-lg bg-blue-50 dark:bg-blue-900/30">
      <svg class="w-5 h-5 text-blue-600 dark:text-blue-400"><!-- Icon --></svg>
    </div>
  </div>
  <div class="flex items-center gap-2 mt-4">
    <span class="inline-flex items-center text-metric-sm font-medium text-gain-600">
      <span class="tabular-nums">+12.5%</span>
    </span>
    <span class="text-metric-xs text-gray-400">vs last period</span>
  </div>
</div>

Chart Container

<div class="bg-white dark:bg-dashboard-card-dark rounded-lg border border-dashboard-border 
            dark:border-dashboard-border-dark overflow-hidden">
  <div class="px-card-lg pt-card-lg pb-2 border-b border-dashboard-border dark:border-dashboard-border-dark">
    <h3 class="text-metric-sm font-semibold text-gray-900 dark:text-white">GDP Growth Rate</h3>
    <p class="text-metric-xs text-gray-500 dark:text-gray-400 mt-1">Quarterly, seasonally adjusted</p>
  </div>
  <div class="p-card aspect-[16/9]"><!-- Nivo chart --></div>
</div>

Data Table

<div class="overflow-hidden rounded-lg border border-dashboard-border dark:border-dashboard-border-dark">
  <table class="min-w-full divide-y divide-dashboard-border dark:divide-dashboard-border-dark">
    <thead class="bg-gray-50 dark:bg-gray-800/50">
      <tr>
        <th class="px-4 py-3 text-left text-metric-xs font-medium text-gray-500 uppercase">Symbol</th>
        <th class="px-4 py-3 text-right text-metric-xs font-medium text-gray-500 uppercase">Price</th>
        <th class="px-4 py-3 text-right text-metric-xs font-medium text-gray-500 uppercase">Change</th>
      </tr>
    </thead>
    <tbody class="bg-white dark:bg-dashboard-card-dark divide-y divide-dashboard-border">
      <tr class="hover:bg-gray-50 dark:hover:bg-gray-800/50 transition-colors">
        <td class="px-4 py-3 text-metric-sm font-medium text-gray-900 dark:text-white">AAPL</td>
        <td class="px-4 py-3 text-metric-sm tabular-nums text-right text-gray-900">$178.23</td>
        <td class="px-4 py-3 text-metric-sm tabular-nums text-right text-gain-500">+2.34%</td>
      </tr>
    </tbody>
  </table>
</div>

States: Loading, Error, Empty

<!-- Loading Skeleton -->
<div class="animate-pulse">
  <div class="h-8 bg-gray-200 dark:bg-gray-700 rounded w-48 mb-4"></div>
  <div class="aspect-video bg-gray-200 dark:bg-gray-700 rounded"></div>
</div>

<!-- Error State -->
<div class="flex flex-col items-center justify-center aspect-video bg-red-50 dark:bg-red-950/20 
            rounded-lg border border-red-200 dark:border-red-800 p-6">
  <p class="text-red-600 dark:text-red-400 font-medium">Failed to load data</p>
  <button class="mt-3 text-sm text-red-500 hover:text-red-600 underline">Retry</button>
</div>

<!-- Empty State -->
<div class="flex flex-col items-center justify-center aspect-video bg-gray-50 dark:bg-gray-800/50 
            rounded-lg border-2 border-dashed border-gray-300 dark:border-gray-600 p-6">
  <p class="text-gray-500 dark:text-gray-400 font-medium">No data available</p>
</div>

Tabular Numbers

<span class="tabular-nums lining-nums slashed-zero text-right">$1,234,567.89</span>
<span class="tabular-nums text-gain-500">+12.34%</span>
<span class="tabular-nums text-loss-500">-5.67%</span>

Dark Mode Toggle

function toggleDarkMode() {
  document.documentElement.classList.toggle('dark');
  localStorage.setItem('theme', document.documentElement.classList.contains('dark') ? 'dark' : 'light');
}

// Initialize
if (localStorage.theme === 'dark' || (!localStorage.theme && window.matchMedia('(prefers-color-scheme: dark)').matches)) {
  document.documentElement.classList.add('dark');
}
Install via CLI
npx skills add https://github.com/C00ldudeNoonan/economic-data-project --skill tailwind-css-data-visualization-patterns
Repository Details
star Stars 40
call_split Forks 8
navigation Branch main
article Path SKILL.md
More from Creator
C00ldudeNoonan
C00ldudeNoonan Explore all skills →