// ============================================================================= // Analytics Feature - UnoCSS Configuration Template // ============================================================================= // This file demonstrates layered override system for feature-specific styles. // It will be merged with base UnoCSS config when analytics feature is enabled. // Layer: Feature > Template > Framework import { defineConfig } from 'unocss' export default defineConfig({ // Analytics-specific theme extensions theme: { colors: { // Analytics color palette analytics: { primary: '#10b981', // Green for positive metrics secondary: '#3b82f6', // Blue for neutral metrics warning: '#f59e0b', // Amber for warnings danger: '#ef4444', // Red for errors/negative metrics info: '#06b6d4', // Cyan for informational metrics success: '#22c55e', // Light green for success states muted: '#6b7280', // Gray for disabled/muted elements }, // Chart specific colors chart: { line1: '#8b5cf6', // Purple line2: '#06b6d4', // Cyan line3: '#f59e0b', // Amber line4: '#ef4444', // Red line5: '#22c55e', // Green area: '#e5e7eb20', // Light gray with transparency grid: '#f3f4f6', // Very light gray }, // Status indicators status: { online: '#22c55e', // Green offline: '#ef4444', // Red pending: '#f59e0b', // Amber processing: '#3b82f6', // Blue } }, // Analytics-specific font sizes for metrics fontSize: { 'metric-xs': '0.625rem', // 10px - small labels 'metric-sm': '0.75rem', // 12px - secondary metrics 'metric-base': '0.875rem', // 14px - base metrics 'metric-lg': '1rem', // 16px - primary metrics 'metric-xl': '1.25rem', // 20px - featured metrics 'metric-2xl': '1.5rem', // 24px - hero metrics 'metric-3xl': '2rem', // 32px - dashboard highlights 'metric-4xl': '2.5rem', // 40px - main KPIs }, // Spacing for analytics layouts spacing: { 'metric': '0.375rem', // 6px - metric spacing 'chart': '1rem', // 16px - chart padding 'dashboard': '1.5rem', // 24px - dashboard sections 'kpi': '2rem', // 32px - KPI spacing }, }, // Analytics-specific utility shortcuts shortcuts: { // Metric display components 'metric-card': 'bg-white dark:bg-gray-800 shadow-sm border border-gray-200 dark:border-gray-700 rounded-lg p-4 hover:shadow-md transition-shadow', 'metric-card-featured': 'metric-card border-analytics-primary bg-gradient-to-br from-analytics-primary/5 to-transparent', 'metric-value': 'text-metric-2xl font-bold text-gray-900 dark:text-gray-100', 'metric-label': 'text-metric-sm font-medium text-gray-600 dark:text-gray-400 uppercase tracking-wide', 'metric-change-positive': 'text-metric-sm font-medium text-analytics-success', 'metric-change-negative': 'text-metric-sm font-medium text-analytics-danger', 'metric-change-neutral': 'text-metric-sm font-medium text-gray-500', // Chart containers 'chart-container': 'bg-white dark:bg-gray-800 rounded-lg p-chart shadow-sm border border-gray-200 dark:border-gray-700', 'chart-header': 'flex items-center justify-between mb-4', 'chart-title': 'text-lg font-semibold text-gray-900 dark:text-gray-100', 'chart-subtitle': 'text-metric-sm text-gray-600 dark:text-gray-400', 'chart-legend': 'flex flex-wrap gap-4 text-metric-sm', 'chart-legend-item': 'flex items-center gap-1.5', 'chart-legend-dot': 'w-3 h-3 rounded-full', // Dashboard layouts 'dashboard-grid': 'grid grid-cols-1 sm:grid-cols-2 lg:grid-cols-3 xl:grid-cols-4 gap-dashboard', 'dashboard-section': 'space-y-dashboard', 'dashboard-header': 'flex items-center justify-between py-4 border-b border-gray-200 dark:border-gray-700', 'dashboard-title': 'text-2xl font-bold text-gray-900 dark:text-gray-100', 'dashboard-filters': 'flex flex-wrap items-center gap-2', // Status indicators 'status-badge': 'inline-flex items-center px-2.5 py-0.5 rounded-full text-metric-xs font-medium', 'status-online': 'status-badge bg-status-online/10 text-status-online', 'status-offline': 'status-badge bg-status-offline/10 text-status-offline', 'status-pending': 'status-badge bg-status-pending/10 text-status-pending', 'status-processing': 'status-badge bg-status-processing/10 text-status-processing', // Analytics-specific buttons 'btn-analytics': 'btn bg-analytics-primary hover:bg-analytics-primary/80 text-white', 'btn-analytics-outline': 'btn border-2 border-analytics-primary text-analytics-primary hover:bg-analytics-primary hover:text-white', 'btn-export': 'btn bg-analytics-info hover:bg-analytics-info/80 text-white', 'btn-refresh': 'btn bg-gray-100 hover:bg-gray-200 text-gray-700 dark:bg-gray-700 dark:hover:bg-gray-600 dark:text-gray-200', // Interactive elements 'metric-hover': 'transition-all duration-200 hover:scale-105 cursor-pointer', 'chart-point': 'w-2 h-2 rounded-full transition-all hover:w-3 hover:h-3', 'tooltip-analytics': 'bg-gray-900 text-white text-metric-xs px-2 py-1 rounded shadow-lg', // Loading states 'loading-metric': 'animate-pulse bg-gray-200 dark:bg-gray-700 rounded h-8', 'loading-chart': 'animate-pulse bg-gray-200 dark:bg-gray-700 rounded h-48', 'loading-shimmer': 'animate-pulse bg-gradient-to-r from-gray-200 via-gray-100 to-gray-200 dark:from-gray-700 dark:via-gray-600 dark:to-gray-700', }, // Analytics-specific rules for dynamic utilities rules: [ // Metric size rule: metric-{number} [/^metric-(\d+)$/, ([, d]) => ({ 'font-size': `${d}px`, 'line-height': '1.2' })], // Chart height rule: chart-h-{number} [/^chart-h-(\d+)$/, ([, h]) => ({ height: `${h}px` })], // Status color rule: status-{color} [/^status-(.+)$/, ([, color]) => { const colors: Record = { success: '#22c55e', error: '#ef4444', warning: '#f59e0b', info: '#06b6d4', } return colors[color] ? { color: colors[color] } : {} }], // Analytics gradient rule: analytics-gradient-{direction} [/^analytics-gradient-(.+)$/, ([, direction]) => { const gradients: Record = { 'success': 'linear-gradient(135deg, #22c55e 0%, #16a34a 100%)', 'warning': 'linear-gradient(135deg, #f59e0b 0%, #d97706 100%)', 'info': 'linear-gradient(135deg, #06b6d4 0%, #0891b2 100%)', 'primary': 'linear-gradient(135deg, #10b981 0%, #059669 100%)', } return gradients[direction] ? { 'background-image': gradients[direction] } : {} }], ], // Safelist for analytics classes that should always be included safelist: [ // Ensure all status colors are included 'status-online', 'status-offline', 'status-pending', 'status-processing', // Metric display classes 'metric-card', 'metric-value', 'metric-label', 'metric-change-positive', 'metric-change-negative', 'metric-change-neutral', // Chart classes 'chart-container', 'chart-title', 'chart-legend', // Dashboard layout 'dashboard-grid', 'dashboard-section', // Dynamic classes that might be used in JavaScript 'text-analytics-primary', 'text-analytics-success', 'text-analytics-danger', 'text-analytics-warning', 'text-analytics-info', // Chart colors for dynamic generation 'text-chart-line1', 'text-chart-line2', 'text-chart-line3', 'text-chart-line4', 'text-chart-line5', 'bg-chart-line1', 'bg-chart-line2', 'bg-chart-line3', 'bg-chart-line4', 'bg-chart-line5', ], // Content sources specific to analytics components content: [ 'src/components/features/analytics/**/*.rs', 'crates/client/src/components/analytics/**/*.rs', 'features/analytics/src/**/*.rs', 'templates/analytics/**/*.html', ], // Preflights for analytics-specific base styles preflights: [ { getCSS: () => ` /* Analytics-specific global styles */ .analytics-dashboard { --analytics-spacing: 1.5rem; --analytics-border-radius: 0.5rem; --analytics-shadow: 0 1px 3px 0 rgba(0, 0, 0, 0.1); } /* Chart container base styles */ .chart-container { position: relative; overflow: hidden; } /* Metric card hover effects */ .metric-card { transition: all 0.2s ease-in-out; } /* Tooltip styling */ [data-tooltip]::after { content: attr(data-tooltip); position: absolute; bottom: 100%; left: 50%; transform: translateX(-50%); background: rgba(17, 24, 39, 0.9); color: white; padding: 0.25rem 0.5rem; border-radius: 0.25rem; font-size: 0.75rem; white-space: nowrap; opacity: 0; pointer-events: none; transition: opacity 0.2s; z-index: 1000; } [data-tooltip]:hover::after { opacity: 1; } /* Loading animation */ @keyframes pulse-analytics { 0%, 100% { opacity: 1; } 50% { opacity: 0.5; } } .loading-analytics { animation: pulse-analytics 2s cubic-bezier(0.4, 0, 0.6, 1) infinite; } ` } ], // Transformers for analytics-specific functionality transformers: [ // Add data attributes for analytics tracking { name: 'analytics-tracking', enforce: 'pre', transform: (code: string) => { // Add tracking attributes to analytics components return code.replace( /class="([^"]*metric-card[^"]*)"/g, 'class="$1" data-analytics-component="metric-card"' ) } } ], })