@actionexec/dashboards 0.5.3 → 0.5.5

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","sources":["../src/hooks/useDashboardData.ts","../src/widgets/KPIWidget.tsx","../src/widgets/GaugeWidget.tsx","../src/widgets/ChartWidget.tsx","../src/widgets/FilterWidget.tsx","../src/widgets/VariableWidget.tsx","../src/widgets/ColorPaletteWidget.tsx","../src/widgets/WidgetRenderer.tsx","../src/Dashboard.tsx"],"sourcesContent":["// Purpose: Hook que gerencia estado + fetch de um dashboard inteiro.\n// Scope: Carrega layout uma vez + render com debounce quando filtros/variaveis mudam.\n// Sincroniza estado local com os defaults aplicados pelo backend na 1a carga.\n// Public API: useDashboardData\n\nimport { useState, useEffect, useCallback, useMemo, useRef } from 'react';\nimport { fetchLayout, fetchRender } from '../api/fetcher';\nimport type { LayoutResponse, RenderResponse } from '../types';\n\nexport interface UseDashboardDataResult {\n layout: LayoutResponse | null;\n renderData: RenderResponse | null;\n loading: boolean;\n error: string | null;\n /** Filtros selecionados (formato string por widget — date_range como \"start|end\"). */\n filters: Record<string, string>;\n /** Overrides de variaveis por widget. */\n variables: Record<string, number>;\n /** Paleta efetiva (override local substitui a do layout). */\n palette: string[];\n setFilter(widgetId: string, value: string): void;\n setVariable(widgetId: string, value: number): void;\n setPalette(colors: string[]): void;\n}\n\nconst DEBOUNCE_MS = 300;\n\nexport function useDashboardData(token: string): UseDashboardDataResult {\n const [layout, setLayout] = useState<LayoutResponse | null>(null);\n const [renderData, setRenderData] = useState<RenderResponse | null>(null);\n const [filters, setFilters] = useState<Record<string, string>>({});\n const [variables, setVariables] = useState<Record<string, number>>({});\n const [localPalette, setLocalPalette] = useState<string[] | null>(null);\n const [loading, setLoading] = useState(true);\n const [error, setError] = useState<string | null>(null);\n\n const debounceRef = useRef<ReturnType<typeof setTimeout>>();\n const appliedSyncedRef = useRef(false);\n\n // -------Carrega layout uma unica vez (por token)-------\n useEffect(() => {\n let cancelled = false;\n fetchLayout(token)\n .then((res) => { if (!cancelled) setLayout(res); })\n .catch((err: Error) => { if (!cancelled) setError(err.message); });\n return () => { cancelled = true; };\n }, [token]);\n\n // -------Render com debounce quando filtros/variaveis mudam-------\n useEffect(() => {\n if (!layout) return;\n if (debounceRef.current) clearTimeout(debounceRef.current);\n\n debounceRef.current = setTimeout(() => {\n const params = buildQueryParams(filters, variables);\n setLoading(true);\n fetchRender(token, params)\n .then((res) => {\n setRenderData(res);\n if (!appliedSyncedRef.current && res.applied) {\n appliedSyncedRef.current = true;\n setFilters((prev) => ({ ...syncFiltersFromApplied(res.applied), ...prev }));\n }\n setError(null);\n })\n .catch((err: Error) => setError(err.message))\n .finally(() => setLoading(false));\n }, DEBOUNCE_MS);\n\n return () => {\n if (debounceRef.current) clearTimeout(debounceRef.current);\n };\n }, [token, layout, filters, variables]);\n\n const setFilter = useCallback((widgetId: string, value: string) => {\n setFilters((prev) => ({ ...prev, [widgetId]: value }));\n }, []);\n\n const setVariable = useCallback((widgetId: string, value: number) => {\n setVariables((prev) => ({ ...prev, [widgetId]: value }));\n }, []);\n\n const setPalette = useCallback((colors: string[]) => {\n setLocalPalette(colors);\n }, []);\n\n const palette = useMemo(\n () => localPalette ?? layout?.palette ?? [],\n [localPalette, layout],\n );\n\n return {\n layout, renderData, loading, error,\n filters, variables, palette,\n setFilter, setVariable, setPalette,\n };\n}\n\n// -------Helpers-------\n\n/** Constroi query params no formato esperado pela API (/render). */\nfunction buildQueryParams(\n filters: Record<string, string>,\n variables: Record<string, number>,\n): Record<string, string> {\n const params: Record<string, string> = {};\n\n for (const [key, val] of Object.entries(filters)) {\n if (val.includes('|')) {\n const [start, end] = val.split('|');\n if (start) params['f_date_start'] = start;\n if (end) params['f_date_end'] = end;\n } else {\n params[`f_${key}`] = val;\n }\n }\n\n for (const [key, val] of Object.entries(variables)) {\n params[`v_${key}`] = String(val);\n }\n\n return params;\n}\n\n/** Converte `applied` do backend para o formato local de filtros. */\nfunction syncFiltersFromApplied(applied: Record<string, unknown>): Record<string, string> {\n const synced: Record<string, string> = {};\n for (const [id, val] of Object.entries(applied)) {\n if (val && typeof val === 'object' && 'start' in val) {\n const d = val as { start?: string; end?: string };\n synced[id] = `${d.start || ''}|${d.end || ''}`;\n } else if (Array.isArray(val)) {\n synced[id] = val.join(',');\n } else if (typeof val === 'string') {\n synced[id] = val;\n }\n }\n return synced;\n}\n","// Purpose: KPI card com valor computado + comparacao.\n// Scope: Renderiza label, valor formatado, seta de trend, variance.\n// Public API: KPIWidget\n\ninterface Props {\n data: Record<string, unknown>;\n label?: string;\n}\n\nexport function KPIWidget({ data, label }: Props) {\n const displayLabel = label || String(data.label || '');\n const formatted = String(data.formatted || '-');\n const comparison = data.comparison as {\n previous_value?: number | null;\n variance_pct?: number | null;\n trend?: string | null;\n label?: string | null;\n } | null;\n\n const trendClass = comparison?.trend === 'up'\n ? 'widget-kpi__trend--up'\n : comparison?.trend === 'down'\n ? 'widget-kpi__trend--down'\n : '';\n\n const arrow = comparison?.trend === 'up' ? '↑' : comparison?.trend === 'down' ? '↓' : '';\n\n return (\n <div className=\"widget widget-kpi\">\n <span className=\"widget-kpi__label\">{displayLabel}</span>\n <span className=\"widget-kpi__value\">{formatted}</span>\n {comparison && comparison.variance_pct != null && (\n <div className={`widget-kpi__trend ${trendClass}`}>\n <span className=\"widget-kpi__variance\">\n {arrow} {comparison.variance_pct > 0 ? '+' : ''}{comparison.variance_pct.toFixed(1)}%\n </span>\n {comparison.label && (\n <span className=\"widget-kpi__trend-label\">{comparison.label}</span>\n )}\n </div>\n )}\n </div>\n );\n}\n","// Purpose: Gauge widget (progresso vs meta).\n// Scope: Semicirculo SVG com percentual, valores brutos e indicador de meta batida.\n// Public API: GaugeWidget\n\ninterface Props {\n data: Record<string, unknown>;\n palette: string[];\n label?: string;\n}\n\nconst COLOR_EMPTY = 'var(--bg-elevated)';\n\n/** Gera path SVG de um arco semicircular (de esquerda para direita, no topo). */\nfunction arcPath(cx: number, cy: number, r: number, fraction: number): string {\n if (fraction <= 0) return '';\n if (fraction >= 1) {\n // Semicirculo completo: dois arcos de 90° (SVG nao desenha arco de exatamente 180°)\n return `M ${cx - r} ${cy} A ${r} ${r} 0 0 1 ${cx} ${cy - r} A ${r} ${r} 0 0 1 ${cx + r} ${cy}`;\n }\n const angle = fraction * Math.PI;\n const endX = cx - r * Math.cos(angle);\n const endY = cy - r * Math.sin(angle);\n return `M ${cx - r} ${cy} A ${r} ${r} 0 0 1 ${endX} ${endY}`;\n}\n\nfunction formatCompact(value: number): string {\n const abs = Math.abs(value);\n if (abs >= 1_000_000) return `${(value / 1_000_000).toFixed(1)}M`;\n if (abs >= 1_000) return `${(value / 1_000).toFixed(1)}K`;\n return value.toLocaleString('pt-BR');\n}\n\nexport function GaugeWidget({ data, palette, label: propLabel }: Props) {\n const label = propLabel || String(data.label || '');\n const rawValue = typeof data.value === 'number' ? data.value : null;\n const valueFormatted = rawValue != null ? formatCompact(rawValue) : '-';\n const formatted = String(data.formatted || '-');\n const ratio = typeof data.ratio === 'number' ? data.ratio : 0;\n const targetValue = data.target_value as number | null;\n\n const comparisonLabel = data.comparison_label as string | null;\n const exceeded = ratio >= 1;\n const clamped = Math.min(Math.max(ratio, 0), 1);\n\n const fillColor = exceeded\n ? 'var(--action-green)'\n : ratio >= 0.7\n ? (palette[0] || 'var(--color-info)')\n : ratio >= 0.4\n ? 'var(--color-warning)'\n : 'var(--color-error)';\n\n const targetFormatted = targetValue != null ? formatCompact(targetValue) : '-';\n\n const cx = 50, cy = 50, r = 44, stroke = 10;\n\n return (\n <div className=\"widget widget-gauge\">\n <span className=\"widget-gauge__label\">{label}</span>\n <div className=\"widget-gauge__chart\">\n <svg viewBox=\"0 0 100 56\" preserveAspectRatio=\"xMidYMax meet\">\n <path d={arcPath(cx, cy, r, 1)} fill=\"none\" stroke={COLOR_EMPTY} strokeWidth={stroke} strokeLinecap=\"butt\" />\n {clamped > 0 && (\n <path d={arcPath(cx, cy, r, clamped)} fill=\"none\" stroke={fillColor} strokeWidth={stroke} strokeLinecap=\"butt\" />\n )}\n </svg>\n <div className=\"widget-gauge__center\">\n <span className=\"widget-gauge__percent\">{formatted}</span>\n <span className=\"widget-gauge__comparison\">{valueFormatted} / {targetFormatted}</span>\n {exceeded && <span className=\"widget-gauge__badge\">{comparisonLabel || 'Meta batida'}</span>}\n {!exceeded && comparisonLabel && <span className=\"widget-gauge__comparison\">{comparisonLabel}</span>}\n </div>\n </div>\n </div>\n );\n}\n","// Purpose: Chart widget (bar/line/area/pie via Recharts).\n// Scope: Renderiza com dados pre-calculados pelo backend + tooltip tematizado.\n// Public API: ChartWidget\n\nimport { useRef, useState, useEffect, type ComponentType, type ReactElement } from 'react';\nimport {\n BarChart, Bar,\n LineChart, Line,\n AreaChart, Area,\n PieChart, Pie, Cell,\n XAxis, YAxis, CartesianGrid, Tooltip, Legend,\n} from 'recharts';\n\nconst AXIS_STYLE = { fontSize: 10, fill: 'var(--text-muted)' };\nconst GRID_STROKE = 'var(--bg-elevated)';\n\n// Tooltip segue a paleta do dashboard via CSS variables (getPaletteCssVars)\nconst TOOLTIP_CONTENT_STYLE = {\n backgroundColor: 'var(--bg-elevated)',\n border: '1px solid var(--bg-paper)',\n borderRadius: '6px',\n color: 'var(--text-primary)',\n};\nconst TOOLTIP_LABEL_STYLE = {\n color: 'var(--text-primary)',\n fontWeight: 600,\n};\n\n// Usa `tooltipLabel` (versao verbose) do data point quando presente,\n// fallback para o label do eixo X (compacto).\nfunction tooltipLabelFormatter(label: unknown, payload: readonly unknown[]): string {\n const first = (Array.isArray(payload) ? payload[0] : undefined) as { payload?: Record<string, unknown> } | undefined;\n const verbose = first?.payload?.tooltipLabel;\n if (typeof verbose === 'string' && verbose) return verbose;\n return String(label ?? '');\n}\n\ninterface SeriesInfo { key: string; label: string }\n\n// Hook para medir dimensoes do container via ResizeObserver\nfunction useContainerSize(ref: React.RefObject<HTMLDivElement | null>) {\n const [size, setSize] = useState({ width: 0, height: 0 });\n\n useEffect(() => {\n const el = ref.current;\n if (!el) return;\n\n const observer = new ResizeObserver(([entry]) => {\n const { width, height } = entry.contentRect;\n setSize((prev) =>\n prev.width !== Math.floor(width) || prev.height !== Math.floor(height)\n ? { width: Math.floor(width), height: Math.floor(height) }\n : prev\n );\n });\n observer.observe(el);\n return () => observer.disconnect();\n }, [ref]);\n\n return size;\n}\n\n// Componente generico para charts cartesianos (bar/line/area)\nfunction CartesianChart({ Chart, chartData, xKey, series, palette, renderSeries, width, height }: {\n // eslint-disable-next-line @typescript-eslint/no-explicit-any\n Chart: ComponentType<any>;\n chartData: Record<string, unknown>[];\n xKey: string;\n series: SeriesInfo[];\n palette: string[];\n renderSeries: (s: SeriesInfo, color: string, idx: number) => ReactElement;\n width: number;\n height: number;\n}) {\n return (\n <Chart data={chartData} width={width} height={height}>\n <CartesianGrid strokeDasharray=\"3 3\" stroke={GRID_STROKE} />\n <XAxis dataKey={xKey} tick={AXIS_STYLE} />\n <YAxis tick={AXIS_STYLE} />\n <Tooltip\n contentStyle={TOOLTIP_CONTENT_STYLE}\n labelStyle={TOOLTIP_LABEL_STYLE}\n labelFormatter={tooltipLabelFormatter}\n cursor={{ fill: 'var(--bg-paper)', opacity: 0.3 }}\n />\n {series.length > 1 && <Legend />}\n {series.map((s, i) => renderSeries(s, palette[i % palette.length], i))}\n </Chart>\n );\n}\n\ninterface Props {\n data: Record<string, unknown>;\n palette: string[];\n label?: string;\n}\n\nexport function ChartWidget({ data, palette, label: propLabel }: Props) {\n const chartType = String(data.chartType || 'bar');\n const title = propLabel || String(data.label || '');\n const xKey = String(data.xKey || 'label');\n const series = (data.series || []) as SeriesInfo[];\n const chartData = (data.data || []) as Record<string, unknown>[];\n\n const containerRef = useRef<HTMLDivElement>(null);\n const { width, height } = useContainerSize(containerRef);\n\n if (!chartData.length) {\n return <div className=\"widget widget-chart widget-chart--empty\">Sem dados</div>;\n }\n\n const renderChart = () => {\n if (width <= 0 || height <= 0) return null;\n\n if (chartType === 'pie') {\n return (\n <PieChart width={width} height={height}>\n <Pie\n data={chartData}\n dataKey={series[0]?.key || 's0'}\n nameKey={xKey}\n cx=\"50%\" cy=\"50%\" outerRadius=\"75%\"\n label={({ name, percent }: { name: string; percent: number }) =>\n `${name}: ${(percent * 100).toFixed(0)}%`\n }\n labelLine={false}\n >\n {chartData.map((_, i) => (\n <Cell key={i} fill={palette[i % palette.length]} />\n ))}\n </Pie>\n <Tooltip\n contentStyle={TOOLTIP_CONTENT_STYLE}\n labelStyle={TOOLTIP_LABEL_STYLE}\n labelFormatter={tooltipLabelFormatter}\n />\n </PieChart>\n );\n }\n\n const common = { chartData, xKey, series, palette, width, height };\n\n if (chartType === 'line') {\n return (\n <CartesianChart {...common} Chart={LineChart} renderSeries={(s, color) => (\n <Line key={s.key} type=\"monotone\" dataKey={s.key} name={s.label}\n stroke={color} strokeWidth={2} dot={chartData.length <= 31} />\n )} />\n );\n }\n\n if (chartType === 'area') {\n return (\n <CartesianChart {...common} Chart={AreaChart} renderSeries={(s, color) => (\n <Area key={s.key} type=\"monotone\" dataKey={s.key} name={s.label}\n fill={color} stroke={color} fillOpacity={0.3} />\n )} />\n );\n }\n\n return (\n <CartesianChart {...common} Chart={BarChart} renderSeries={(s, color) => (\n <Bar key={s.key} dataKey={s.key} name={s.label}\n fill={color} radius={[3, 3, 0, 0]} />\n )} />\n );\n };\n\n return (\n <div className=\"widget widget-chart\">\n {title && <h4 className=\"widget-chart__title\">{title}</h4>}\n <div ref={containerRef} className=\"widget-chart__container\">\n {renderChart()}\n </div>\n </div>\n );\n}\n","// Purpose: Widget de filtro interativo no grid (date_range, select, multi_select).\n// Scope: Modos temporais (range, monthly, weekly, yearly), select unico, multi-select.\n// Public API: FilterWidget\n\nimport type { FilterConfig, DateFilterMode } from '../types';\nimport {\n MONTH_NAMES_SHORT, getFullYearRange, getMonthRange,\n getMonthWeeks, parseMonthWeekFromRange,\n parseYearFromRange, parseMonthFromRange, getYearRange,\n} from '../utils/date';\nimport { DashboardDatePicker } from '../components/DashboardDatePicker';\n\ninterface Props {\n config: FilterConfig;\n value: string;\n options?: string[];\n dateBounds?: { min: string | null; max: string | null } | null;\n onChange: (value: string) => void;\n}\n\n// -------Componente principal-------\n\nexport function FilterWidget({ config, value, options = [], dateBounds, onChange }: Props) {\n const filterType = config.filterType || 'select';\n const label = config.label || 'Filtro';\n const dateMode: DateFilterMode = config.dateFilterMode || 'range';\n\n return (\n <div className=\"widget-filter\">\n <label className=\"widget-filter__label\">{label}</label>\n {filterType === 'date_range' ? (\n dateMode === 'yearly' ? (\n <YearlyFilter value={value} dateBounds={dateBounds} onChange={onChange} />\n ) : dateMode === 'monthly' ? (\n <MonthlyFilter value={value} dateBounds={dateBounds} onChange={onChange} />\n ) : dateMode === 'weekly' ? (\n <WeeklyFilter value={value} dateBounds={dateBounds} onChange={onChange} />\n ) : (\n <DateRangeFilter value={value} dateBounds={dateBounds} onChange={onChange} />\n )\n ) : (\n <SelectFilter\n value={value}\n options={options}\n multi={filterType === 'multi_select'}\n onChange={onChange}\n />\n )}\n </div>\n );\n}\n\n// -------DateRangeFilter (modo range puro)-------\n\nfunction DateRangeFilter({ value, dateBounds, onChange }: {\n value: string;\n dateBounds?: { min: string | null; max: string | null } | null;\n onChange: (value: string) => void;\n}) {\n const [start, end] = value ? value.split('|') : ['', ''];\n\n return (\n <div className=\"widget-filter__date-range widget-filter__date-range--stacked\">\n <DashboardDatePicker\n value={start}\n minIso={dateBounds?.min}\n maxIso={end || dateBounds?.max}\n selectsStart\n startIso={start}\n endIso={end}\n placeholder=\"Data inicial\"\n onChange={(iso) => onChange(`${iso}|${end}`)}\n />\n <DashboardDatePicker\n value={end}\n minIso={start || dateBounds?.min}\n maxIso={dateBounds?.max}\n selectsEnd\n startIso={start}\n endIso={end}\n placeholder=\"Data final\"\n onChange={(iso) => onChange(`${start}|${iso}`)}\n />\n </div>\n );\n}\n\n// -------YearlyFilter (modo anual)-------\n\nfunction YearlyFilter({ value, dateBounds, onChange }: {\n value: string;\n dateBounds?: { min: string | null; max: string | null } | null;\n onChange: (value: string) => void;\n}) {\n const [start] = value ? value.split('|') : [''];\n const parsed = parseYearFromRange(start);\n const now = new Date();\n const selectedYear = parsed?.year ?? now.getFullYear();\n const years = getYearRange(dateBounds);\n\n const handleYearChange = (year: number) => {\n const yr = getFullYearRange(year);\n onChange(`${yr.start}|${yr.end}`);\n };\n\n return (\n <div className=\"widget-filter__date-range widget-filter__date-range--year\">\n <select\n className=\"widget-filter__select\"\n value={selectedYear}\n onChange={(e) => handleYearChange(parseInt(e.target.value))}\n >\n {years.map((y) => <option key={y} value={y}>{y}</option>)}\n </select>\n </div>\n );\n}\n\n// -------MonthlyFilter (modo mensal)-------\n\nfunction MonthlyFilter({ value, dateBounds, onChange }: {\n value: string;\n dateBounds?: { min: string | null; max: string | null } | null;\n onChange: (value: string) => void;\n}) {\n const [start] = value ? value.split('|') : [''];\n const parsed = parseMonthFromRange(start);\n const now = new Date();\n const selectedYear = parsed?.year ?? now.getFullYear();\n const selectedMonth = parsed?.month ?? (now.getMonth() + 1);\n const years = getYearRange(dateBounds);\n\n const handleMonthChange = (year: number, month: number) => {\n const range = getMonthRange(year, month);\n onChange(`${range.start}|${range.end}`);\n };\n\n return (\n <div className=\"widget-filter__date-range widget-filter__date-range--month\">\n <select\n className=\"widget-filter__select\"\n value={selectedMonth}\n onChange={(e) => handleMonthChange(selectedYear, parseInt(e.target.value))}\n >\n {MONTH_NAMES_SHORT.map((name, i) => (\n <option key={i + 1} value={i + 1}>{name}</option>\n ))}\n </select>\n <select\n className=\"widget-filter__select\"\n value={selectedYear}\n onChange={(e) => handleMonthChange(parseInt(e.target.value), selectedMonth)}\n >\n {years.map((y) => <option key={y} value={y}>{y}</option>)}\n </select>\n </div>\n );\n}\n\n// -------WeeklyFilter (modo semanal)-------\n\nfunction WeeklyFilter({ value, dateBounds, onChange }: {\n value: string;\n dateBounds?: { min: string | null; max: string | null } | null;\n onChange: (value: string) => void;\n}) {\n const [start] = value ? value.split('|') : [''];\n const parsed = parseMonthFromRange(start);\n const now = new Date();\n const selectedYear = parsed?.year ?? now.getFullYear();\n const selectedMonth = parsed?.month ?? (now.getMonth() + 1);\n const years = getYearRange(dateBounds);\n\n const monthWeeks = getMonthWeeks(selectedYear, selectedMonth);\n const selectedWeekIdx = parseMonthWeekFromRange(start, selectedYear, selectedMonth) || 1;\n\n return (\n <div className=\"widget-filter__date-range widget-filter__date-range--week\">\n <select\n className=\"widget-filter__select\"\n value={selectedYear}\n onChange={(e) => {\n const y = parseInt(e.target.value);\n const weeks = getMonthWeeks(y, selectedMonth);\n const w = weeks[0];\n if (w) onChange(`${w.start}|${w.end}`);\n }}\n >\n {years.map((y) => <option key={y} value={y}>{y}</option>)}\n </select>\n <select\n className=\"widget-filter__select\"\n value={selectedMonth}\n onChange={(e) => {\n const m = parseInt(e.target.value);\n const weeks = getMonthWeeks(selectedYear, m);\n const w = weeks[0];\n if (w) onChange(`${w.start}|${w.end}`);\n }}\n >\n {MONTH_NAMES_SHORT.map((name, i) => (\n <option key={i + 1} value={i + 1}>{name}</option>\n ))}\n </select>\n <select\n className=\"widget-filter__select\"\n value={selectedWeekIdx}\n onChange={(e) => {\n const w = monthWeeks[parseInt(e.target.value) - 1];\n if (w) onChange(`${w.start}|${w.end}`);\n }}\n >\n {monthWeeks.map((w) => (\n <option key={w.index} value={w.index}>{w.label}</option>\n ))}\n </select>\n </div>\n );\n}\n\n// -------SelectFilter (categorico)-------\n\nfunction SelectFilter({ value, options, multi, onChange }: {\n value: string;\n options: string[];\n multi: boolean;\n onChange: (value: string) => void;\n}) {\n if (multi) {\n const selected = value ? value.split(',') : [];\n const toggle = (opt: string) => {\n const next = selected.includes(opt)\n ? selected.filter((s) => s !== opt)\n : [...selected, opt];\n onChange(next.join(','));\n };\n\n return (\n <div className=\"widget-filter__multi\">\n {options.map((opt) => (\n <label key={opt} className=\"widget-filter__multi-option\">\n <input\n type=\"checkbox\"\n checked={selected.includes(opt)}\n onChange={() => toggle(opt)}\n />\n {opt}\n </label>\n ))}\n </div>\n );\n }\n\n return (\n <select\n className=\"widget-filter__select\"\n value={value}\n onChange={(e) => onChange(e.target.value)}\n >\n <option value=\"\">Todos</option>\n {options.map((opt) => (\n <option key={opt} value={opt}>{opt}</option>\n ))}\n </select>\n );\n}\n","// Purpose: Widget de variavel editavel no grid (what-if scenarios).\n// Scope: Input numerico com label, formato e opcao de bloqueio.\n// Public API: VariableWidget\n\nimport type { VariableConfig } from '../types';\n\ninterface Props {\n config: VariableConfig;\n value: number;\n onChange: (value: number) => void;\n}\n\nconst FORMAT_SUFFIX: Record<string, string> = {\n currency: 'R$',\n percentage: '%',\n};\n\nexport function VariableWidget({ config, value, onChange }: Props) {\n const label = config.label || 'Variavel';\n const locked = config.locked || false;\n const fmt = config.variableFormat || 'number';\n const suffix = FORMAT_SUFFIX[fmt] || '';\n\n return (\n <div className={`widget-variable ${locked ? 'widget-variable--locked' : ''}`}>\n <label className=\"widget-variable__label\">{label}</label>\n <div className=\"widget-variable__input-wrapper\">\n <input\n className=\"widget-variable__input\"\n type=\"number\"\n value={value}\n onChange={(e) => onChange(parseFloat(e.target.value) || 0)}\n disabled={locked}\n step={fmt === 'integer' ? 1 : 0.01}\n />\n {suffix && <span className=\"widget-variable__suffix\">{suffix}</span>}\n </div>\n {locked && <span className=\"widget-variable__lock-icon\" title=\"Bloqueado\">🔒</span>}\n </div>\n );\n}\n","// Purpose: Widget de paleta de cores editavel no grid.\n// Scope: Permite ao usuario do dashboard trocar a paleta em runtime. Respeita bloqueio.\n// Public API: ColorPaletteWidget\n\nimport type { PaletteConfig } from '../types';\nimport { ColorPaletteSelector } from '../components/ColorPaletteSelector';\n\ninterface Props {\n config: PaletteConfig;\n palette: string[];\n onChange: (colors: string[]) => void;\n}\n\nexport function ColorPaletteWidget({ config, palette, onChange }: Props) {\n const label = config.label || 'Cores';\n const locked = config.locked || false;\n\n return (\n <div className={`widget-palette ${locked ? 'widget-palette--locked' : ''}`}>\n <label className=\"widget-palette__label\">{label}</label>\n <ColorPaletteSelector selected={palette} onSelect={onChange} customMode disabled={locked} />\n {locked && <span className=\"widget-palette__lock-icon\" title=\"Bloqueado\">🔒</span>}\n </div>\n );\n}\n","// Purpose: Dispatch de rendering por tipo de widget (dados + controle).\n// Scope: Recebe computed data e/ou config, renderiza widget correto.\n// Public API: WidgetRenderer\n\nimport type { WidgetType, AnyWidgetConfig, FilterConfig, VariableConfig, PaletteConfig } from '../types';\nimport { getSeries } from '../palettes';\nimport { KPIWidget } from './KPIWidget';\nimport { GaugeWidget } from './GaugeWidget';\nimport { ChartWidget } from './ChartWidget';\nimport { FilterWidget } from './FilterWidget';\nimport { VariableWidget } from './VariableWidget';\nimport { ColorPaletteWidget } from './ColorPaletteWidget';\n\ninterface Props {\n type: WidgetType;\n computed: Record<string, unknown>;\n palette: string[];\n // Control widget props (opcionais)\n config?: AnyWidgetConfig;\n filterValue?: string;\n filterOptions?: string[];\n dateBounds?: { min: string; max: string } | null;\n onFilterChange?: (value: string) => void;\n variableValue?: number;\n onVariableChange?: (value: number) => void;\n onPaletteChange?: (colors: string[]) => void;\n}\n\nexport function WidgetRenderer({\n type, computed, palette, config,\n filterValue, filterOptions, dateBounds, onFilterChange,\n variableValue, onVariableChange,\n onPaletteChange,\n}: Props) {\n if (computed.error) {\n return (\n <div className=\"widget widget--error\">\n <span className=\"widget__error-text\">{String(computed.error)}</span>\n </div>\n );\n }\n\n // Widgets de dados usam apenas as cores de series (5 primeiras).\n // UI colors sao aplicadas via CSS vars no grid container.\n const seriesColors = getSeries(palette);\n\n switch (type) {\n case 'kpi_card':\n return <KPIWidget data={computed} label={config?.label} />;\n case 'gauge':\n return <GaugeWidget data={computed} palette={seriesColors} label={config?.label} />;\n case 'chart':\n return <ChartWidget data={computed} palette={seriesColors} label={config?.label} />;\n case 'filter':\n return config && onFilterChange ? (\n <FilterWidget\n config={config as FilterConfig}\n value={filterValue || ''}\n options={filterOptions}\n dateBounds={dateBounds}\n onChange={onFilterChange}\n />\n ) : null;\n case 'variable': {\n const vc = config as VariableConfig | undefined;\n return vc && onVariableChange ? (\n <VariableWidget\n config={vc}\n value={variableValue ?? vc.variableValue ?? 0}\n onChange={onVariableChange}\n />\n ) : null;\n }\n case 'color_palette':\n return config && onPaletteChange ? (\n <ColorPaletteWidget\n config={config as PaletteConfig}\n palette={palette}\n onChange={onPaletteChange}\n />\n ) : null;\n default:\n return <div className=\"widget\">Widget: {type}</div>;\n }\n}\n","// Purpose: Componente top-level que renderiza um dashboard completo.\n// Scope: Busca layout + render da API Action com o token, aplica paleta como CSS vars,\n// renderiza grid com widgets interativos (filtros + variaveis + paleta).\n// Public API: Dashboard\n\nimport type { CSSProperties } from 'react';\nimport { useDashboardData } from './hooks/useDashboardData';\nimport { WidgetRenderer } from './widgets/WidgetRenderer';\nimport { getPaletteCssVars } from './palettes';\nimport { CONTROL_WIDGET_SET } from './types';\n\nconst GRID_ROW_HEIGHT_REM = 2.5;\nconst GRID_GAP_REM = 0.375;\n\ninterface DashboardProps {\n /** Token Bearer de acesso ao dashboard. */\n token: string;\n /** Altura de cada linha do grid em rem. Default 2.5 (40px no base 16). */\n rowHeight?: number;\n /** Gap entre widgets em rem. Default 0.375 (6px no base 16). */\n gridGap?: number;\n /** Classe CSS adicional no container raiz. */\n className?: string;\n}\n\nexport function Dashboard({\n token,\n rowHeight = GRID_ROW_HEIGHT_REM,\n gridGap = GRID_GAP_REM,\n className,\n}: DashboardProps) {\n const {\n layout, renderData, loading, error,\n filters, variables, palette,\n setFilter, setVariable, setPalette,\n } = useDashboardData(token);\n\n if (error && !layout) {\n return <div className={`preview-tab ${className ?? ''}`}><div className=\"preview-tab__error\">{error}</div></div>;\n }\n\n if (!layout) {\n return <div className={`preview-tab ${className ?? ''}`}><div className=\"preview-tab__loading\">Carregando dashboard...</div></div>;\n }\n\n if (layout.widgets.length === 0) {\n return (\n <div className={`preview-tab ${className ?? ''}`}>\n <div className=\"preview-tab__empty\">Este dashboard nao possui widgets.</div>\n </div>\n );\n }\n\n const widgetsData = renderData?.widgets ?? {};\n const dateBounds = renderData?.date_bounds ?? null;\n\n const gridStyle: CSSProperties = {\n display: 'grid',\n gridTemplateColumns: `repeat(${layout.gridColumns}, 1fr)`,\n gridTemplateRows: `repeat(${layout.gridRows}, ${rowHeight}rem)`,\n gap: `${gridGap}rem`,\n ...getPaletteCssVars(palette),\n } as CSSProperties;\n\n return (\n <div className={`preview-tab ${className ?? ''}`}>\n {error && !renderData && <div className=\"preview-tab__error\">{error}</div>}\n\n {renderData && (\n <div className=\"preview-tab__grid\" style={gridStyle}>\n {layout.widgets.map((widget) => {\n const isControl = CONTROL_WIDGET_SET.has(widget.type);\n const computed = widgetsData[widget.id];\n const widgetStyle: CSSProperties = {\n gridColumn: `${widget.grid.x + 1} / span ${widget.grid.w}`,\n gridRow: `${widget.grid.y + 1} / span ${widget.grid.h}`,\n };\n\n const variableValue = widget.type === 'variable'\n ? variables[widget.id] ?? (computed?.value as number) ?? widget.config.variableValue ?? 0\n : undefined;\n\n return (\n <div\n key={widget.id}\n className={`preview-tab__widget ${isControl ? 'preview-tab__widget--control' : ''}`}\n style={widgetStyle}\n >\n {isControl || computed ? (\n <WidgetRenderer\n type={widget.type}\n computed={computed || {}}\n palette={palette}\n config={widget.config}\n filterValue={filters[widget.id] || ''}\n filterOptions={(computed?.available_values as string[]) || []}\n dateBounds={dateBounds}\n onFilterChange={(val) => setFilter(widget.id, val)}\n variableValue={variableValue}\n onVariableChange={(val) => setVariable(widget.id, val)}\n onPaletteChange={setPalette}\n />\n ) : (\n <div className=\"preview-tab__widget-loading\">\n {loading ? 'Carregando...' : 'Sem dados'}\n </div>\n )}\n </div>\n );\n })}\n </div>\n )}\n\n {loading && renderData && (\n <div className=\"preview-tab__recalculating\">Atualizando...</div>\n )}\n </div>\n );\n}\n"],"names":["DEBOUNCE_MS","useDashboardData","token","layout","setLayout","useState","renderData","setRenderData","filters","setFilters","variables","setVariables","localPalette","setLocalPalette","loading","setLoading","error","setError","debounceRef","useRef","appliedSyncedRef","useEffect","cancelled","fetchLayout","res","err","params","buildQueryParams","fetchRender","prev","syncFiltersFromApplied","setFilter","useCallback","widgetId","value","setVariable","setPalette","colors","palette","useMemo","key","val","start","end","applied","synced","id","d","KPIWidget","data","label","displayLabel","formatted","comparison","trendClass","arrow","jsxs","jsx","COLOR_EMPTY","arcPath","cx","cy","r","fraction","angle","endX","endY","formatCompact","abs","GaugeWidget","propLabel","rawValue","valueFormatted","ratio","targetValue","comparisonLabel","exceeded","clamped","fillColor","targetFormatted","stroke","AXIS_STYLE","GRID_STROKE","TOOLTIP_CONTENT_STYLE","TOOLTIP_LABEL_STYLE","tooltipLabelFormatter","payload","first","verbose","_a","useContainerSize","ref","size","setSize","el","observer","entry","width","height","CartesianChart","Chart","chartData","xKey","series","renderSeries","CartesianGrid","XAxis","YAxis","Tooltip","Legend","s","i","ChartWidget","chartType","title","containerRef","PieChart","Pie","name","percent","_","Cell","common","LineChart","color","Line","AreaChart","Area","BarChart","Bar","FilterWidget","config","options","dateBounds","onChange","filterType","dateMode","YearlyFilter","MonthlyFilter","WeeklyFilter","DateRangeFilter","SelectFilter","DashboardDatePicker","iso","parsed","parseYearFromRange","now","selectedYear","years","getYearRange","handleYearChange","year","yr","getFullYearRange","e","y","parseMonthFromRange","selectedMonth","handleMonthChange","month","range","getMonthRange","MONTH_NAMES_SHORT","monthWeeks","getMonthWeeks","selectedWeekIdx","parseMonthWeekFromRange","w","m","multi","selected","toggle","opt","next","FORMAT_SUFFIX","VariableWidget","locked","fmt","suffix","ColorPaletteWidget","ColorPaletteSelector","WidgetRenderer","type","computed","filterValue","filterOptions","onFilterChange","variableValue","onVariableChange","onPaletteChange","seriesColors","getSeries","vc","GRID_ROW_HEIGHT_REM","GRID_GAP_REM","Dashboard","rowHeight","gridGap","className","widgetsData","gridStyle","getPaletteCssVars","widget","isControl","CONTROL_WIDGET_SET","widgetStyle"],"mappings":"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"}
1
+ {"version":3,"file":"index.js","sources":["../src/hooks/useDashboardData.ts","../src/widgets/KPIWidget.tsx","../src/widgets/GaugeWidget.tsx","../src/widgets/ChartWidget.tsx","../src/widgets/FilterWidget.tsx","../src/widgets/VariableWidget.tsx","../src/widgets/ColorPaletteWidget.tsx","../src/widgets/WidgetRenderer.tsx","../src/Dashboard.tsx"],"sourcesContent":["// Purpose: Hook que gerencia estado + fetch de um dashboard inteiro.\n// Scope: Carrega layout uma vez + render com debounce quando filtros/variaveis mudam.\n// Sincroniza estado local com os defaults aplicados pelo backend na 1a carga.\n// Public API: useDashboardData\n\nimport { useState, useEffect, useCallback, useMemo, useRef } from 'react';\nimport { fetchLayout, fetchRender } from '../api/fetcher';\nimport type { LayoutResponse, RenderResponse } from '../types';\nimport { MULTI_VALUE_SEPARATOR } from '../types';\n\nexport interface UseDashboardDataResult {\n layout: LayoutResponse | null;\n renderData: RenderResponse | null;\n loading: boolean;\n error: string | null;\n /** Filtros selecionados (formato string por widget — date_range como \"start|end\"). */\n filters: Record<string, string>;\n /** Overrides de variaveis por widget. */\n variables: Record<string, number>;\n /** Paleta efetiva (override local substitui a do layout). */\n palette: string[];\n setFilter(widgetId: string, value: string): void;\n setVariable(widgetId: string, value: number): void;\n setPalette(colors: string[]): void;\n}\n\nconst DEBOUNCE_MS = 300;\n\nexport function useDashboardData(token: string): UseDashboardDataResult {\n const [layout, setLayout] = useState<LayoutResponse | null>(null);\n const [renderData, setRenderData] = useState<RenderResponse | null>(null);\n const [filters, setFilters] = useState<Record<string, string>>({});\n const [variables, setVariables] = useState<Record<string, number>>({});\n const [localPalette, setLocalPalette] = useState<string[] | null>(null);\n const [loading, setLoading] = useState(true);\n const [error, setError] = useState<string | null>(null);\n\n const debounceRef = useRef<ReturnType<typeof setTimeout>>();\n const appliedSyncedRef = useRef(false);\n\n // -------Carrega layout uma unica vez (por token)-------\n useEffect(() => {\n let cancelled = false;\n fetchLayout(token)\n .then((res) => { if (!cancelled) setLayout(res); })\n .catch((err: Error) => { if (!cancelled) setError(err.message); });\n return () => { cancelled = true; };\n }, [token]);\n\n // -------Render com debounce quando filtros/variaveis mudam-------\n useEffect(() => {\n if (!layout) return;\n if (debounceRef.current) clearTimeout(debounceRef.current);\n\n debounceRef.current = setTimeout(() => {\n const params = buildQueryParams(filters, variables);\n setLoading(true);\n fetchRender(token, params)\n .then((res) => {\n setRenderData(res);\n if (!appliedSyncedRef.current && res.applied) {\n appliedSyncedRef.current = true;\n setFilters((prev) => ({ ...syncFiltersFromApplied(res.applied), ...prev }));\n }\n setError(null);\n })\n .catch((err: Error) => setError(err.message))\n .finally(() => setLoading(false));\n }, DEBOUNCE_MS);\n\n return () => {\n if (debounceRef.current) clearTimeout(debounceRef.current);\n };\n }, [token, layout, filters, variables]);\n\n const setFilter = useCallback((widgetId: string, value: string) => {\n setFilters((prev) => ({ ...prev, [widgetId]: value }));\n }, []);\n\n const setVariable = useCallback((widgetId: string, value: number) => {\n setVariables((prev) => ({ ...prev, [widgetId]: value }));\n }, []);\n\n const setPalette = useCallback((colors: string[]) => {\n setLocalPalette(colors);\n }, []);\n\n const palette = useMemo(\n () => localPalette ?? layout?.palette ?? [],\n [localPalette, layout],\n );\n\n return {\n layout, renderData, loading, error,\n filters, variables, palette,\n setFilter, setVariable, setPalette,\n };\n}\n\n// -------Helpers-------\n\n/** Constroi query params no formato esperado pela API (/render). */\nfunction buildQueryParams(\n filters: Record<string, string>,\n variables: Record<string, number>,\n): Record<string, string> {\n const params: Record<string, string> = {};\n\n for (const [key, val] of Object.entries(filters)) {\n if (val.includes('|')) {\n const [start, end] = val.split('|');\n if (start) params['f_date_start'] = start;\n if (end) params['f_date_end'] = end;\n } else {\n params[`f_${key}`] = val;\n }\n }\n\n for (const [key, val] of Object.entries(variables)) {\n params[`v_${key}`] = String(val);\n }\n\n return params;\n}\n\n/** Converte `applied` do backend para o formato local de filtros. */\nfunction syncFiltersFromApplied(applied: Record<string, unknown>): Record<string, string> {\n const synced: Record<string, string> = {};\n for (const [id, val] of Object.entries(applied)) {\n if (val && typeof val === 'object' && 'start' in val) {\n const d = val as { start?: string; end?: string };\n synced[id] = `${d.start || ''}|${d.end || ''}`;\n } else if (Array.isArray(val)) {\n synced[id] = val.join(MULTI_VALUE_SEPARATOR);\n } else if (typeof val === 'string') {\n synced[id] = val;\n }\n }\n return synced;\n}\n","// Purpose: KPI card com valor computado + comparacao.\n// Scope: Renderiza label, valor formatado, seta de trend, variance.\n// Public API: KPIWidget\n\ninterface Props {\n data: Record<string, unknown>;\n label?: string;\n}\n\nexport function KPIWidget({ data, label }: Props) {\n const displayLabel = label || String(data.label || '');\n const formatted = String(data.formatted || '-');\n const comparison = data.comparison as {\n previous_value?: number | null;\n variance_pct?: number | null;\n trend?: string | null;\n label?: string | null;\n } | null;\n\n const trendClass = comparison?.trend === 'up'\n ? 'widget-kpi__trend--up'\n : comparison?.trend === 'down'\n ? 'widget-kpi__trend--down'\n : '';\n\n const arrow = comparison?.trend === 'up' ? '↑' : comparison?.trend === 'down' ? '↓' : '';\n\n return (\n <div className=\"widget widget-kpi\">\n <span className=\"widget-kpi__label\">{displayLabel}</span>\n <span className=\"widget-kpi__value\">{formatted}</span>\n {comparison && comparison.variance_pct != null && (\n <div className={`widget-kpi__trend ${trendClass}`}>\n <span className=\"widget-kpi__variance\">\n {arrow} {comparison.variance_pct > 0 ? '+' : ''}{comparison.variance_pct.toFixed(1)}%\n </span>\n {comparison.label && (\n <span className=\"widget-kpi__trend-label\">{comparison.label}</span>\n )}\n </div>\n )}\n </div>\n );\n}\n","// Purpose: Gauge widget (progresso vs meta).\n// Scope: Semicirculo SVG com percentual, valores brutos e indicador de meta batida.\n// Public API: GaugeWidget\n\ninterface Props {\n data: Record<string, unknown>;\n palette: string[];\n label?: string;\n}\n\nconst COLOR_EMPTY = 'var(--bg-elevated)';\n\n/** Gera path SVG de um arco semicircular (de esquerda para direita, no topo). */\nfunction arcPath(cx: number, cy: number, r: number, fraction: number): string {\n if (fraction <= 0) return '';\n if (fraction >= 1) {\n // Semicirculo completo: dois arcos de 90° (SVG nao desenha arco de exatamente 180°)\n return `M ${cx - r} ${cy} A ${r} ${r} 0 0 1 ${cx} ${cy - r} A ${r} ${r} 0 0 1 ${cx + r} ${cy}`;\n }\n const angle = fraction * Math.PI;\n const endX = cx - r * Math.cos(angle);\n const endY = cy - r * Math.sin(angle);\n return `M ${cx - r} ${cy} A ${r} ${r} 0 0 1 ${endX} ${endY}`;\n}\n\nfunction formatCompact(value: number): string {\n const abs = Math.abs(value);\n if (abs >= 1_000_000) return `${(value / 1_000_000).toFixed(1)}M`;\n if (abs >= 1_000) return `${(value / 1_000).toFixed(1)}K`;\n return value.toLocaleString('pt-BR');\n}\n\nexport function GaugeWidget({ data, palette, label: propLabel }: Props) {\n const label = propLabel || String(data.label || '');\n const rawValue = typeof data.value === 'number' ? data.value : null;\n const valueFormatted = rawValue != null ? formatCompact(rawValue) : '-';\n const formatted = String(data.formatted || '-');\n const ratio = typeof data.ratio === 'number' ? data.ratio : 0;\n const targetValue = data.target_value as number | null;\n\n const comparisonLabel = data.comparison_label as string | null;\n const exceeded = ratio >= 1;\n const clamped = Math.min(Math.max(ratio, 0), 1);\n\n const fillColor = exceeded\n ? 'var(--action-green)'\n : ratio >= 0.7\n ? (palette[0] || 'var(--color-info)')\n : ratio >= 0.4\n ? 'var(--color-warning)'\n : 'var(--color-error)';\n\n const targetFormatted = targetValue != null ? formatCompact(targetValue) : '-';\n\n const cx = 50, cy = 50, r = 44, stroke = 10;\n\n return (\n <div className=\"widget widget-gauge\">\n <span className=\"widget-gauge__label\">{label}</span>\n <div className=\"widget-gauge__chart\">\n <svg viewBox=\"0 0 100 56\" preserveAspectRatio=\"xMidYMax meet\">\n <path d={arcPath(cx, cy, r, 1)} fill=\"none\" stroke={COLOR_EMPTY} strokeWidth={stroke} strokeLinecap=\"butt\" />\n {clamped > 0 && (\n <path d={arcPath(cx, cy, r, clamped)} fill=\"none\" stroke={fillColor} strokeWidth={stroke} strokeLinecap=\"butt\" />\n )}\n </svg>\n <div className=\"widget-gauge__center\">\n <span className=\"widget-gauge__percent\">{formatted}</span>\n <span className=\"widget-gauge__comparison\">{valueFormatted} / {targetFormatted}</span>\n {exceeded && <span className=\"widget-gauge__badge\">{comparisonLabel || 'Meta batida'}</span>}\n {!exceeded && comparisonLabel && <span className=\"widget-gauge__comparison\">{comparisonLabel}</span>}\n </div>\n </div>\n </div>\n );\n}\n","// Purpose: Chart widget (bar/line/area/pie via Recharts).\n// Scope: Renderiza com dados pre-calculados pelo backend + tooltip tematizado.\n// Public API: ChartWidget\n\nimport { useRef, useState, useEffect, type ComponentType, type ReactElement } from 'react';\nimport {\n BarChart, Bar,\n LineChart, Line,\n AreaChart, Area,\n PieChart, Pie, Cell,\n XAxis, YAxis, CartesianGrid, Tooltip, Legend,\n} from 'recharts';\n\nconst AXIS_STYLE = { fontSize: 10, fill: 'var(--text-muted)' };\nconst GRID_STROKE = 'var(--bg-elevated)';\n\n// Tooltip segue a paleta do dashboard via CSS variables (getPaletteCssVars)\nconst TOOLTIP_CONTENT_STYLE = {\n backgroundColor: 'var(--bg-elevated)',\n border: '1px solid var(--bg-paper)',\n borderRadius: '6px',\n color: 'var(--text-primary)',\n};\nconst TOOLTIP_LABEL_STYLE = {\n color: 'var(--text-primary)',\n fontWeight: 600,\n};\n\n// Usa `tooltipLabel` (versao verbose) do data point quando presente,\n// fallback para o label do eixo X (compacto).\nfunction tooltipLabelFormatter(label: unknown, payload: readonly unknown[]): string {\n const first = (Array.isArray(payload) ? payload[0] : undefined) as { payload?: Record<string, unknown> } | undefined;\n const verbose = first?.payload?.tooltipLabel;\n if (typeof verbose === 'string' && verbose) return verbose;\n return String(label ?? '');\n}\n\ninterface SeriesInfo { key: string; label: string }\n\n// Hook para medir dimensoes do container via ResizeObserver\nfunction useContainerSize(ref: React.RefObject<HTMLDivElement | null>) {\n const [size, setSize] = useState({ width: 0, height: 0 });\n\n useEffect(() => {\n const el = ref.current;\n if (!el) return;\n\n const observer = new ResizeObserver(([entry]) => {\n const { width, height } = entry.contentRect;\n setSize((prev) =>\n prev.width !== Math.floor(width) || prev.height !== Math.floor(height)\n ? { width: Math.floor(width), height: Math.floor(height) }\n : prev\n );\n });\n observer.observe(el);\n return () => observer.disconnect();\n }, [ref]);\n\n return size;\n}\n\n// Componente generico para charts cartesianos (bar/line/area)\nfunction CartesianChart({ Chart, chartData, xKey, series, palette, renderSeries, width, height }: {\n // eslint-disable-next-line @typescript-eslint/no-explicit-any\n Chart: ComponentType<any>;\n chartData: Record<string, unknown>[];\n xKey: string;\n series: SeriesInfo[];\n palette: string[];\n renderSeries: (s: SeriesInfo, color: string, idx: number) => ReactElement;\n width: number;\n height: number;\n}) {\n return (\n <Chart data={chartData} width={width} height={height}>\n <CartesianGrid strokeDasharray=\"3 3\" stroke={GRID_STROKE} />\n <XAxis dataKey={xKey} tick={AXIS_STYLE} />\n <YAxis tick={AXIS_STYLE} />\n <Tooltip\n contentStyle={TOOLTIP_CONTENT_STYLE}\n labelStyle={TOOLTIP_LABEL_STYLE}\n labelFormatter={tooltipLabelFormatter}\n cursor={{ fill: 'var(--bg-paper)', opacity: 0.3 }}\n />\n {series.length > 1 && <Legend />}\n {series.map((s, i) => renderSeries(s, palette[i % palette.length], i))}\n </Chart>\n );\n}\n\ninterface Props {\n data: Record<string, unknown>;\n palette: string[];\n label?: string;\n}\n\nexport function ChartWidget({ data, palette, label: propLabel }: Props) {\n const chartType = String(data.chartType || 'bar');\n const title = propLabel || String(data.label || '');\n const xKey = String(data.xKey || 'label');\n const series = (data.series || []) as SeriesInfo[];\n const chartData = (data.data || []) as Record<string, unknown>[];\n\n const containerRef = useRef<HTMLDivElement>(null);\n const { width, height } = useContainerSize(containerRef);\n\n const renderChart = () => {\n if (width <= 0 || height <= 0) return null;\n\n if (chartType === 'pie') {\n return (\n <PieChart width={width} height={height}>\n <Pie\n data={chartData}\n dataKey={series[0]?.key || 's0'}\n nameKey={xKey}\n cx=\"50%\" cy=\"50%\" outerRadius=\"75%\"\n label={({ name, percent }: { name: string; percent: number }) =>\n `${name}: ${(percent * 100).toFixed(0)}%`\n }\n labelLine={false}\n >\n {chartData.map((_, i) => (\n <Cell key={i} fill={palette[i % palette.length]} />\n ))}\n </Pie>\n <Tooltip\n contentStyle={TOOLTIP_CONTENT_STYLE}\n labelStyle={TOOLTIP_LABEL_STYLE}\n labelFormatter={tooltipLabelFormatter}\n />\n </PieChart>\n );\n }\n\n const common = { chartData, xKey, series, palette, width, height };\n\n if (chartType === 'line') {\n return (\n <CartesianChart {...common} Chart={LineChart} renderSeries={(s, color) => (\n <Line key={s.key} type=\"monotone\" dataKey={s.key} name={s.label}\n stroke={color} strokeWidth={2} dot={chartData.length <= 31} />\n )} />\n );\n }\n\n if (chartType === 'area') {\n return (\n <CartesianChart {...common} Chart={AreaChart} renderSeries={(s, color) => (\n <Area key={s.key} type=\"monotone\" dataKey={s.key} name={s.label}\n fill={color} stroke={color} fillOpacity={0.3} />\n )} />\n );\n }\n\n return (\n <CartesianChart {...common} Chart={BarChart} renderSeries={(s, color) => (\n <Bar key={s.key} dataKey={s.key} name={s.label}\n fill={color} radius={[3, 3, 0, 0]} />\n )} />\n );\n };\n\n return (\n <div className=\"widget widget-chart\">\n {title && <h4 className=\"widget-chart__title\">{title}</h4>}\n {/* Container sempre montado: mantem o ResizeObserver atado ao mesmo elemento\n mesmo no estado vazio, evitando que o grafico nao remonte ao voltar dados. */}\n <div ref={containerRef} className=\"widget-chart__container\">\n {chartData.length === 0\n ? <div className=\"widget-chart__empty\">Sem dados</div>\n : renderChart()}\n </div>\n </div>\n );\n}\n","// Purpose: Widget de filtro interativo no grid (date_range, select, multi_select).\n// Scope: Modos temporais (range, monthly, weekly, yearly), select unico, multi-select.\n// Modo categorico padrao (select/checkbox) ou lista com busca (searchable).\n// Public API: FilterWidget\n\nimport type { FilterConfig, DateFilterMode } from '../types';\nimport {\n MONTH_NAMES_SHORT, getFullYearRange, getMonthRange,\n getMonthWeeks, parseMonthWeekFromRange,\n parseYearFromRange, parseMonthFromRange, getYearRange,\n} from '../utils/date';\nimport { DashboardDatePicker } from '../components/DashboardDatePicker';\nimport { SearchableSelect } from '../components/SearchableSelect';\nimport { MULTI_VALUE_SEPARATOR } from '../types';\n\ninterface Props {\n config: FilterConfig;\n value: string;\n options?: string[];\n dateBounds?: { min: string | null; max: string | null } | null;\n onChange: (value: string) => void;\n}\n\n// -------Componente principal-------\n\nexport function FilterWidget({ config, value, options = [], dateBounds, onChange }: Props) {\n const filterType = config.filterType || 'select';\n const label = config.label || 'Filtro';\n const dateMode: DateFilterMode = config.dateFilterMode || 'range';\n\n return (\n <div className=\"widget-filter\">\n <label className=\"widget-filter__label\">{label}</label>\n {filterType === 'date_range' ? (\n dateMode === 'yearly' ? (\n <YearlyFilter value={value} dateBounds={dateBounds} onChange={onChange} />\n ) : dateMode === 'monthly' ? (\n <MonthlyFilter value={value} dateBounds={dateBounds} onChange={onChange} />\n ) : dateMode === 'weekly' ? (\n <WeeklyFilter value={value} dateBounds={dateBounds} onChange={onChange} />\n ) : (\n <DateRangeFilter value={value} dateBounds={dateBounds} onChange={onChange} />\n )\n ) : (\n <SelectFilter\n value={value}\n options={options}\n multi={filterType === 'multi_select'}\n searchable={config.searchable || false}\n onChange={onChange}\n />\n )}\n </div>\n );\n}\n\n// -------DateRangeFilter (modo range puro)-------\n\nfunction DateRangeFilter({ value, dateBounds, onChange }: {\n value: string;\n dateBounds?: { min: string | null; max: string | null } | null;\n onChange: (value: string) => void;\n}) {\n const [start, end] = value ? value.split('|') : ['', ''];\n\n return (\n <div className=\"widget-filter__date-range widget-filter__date-range--stacked\">\n <DashboardDatePicker\n value={start}\n minIso={dateBounds?.min}\n maxIso={end || dateBounds?.max}\n selectsStart\n startIso={start}\n endIso={end}\n placeholder=\"Data inicial\"\n onChange={(iso) => onChange(`${iso}|${end}`)}\n />\n <DashboardDatePicker\n value={end}\n minIso={start || dateBounds?.min}\n maxIso={dateBounds?.max}\n selectsEnd\n startIso={start}\n endIso={end}\n placeholder=\"Data final\"\n onChange={(iso) => onChange(`${start}|${iso}`)}\n />\n </div>\n );\n}\n\n// -------YearlyFilter (modo anual)-------\n\nfunction YearlyFilter({ value, dateBounds, onChange }: {\n value: string;\n dateBounds?: { min: string | null; max: string | null } | null;\n onChange: (value: string) => void;\n}) {\n const [start] = value ? value.split('|') : [''];\n const parsed = parseYearFromRange(start);\n const now = new Date();\n const selectedYear = parsed?.year ?? now.getFullYear();\n const years = getYearRange(dateBounds);\n\n const handleYearChange = (year: number) => {\n const yr = getFullYearRange(year);\n onChange(`${yr.start}|${yr.end}`);\n };\n\n return (\n <div className=\"widget-filter__date-range widget-filter__date-range--year\">\n <select\n className=\"widget-filter__select\"\n value={selectedYear}\n onChange={(e) => handleYearChange(parseInt(e.target.value))}\n >\n {years.map((y) => <option key={y} value={y}>{y}</option>)}\n </select>\n </div>\n );\n}\n\n// -------MonthlyFilter (modo mensal)-------\n\nfunction MonthlyFilter({ value, dateBounds, onChange }: {\n value: string;\n dateBounds?: { min: string | null; max: string | null } | null;\n onChange: (value: string) => void;\n}) {\n const [start] = value ? value.split('|') : [''];\n const parsed = parseMonthFromRange(start);\n const now = new Date();\n const selectedYear = parsed?.year ?? now.getFullYear();\n const selectedMonth = parsed?.month ?? (now.getMonth() + 1);\n const years = getYearRange(dateBounds);\n\n const handleMonthChange = (year: number, month: number) => {\n const range = getMonthRange(year, month);\n onChange(`${range.start}|${range.end}`);\n };\n\n return (\n <div className=\"widget-filter__date-range widget-filter__date-range--month\">\n <select\n className=\"widget-filter__select\"\n value={selectedMonth}\n onChange={(e) => handleMonthChange(selectedYear, parseInt(e.target.value))}\n >\n {MONTH_NAMES_SHORT.map((name, i) => (\n <option key={i + 1} value={i + 1}>{name}</option>\n ))}\n </select>\n <select\n className=\"widget-filter__select\"\n value={selectedYear}\n onChange={(e) => handleMonthChange(parseInt(e.target.value), selectedMonth)}\n >\n {years.map((y) => <option key={y} value={y}>{y}</option>)}\n </select>\n </div>\n );\n}\n\n// -------WeeklyFilter (modo semanal)-------\n\nfunction WeeklyFilter({ value, dateBounds, onChange }: {\n value: string;\n dateBounds?: { min: string | null; max: string | null } | null;\n onChange: (value: string) => void;\n}) {\n const [start] = value ? value.split('|') : [''];\n const parsed = parseMonthFromRange(start);\n const now = new Date();\n const selectedYear = parsed?.year ?? now.getFullYear();\n const selectedMonth = parsed?.month ?? (now.getMonth() + 1);\n const years = getYearRange(dateBounds);\n\n const monthWeeks = getMonthWeeks(selectedYear, selectedMonth);\n const selectedWeekIdx = parseMonthWeekFromRange(start, selectedYear, selectedMonth) || 1;\n\n return (\n <div className=\"widget-filter__date-range widget-filter__date-range--week\">\n <select\n className=\"widget-filter__select\"\n value={selectedYear}\n onChange={(e) => {\n const y = parseInt(e.target.value);\n const weeks = getMonthWeeks(y, selectedMonth);\n const w = weeks[0];\n if (w) onChange(`${w.start}|${w.end}`);\n }}\n >\n {years.map((y) => <option key={y} value={y}>{y}</option>)}\n </select>\n <select\n className=\"widget-filter__select\"\n value={selectedMonth}\n onChange={(e) => {\n const m = parseInt(e.target.value);\n const weeks = getMonthWeeks(selectedYear, m);\n const w = weeks[0];\n if (w) onChange(`${w.start}|${w.end}`);\n }}\n >\n {MONTH_NAMES_SHORT.map((name, i) => (\n <option key={i + 1} value={i + 1}>{name}</option>\n ))}\n </select>\n <select\n className=\"widget-filter__select\"\n value={selectedWeekIdx}\n onChange={(e) => {\n const w = monthWeeks[parseInt(e.target.value) - 1];\n if (w) onChange(`${w.start}|${w.end}`);\n }}\n >\n {monthWeeks.map((w) => (\n <option key={w.index} value={w.index}>{w.label}</option>\n ))}\n </select>\n </div>\n );\n}\n\n// -------SelectFilter (categorico)-------\n\nfunction SelectFilter({ value, options, multi, searchable, onChange }: {\n value: string;\n options: string[];\n multi: boolean;\n searchable: boolean;\n onChange: (value: string) => void;\n}) {\n // Modo lista com busca: unico componente cobre selecao unica e multipla\n if (searchable) {\n return (\n <SearchableSelect\n value={value}\n options={options}\n multi={multi}\n onChange={onChange}\n />\n );\n }\n\n if (multi) {\n const selected = value ? value.split(MULTI_VALUE_SEPARATOR) : [];\n const toggle = (opt: string) => {\n const next = selected.includes(opt)\n ? selected.filter((s) => s !== opt)\n : [...selected, opt];\n onChange(next.join(MULTI_VALUE_SEPARATOR));\n };\n\n return (\n <div className=\"widget-filter__multi\">\n {/* Limpar filtro: desmarca tudo. Vazio = todos selecionados (sem filtro). */}\n {selected.length > 0 && (\n <button\n type=\"button\"\n className=\"widget-filter__multi-clear\"\n onClick={() => onChange('')}\n >\n Limpar filtro\n </button>\n )}\n {options.map((opt) => (\n <label key={opt} className=\"widget-filter__multi-option\">\n <input\n type=\"checkbox\"\n checked={selected.includes(opt)}\n onChange={() => toggle(opt)}\n />\n {opt}\n </label>\n ))}\n </div>\n );\n }\n\n return (\n <select\n className=\"widget-filter__select\"\n value={value}\n onChange={(e) => onChange(e.target.value)}\n >\n <option value=\"\">Todos</option>\n {options.map((opt) => (\n <option key={opt} value={opt}>{opt}</option>\n ))}\n </select>\n );\n}\n","// Purpose: Widget de variavel editavel no grid (what-if scenarios).\n// Scope: Input numerico com label, formato e opcao de bloqueio.\n// Public API: VariableWidget\n\nimport type { VariableConfig } from '../types';\n\ninterface Props {\n config: VariableConfig;\n value: number;\n onChange: (value: number) => void;\n}\n\nconst FORMAT_SUFFIX: Record<string, string> = {\n currency: 'R$',\n percentage: '%',\n};\n\nexport function VariableWidget({ config, value, onChange }: Props) {\n const label = config.label || 'Variavel';\n const locked = config.locked || false;\n const fmt = config.variableFormat || 'number';\n const suffix = FORMAT_SUFFIX[fmt] || '';\n\n return (\n <div className={`widget-variable ${locked ? 'widget-variable--locked' : ''}`}>\n <label className=\"widget-variable__label\">{label}</label>\n <div className=\"widget-variable__input-wrapper\">\n <input\n className=\"widget-variable__input\"\n type=\"number\"\n value={value}\n onChange={(e) => onChange(parseFloat(e.target.value) || 0)}\n disabled={locked}\n step={fmt === 'integer' ? 1 : 0.01}\n />\n {suffix && <span className=\"widget-variable__suffix\">{suffix}</span>}\n </div>\n {locked && <span className=\"widget-variable__lock-icon\" title=\"Bloqueado\">🔒</span>}\n </div>\n );\n}\n","// Purpose: Widget de paleta de cores editavel no grid.\n// Scope: Permite ao usuario do dashboard trocar a paleta em runtime. Respeita bloqueio.\n// Public API: ColorPaletteWidget\n\nimport type { PaletteConfig } from '../types';\nimport { ColorPaletteSelector } from '../components/ColorPaletteSelector';\n\ninterface Props {\n config: PaletteConfig;\n palette: string[];\n onChange: (colors: string[]) => void;\n}\n\nexport function ColorPaletteWidget({ config, palette, onChange }: Props) {\n const label = config.label || 'Cores';\n const locked = config.locked || false;\n\n return (\n <div className={`widget-palette ${locked ? 'widget-palette--locked' : ''}`}>\n <label className=\"widget-palette__label\">{label}</label>\n <ColorPaletteSelector selected={palette} onSelect={onChange} customMode disabled={locked} />\n {locked && <span className=\"widget-palette__lock-icon\" title=\"Bloqueado\">🔒</span>}\n </div>\n );\n}\n","// Purpose: Dispatch de rendering por tipo de widget (dados + controle).\n// Scope: Recebe computed data e/ou config, renderiza widget correto.\n// Public API: WidgetRenderer\n\nimport type { WidgetType, AnyWidgetConfig, FilterConfig, VariableConfig, PaletteConfig } from '../types';\nimport { getSeries } from '../palettes';\nimport { KPIWidget } from './KPIWidget';\nimport { GaugeWidget } from './GaugeWidget';\nimport { ChartWidget } from './ChartWidget';\nimport { FilterWidget } from './FilterWidget';\nimport { VariableWidget } from './VariableWidget';\nimport { ColorPaletteWidget } from './ColorPaletteWidget';\n\ninterface Props {\n type: WidgetType;\n computed: Record<string, unknown>;\n palette: string[];\n // Control widget props (opcionais)\n config?: AnyWidgetConfig;\n filterValue?: string;\n filterOptions?: string[];\n dateBounds?: { min: string; max: string } | null;\n onFilterChange?: (value: string) => void;\n variableValue?: number;\n onVariableChange?: (value: number) => void;\n onPaletteChange?: (colors: string[]) => void;\n}\n\nexport function WidgetRenderer({\n type, computed, palette, config,\n filterValue, filterOptions, dateBounds, onFilterChange,\n variableValue, onVariableChange,\n onPaletteChange,\n}: Props) {\n if (computed.error) {\n return (\n <div className=\"widget widget--error\">\n <span className=\"widget__error-text\">{String(computed.error)}</span>\n </div>\n );\n }\n\n // Widgets de dados usam apenas as cores de series (5 primeiras).\n // UI colors sao aplicadas via CSS vars no grid container.\n const seriesColors = getSeries(palette);\n\n switch (type) {\n case 'kpi_card':\n return <KPIWidget data={computed} label={config?.label} />;\n case 'gauge':\n return <GaugeWidget data={computed} palette={seriesColors} label={config?.label} />;\n case 'chart':\n return <ChartWidget data={computed} palette={seriesColors} label={config?.label} />;\n case 'filter':\n return config && onFilterChange ? (\n <FilterWidget\n config={config as FilterConfig}\n value={filterValue || ''}\n options={filterOptions}\n dateBounds={dateBounds}\n onChange={onFilterChange}\n />\n ) : null;\n case 'variable': {\n const vc = config as VariableConfig | undefined;\n return vc && onVariableChange ? (\n <VariableWidget\n config={vc}\n value={variableValue ?? vc.variableValue ?? 0}\n onChange={onVariableChange}\n />\n ) : null;\n }\n case 'color_palette':\n return config && onPaletteChange ? (\n <ColorPaletteWidget\n config={config as PaletteConfig}\n palette={palette}\n onChange={onPaletteChange}\n />\n ) : null;\n default:\n return <div className=\"widget\">Widget: {type}</div>;\n }\n}\n","// Purpose: Componente top-level que renderiza um dashboard completo.\n// Scope: Busca layout + render da API Action com o token, aplica paleta como CSS vars,\n// renderiza grid com widgets interativos (filtros + variaveis + paleta).\n// Public API: Dashboard\n\nimport type { CSSProperties } from 'react';\nimport { useDashboardData } from './hooks/useDashboardData';\nimport { WidgetRenderer } from './widgets/WidgetRenderer';\nimport { getPaletteCssVars } from './palettes';\nimport { CONTROL_WIDGET_SET } from './types';\n\nconst GRID_ROW_HEIGHT_REM = 2.5;\nconst GRID_GAP_REM = 0.375;\n\ninterface DashboardProps {\n /** Token Bearer de acesso ao dashboard. */\n token: string;\n /** Altura de cada linha do grid em rem. Default 2.5 (40px no base 16). */\n rowHeight?: number;\n /** Gap entre widgets em rem. Default 0.375 (6px no base 16). */\n gridGap?: number;\n /** Classe CSS adicional no container raiz. */\n className?: string;\n}\n\nexport function Dashboard({\n token,\n rowHeight = GRID_ROW_HEIGHT_REM,\n gridGap = GRID_GAP_REM,\n className,\n}: DashboardProps) {\n const {\n layout, renderData, loading, error,\n filters, variables, palette,\n setFilter, setVariable, setPalette,\n } = useDashboardData(token);\n\n if (error && !layout) {\n return <div className={`preview-tab ${className ?? ''}`}><div className=\"preview-tab__error\">{error}</div></div>;\n }\n\n if (!layout) {\n return <div className={`preview-tab ${className ?? ''}`}><div className=\"preview-tab__loading\">Carregando dashboard...</div></div>;\n }\n\n if (layout.widgets.length === 0) {\n return (\n <div className={`preview-tab ${className ?? ''}`}>\n <div className=\"preview-tab__empty\">Este dashboard nao possui widgets.</div>\n </div>\n );\n }\n\n const widgetsData = renderData?.widgets ?? {};\n const dateBounds = renderData?.date_bounds ?? null;\n\n const gridStyle: CSSProperties = {\n display: 'grid',\n gridTemplateColumns: `repeat(${layout.gridColumns}, 1fr)`,\n gridTemplateRows: `repeat(${layout.gridRows}, ${rowHeight}rem)`,\n gap: `${gridGap}rem`,\n ...getPaletteCssVars(palette),\n } as CSSProperties;\n\n return (\n <div className={`preview-tab ${className ?? ''}`}>\n {error && !renderData && <div className=\"preview-tab__error\">{error}</div>}\n\n {renderData && (\n <div className=\"preview-tab__grid\" style={gridStyle}>\n {layout.widgets.map((widget) => {\n const isControl = CONTROL_WIDGET_SET.has(widget.type);\n const computed = widgetsData[widget.id];\n const widgetStyle: CSSProperties = {\n gridColumn: `${widget.grid.x + 1} / span ${widget.grid.w}`,\n gridRow: `${widget.grid.y + 1} / span ${widget.grid.h}`,\n };\n\n const variableValue = widget.type === 'variable'\n ? variables[widget.id] ?? (computed?.value as number) ?? widget.config.variableValue ?? 0\n : undefined;\n\n return (\n <div\n key={widget.id}\n className={`preview-tab__widget ${isControl ? 'preview-tab__widget--control' : ''}`}\n style={widgetStyle}\n >\n {isControl || computed ? (\n <WidgetRenderer\n type={widget.type}\n computed={computed || {}}\n palette={palette}\n config={widget.config}\n filterValue={filters[widget.id] || ''}\n filterOptions={(computed?.available_values as string[]) || []}\n dateBounds={dateBounds}\n onFilterChange={(val) => setFilter(widget.id, val)}\n variableValue={variableValue}\n onVariableChange={(val) => setVariable(widget.id, val)}\n onPaletteChange={setPalette}\n />\n ) : (\n <div className=\"preview-tab__widget-loading\">\n {loading ? 'Carregando...' : 'Sem dados'}\n </div>\n )}\n </div>\n );\n })}\n </div>\n )}\n\n {loading && renderData && (\n <div className=\"preview-tab__recalculating\">Atualizando...</div>\n )}\n </div>\n );\n}\n"],"names":["DEBOUNCE_MS","useDashboardData","token","layout","setLayout","useState","renderData","setRenderData","filters","setFilters","variables","setVariables","localPalette","setLocalPalette","loading","setLoading","error","setError","debounceRef","useRef","appliedSyncedRef","useEffect","cancelled","fetchLayout","res","err","params","buildQueryParams","fetchRender","prev","syncFiltersFromApplied","setFilter","useCallback","widgetId","value","setVariable","setPalette","colors","palette","useMemo","key","val","start","end","applied","synced","id","d","MULTI_VALUE_SEPARATOR","KPIWidget","data","label","displayLabel","formatted","comparison","trendClass","arrow","jsxs","jsx","COLOR_EMPTY","arcPath","cx","cy","r","fraction","angle","endX","endY","formatCompact","abs","GaugeWidget","propLabel","rawValue","valueFormatted","ratio","targetValue","comparisonLabel","exceeded","clamped","fillColor","targetFormatted","stroke","AXIS_STYLE","GRID_STROKE","TOOLTIP_CONTENT_STYLE","TOOLTIP_LABEL_STYLE","tooltipLabelFormatter","payload","first","verbose","_a","useContainerSize","ref","size","setSize","el","observer","entry","width","height","CartesianChart","Chart","chartData","xKey","series","renderSeries","CartesianGrid","XAxis","YAxis","Tooltip","Legend","s","i","ChartWidget","chartType","title","containerRef","renderChart","PieChart","Pie","name","percent","_","Cell","common","LineChart","color","Line","AreaChart","Area","BarChart","Bar","FilterWidget","config","options","dateBounds","onChange","filterType","dateMode","YearlyFilter","MonthlyFilter","WeeklyFilter","DateRangeFilter","SelectFilter","DashboardDatePicker","iso","parsed","parseYearFromRange","now","selectedYear","years","getYearRange","handleYearChange","year","yr","getFullYearRange","e","y","parseMonthFromRange","selectedMonth","handleMonthChange","month","range","getMonthRange","MONTH_NAMES_SHORT","monthWeeks","getMonthWeeks","selectedWeekIdx","parseMonthWeekFromRange","w","m","multi","searchable","SearchableSelect","selected","toggle","opt","next","FORMAT_SUFFIX","VariableWidget","locked","fmt","suffix","ColorPaletteWidget","ColorPaletteSelector","WidgetRenderer","type","computed","filterValue","filterOptions","onFilterChange","variableValue","onVariableChange","onPaletteChange","seriesColors","getSeries","vc","GRID_ROW_HEIGHT_REM","GRID_GAP_REM","Dashboard","rowHeight","gridGap","className","widgetsData","gridStyle","getPaletteCssVars","widget","isControl","CONTROL_WIDGET_SET","widgetStyle"],"mappings":"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"}
@@ -1,9 +1,10 @@
1
1
  export { setApiUrl } from './api/fetcher';
2
2
  export type { AggregationType, ComparisonType, FilterType, WidgetType, DataWidgetType, ControlWidgetType, ChartType, FormatType, DateFilterMode, Granularity, FilterDefinition, TargetDefinition, GridPosition, ComparisonConfig, AggregationStep, ColumnExpressionTerm, KpiOperand, KpiTerm, ChartSeriesConfig, ChartAxisConfig, KpiCardConfig, GaugeConfig, ChartConfig, FilterConfig, VariableConfig, PaletteConfig, AnyWidgetConfig, WidgetDefinition, WidgetConfigOf, DashboardLayout, FilterValuesResponse, RenderResponse, LayoutResponse, } from './types';
3
- export { DEFAULT_PALETTE, DEFAULT_GRID_COLUMNS, DEFAULT_GRID_ROWS, EMPTY_LAYOUT, WIDGET_TYPE_LABELS, DATA_WIDGET_TYPES, CONTROL_WIDGET_TYPES, CONTROL_WIDGET_SET, AGGREGATION_LABELS, FORMAT_LABELS, NUMERIC_FORMAT_OPTIONS, COMPARISON_LABELS, CHART_TYPE_LABELS, FILTER_TYPE_LABELS, DEFAULT_GRID, DEFAULT_CONFIG, } from './types';
3
+ export { DEFAULT_PALETTE, DEFAULT_GRID_COLUMNS, DEFAULT_GRID_ROWS, EMPTY_LAYOUT, WIDGET_TYPE_LABELS, DATA_WIDGET_TYPES, CONTROL_WIDGET_TYPES, CONTROL_WIDGET_SET, AGGREGATION_LABELS, FORMAT_LABELS, NUMERIC_FORMAT_OPTIONS, COMPARISON_LABELS, CHART_TYPE_LABELS, FILTER_TYPE_LABELS, DEFAULT_GRID, DEFAULT_CONFIG, MULTI_VALUE_SEPARATOR, } from './types';
4
4
  export { PALETTES, DEFAULT_PALETTE_COLORS, SLOT_INDEX, SLOT_LABELS, SERIES_COUNT, TOTAL_SLOTS, ensurePaletteShape, getSeries, getPaletteCssVars, } from './palettes';
5
5
  export type { Palette, PaletteKey } from './palettes';
6
6
  export { MONTH_NAMES_SHORT, MONTH_NAMES_FULL, getFullYearRange, getMonthRange, getWeekRange, getISOWeek, getWeeksInMonth, getMonthWeeks, parseYearFromRange, parseMonthFromRange, parseWeekFromRange, parseMonthWeekFromRange, getYearRange, } from './utils/date';
7
7
  export type { MonthWeek } from './utils/date';
8
8
  export { ColorPaletteSelector } from './components/ColorPaletteSelector';
9
9
  export { DashboardDatePicker, isoToDate, dateToIso } from './components/DashboardDatePicker';
10
+ export { SearchableSelect } from './components/SearchableSelect';
package/dist/internals.js CHANGED
@@ -1,4 +1,4 @@
1
- import { A as e, C as T, a as E, b as L, c as _, d as A, D as S, e as t, f as O, g as R, h as r, i as o, j as D, k as I, E as g, F, l as n, M, m as P, N, P as C, S as G, n as U, o as W, T as Y, W as l, p as h, q as k, r as p, s as B, t as m, u as i, v as H, w as c, x as d, y as u, z as b, B as f, G as x, H as j, I as q, J as v, K as w } from "./index-CxUAEQYp.js";
1
+ import { A as e, C as T, a as E, b as L, c as _, d as A, D as S, e as t, f as O, g as R, h as r, i as o, j as I, k as D, E as g, F, l as M, M as P, m as n, n as N, N as U, P as C, S as G, o as W, p as l, q as Y, T as h, W as k, r as p, s as B, t as m, u as c, v as i, w as H, x as b, y as d, z as u, B as f, G as x, H as V, I as j, J as q, K as v, L as w, O as y } from "./ColorPaletteSelector-B4ojsspD.js";
2
2
  export {
3
3
  e as AGGREGATION_LABELS,
4
4
  T as CHART_TYPE_LABELS,
@@ -12,36 +12,38 @@ export {
12
12
  R as DEFAULT_GRID_COLUMNS,
13
13
  r as DEFAULT_GRID_ROWS,
14
14
  o as DEFAULT_PALETTE,
15
- D as DEFAULT_PALETTE_COLORS,
16
- I as DashboardDatePicker,
15
+ I as DEFAULT_PALETTE_COLORS,
16
+ D as DashboardDatePicker,
17
17
  g as EMPTY_LAYOUT,
18
18
  F as FILTER_TYPE_LABELS,
19
- n as FORMAT_LABELS,
20
- M as MONTH_NAMES_FULL,
21
- P as MONTH_NAMES_SHORT,
22
- N as NUMERIC_FORMAT_OPTIONS,
19
+ M as FORMAT_LABELS,
20
+ P as MONTH_NAMES_FULL,
21
+ n as MONTH_NAMES_SHORT,
22
+ N as MULTI_VALUE_SEPARATOR,
23
+ U as NUMERIC_FORMAT_OPTIONS,
23
24
  C as PALETTES,
24
25
  G as SERIES_COUNT,
25
- U as SLOT_INDEX,
26
- W as SLOT_LABELS,
27
- Y as TOTAL_SLOTS,
28
- l as WIDGET_TYPE_LABELS,
29
- h as dateToIso,
30
- k as ensurePaletteShape,
31
- p as getFullYearRange,
32
- B as getISOWeek,
33
- m as getMonthRange,
34
- i as getMonthWeeks,
35
- H as getPaletteCssVars,
36
- c as getSeries,
37
- d as getWeekRange,
38
- u as getWeeksInMonth,
39
- b as getYearRange,
40
- f as isoToDate,
41
- x as parseMonthFromRange,
42
- j as parseMonthWeekFromRange,
43
- q as parseWeekFromRange,
44
- v as parseYearFromRange,
45
- w as setApiUrl
26
+ W as SLOT_INDEX,
27
+ l as SLOT_LABELS,
28
+ Y as SearchableSelect,
29
+ h as TOTAL_SLOTS,
30
+ k as WIDGET_TYPE_LABELS,
31
+ p as dateToIso,
32
+ B as ensurePaletteShape,
33
+ m as getFullYearRange,
34
+ c as getISOWeek,
35
+ i as getMonthRange,
36
+ H as getMonthWeeks,
37
+ b as getPaletteCssVars,
38
+ d as getSeries,
39
+ u as getWeekRange,
40
+ f as getWeeksInMonth,
41
+ x as getYearRange,
42
+ V as isoToDate,
43
+ j as parseMonthFromRange,
44
+ q as parseMonthWeekFromRange,
45
+ v as parseWeekFromRange,
46
+ w as parseYearFromRange,
47
+ y as setApiUrl
46
48
  };
47
49
  //# sourceMappingURL=internals.js.map
package/dist/styles.css CHANGED
@@ -1 +1 @@
1
- @charset "UTF-8";.react-datepicker__navigation-icon:before,.react-datepicker__year-read-view--down-arrow,.react-datepicker__month-read-view--down-arrow,.react-datepicker__month-year-read-view--down-arrow{border-color:#ccc;border-style:solid;border-width:3px 3px 0 0;content:"";display:block;height:9px;position:absolute;top:6px;width:9px}.react-datepicker__sr-only{position:absolute;width:1px;height:1px;padding:0;margin:-1px;overflow:hidden;clip-path:inset(50%);white-space:nowrap;border:0}.react-datepicker-wrapper{display:inline-block;padding:0;border:0}.react-datepicker{font-family:Helvetica Neue,helvetica,arial,sans-serif;font-size:.8rem;background-color:#fff;color:#000;border:1px solid #aeaeae;border-radius:.3rem;display:inline-block;position:relative;line-height:initial}.react-datepicker--time-only .react-datepicker__time-container{border-left:0}.react-datepicker--time-only .react-datepicker__time,.react-datepicker--time-only .react-datepicker__time-box{border-bottom-left-radius:.375em;border-bottom-right-radius:.375em}.react-datepicker-popper{z-index:1;line-height:0}.react-datepicker-popper .react-datepicker__triangle{stroke:#aeaeae}.react-datepicker-popper[data-placement^=bottom] .react-datepicker__triangle{fill:#f0f0f0;color:#f0f0f0}.react-datepicker-popper[data-placement^=top] .react-datepicker__triangle,.react-datepicker-popper--header-middle[data-placement^=bottom] .react-datepicker__triangle,.react-datepicker-popper--header-bottom[data-placement^=bottom] .react-datepicker__triangle{fill:#fff;color:#fff}.react-datepicker-popper--header-bottom[data-placement^=top] .react-datepicker__triangle{fill:#f0f0f0;color:#f0f0f0}.react-datepicker__header{text-align:center;background-color:#f0f0f0;border-bottom:1px solid #aeaeae;border-top-left-radius:.3rem;padding:8px 0;position:relative}.react-datepicker__header--time{padding-bottom:8px;padding-left:5px;padding-right:5px}.react-datepicker__header--time:not(.react-datepicker__header--time--only){border-top-left-radius:0}.react-datepicker__header:not(.react-datepicker__header--has-time-select,.react-datepicker__header--middle,.react-datepicker__header--bottom){border-top-right-radius:.3rem}.react-datepicker__header--middle{border-top:1px solid #aeaeae;border-radius:0;margin-top:4px}.react-datepicker__header--bottom{border-bottom:none;border-top:1px solid #aeaeae;border-radius:0 0 .3rem .3rem}.react-datepicker__header-wrapper{position:relative}.react-datepicker__header-wrapper .react-datepicker__navigation--next--with-time:not(.react-datepicker__navigation--next--with-today-button){right:2px}.react-datepicker__year-dropdown-container--select,.react-datepicker__month-dropdown-container--select,.react-datepicker__month-year-dropdown-container--select,.react-datepicker__year-dropdown-container--scroll,.react-datepicker__month-dropdown-container--scroll,.react-datepicker__month-year-dropdown-container--scroll{display:inline-block;margin:0 15px}.react-datepicker__month-select,.react-datepicker__year-select,.react-datepicker__month-year-select{background-color:transparent;border:1px solid #aeaeae;border-radius:.3rem;color:inherit;cursor:pointer;font-family:inherit;font-size:inherit;margin-top:5px;padding:2px 5px}.react-datepicker__month-select:focus-visible,.react-datepicker__year-select:focus-visible,.react-datepicker__month-year-select:focus-visible{outline:auto 1px}.react-datepicker__current-month,.react-datepicker-time__header,.react-datepicker-year-header{margin-top:0;color:#000;font-weight:700;font-size:.944rem}h2.react-datepicker__current-month{padding:0;margin:0}.react-datepicker-time__header{text-overflow:ellipsis;white-space:nowrap;overflow:hidden}.react-datepicker__navigation{align-items:center;background:none;display:flex;justify-content:center;text-align:center;cursor:pointer;position:absolute;top:2px;padding:0;border:none;z-index:1;height:32px;width:32px;text-indent:-999em;overflow:hidden}.react-datepicker__navigation--previous{left:2px}.react-datepicker__navigation--next{right:2px}.react-datepicker__navigation--next--with-time:not(.react-datepicker__navigation--next--with-today-button){right:85px}.react-datepicker__navigation--years{position:relative;top:0;display:block;margin-left:auto;margin-right:auto}.react-datepicker__navigation--years-previous{top:4px}.react-datepicker__navigation--years-upcoming{top:-4px}.react-datepicker__navigation:hover *:before{border-color:#a6a6a6}.react-datepicker__navigation-icon{position:relative;top:-1px;font-size:20px;width:0}.react-datepicker__navigation-icon--next{left:-2px}.react-datepicker__navigation-icon--next:before{transform:rotate(45deg);left:-7px}.react-datepicker__navigation-icon--previous{right:-2px}.react-datepicker__navigation-icon--previous:before{transform:rotate(225deg);right:-7px}.react-datepicker__month-container{float:left}.react-datepicker__year{margin:.5em;text-align:center}.react-datepicker__year-wrapper{display:flex;flex-wrap:wrap;max-width:180px}.react-datepicker__year .react-datepicker__year-text{display:inline-block;width:5em;margin:2px}.react-datepicker__month{margin:.5em;text-align:center}.react-datepicker__month .react-datepicker__month-text,.react-datepicker__month .react-datepicker__quarter-text{display:inline-block;width:5em;margin:2px}.react-datepicker__input-time-container{clear:both;width:100%;float:left;margin:5px 0 10px 15px;text-align:left}.react-datepicker__input-time-container .react-datepicker-time__caption,.react-datepicker__input-time-container .react-datepicker-time__input-container{display:inline-block}.react-datepicker__input-time-container .react-datepicker-time__input-container .react-datepicker-time__input{display:inline-block;margin-left:10px}.react-datepicker__input-time-container .react-datepicker-time__input-container .react-datepicker-time__input input{width:auto}.react-datepicker__input-time-container .react-datepicker-time__input-container .react-datepicker-time__input input[type=time]::-webkit-inner-spin-button,.react-datepicker__input-time-container .react-datepicker-time__input-container .react-datepicker-time__input input[type=time]::-webkit-outer-spin-button{-webkit-appearance:none;margin:0}.react-datepicker__input-time-container .react-datepicker-time__input-container .react-datepicker-time__input input[type=time]{-moz-appearance:textfield}.react-datepicker__input-time-container .react-datepicker-time__input-container .react-datepicker-time__delimiter{margin-left:5px;display:inline-block}.react-datepicker__time-container{float:right;border-left:1px solid #aeaeae;width:85px}.react-datepicker__time-container--with-today-button{display:inline;border:1px solid #aeaeae;border-radius:.375em;position:absolute;right:-87px;top:0}.react-datepicker__time-container .react-datepicker__time{position:relative;background:#fff;border-bottom-right-radius:.375em}.react-datepicker__time-container .react-datepicker__time .react-datepicker__time-box{width:85px;overflow-x:hidden;margin:0 auto;text-align:center;border-bottom-right-radius:.375em}.react-datepicker__time-container .react-datepicker__time .react-datepicker__time-box ul.react-datepicker__time-list{list-style:none;margin:0;height:calc(195px + 1.0625em);overflow-y:scroll;padding-right:0;padding-left:0;width:100%;box-sizing:content-box}.react-datepicker__time-container .react-datepicker__time .react-datepicker__time-box ul.react-datepicker__time-list li.react-datepicker__time-list-item{height:30px;padding:5px 10px;white-space:nowrap}.react-datepicker__time-container .react-datepicker__time .react-datepicker__time-box ul.react-datepicker__time-list li.react-datepicker__time-list-item:hover{cursor:pointer;background-color:#f0f0f0}.react-datepicker__time-container .react-datepicker__time .react-datepicker__time-box ul.react-datepicker__time-list li.react-datepicker__time-list-item--selected{background-color:#216ba5;color:#fff;font-weight:700}.react-datepicker__time-container .react-datepicker__time .react-datepicker__time-box ul.react-datepicker__time-list li.react-datepicker__time-list-item--selected:hover{background-color:#216ba5}.react-datepicker__time-container .react-datepicker__time .react-datepicker__time-box ul.react-datepicker__time-list li.react-datepicker__time-list-item--disabled{color:#ccc}.react-datepicker__time-container .react-datepicker__time .react-datepicker__time-box ul.react-datepicker__time-list li.react-datepicker__time-list-item--disabled:hover{cursor:default;background-color:transparent}.react-datepicker__week-number{color:#ccc;display:inline-block;width:2.125em;line-height:2.125em;text-align:center;margin:.208em}.react-datepicker__week-number.react-datepicker__week-number--clickable{cursor:pointer}.react-datepicker__week-number.react-datepicker__week-number--clickable:not(.react-datepicker__week-number--selected):hover{border-radius:.3rem;background-color:#f0f0f0}.react-datepicker__week-number--selected{border-radius:.3rem;background-color:#216ba5;color:#fff}.react-datepicker__week-number--selected:hover{background-color:#1d5d90}.react-datepicker__day-names{text-align:center;white-space:nowrap;margin-bottom:-8px}.react-datepicker__week{white-space:nowrap}.react-datepicker__day-name,.react-datepicker__day,.react-datepicker__time-name{color:#000;display:inline-block;width:2.125em;line-height:2.125em;text-align:center;margin:.208em}.react-datepicker__day-name--disabled,.react-datepicker__day--disabled,.react-datepicker__time-name--disabled{cursor:default;color:#ccc}.react-datepicker__day,.react-datepicker__month-text,.react-datepicker__quarter-text,.react-datepicker__year-text{cursor:pointer}.react-datepicker__day:not([aria-disabled=true]):hover,.react-datepicker__month-text:not([aria-disabled=true]):hover,.react-datepicker__quarter-text:not([aria-disabled=true]):hover,.react-datepicker__year-text:not([aria-disabled=true]):hover{border-radius:.3rem;background-color:#f0f0f0}.react-datepicker__day--today,.react-datepicker__month-text--today,.react-datepicker__quarter-text--today,.react-datepicker__year-text--today{font-weight:700}.react-datepicker__day--highlighted,.react-datepicker__month-text--highlighted,.react-datepicker__quarter-text--highlighted,.react-datepicker__year-text--highlighted{border-radius:.3rem;background-color:#3dcc4a;color:#fff}.react-datepicker__day--highlighted:not([aria-disabled=true]):hover,.react-datepicker__month-text--highlighted:not([aria-disabled=true]):hover,.react-datepicker__quarter-text--highlighted:not([aria-disabled=true]):hover,.react-datepicker__year-text--highlighted:not([aria-disabled=true]):hover{background-color:#32be3f}.react-datepicker__day--highlighted-custom-1,.react-datepicker__month-text--highlighted-custom-1,.react-datepicker__quarter-text--highlighted-custom-1,.react-datepicker__year-text--highlighted-custom-1{color:#f0f}.react-datepicker__day--highlighted-custom-2,.react-datepicker__month-text--highlighted-custom-2,.react-datepicker__quarter-text--highlighted-custom-2,.react-datepicker__year-text--highlighted-custom-2{color:green}.react-datepicker__day--holidays,.react-datepicker__month-text--holidays,.react-datepicker__quarter-text--holidays,.react-datepicker__year-text--holidays{position:relative;border-radius:.3rem;background-color:#ff6803;color:#fff}.react-datepicker__day--holidays .overlay,.react-datepicker__month-text--holidays .overlay,.react-datepicker__quarter-text--holidays .overlay,.react-datepicker__year-text--holidays .overlay{position:absolute;bottom:100%;left:50%;transform:translate(-50%);background-color:#333;color:#fff;padding:4px;border-radius:4px;white-space:nowrap;visibility:hidden;opacity:0;transition:visibility 0s,opacity .3s ease-in-out}.react-datepicker__day--holidays:not([aria-disabled=true]):hover,.react-datepicker__month-text--holidays:not([aria-disabled=true]):hover,.react-datepicker__quarter-text--holidays:not([aria-disabled=true]):hover,.react-datepicker__year-text--holidays:not([aria-disabled=true]):hover{background-color:#cf5300}.react-datepicker__day--holidays:hover .overlay,.react-datepicker__month-text--holidays:hover .overlay,.react-datepicker__quarter-text--holidays:hover .overlay,.react-datepicker__year-text--holidays:hover .overlay{visibility:visible;opacity:1}.react-datepicker__day--selected,.react-datepicker__day--in-selecting-range,.react-datepicker__day--in-range,.react-datepicker__month-text--selected,.react-datepicker__month-text--in-selecting-range,.react-datepicker__month-text--in-range,.react-datepicker__quarter-text--selected,.react-datepicker__quarter-text--in-selecting-range,.react-datepicker__quarter-text--in-range,.react-datepicker__year-text--selected,.react-datepicker__year-text--in-selecting-range,.react-datepicker__year-text--in-range{border-radius:.3rem;background-color:#216ba5;color:#fff}.react-datepicker__day--selected:not([aria-disabled=true]):hover,.react-datepicker__day--in-selecting-range:not([aria-disabled=true]):hover,.react-datepicker__day--in-range:not([aria-disabled=true]):hover,.react-datepicker__month-text--selected:not([aria-disabled=true]):hover,.react-datepicker__month-text--in-selecting-range:not([aria-disabled=true]):hover,.react-datepicker__month-text--in-range:not([aria-disabled=true]):hover,.react-datepicker__quarter-text--selected:not([aria-disabled=true]):hover,.react-datepicker__quarter-text--in-selecting-range:not([aria-disabled=true]):hover,.react-datepicker__quarter-text--in-range:not([aria-disabled=true]):hover,.react-datepicker__year-text--selected:not([aria-disabled=true]):hover,.react-datepicker__year-text--in-selecting-range:not([aria-disabled=true]):hover,.react-datepicker__year-text--in-range:not([aria-disabled=true]):hover{background-color:#1d5d90}.react-datepicker__day--keyboard-selected,.react-datepicker__month-text--keyboard-selected,.react-datepicker__quarter-text--keyboard-selected,.react-datepicker__year-text--keyboard-selected{border-radius:.3rem;background-color:#bad9f1;color:#000}.react-datepicker__day--keyboard-selected:not([aria-disabled=true]):hover,.react-datepicker__month-text--keyboard-selected:not([aria-disabled=true]):hover,.react-datepicker__quarter-text--keyboard-selected:not([aria-disabled=true]):hover,.react-datepicker__year-text--keyboard-selected:not([aria-disabled=true]):hover{background-color:#1d5d90;color:#fff}.react-datepicker__day--in-selecting-range:not(.react-datepicker__day--in-range,.react-datepicker__month-text--in-range,.react-datepicker__quarter-text--in-range,.react-datepicker__year-text--in-range),.react-datepicker__month-text--in-selecting-range:not(.react-datepicker__day--in-range,.react-datepicker__month-text--in-range,.react-datepicker__quarter-text--in-range,.react-datepicker__year-text--in-range),.react-datepicker__quarter-text--in-selecting-range:not(.react-datepicker__day--in-range,.react-datepicker__month-text--in-range,.react-datepicker__quarter-text--in-range,.react-datepicker__year-text--in-range),.react-datepicker__year-text--in-selecting-range:not(.react-datepicker__day--in-range,.react-datepicker__month-text--in-range,.react-datepicker__quarter-text--in-range,.react-datepicker__year-text--in-range){background-color:#216ba580}.react-datepicker__month--selecting-range .react-datepicker__day--in-range:not(.react-datepicker__day--in-selecting-range,.react-datepicker__month-text--in-selecting-range,.react-datepicker__quarter-text--in-selecting-range,.react-datepicker__year-text--in-selecting-range),.react-datepicker__year--selecting-range .react-datepicker__day--in-range:not(.react-datepicker__day--in-selecting-range,.react-datepicker__month-text--in-selecting-range,.react-datepicker__quarter-text--in-selecting-range,.react-datepicker__year-text--in-selecting-range),.react-datepicker__month--selecting-range .react-datepicker__month-text--in-range:not(.react-datepicker__day--in-selecting-range,.react-datepicker__month-text--in-selecting-range,.react-datepicker__quarter-text--in-selecting-range,.react-datepicker__year-text--in-selecting-range),.react-datepicker__year--selecting-range .react-datepicker__month-text--in-range:not(.react-datepicker__day--in-selecting-range,.react-datepicker__month-text--in-selecting-range,.react-datepicker__quarter-text--in-selecting-range,.react-datepicker__year-text--in-selecting-range),.react-datepicker__month--selecting-range .react-datepicker__quarter-text--in-range:not(.react-datepicker__day--in-selecting-range,.react-datepicker__month-text--in-selecting-range,.react-datepicker__quarter-text--in-selecting-range,.react-datepicker__year-text--in-selecting-range),.react-datepicker__year--selecting-range .react-datepicker__quarter-text--in-range:not(.react-datepicker__day--in-selecting-range,.react-datepicker__month-text--in-selecting-range,.react-datepicker__quarter-text--in-selecting-range,.react-datepicker__year-text--in-selecting-range),.react-datepicker__month--selecting-range .react-datepicker__year-text--in-range:not(.react-datepicker__day--in-selecting-range,.react-datepicker__month-text--in-selecting-range,.react-datepicker__quarter-text--in-selecting-range,.react-datepicker__year-text--in-selecting-range),.react-datepicker__year--selecting-range .react-datepicker__year-text--in-range:not(.react-datepicker__day--in-selecting-range,.react-datepicker__month-text--in-selecting-range,.react-datepicker__quarter-text--in-selecting-range,.react-datepicker__year-text--in-selecting-range){background-color:#f0f0f0;color:#000}.react-datepicker__day--disabled,.react-datepicker__month-text--disabled,.react-datepicker__quarter-text--disabled,.react-datepicker__year-text--disabled{cursor:default;color:#ccc}.react-datepicker__day--disabled .overlay,.react-datepicker__month-text--disabled .overlay,.react-datepicker__quarter-text--disabled .overlay,.react-datepicker__year-text--disabled .overlay{position:absolute;bottom:70%;left:50%;transform:translate(-50%);background-color:#333;color:#fff;padding:4px;border-radius:4px;white-space:nowrap;visibility:hidden;opacity:0;transition:visibility 0s,opacity .3s ease-in-out}.react-datepicker__input-container{position:relative;display:inline-block;width:100%}.react-datepicker__input-container .react-datepicker__calendar-icon{position:absolute;padding:.625em;box-sizing:content-box}.react-datepicker__view-calendar-icon input{padding:6px 10px 5px 25px}.react-datepicker__year-read-view,.react-datepicker__month-read-view,.react-datepicker__month-year-read-view{border:1px solid transparent;border-radius:.3rem;position:relative}.react-datepicker__year-read-view:hover,.react-datepicker__month-read-view:hover,.react-datepicker__month-year-read-view:hover{cursor:pointer}.react-datepicker__year-read-view:hover .react-datepicker__year-read-view--down-arrow,.react-datepicker__year-read-view:hover .react-datepicker__month-read-view--down-arrow,.react-datepicker__month-read-view:hover .react-datepicker__year-read-view--down-arrow,.react-datepicker__month-read-view:hover .react-datepicker__month-read-view--down-arrow,.react-datepicker__month-year-read-view:hover .react-datepicker__year-read-view--down-arrow,.react-datepicker__month-year-read-view:hover .react-datepicker__month-read-view--down-arrow{border-top-color:#b3b3b3}.react-datepicker__year-read-view--down-arrow,.react-datepicker__month-read-view--down-arrow,.react-datepicker__month-year-read-view--down-arrow{transform:rotate(135deg);right:-16px;top:0}.react-datepicker__year-dropdown,.react-datepicker__month-dropdown,.react-datepicker__month-year-dropdown{background-color:#f0f0f0;position:absolute;width:50%;left:25%;top:30px;z-index:1;text-align:center;border-radius:.3rem;border:1px solid #aeaeae}.react-datepicker__year-dropdown:hover,.react-datepicker__month-dropdown:hover,.react-datepicker__month-year-dropdown:hover{cursor:pointer}.react-datepicker__year-dropdown--scrollable,.react-datepicker__month-dropdown--scrollable,.react-datepicker__month-year-dropdown--scrollable{height:150px;overflow-y:scroll}.react-datepicker__year-option,.react-datepicker__month-option,.react-datepicker__month-year-option{line-height:20px;width:100%;display:block;margin-left:auto;margin-right:auto}.react-datepicker__year-option:first-of-type,.react-datepicker__month-option:first-of-type,.react-datepicker__month-year-option:first-of-type{border-top-left-radius:.3rem;border-top-right-radius:.3rem}.react-datepicker__year-option:last-of-type,.react-datepicker__month-option:last-of-type,.react-datepicker__month-year-option:last-of-type{-webkit-user-select:none;-moz-user-select:none;-ms-user-select:none;user-select:none;border-bottom-left-radius:.3rem;border-bottom-right-radius:.3rem}.react-datepicker__year-option:hover,.react-datepicker__month-option:hover,.react-datepicker__month-year-option:hover{background-color:#ccc}.react-datepicker__year-option:hover .react-datepicker__navigation--years-upcoming,.react-datepicker__month-option:hover .react-datepicker__navigation--years-upcoming,.react-datepicker__month-year-option:hover .react-datepicker__navigation--years-upcoming{border-bottom-color:#b3b3b3}.react-datepicker__year-option:hover .react-datepicker__navigation--years-previous,.react-datepicker__month-option:hover .react-datepicker__navigation--years-previous,.react-datepicker__month-year-option:hover .react-datepicker__navigation--years-previous{border-top-color:#b3b3b3}.react-datepicker__year-option--selected,.react-datepicker__month-option--selected,.react-datepicker__month-year-option--selected{position:absolute;left:15px}.react-datepicker__close-icon{cursor:pointer;background-color:transparent;border:0;outline:0;padding:0 6px 0 0;position:absolute;top:0;right:0;height:100%;display:table-cell;vertical-align:middle}.react-datepicker__close-icon:after{cursor:pointer;background-color:#216ba5;color:#fff;border-radius:50%;height:16px;width:16px;padding:2px;font-size:12px;line-height:1;text-align:center;display:table-cell;vertical-align:middle;content:"×"}.react-datepicker__close-icon--disabled{cursor:default}.react-datepicker__close-icon--disabled:after{cursor:default;background-color:#ccc}.react-datepicker__today-button{background:#f0f0f0;border-top:1px solid #aeaeae;cursor:pointer;text-align:center;font-weight:700;padding:5px 0;clear:left}.react-datepicker__portal{position:fixed;width:100vw;height:100vh;background-color:#000c;left:0;top:0;justify-content:center;align-items:center;display:flex;z-index:2147483647}.react-datepicker__children-container{width:17.25em;margin:.5em;padding-right:.25em;padding-left:.25em;height:auto}.react-datepicker__aria-live{position:absolute;clip-path:circle(0);border:0;height:1px;margin:-1px;overflow:hidden;padding:0;width:1px;white-space:nowrap}.react-datepicker__calendar-icon{width:1em;height:1em;vertical-align:-.125em}.react-datepicker-popper-offset{margin-top:-.7em}:where(.preview-tab,.widget,.palette-selector,.ddp-field){--spacing-xs: 4px;--spacing-sm: 8px;--spacing-md: 16px;--spacing-lg: 24px;--spacing-xl: 32px;--spacing-2xl: 48px;--radius-sm: 4px;--radius-md: 8px;--radius-lg: 12px;--font-weight-normal: 400;--font-weight-medium: 500;--font-weight-semibold: 600;--font-weight-bold: 700;--transition-fast: .15s ease;--shadow-lg: 0 10px 25px rgba(0, 0, 0, .4)}.preview-tab{display:flex;flex-direction:column;gap:var(--spacing-md);position:relative}.preview-tab__empty{display:flex;align-items:center;justify-content:center;min-height:300px;color:var(--text-muted);font-size:.9rem;border:2px dashed var(--bg-elevated);border-radius:var(--radius-lg)}.preview-tab__loading{display:flex;align-items:center;justify-content:center;padding:var(--spacing-2xl) 0;color:var(--text-secondary)}.preview-tab__error{padding:var(--spacing-md);background:#f443361a;border:1px solid var(--color-error);border-radius:var(--radius-md);color:var(--color-error);font-size:.875rem;text-align:center}.preview-tab__grid{background:var(--bg-dark);padding:var(--spacing-md);border-radius:var(--radius-lg)}.preview-tab__widget{display:flex;background:var(--bg-elevated);border:1px solid rgba(255,255,255,.08);border-radius:var(--radius-md);overflow:hidden;min-height:0;container-type:size}.preview-tab__widget--control{background:var(--bg-elevated);border:1px dashed rgba(255,255,255,.15)}.preview-tab__widget-loading{display:flex;align-items:center;justify-content:center;height:100%;min-height:80px;color:var(--text-muted);font-size:.8125rem}.preview-tab__recalculating{position:fixed;bottom:var(--spacing-lg);right:var(--spacing-lg);padding:var(--spacing-sm) var(--spacing-lg);background:var(--bg-elevated);border:1px solid var(--action-orange);border-radius:var(--radius-md);color:var(--action-orange);font-size:.8125rem;font-weight:var(--font-weight-medium);box-shadow:var(--shadow-lg);z-index:50}.palette-selector{display:flex;flex-direction:column;gap:var(--spacing-sm)}.palette-selector--disabled{opacity:.5;pointer-events:none}.palette-selector__options{display:flex;flex-direction:column;gap:var(--spacing-xs)}.palette-selector__option{display:flex;flex-direction:column;gap:var(--spacing-xs);padding:var(--spacing-xs);background:transparent;border:1.5px solid var(--bg-elevated);border-radius:var(--radius-sm);cursor:pointer;transition:border-color var(--transition-fast)}.palette-selector__option:hover:not(:disabled){border-color:var(--text-muted)}.palette-selector__option--active{border-color:var(--action-orange)}.palette-selector__bar{display:flex;width:100%;height:18px;border-radius:3px;overflow:hidden}.palette-selector__bar--theme{height:12px;opacity:.85}.palette-selector__swatch{flex:1;min-width:0}.palette-selector__label{font-size:.7rem;color:var(--text-muted);text-align:left}.palette-selector__custom{display:flex;flex-direction:column;gap:6px}.palette-selector__row{display:flex;flex-direction:column;gap:4px}.palette-selector__row-label{font-size:.6rem;color:var(--text-muted);text-transform:uppercase;letter-spacing:.5px;font-weight:var(--font-weight-semibold)}.palette-selector__row-slots{display:flex;gap:4px;flex-wrap:wrap}.palette-selector__color-input{width:24px;height:24px;padding:0;border:1.5px solid rgba(255,255,255,.25);border-radius:var(--radius-sm);background:transparent;cursor:pointer;transition:border-color var(--transition-fast);flex-shrink:0}.palette-selector__color-input:hover:not(:disabled){border-color:#ffffff80}.palette-selector__color-input:hover:not(:disabled){border-color:var(--action-orange)}.palette-selector__color-input::-webkit-color-swatch-wrapper{padding:2px}.palette-selector__color-input::-webkit-color-swatch{border:none;border-radius:2px}.ddp-field{width:100%;min-width:0;display:block}.ddp-field .react-datepicker-wrapper,.ddp-field .react-datepicker__input-container{width:100%;display:block}.ddp-field .react-datepicker__input-container input{width:100%;padding:var(--spacing-sm) var(--spacing-md);background:var(--bg-elevated);border:1.5px solid var(--bg-elevated);border-radius:var(--radius-sm);font-size:.8125rem;color:var(--text-primary);box-sizing:border-box;transition:border-color var(--transition-fast)}.ddp-field .react-datepicker__input-container input:focus{outline:none;border-color:var(--action-orange)}.ddp-field .react-datepicker__input-container input::placeholder{color:var(--text-muted)}.ddp-field .react-datepicker__input-container input:disabled{opacity:.6;cursor:not-allowed}.ddp-field .react-datepicker__month{min-height:168px}.react-datepicker-popper{z-index:1100!important}.widget{flex:1;display:flex;flex-direction:column;padding:var(--spacing-sm);background:var(--bg-elevated);border-radius:var(--radius-md);overflow:hidden;box-sizing:border-box;min-height:0;min-width:0}.widget--error{align-items:center;justify-content:center}.widget__error-text{color:var(--color-error);font-size:clamp(.45rem,2.5cqi,.85rem);text-align:center}.widget-filter,.widget-palette{flex:1;display:flex;flex-direction:column;align-items:center;justify-content:flex-start;gap:clamp(4px,1.5cqi,12px);padding:clamp(4px,1cqi,8px) clamp(6px,1.5cqi,12px);box-sizing:border-box;min-height:0;min-width:0;overflow:hidden}.widget-variable{flex:1;display:flex;flex-direction:column;justify-content:center;align-items:center;box-sizing:border-box;min-height:0;min-width:0;overflow:hidden}.widget-filter__label,.widget-palette__label,.widget-variable__label{flex-shrink:0;font-size:clamp(.45rem,6cqi,3rem);color:var(--text-muted);font-weight:var(--font-weight-medium)}.widget-kpi{justify-content:center;align-items:center;text-align:center;gap:clamp(2px,1cqmin,10px);padding:clamp(4px,2cqmin,16px)}.widget-kpi__label{font-size:clamp(.45rem,min(12cqi,12cqb),6rem);color:var(--text-muted);font-weight:var(--font-weight-medium);line-height:1.2;max-width:100%;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}.widget-kpi__value{font-size:clamp(.85rem,min(22cqi,22cqb),8rem);font-weight:var(--font-weight-bold);color:var(--text-primary);line-height:1.1;max-width:100%;overflow:hidden;text-overflow:ellipsis;white-space:nowrap;font-variant-numeric:tabular-nums}.widget-kpi__trend{display:flex;align-items:center;justify-content:center;gap:clamp(2px,.8cqmin,6px);font-size:clamp(.4rem,min(8cqi,8cqb),2rem);max-width:100%;overflow:hidden;flex-wrap:wrap}.widget-kpi__trend--up{color:var(--action-green)}.widget-kpi__trend--down{color:var(--color-error)}.widget-kpi__variance{font-weight:var(--font-weight-semibold);white-space:nowrap}.widget-kpi__trend-label{color:var(--text-muted);white-space:nowrap;overflow:hidden;text-overflow:ellipsis}@container (max-width: 180px){.widget-kpi__trend-label{display:none}}@container (max-height: 70px){.widget-kpi__label{display:none}}.widget-gauge{align-items:center;gap:0;overflow:hidden}.widget-gauge__label{font-size:clamp(.5rem,6cqi,3rem);color:var(--text-muted);font-weight:var(--font-weight-medium);flex-shrink:0}.widget-gauge__chart{position:relative;width:100%;flex:1;min-height:0}.widget-gauge__chart svg{margin-top:5%;display:block;width:100%;height:100%}.widget-gauge__center{position:absolute;top:0;right:0;bottom:0;left:0;display:flex;flex-direction:column;align-items:center;justify-content:center;gap:2px;margin-top:25%}.widget-gauge__percent{font-size:clamp(.5rem,9cqi,4rem);font-weight:var(--font-weight-bold);color:var(--text-primary);line-height:1}.widget-gauge__comparison{font-size:clamp(.4rem,3.5cqi,2rem);color:var(--text-muted)}.widget-gauge__badge{font-size:clamp(.35rem,3cqi,1.25rem);font-weight:var(--font-weight-semibold);text-transform:uppercase;letter-spacing:.3px;padding:1px var(--spacing-xs);border-radius:var(--radius-sm);background:#a4c63926;color:var(--action-green)}.widget-chart{gap:var(--spacing-xs)}.widget-chart--empty{align-items:center;justify-content:center;color:var(--text-muted);font-size:clamp(.5rem,2.5cqi,.85rem)}.widget-chart__title{font-size:clamp(.5rem,2.5cqi,.85rem);font-weight:var(--font-weight-semibold);color:var(--text-primary);margin:0}.widget-chart__container{flex:1;min-height:0;overflow:hidden}.widget-filter__date-range{display:flex;align-items:center;gap:clamp(2px,1cqi,8px);flex:1;min-width:0}.widget-filter__date-range--stacked{flex-direction:column;align-items:stretch;gap:clamp(4px,1.5cqmin,10px);width:100%;padding:clamp(2px,1cqmin,8px) 0}.widget-filter__date-range .ddp-field{flex:1;min-width:0;width:100%}.widget-filter__date-range .ddp-field .react-datepicker__input-container input,.widget-filter__select{padding:clamp(8px,4cqmin,22px) clamp(6px,1.5cqmin,12px);font-size:clamp(.5rem,10cqmin,2rem);background:var(--bg-paper);border:1px solid rgba(255,255,255,.1);border-radius:var(--radius-sm);color:var(--text-primary);flex:1;min-width:0;width:100%;box-sizing:border-box;text-align:center;font-variant-numeric:tabular-nums}.widget-filter__date-sep{font-size:clamp(.35rem,2.5cqi,.8rem);color:var(--text-muted)}.widget-filter__multi{display:flex;flex-direction:column;align-items:stretch;justify-content:space-around;gap:clamp(4px,1.5cqmin,14px);flex:1;min-height:0;width:100%;padding:clamp(6px,2cqmin,14px) clamp(4px,2cqmin,12px);box-sizing:border-box;overflow-y:auto}.widget-filter__multi::-webkit-scrollbar{width:6px}.widget-filter__multi::-webkit-scrollbar-track{background:transparent}.widget-filter__multi::-webkit-scrollbar-thumb{background:var(--bg-elevated);border-radius:3px}.widget-filter__multi::-webkit-scrollbar-thumb:hover{background:var(--text-muted)}.widget-filter__multi-option{display:flex;align-items:center;gap:clamp(6px,4cqmin,14px);padding:clamp(4px,1.5cqmin,12px) clamp(8px,2.5cqmin,14px);height:clamp(20px,18cqb,120px);background:var(--bg-paper);border:1px solid var(--bg-elevated);border-radius:var(--radius-sm);cursor:pointer;transition:border-color var(--transition-fast),background-color var(--transition-fast);font-size:clamp(.45rem,8cqmin,1.2rem);font-weight:var(--font-weight-medium);color:var(--text-primary);line-height:1;flex-shrink:0;box-sizing:border-box}.widget-filter__multi-option:hover{border-color:var(--text-muted);background-color:var(--bg-elevated)}.widget-filter__multi-option:has(input[type=checkbox]:checked){border-color:var(--text-muted);background-color:var(--bg-elevated)}.widget-filter__multi-option input[type=checkbox]{appearance:none;-webkit-appearance:none;-moz-appearance:none;width:clamp(12px,7cqmin,22px);height:clamp(12px,7cqmin,22px);border:1.5px solid var(--text-muted);border-radius:3px;background:var(--bg-elevated);cursor:pointer;position:relative;flex-shrink:0;transition:border-color var(--transition-fast),background-color var(--transition-fast);margin:0}.widget-filter__multi-option input[type=checkbox]:hover{border-color:var(--action-orange)}.widget-filter__multi-option input[type=checkbox]:checked{background:var(--action-orange);border-color:var(--action-orange)}.widget-filter__multi-option input[type=checkbox]:checked:after{content:"";position:absolute;left:30%;top:8%;width:30%;height:60%;border:solid var(--bg-dark);border-width:0 2px 2px 0;transform:rotate(45deg)}.widget-filter__select{width:95%;max-height:45%;margin-top:2%;flex:1;font-size:clamp(.4rem,5cqi,1.5rem);font-weight:var(--font-weight-semibold);color:var(--text-primary);text-align:left;padding:clamp(8px,4cqi,22px) clamp(6px,1.5cqi,12px);min-width:0;box-sizing:border-box}.widget-filter>.widget-filter__select,.widget-filter__date-range--year .widget-filter__select,.widget-filter__date-range--month .widget-filter__select,.widget-filter__date-range--week .widget-filter__select{text-align:center;text-align-last:center;font-weight:var(--font-weight-semibold);color:var(--text-primary);background:var(--bg-paper);border:1px solid rgba(255,255,255,.1);border-radius:var(--radius-sm);cursor:pointer;appearance:none;-webkit-appearance:none;-moz-appearance:none;background-image:none;transition:border-color var(--transition-fast),background-color var(--transition-fast);box-sizing:border-box;width:100%;margin-top:0;max-height:none;padding:clamp(2px,.8cqmin,6px) clamp(6px,1.5cqmin,12px);line-height:1}.widget-filter>.widget-filter__select:hover,.widget-filter>.widget-filter__select:focus,.widget-filter__date-range--year .widget-filter__select:hover,.widget-filter__date-range--year .widget-filter__select:focus,.widget-filter__date-range--month .widget-filter__select:hover,.widget-filter__date-range--month .widget-filter__select:focus,.widget-filter__date-range--week .widget-filter__select:hover,.widget-filter__date-range--week .widget-filter__select:focus{outline:none;border-color:var(--action-orange);background-color:var(--bg-elevated)}.widget-filter>.widget-filter__select option,.widget-filter__date-range--year .widget-filter__select option,.widget-filter__date-range--month .widget-filter__select option,.widget-filter__date-range--week .widget-filter__select option{background:var(--bg-paper);color:var(--text-primary);font-size:.875rem;font-weight:var(--font-weight-normal);text-align:left;padding:6px 10px}.widget-filter>.widget-filter__select{flex:0 1 auto;height:clamp(50px,22cqmin,140px);max-height:75%;margin-block:auto;align-self:center;font-size:clamp(.6rem,12cqmin,2.2rem)}.widget-filter__date-range--year,.widget-filter__date-range--month,.widget-filter__date-range--week{display:flex;flex-direction:column;align-items:stretch;justify-content:center;gap:clamp(6px,2.5cqmin,16px);flex:1;width:100%;padding:clamp(6px,2cqmin,16px) clamp(4px,2cqmin,14px);box-sizing:border-box}.widget-filter__date-range--year .widget-filter__select{flex:0 1 auto;height:clamp(50px,22cqmin,140px);font-size:clamp(.6rem,12cqmin,2.2rem)}.widget-filter__date-range--month .widget-filter__select{flex:0 1 auto;height:clamp(30px,10cqmin,66px);font-size:clamp(.5rem,10cqmin,1.4rem)}.widget-filter__date-range--week .widget-filter__select{flex:0 1 auto;height:clamp(22px,12cqmin,48px);font-size:clamp(.45rem,8cqmin,3rem)}.widget-variable__input-wrapper{display:flex;align-items:center;margin-top:2%;width:90%;background:var(--bg-paper);border:1px solid rgba(255,255,255,.1);border-radius:var(--radius-sm);overflow:hidden}.widget-variable__input{flex:1;font-size:clamp(.4rem,5cqi,1.5rem);font-weight:var(--font-weight-semibold);background:transparent;border:none;outline:none;color:var(--text-primary);text-align:left;padding:clamp(2px,1cqi,6px) clamp(4px,1.5cqi,8px);min-width:0;box-sizing:border-box}.widget-variable__input::-webkit-outer-spin-button,.widget-variable__input::-webkit-inner-spin-button{-webkit-appearance:none;margin:0}.widget-variable__input[type=number]{-moz-appearance:textfield;-webkit-appearance:textfield;appearance:textfield}.widget-variable__input:disabled{opacity:.6;cursor:not-allowed}.widget-variable__suffix{font-size:clamp(.4rem,4cqi,1.25rem);color:var(--text-muted);white-space:nowrap;padding:0 clamp(4px,1.5cqi,8px);border-left:1px solid rgba(255,255,255,.1);flex-shrink:0}.widget-variable__lock-icon{font-size:clamp(.45rem,2.5cqi,.75rem)}.widget-variable--locked .widget-variable__input-wrapper{border-style:dashed}.widget-palette{flex-direction:column;justify-content:flex-start;align-items:stretch;padding:clamp(4px,1.5cqmin,12px);gap:clamp(2px,1cqmin,8px);overflow:auto}.widget-palette__label{text-align:center;flex-shrink:0}.widget-palette__lock-icon{font-size:clamp(.45rem,2.5cqmin,.75rem);align-self:center}.widget-palette--locked .palette-selector__color-input{opacity:.6;cursor:not-allowed}.widget-palette .palette-selector{gap:clamp(2px,3cqmin,28px);flex:1;min-height:0;justify-content:center}.widget-palette .palette-selector__row{gap:clamp(1px,1.2cqmin,10px);min-height:0}.widget-palette .palette-selector__row-label{font-size:clamp(.35rem,1.8cqmin,.7rem);line-height:1}.widget-palette .palette-selector__row-slots{gap:clamp(1px,.8cqmin,6px);flex-wrap:nowrap;justify-content:space-between;width:100%;min-height:0}.widget-palette .palette-selector__color-input{flex:1 1 0;min-width:0;min-height:0;width:auto;height:clamp(8px,10cqmin,60px);border:1px solid rgba(255,255,255,.2);padding:0}.widget-palette .palette-selector__color-input:hover:not(:disabled){border-color:#fff6}
1
+ @charset "UTF-8";.react-datepicker__navigation-icon:before,.react-datepicker__year-read-view--down-arrow,.react-datepicker__month-read-view--down-arrow,.react-datepicker__month-year-read-view--down-arrow{border-color:#ccc;border-style:solid;border-width:3px 3px 0 0;content:"";display:block;height:9px;position:absolute;top:6px;width:9px}.react-datepicker__sr-only{position:absolute;width:1px;height:1px;padding:0;margin:-1px;overflow:hidden;clip-path:inset(50%);white-space:nowrap;border:0}.react-datepicker-wrapper{display:inline-block;padding:0;border:0}.react-datepicker{font-family:Helvetica Neue,helvetica,arial,sans-serif;font-size:.8rem;background-color:#fff;color:#000;border:1px solid #aeaeae;border-radius:.3rem;display:inline-block;position:relative;line-height:initial}.react-datepicker--time-only .react-datepicker__time-container{border-left:0}.react-datepicker--time-only .react-datepicker__time,.react-datepicker--time-only .react-datepicker__time-box{border-bottom-left-radius:.375em;border-bottom-right-radius:.375em}.react-datepicker-popper{z-index:1;line-height:0}.react-datepicker-popper .react-datepicker__triangle{stroke:#aeaeae}.react-datepicker-popper[data-placement^=bottom] .react-datepicker__triangle{fill:#f0f0f0;color:#f0f0f0}.react-datepicker-popper[data-placement^=top] .react-datepicker__triangle,.react-datepicker-popper--header-middle[data-placement^=bottom] .react-datepicker__triangle,.react-datepicker-popper--header-bottom[data-placement^=bottom] .react-datepicker__triangle{fill:#fff;color:#fff}.react-datepicker-popper--header-bottom[data-placement^=top] .react-datepicker__triangle{fill:#f0f0f0;color:#f0f0f0}.react-datepicker__header{text-align:center;background-color:#f0f0f0;border-bottom:1px solid #aeaeae;border-top-left-radius:.3rem;padding:8px 0;position:relative}.react-datepicker__header--time{padding-bottom:8px;padding-left:5px;padding-right:5px}.react-datepicker__header--time:not(.react-datepicker__header--time--only){border-top-left-radius:0}.react-datepicker__header:not(.react-datepicker__header--has-time-select,.react-datepicker__header--middle,.react-datepicker__header--bottom){border-top-right-radius:.3rem}.react-datepicker__header--middle{border-top:1px solid #aeaeae;border-radius:0;margin-top:4px}.react-datepicker__header--bottom{border-bottom:none;border-top:1px solid #aeaeae;border-radius:0 0 .3rem .3rem}.react-datepicker__header-wrapper{position:relative}.react-datepicker__header-wrapper .react-datepicker__navigation--next--with-time:not(.react-datepicker__navigation--next--with-today-button){right:2px}.react-datepicker__year-dropdown-container--select,.react-datepicker__month-dropdown-container--select,.react-datepicker__month-year-dropdown-container--select,.react-datepicker__year-dropdown-container--scroll,.react-datepicker__month-dropdown-container--scroll,.react-datepicker__month-year-dropdown-container--scroll{display:inline-block;margin:0 15px}.react-datepicker__month-select,.react-datepicker__year-select,.react-datepicker__month-year-select{background-color:transparent;border:1px solid #aeaeae;border-radius:.3rem;color:inherit;cursor:pointer;font-family:inherit;font-size:inherit;margin-top:5px;padding:2px 5px}.react-datepicker__month-select:focus-visible,.react-datepicker__year-select:focus-visible,.react-datepicker__month-year-select:focus-visible{outline:auto 1px}.react-datepicker__current-month,.react-datepicker-time__header,.react-datepicker-year-header{margin-top:0;color:#000;font-weight:700;font-size:.944rem}h2.react-datepicker__current-month{padding:0;margin:0}.react-datepicker-time__header{text-overflow:ellipsis;white-space:nowrap;overflow:hidden}.react-datepicker__navigation{align-items:center;background:none;display:flex;justify-content:center;text-align:center;cursor:pointer;position:absolute;top:2px;padding:0;border:none;z-index:1;height:32px;width:32px;text-indent:-999em;overflow:hidden}.react-datepicker__navigation--previous{left:2px}.react-datepicker__navigation--next{right:2px}.react-datepicker__navigation--next--with-time:not(.react-datepicker__navigation--next--with-today-button){right:85px}.react-datepicker__navigation--years{position:relative;top:0;display:block;margin-left:auto;margin-right:auto}.react-datepicker__navigation--years-previous{top:4px}.react-datepicker__navigation--years-upcoming{top:-4px}.react-datepicker__navigation:hover *:before{border-color:#a6a6a6}.react-datepicker__navigation-icon{position:relative;top:-1px;font-size:20px;width:0}.react-datepicker__navigation-icon--next{left:-2px}.react-datepicker__navigation-icon--next:before{transform:rotate(45deg);left:-7px}.react-datepicker__navigation-icon--previous{right:-2px}.react-datepicker__navigation-icon--previous:before{transform:rotate(225deg);right:-7px}.react-datepicker__month-container{float:left}.react-datepicker__year{margin:.5em;text-align:center}.react-datepicker__year-wrapper{display:flex;flex-wrap:wrap;max-width:180px}.react-datepicker__year .react-datepicker__year-text{display:inline-block;width:5em;margin:2px}.react-datepicker__month{margin:.5em;text-align:center}.react-datepicker__month .react-datepicker__month-text,.react-datepicker__month .react-datepicker__quarter-text{display:inline-block;width:5em;margin:2px}.react-datepicker__input-time-container{clear:both;width:100%;float:left;margin:5px 0 10px 15px;text-align:left}.react-datepicker__input-time-container .react-datepicker-time__caption,.react-datepicker__input-time-container .react-datepicker-time__input-container{display:inline-block}.react-datepicker__input-time-container .react-datepicker-time__input-container .react-datepicker-time__input{display:inline-block;margin-left:10px}.react-datepicker__input-time-container .react-datepicker-time__input-container .react-datepicker-time__input input{width:auto}.react-datepicker__input-time-container .react-datepicker-time__input-container .react-datepicker-time__input input[type=time]::-webkit-inner-spin-button,.react-datepicker__input-time-container .react-datepicker-time__input-container .react-datepicker-time__input input[type=time]::-webkit-outer-spin-button{-webkit-appearance:none;margin:0}.react-datepicker__input-time-container .react-datepicker-time__input-container .react-datepicker-time__input input[type=time]{-moz-appearance:textfield}.react-datepicker__input-time-container .react-datepicker-time__input-container .react-datepicker-time__delimiter{margin-left:5px;display:inline-block}.react-datepicker__time-container{float:right;border-left:1px solid #aeaeae;width:85px}.react-datepicker__time-container--with-today-button{display:inline;border:1px solid #aeaeae;border-radius:.375em;position:absolute;right:-87px;top:0}.react-datepicker__time-container .react-datepicker__time{position:relative;background:#fff;border-bottom-right-radius:.375em}.react-datepicker__time-container .react-datepicker__time .react-datepicker__time-box{width:85px;overflow-x:hidden;margin:0 auto;text-align:center;border-bottom-right-radius:.375em}.react-datepicker__time-container .react-datepicker__time .react-datepicker__time-box ul.react-datepicker__time-list{list-style:none;margin:0;height:calc(195px + 1.0625em);overflow-y:scroll;padding-right:0;padding-left:0;width:100%;box-sizing:content-box}.react-datepicker__time-container .react-datepicker__time .react-datepicker__time-box ul.react-datepicker__time-list li.react-datepicker__time-list-item{height:30px;padding:5px 10px;white-space:nowrap}.react-datepicker__time-container .react-datepicker__time .react-datepicker__time-box ul.react-datepicker__time-list li.react-datepicker__time-list-item:hover{cursor:pointer;background-color:#f0f0f0}.react-datepicker__time-container .react-datepicker__time .react-datepicker__time-box ul.react-datepicker__time-list li.react-datepicker__time-list-item--selected{background-color:#216ba5;color:#fff;font-weight:700}.react-datepicker__time-container .react-datepicker__time .react-datepicker__time-box ul.react-datepicker__time-list li.react-datepicker__time-list-item--selected:hover{background-color:#216ba5}.react-datepicker__time-container .react-datepicker__time .react-datepicker__time-box ul.react-datepicker__time-list li.react-datepicker__time-list-item--disabled{color:#ccc}.react-datepicker__time-container .react-datepicker__time .react-datepicker__time-box ul.react-datepicker__time-list li.react-datepicker__time-list-item--disabled:hover{cursor:default;background-color:transparent}.react-datepicker__week-number{color:#ccc;display:inline-block;width:2.125em;line-height:2.125em;text-align:center;margin:.208em}.react-datepicker__week-number.react-datepicker__week-number--clickable{cursor:pointer}.react-datepicker__week-number.react-datepicker__week-number--clickable:not(.react-datepicker__week-number--selected):hover{border-radius:.3rem;background-color:#f0f0f0}.react-datepicker__week-number--selected{border-radius:.3rem;background-color:#216ba5;color:#fff}.react-datepicker__week-number--selected:hover{background-color:#1d5d90}.react-datepicker__day-names{text-align:center;white-space:nowrap;margin-bottom:-8px}.react-datepicker__week{white-space:nowrap}.react-datepicker__day-name,.react-datepicker__day,.react-datepicker__time-name{color:#000;display:inline-block;width:2.125em;line-height:2.125em;text-align:center;margin:.208em}.react-datepicker__day-name--disabled,.react-datepicker__day--disabled,.react-datepicker__time-name--disabled{cursor:default;color:#ccc}.react-datepicker__day,.react-datepicker__month-text,.react-datepicker__quarter-text,.react-datepicker__year-text{cursor:pointer}.react-datepicker__day:not([aria-disabled=true]):hover,.react-datepicker__month-text:not([aria-disabled=true]):hover,.react-datepicker__quarter-text:not([aria-disabled=true]):hover,.react-datepicker__year-text:not([aria-disabled=true]):hover{border-radius:.3rem;background-color:#f0f0f0}.react-datepicker__day--today,.react-datepicker__month-text--today,.react-datepicker__quarter-text--today,.react-datepicker__year-text--today{font-weight:700}.react-datepicker__day--highlighted,.react-datepicker__month-text--highlighted,.react-datepicker__quarter-text--highlighted,.react-datepicker__year-text--highlighted{border-radius:.3rem;background-color:#3dcc4a;color:#fff}.react-datepicker__day--highlighted:not([aria-disabled=true]):hover,.react-datepicker__month-text--highlighted:not([aria-disabled=true]):hover,.react-datepicker__quarter-text--highlighted:not([aria-disabled=true]):hover,.react-datepicker__year-text--highlighted:not([aria-disabled=true]):hover{background-color:#32be3f}.react-datepicker__day--highlighted-custom-1,.react-datepicker__month-text--highlighted-custom-1,.react-datepicker__quarter-text--highlighted-custom-1,.react-datepicker__year-text--highlighted-custom-1{color:#f0f}.react-datepicker__day--highlighted-custom-2,.react-datepicker__month-text--highlighted-custom-2,.react-datepicker__quarter-text--highlighted-custom-2,.react-datepicker__year-text--highlighted-custom-2{color:green}.react-datepicker__day--holidays,.react-datepicker__month-text--holidays,.react-datepicker__quarter-text--holidays,.react-datepicker__year-text--holidays{position:relative;border-radius:.3rem;background-color:#ff6803;color:#fff}.react-datepicker__day--holidays .overlay,.react-datepicker__month-text--holidays .overlay,.react-datepicker__quarter-text--holidays .overlay,.react-datepicker__year-text--holidays .overlay{position:absolute;bottom:100%;left:50%;transform:translate(-50%);background-color:#333;color:#fff;padding:4px;border-radius:4px;white-space:nowrap;visibility:hidden;opacity:0;transition:visibility 0s,opacity .3s ease-in-out}.react-datepicker__day--holidays:not([aria-disabled=true]):hover,.react-datepicker__month-text--holidays:not([aria-disabled=true]):hover,.react-datepicker__quarter-text--holidays:not([aria-disabled=true]):hover,.react-datepicker__year-text--holidays:not([aria-disabled=true]):hover{background-color:#cf5300}.react-datepicker__day--holidays:hover .overlay,.react-datepicker__month-text--holidays:hover .overlay,.react-datepicker__quarter-text--holidays:hover .overlay,.react-datepicker__year-text--holidays:hover .overlay{visibility:visible;opacity:1}.react-datepicker__day--selected,.react-datepicker__day--in-selecting-range,.react-datepicker__day--in-range,.react-datepicker__month-text--selected,.react-datepicker__month-text--in-selecting-range,.react-datepicker__month-text--in-range,.react-datepicker__quarter-text--selected,.react-datepicker__quarter-text--in-selecting-range,.react-datepicker__quarter-text--in-range,.react-datepicker__year-text--selected,.react-datepicker__year-text--in-selecting-range,.react-datepicker__year-text--in-range{border-radius:.3rem;background-color:#216ba5;color:#fff}.react-datepicker__day--selected:not([aria-disabled=true]):hover,.react-datepicker__day--in-selecting-range:not([aria-disabled=true]):hover,.react-datepicker__day--in-range:not([aria-disabled=true]):hover,.react-datepicker__month-text--selected:not([aria-disabled=true]):hover,.react-datepicker__month-text--in-selecting-range:not([aria-disabled=true]):hover,.react-datepicker__month-text--in-range:not([aria-disabled=true]):hover,.react-datepicker__quarter-text--selected:not([aria-disabled=true]):hover,.react-datepicker__quarter-text--in-selecting-range:not([aria-disabled=true]):hover,.react-datepicker__quarter-text--in-range:not([aria-disabled=true]):hover,.react-datepicker__year-text--selected:not([aria-disabled=true]):hover,.react-datepicker__year-text--in-selecting-range:not([aria-disabled=true]):hover,.react-datepicker__year-text--in-range:not([aria-disabled=true]):hover{background-color:#1d5d90}.react-datepicker__day--keyboard-selected,.react-datepicker__month-text--keyboard-selected,.react-datepicker__quarter-text--keyboard-selected,.react-datepicker__year-text--keyboard-selected{border-radius:.3rem;background-color:#bad9f1;color:#000}.react-datepicker__day--keyboard-selected:not([aria-disabled=true]):hover,.react-datepicker__month-text--keyboard-selected:not([aria-disabled=true]):hover,.react-datepicker__quarter-text--keyboard-selected:not([aria-disabled=true]):hover,.react-datepicker__year-text--keyboard-selected:not([aria-disabled=true]):hover{background-color:#1d5d90;color:#fff}.react-datepicker__day--in-selecting-range:not(.react-datepicker__day--in-range,.react-datepicker__month-text--in-range,.react-datepicker__quarter-text--in-range,.react-datepicker__year-text--in-range),.react-datepicker__month-text--in-selecting-range:not(.react-datepicker__day--in-range,.react-datepicker__month-text--in-range,.react-datepicker__quarter-text--in-range,.react-datepicker__year-text--in-range),.react-datepicker__quarter-text--in-selecting-range:not(.react-datepicker__day--in-range,.react-datepicker__month-text--in-range,.react-datepicker__quarter-text--in-range,.react-datepicker__year-text--in-range),.react-datepicker__year-text--in-selecting-range:not(.react-datepicker__day--in-range,.react-datepicker__month-text--in-range,.react-datepicker__quarter-text--in-range,.react-datepicker__year-text--in-range){background-color:#216ba580}.react-datepicker__month--selecting-range .react-datepicker__day--in-range:not(.react-datepicker__day--in-selecting-range,.react-datepicker__month-text--in-selecting-range,.react-datepicker__quarter-text--in-selecting-range,.react-datepicker__year-text--in-selecting-range),.react-datepicker__year--selecting-range .react-datepicker__day--in-range:not(.react-datepicker__day--in-selecting-range,.react-datepicker__month-text--in-selecting-range,.react-datepicker__quarter-text--in-selecting-range,.react-datepicker__year-text--in-selecting-range),.react-datepicker__month--selecting-range .react-datepicker__month-text--in-range:not(.react-datepicker__day--in-selecting-range,.react-datepicker__month-text--in-selecting-range,.react-datepicker__quarter-text--in-selecting-range,.react-datepicker__year-text--in-selecting-range),.react-datepicker__year--selecting-range .react-datepicker__month-text--in-range:not(.react-datepicker__day--in-selecting-range,.react-datepicker__month-text--in-selecting-range,.react-datepicker__quarter-text--in-selecting-range,.react-datepicker__year-text--in-selecting-range),.react-datepicker__month--selecting-range .react-datepicker__quarter-text--in-range:not(.react-datepicker__day--in-selecting-range,.react-datepicker__month-text--in-selecting-range,.react-datepicker__quarter-text--in-selecting-range,.react-datepicker__year-text--in-selecting-range),.react-datepicker__year--selecting-range .react-datepicker__quarter-text--in-range:not(.react-datepicker__day--in-selecting-range,.react-datepicker__month-text--in-selecting-range,.react-datepicker__quarter-text--in-selecting-range,.react-datepicker__year-text--in-selecting-range),.react-datepicker__month--selecting-range .react-datepicker__year-text--in-range:not(.react-datepicker__day--in-selecting-range,.react-datepicker__month-text--in-selecting-range,.react-datepicker__quarter-text--in-selecting-range,.react-datepicker__year-text--in-selecting-range),.react-datepicker__year--selecting-range .react-datepicker__year-text--in-range:not(.react-datepicker__day--in-selecting-range,.react-datepicker__month-text--in-selecting-range,.react-datepicker__quarter-text--in-selecting-range,.react-datepicker__year-text--in-selecting-range){background-color:#f0f0f0;color:#000}.react-datepicker__day--disabled,.react-datepicker__month-text--disabled,.react-datepicker__quarter-text--disabled,.react-datepicker__year-text--disabled{cursor:default;color:#ccc}.react-datepicker__day--disabled .overlay,.react-datepicker__month-text--disabled .overlay,.react-datepicker__quarter-text--disabled .overlay,.react-datepicker__year-text--disabled .overlay{position:absolute;bottom:70%;left:50%;transform:translate(-50%);background-color:#333;color:#fff;padding:4px;border-radius:4px;white-space:nowrap;visibility:hidden;opacity:0;transition:visibility 0s,opacity .3s ease-in-out}.react-datepicker__input-container{position:relative;display:inline-block;width:100%}.react-datepicker__input-container .react-datepicker__calendar-icon{position:absolute;padding:.625em;box-sizing:content-box}.react-datepicker__view-calendar-icon input{padding:6px 10px 5px 25px}.react-datepicker__year-read-view,.react-datepicker__month-read-view,.react-datepicker__month-year-read-view{border:1px solid transparent;border-radius:.3rem;position:relative}.react-datepicker__year-read-view:hover,.react-datepicker__month-read-view:hover,.react-datepicker__month-year-read-view:hover{cursor:pointer}.react-datepicker__year-read-view:hover .react-datepicker__year-read-view--down-arrow,.react-datepicker__year-read-view:hover .react-datepicker__month-read-view--down-arrow,.react-datepicker__month-read-view:hover .react-datepicker__year-read-view--down-arrow,.react-datepicker__month-read-view:hover .react-datepicker__month-read-view--down-arrow,.react-datepicker__month-year-read-view:hover .react-datepicker__year-read-view--down-arrow,.react-datepicker__month-year-read-view:hover .react-datepicker__month-read-view--down-arrow{border-top-color:#b3b3b3}.react-datepicker__year-read-view--down-arrow,.react-datepicker__month-read-view--down-arrow,.react-datepicker__month-year-read-view--down-arrow{transform:rotate(135deg);right:-16px;top:0}.react-datepicker__year-dropdown,.react-datepicker__month-dropdown,.react-datepicker__month-year-dropdown{background-color:#f0f0f0;position:absolute;width:50%;left:25%;top:30px;z-index:1;text-align:center;border-radius:.3rem;border:1px solid #aeaeae}.react-datepicker__year-dropdown:hover,.react-datepicker__month-dropdown:hover,.react-datepicker__month-year-dropdown:hover{cursor:pointer}.react-datepicker__year-dropdown--scrollable,.react-datepicker__month-dropdown--scrollable,.react-datepicker__month-year-dropdown--scrollable{height:150px;overflow-y:scroll}.react-datepicker__year-option,.react-datepicker__month-option,.react-datepicker__month-year-option{line-height:20px;width:100%;display:block;margin-left:auto;margin-right:auto}.react-datepicker__year-option:first-of-type,.react-datepicker__month-option:first-of-type,.react-datepicker__month-year-option:first-of-type{border-top-left-radius:.3rem;border-top-right-radius:.3rem}.react-datepicker__year-option:last-of-type,.react-datepicker__month-option:last-of-type,.react-datepicker__month-year-option:last-of-type{-webkit-user-select:none;-moz-user-select:none;-ms-user-select:none;user-select:none;border-bottom-left-radius:.3rem;border-bottom-right-radius:.3rem}.react-datepicker__year-option:hover,.react-datepicker__month-option:hover,.react-datepicker__month-year-option:hover{background-color:#ccc}.react-datepicker__year-option:hover .react-datepicker__navigation--years-upcoming,.react-datepicker__month-option:hover .react-datepicker__navigation--years-upcoming,.react-datepicker__month-year-option:hover .react-datepicker__navigation--years-upcoming{border-bottom-color:#b3b3b3}.react-datepicker__year-option:hover .react-datepicker__navigation--years-previous,.react-datepicker__month-option:hover .react-datepicker__navigation--years-previous,.react-datepicker__month-year-option:hover .react-datepicker__navigation--years-previous{border-top-color:#b3b3b3}.react-datepicker__year-option--selected,.react-datepicker__month-option--selected,.react-datepicker__month-year-option--selected{position:absolute;left:15px}.react-datepicker__close-icon{cursor:pointer;background-color:transparent;border:0;outline:0;padding:0 6px 0 0;position:absolute;top:0;right:0;height:100%;display:table-cell;vertical-align:middle}.react-datepicker__close-icon:after{cursor:pointer;background-color:#216ba5;color:#fff;border-radius:50%;height:16px;width:16px;padding:2px;font-size:12px;line-height:1;text-align:center;display:table-cell;vertical-align:middle;content:"×"}.react-datepicker__close-icon--disabled{cursor:default}.react-datepicker__close-icon--disabled:after{cursor:default;background-color:#ccc}.react-datepicker__today-button{background:#f0f0f0;border-top:1px solid #aeaeae;cursor:pointer;text-align:center;font-weight:700;padding:5px 0;clear:left}.react-datepicker__portal{position:fixed;width:100vw;height:100vh;background-color:#000c;left:0;top:0;justify-content:center;align-items:center;display:flex;z-index:2147483647}.react-datepicker__children-container{width:17.25em;margin:.5em;padding-right:.25em;padding-left:.25em;height:auto}.react-datepicker__aria-live{position:absolute;clip-path:circle(0);border:0;height:1px;margin:-1px;overflow:hidden;padding:0;width:1px;white-space:nowrap}.react-datepicker__calendar-icon{width:1em;height:1em;vertical-align:-.125em}.react-datepicker-popper-offset{margin-top:-.7em}:where(.preview-tab,.widget,.palette-selector,.ddp-field){--spacing-xs: 4px;--spacing-sm: 8px;--spacing-md: 16px;--spacing-lg: 24px;--spacing-xl: 32px;--spacing-2xl: 48px;--radius-sm: 4px;--radius-md: 8px;--radius-lg: 12px;--font-weight-normal: 400;--font-weight-medium: 500;--font-weight-semibold: 600;--font-weight-bold: 700;--transition-fast: .15s ease;--shadow-lg: 0 10px 25px rgba(0, 0, 0, .4)}.preview-tab{display:flex;flex-direction:column;gap:var(--spacing-md);position:relative}.preview-tab__empty{display:flex;align-items:center;justify-content:center;min-height:300px;color:var(--text-muted);font-size:.9rem;border:2px dashed var(--bg-elevated);border-radius:var(--radius-lg)}.preview-tab__loading{display:flex;align-items:center;justify-content:center;padding:var(--spacing-2xl) 0;color:var(--text-secondary)}.preview-tab__error{padding:var(--spacing-md);background:#f443361a;border:1px solid var(--color-error);border-radius:var(--radius-md);color:var(--color-error);font-size:.875rem;text-align:center}.preview-tab__grid{background:var(--bg-dark);padding:var(--spacing-md);border-radius:var(--radius-lg)}.preview-tab__widget{display:flex;background:var(--bg-elevated);border:1px solid rgba(255,255,255,.08);border-radius:var(--radius-md);overflow:hidden;min-height:0;container-type:size}.preview-tab__widget--control{background:var(--bg-elevated);border:1px dashed rgba(255,255,255,.15)}.preview-tab__widget-loading{display:flex;align-items:center;justify-content:center;height:100%;min-height:80px;color:var(--text-muted);font-size:.8125rem}.preview-tab__recalculating{position:fixed;bottom:var(--spacing-lg);right:var(--spacing-lg);padding:var(--spacing-sm) var(--spacing-lg);background:var(--bg-elevated);border:1px solid var(--action-orange);border-radius:var(--radius-md);color:var(--action-orange);font-size:.8125rem;font-weight:var(--font-weight-medium);box-shadow:var(--shadow-lg);z-index:50}.palette-selector{display:flex;flex-direction:column;gap:var(--spacing-sm)}.palette-selector--disabled{opacity:.5;pointer-events:none}.palette-selector__options{display:flex;flex-direction:column;gap:var(--spacing-xs)}.palette-selector__option{display:flex;flex-direction:column;gap:var(--spacing-xs);padding:var(--spacing-xs);background:transparent;border:1.5px solid var(--bg-elevated);border-radius:var(--radius-sm);cursor:pointer;transition:border-color var(--transition-fast)}.palette-selector__option:hover:not(:disabled){border-color:var(--text-muted)}.palette-selector__option--active{border-color:var(--action-orange)}.palette-selector__bar{display:flex;width:100%;height:18px;border-radius:3px;overflow:hidden}.palette-selector__bar--theme{height:12px;opacity:.85}.palette-selector__swatch{flex:1;min-width:0}.palette-selector__label{font-size:.7rem;color:var(--text-muted);text-align:left}.palette-selector__custom{display:flex;flex-direction:column;gap:6px}.palette-selector__row{display:flex;flex-direction:column;gap:4px}.palette-selector__row-label{font-size:.6rem;color:var(--text-muted);text-transform:uppercase;letter-spacing:.5px;font-weight:var(--font-weight-semibold)}.palette-selector__row-slots{display:flex;gap:4px;flex-wrap:wrap}.palette-selector__color-input{width:24px;height:24px;padding:0;border:1.5px solid rgba(255,255,255,.25);border-radius:var(--radius-sm);background:transparent;cursor:pointer;transition:border-color var(--transition-fast);flex-shrink:0}.palette-selector__color-input:hover:not(:disabled){border-color:#ffffff80}.palette-selector__color-input:hover:not(:disabled){border-color:var(--action-orange)}.palette-selector__color-input::-webkit-color-swatch-wrapper{padding:2px}.palette-selector__color-input::-webkit-color-swatch{border:none;border-radius:2px}.ddp-field{width:100%;min-width:0;display:block}.ddp-field .react-datepicker-wrapper,.ddp-field .react-datepicker__input-container{width:100%;display:block}.ddp-field .react-datepicker__input-container input{width:100%;padding:var(--spacing-sm) var(--spacing-md);background:var(--bg-elevated);border:1.5px solid var(--bg-elevated);border-radius:var(--radius-sm);font-size:.8125rem;color:var(--text-primary);box-sizing:border-box;transition:border-color var(--transition-fast)}.ddp-field .react-datepicker__input-container input:focus{outline:none;border-color:var(--action-orange)}.ddp-field .react-datepicker__input-container input::placeholder{color:var(--text-muted)}.ddp-field .react-datepicker__input-container input:disabled{opacity:.6;cursor:not-allowed}.ddp-field .react-datepicker__month{min-height:168px}.react-datepicker-popper{z-index:1100!important}.widget{flex:1;display:flex;flex-direction:column;padding:var(--spacing-sm);background:var(--bg-elevated);border-radius:var(--radius-md);overflow:hidden;box-sizing:border-box;min-height:0;min-width:0}.widget--error{align-items:center;justify-content:center}.widget__error-text{color:var(--color-error);font-size:clamp(.45rem,2.5cqi,.85rem);text-align:center}.widget-filter,.widget-palette{flex:1;display:flex;flex-direction:column;align-items:center;justify-content:flex-start;gap:clamp(4px,1.5cqi,12px);padding:clamp(4px,1cqi,8px) clamp(6px,1.5cqi,12px);box-sizing:border-box;min-height:0;min-width:0;overflow:hidden}.widget-variable{flex:1;display:flex;flex-direction:column;justify-content:center;align-items:center;box-sizing:border-box;min-height:0;min-width:0;overflow:hidden}.widget-filter__label,.widget-palette__label,.widget-variable__label{flex-shrink:0;font-size:clamp(.45rem,6cqi,3rem);color:var(--text-muted);font-weight:var(--font-weight-medium)}.widget-kpi{justify-content:center;align-items:center;text-align:center;gap:clamp(2px,1cqmin,10px);padding:clamp(4px,2cqmin,16px)}.widget-kpi__label{font-size:clamp(.45rem,min(12cqi,12cqb),6rem);color:var(--text-muted);font-weight:var(--font-weight-medium);line-height:1.2;max-width:100%;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}.widget-kpi__value{font-size:clamp(.85rem,min(22cqi,22cqb),8rem);font-weight:var(--font-weight-bold);color:var(--text-primary);line-height:1.1;max-width:100%;overflow:hidden;text-overflow:ellipsis;white-space:nowrap;font-variant-numeric:tabular-nums}.widget-kpi__trend{display:flex;align-items:center;justify-content:center;gap:clamp(2px,.8cqmin,6px);font-size:clamp(.4rem,min(8cqi,8cqb),2rem);max-width:100%;overflow:hidden;flex-wrap:wrap}.widget-kpi__trend--up{color:var(--action-green)}.widget-kpi__trend--down{color:var(--color-error)}.widget-kpi__variance{font-weight:var(--font-weight-semibold);white-space:nowrap}.widget-kpi__trend-label{color:var(--text-muted);white-space:nowrap;overflow:hidden;text-overflow:ellipsis}@container (max-width: 180px){.widget-kpi__trend-label{display:none}}@container (max-height: 70px){.widget-kpi__label{display:none}}.widget-gauge{align-items:center;gap:0;overflow:hidden}.widget-gauge__label{font-size:clamp(.5rem,6cqi,3rem);color:var(--text-muted);font-weight:var(--font-weight-medium);flex-shrink:0}.widget-gauge__chart{position:relative;width:100%;flex:1;min-height:0}.widget-gauge__chart svg{margin-top:5%;display:block;width:100%;height:100%}.widget-gauge__center{position:absolute;top:0;right:0;bottom:0;left:0;display:flex;flex-direction:column;align-items:center;justify-content:center;gap:2px;margin-top:25%}.widget-gauge__percent{font-size:clamp(.5rem,9cqi,4rem);font-weight:var(--font-weight-bold);color:var(--text-primary);line-height:1}.widget-gauge__comparison{font-size:clamp(.4rem,3.5cqi,2rem);color:var(--text-muted)}.widget-gauge__badge{font-size:clamp(.35rem,3cqi,1.25rem);font-weight:var(--font-weight-semibold);text-transform:uppercase;letter-spacing:.3px;padding:1px var(--spacing-xs);border-radius:var(--radius-sm);background:#a4c63926;color:var(--action-green)}.widget-chart{gap:var(--spacing-xs)}.widget-chart__empty{display:flex;align-items:center;justify-content:center;height:100%;color:var(--text-muted);font-size:clamp(.5rem,2.5cqi,.85rem)}.widget-chart__title{font-size:clamp(.5rem,2.5cqi,.85rem);font-weight:var(--font-weight-semibold);color:var(--text-primary);margin:0}.widget-chart__container{flex:1;min-height:0;overflow:hidden}.widget-filter__date-range{display:flex;align-items:center;gap:clamp(2px,1cqi,8px);flex:1;min-width:0}.widget-filter__date-range--stacked{flex-direction:column;align-items:stretch;gap:clamp(4px,1.5cqmin,10px);width:100%;padding:clamp(2px,1cqmin,8px) 0}.widget-filter__date-range .ddp-field{flex:1;min-width:0;width:100%}.widget-filter__date-range .ddp-field .react-datepicker__input-container input,.widget-filter__select{padding:clamp(8px,4cqmin,22px) clamp(6px,1.5cqmin,12px);font-size:clamp(.5rem,10cqmin,2rem);background:var(--bg-paper);border:1px solid rgba(255,255,255,.1);border-radius:var(--radius-sm);color:var(--text-primary);flex:1;min-width:0;width:100%;box-sizing:border-box;text-align:center;font-variant-numeric:tabular-nums}.widget-filter__date-sep{font-size:clamp(.35rem,2.5cqi,.8rem);color:var(--text-muted)}.widget-filter__multi{display:flex;flex-direction:column;align-items:stretch;justify-content:space-around;gap:clamp(4px,1.5cqmin,14px);flex:1;min-height:0;width:100%;padding:clamp(6px,2cqmin,14px) clamp(4px,2cqmin,12px);box-sizing:border-box;overflow-y:auto}.widget-filter__multi::-webkit-scrollbar{width:6px}.widget-filter__multi::-webkit-scrollbar-track{background:transparent}.widget-filter__multi::-webkit-scrollbar-thumb{background:var(--bg-elevated);border-radius:3px}.widget-filter__multi::-webkit-scrollbar-thumb:hover{background:var(--text-muted)}.widget-filter__multi-clear{flex-shrink:0;width:100%;padding:clamp(3px,1cqmin,8px) clamp(8px,2.5cqmin,14px);background:transparent;border:1px solid var(--bg-elevated);border-radius:var(--radius-sm);color:var(--action-orange);font-size:clamp(.4rem,7cqmin,1rem);font-weight:var(--font-weight-semibold);text-align:center;cursor:pointer;transition:background-color var(--transition-fast),border-color var(--transition-fast)}.widget-filter__multi-clear:hover{background-color:var(--bg-elevated);border-color:var(--action-orange)}.widget-filter__multi-option{display:flex;align-items:center;gap:clamp(6px,4cqmin,14px);padding:clamp(4px,1.5cqmin,12px) clamp(8px,2.5cqmin,14px);height:clamp(20px,18cqb,120px);background:var(--bg-paper);border:1px solid var(--bg-elevated);border-radius:var(--radius-sm);cursor:pointer;transition:border-color var(--transition-fast),background-color var(--transition-fast);font-size:clamp(.45rem,8cqmin,1.2rem);font-weight:var(--font-weight-medium);color:var(--text-primary);line-height:1;flex-shrink:0;box-sizing:border-box}.widget-filter__multi-option:hover{border-color:var(--text-muted);background-color:var(--bg-elevated)}.widget-filter__multi-option:has(input[type=checkbox]:checked){border-color:var(--text-muted);background-color:var(--bg-elevated)}.widget-filter__multi-option input[type=checkbox]{appearance:none;-webkit-appearance:none;-moz-appearance:none;width:clamp(12px,7cqmin,22px);height:clamp(12px,7cqmin,22px);border:1.5px solid var(--text-muted);border-radius:3px;background:var(--bg-elevated);cursor:pointer;position:relative;flex-shrink:0;transition:border-color var(--transition-fast),background-color var(--transition-fast);margin:0}.widget-filter__multi-option input[type=checkbox]:hover{border-color:var(--action-orange)}.widget-filter__multi-option input[type=checkbox]:checked{background:var(--action-orange);border-color:var(--action-orange)}.widget-filter__multi-option input[type=checkbox]:checked:after{content:"";position:absolute;left:30%;top:8%;width:30%;height:60%;border:solid var(--bg-dark);border-width:0 2px 2px 0;transform:rotate(45deg)}.widget-filter__select{width:95%;max-height:45%;margin-top:2%;flex:1;font-size:clamp(.4rem,5cqi,1.5rem);font-weight:var(--font-weight-semibold);color:var(--text-primary);text-align:left;padding:clamp(8px,4cqi,22px) clamp(6px,1.5cqi,12px);min-width:0;box-sizing:border-box}.widget-filter>.widget-filter__select,.widget-filter__date-range--year .widget-filter__select,.widget-filter__date-range--month .widget-filter__select,.widget-filter__date-range--week .widget-filter__select{text-align:center;text-align-last:center;font-weight:var(--font-weight-semibold);color:var(--text-primary);background:var(--bg-paper);border:1px solid rgba(255,255,255,.1);border-radius:var(--radius-sm);cursor:pointer;appearance:none;-webkit-appearance:none;-moz-appearance:none;background-image:none;transition:border-color var(--transition-fast),background-color var(--transition-fast);box-sizing:border-box;width:100%;margin-top:0;max-height:none;padding:clamp(2px,.8cqmin,6px) clamp(6px,1.5cqmin,12px);line-height:1}.widget-filter>.widget-filter__select:hover,.widget-filter>.widget-filter__select:focus,.widget-filter__date-range--year .widget-filter__select:hover,.widget-filter__date-range--year .widget-filter__select:focus,.widget-filter__date-range--month .widget-filter__select:hover,.widget-filter__date-range--month .widget-filter__select:focus,.widget-filter__date-range--week .widget-filter__select:hover,.widget-filter__date-range--week .widget-filter__select:focus{outline:none;border-color:var(--action-orange);background-color:var(--bg-elevated)}.widget-filter>.widget-filter__select option,.widget-filter__date-range--year .widget-filter__select option,.widget-filter__date-range--month .widget-filter__select option,.widget-filter__date-range--week .widget-filter__select option{background:var(--bg-paper);color:var(--text-primary);font-size:.875rem;font-weight:var(--font-weight-normal);text-align:left;padding:6px 10px}.widget-filter>.widget-filter__select{flex:0 1 auto;height:clamp(50px,22cqmin,140px);max-height:75%;margin-block:auto;align-self:center;font-size:clamp(.6rem,12cqmin,2.2rem)}.widget-filter__date-range--year,.widget-filter__date-range--month,.widget-filter__date-range--week{display:flex;flex-direction:column;align-items:stretch;justify-content:center;gap:clamp(6px,2.5cqmin,16px);flex:1;width:100%;padding:clamp(6px,2cqmin,16px) clamp(4px,2cqmin,14px);box-sizing:border-box}.widget-filter__date-range--year .widget-filter__select{flex:0 1 auto;height:clamp(50px,22cqmin,140px);font-size:clamp(.6rem,12cqmin,2.2rem)}.widget-filter__date-range--month .widget-filter__select{flex:0 1 auto;height:clamp(30px,10cqmin,66px);font-size:clamp(.5rem,10cqmin,1.4rem)}.widget-filter__date-range--week .widget-filter__select{flex:0 1 auto;height:clamp(22px,12cqmin,48px);font-size:clamp(.45rem,8cqmin,3rem)}.widget-filter__search{position:relative;display:flex;align-items:center;flex:1;min-width:0;width:100%;padding:clamp(2px,1cqmin,8px) 0}.widget-filter .widget-filter__search-field{width:100%;padding:clamp(6px,3cqmin,18px) clamp(8px,2cqmin,14px);background:var(--bg-dark);border:1px solid rgba(255,255,255,.1);border-radius:var(--radius-sm);color:var(--text-primary);font-size:clamp(.55rem,10cqmin,1.8rem);font-weight:var(--font-weight-semibold);text-align:center;box-sizing:border-box;cursor:text;transition:border-color var(--transition-fast),background-color var(--transition-fast)}.widget-filter .widget-filter__search-field::placeholder{color:var(--text-muted);font-weight:var(--font-weight-normal)}.widget-filter .widget-filter__search-field:hover,.widget-filter .widget-filter__search-field:focus{outline:none;border-color:var(--action-orange);background-color:var(--bg-paper)}.widget-filter__search-panel{z-index:10000;display:flex;flex-direction:column;background:var(--bg-paper);border:1px solid var(--bg-elevated);border-radius:var(--radius-sm);box-shadow:var(--shadow-md, 0 8px 28px rgba(0, 0, 0, .45));overflow:hidden}.widget-filter__search-list{display:flex;flex-direction:column;gap:2px;padding:6px;overflow-y:auto}.widget-filter__search-option{display:flex;align-items:center;gap:8px;width:100%;padding:8px 10px;background:transparent;border:none;border-left:3px solid transparent;border-radius:var(--radius-sm);color:var(--text-primary);font-size:.85rem;font-weight:var(--font-weight-medium);text-align:left;cursor:pointer;transition:background-color var(--transition-fast),color var(--transition-fast)}.widget-filter__search-option:hover{background-color:var(--bg-elevated)}.widget-filter__search-option.is-selected{background-color:var(--bg-elevated);border-left-color:var(--action-orange);color:var(--action-orange)}.widget-filter__search-check{flex-shrink:0;width:1em;color:var(--action-orange);font-weight:var(--font-weight-semibold)}.widget-filter__search-option input[type=checkbox]{width:16px;height:16px;flex-shrink:0;accent-color:var(--action-orange);cursor:pointer}.widget-filter__search-clear{width:100%;margin-bottom:4px;padding:8px 10px;background:transparent;border:none;border-bottom:1px solid var(--bg-elevated);border-radius:0;color:var(--action-orange);font-size:.8rem;font-weight:var(--font-weight-semibold);text-align:left;cursor:pointer;transition:background-color var(--transition-fast)}.widget-filter__search-clear:hover{background-color:var(--bg-elevated)}.widget-filter__search-empty{padding:12px;color:var(--text-muted);font-size:.85rem;text-align:center}.widget-filter__search-list::-webkit-scrollbar{width:6px}.widget-filter__search-list::-webkit-scrollbar-track{background:transparent}.widget-filter__search-list::-webkit-scrollbar-thumb{background:var(--bg-elevated);border-radius:3px}.widget-filter__search-list::-webkit-scrollbar-thumb:hover{background:var(--text-muted)}.widget-variable__input-wrapper{display:flex;align-items:center;margin-top:2%;width:90%;background:var(--bg-paper);border:1px solid rgba(255,255,255,.1);border-radius:var(--radius-sm);overflow:hidden}.widget-variable__input{flex:1;font-size:clamp(.4rem,5cqi,1.5rem);font-weight:var(--font-weight-semibold);background:transparent;border:none;outline:none;color:var(--text-primary);text-align:left;padding:clamp(2px,1cqi,6px) clamp(4px,1.5cqi,8px);min-width:0;box-sizing:border-box}.widget-variable__input::-webkit-outer-spin-button,.widget-variable__input::-webkit-inner-spin-button{-webkit-appearance:none;margin:0}.widget-variable__input[type=number]{-moz-appearance:textfield;-webkit-appearance:textfield;appearance:textfield}.widget-variable__input:disabled{opacity:.6;cursor:not-allowed}.widget-variable__suffix{font-size:clamp(.4rem,4cqi,1.25rem);color:var(--text-muted);white-space:nowrap;padding:0 clamp(4px,1.5cqi,8px);border-left:1px solid rgba(255,255,255,.1);flex-shrink:0}.widget-variable__lock-icon{font-size:clamp(.45rem,2.5cqi,.75rem)}.widget-variable--locked .widget-variable__input-wrapper{border-style:dashed}.widget-palette{flex-direction:column;justify-content:flex-start;align-items:stretch;padding:clamp(4px,1.5cqmin,12px);gap:clamp(2px,1cqmin,8px);overflow:auto}.widget-palette__label{text-align:center;flex-shrink:0}.widget-palette__lock-icon{font-size:clamp(.45rem,2.5cqmin,.75rem);align-self:center}.widget-palette--locked .palette-selector__color-input{opacity:.6;cursor:not-allowed}.widget-palette .palette-selector{gap:clamp(2px,3cqmin,28px);flex:1;min-height:0;justify-content:center}.widget-palette .palette-selector__row{gap:clamp(1px,1.2cqmin,10px);min-height:0}.widget-palette .palette-selector__row-label{font-size:clamp(.35rem,1.8cqmin,.7rem);line-height:1}.widget-palette .palette-selector__row-slots{gap:clamp(1px,.8cqmin,6px);flex-wrap:nowrap;justify-content:space-between;width:100%;min-height:0}.widget-palette .palette-selector__color-input{flex:1 1 0;min-width:0;min-height:0;width:auto;height:clamp(8px,10cqmin,60px);border:1px solid rgba(255,255,255,.2);padding:0}.widget-palette .palette-selector__color-input:hover:not(:disabled){border-color:#fff6}