53 lines
1.8 KiB
TypeScript
53 lines
1.8 KiB
TypeScript
'use client'
|
|
import { useEffect, useState } from 'react'
|
|
import {
|
|
isSuppressed,
|
|
type ApoyosMEData,
|
|
type SuppressedPayload,
|
|
type DashboardFilters,
|
|
} from '@/lib/dashboard-types'
|
|
import { queries } from '@/lib/dashboard-queries'
|
|
import { WidgetShell } from './widget-shell'
|
|
|
|
export function ApoyosBarME({ surveyId, filters }: { surveyId: string; filters: DashboardFilters }) {
|
|
const [data, setData] = useState<ApoyosMEData | SuppressedPayload | null>(null)
|
|
const [error, setError] = useState(false)
|
|
|
|
useEffect(() => {
|
|
setData(null); setError(false)
|
|
queries.meApoyos(surveyId, filters)
|
|
.then((d) => setData(d as ApoyosMEData | SuppressedPayload))
|
|
.catch(() => setError(true))
|
|
}, [surveyId, JSON.stringify(filters)])
|
|
|
|
const status = error ? 'error' : data === null ? 'loading' : isSuppressed(data) ? 'suppressed' : 'ok'
|
|
const ok = status === 'ok' ? (data as ApoyosMEData) : null
|
|
|
|
return (
|
|
<WidgetShell
|
|
title="Apoyos más demandados"
|
|
subtitle="9.2 · qué beneficios diseñar (máx. 3 opciones por persona)"
|
|
status={status}
|
|
n={ok?.n}
|
|
colSpan={6}
|
|
>
|
|
{ok && (
|
|
<ul className="db-bar-list" aria-label="Apoyos más demandados">
|
|
{ok.apoyos.length === 0 && (
|
|
<li className="db-suppressed-hint">No hay datos suficientes por apoyo (n<5 en todos).</li>
|
|
)}
|
|
{ok.apoyos.map((item) => (
|
|
<li key={item.apoyo} className="db-bar-item">
|
|
<span className="db-bar-label">{item.apoyo}</span>
|
|
<div className="db-bar-track">
|
|
<div className="db-bar-fill" style={{ width: `${item.pct}%`, background: '#43BBC8' }} />
|
|
</div>
|
|
<span className="db-bar-pct">{item.pct}%</span>
|
|
</li>
|
|
))}
|
|
</ul>
|
|
)}
|
|
</WidgetShell>
|
|
)
|
|
}
|