import type { StatusTone } from '@/components/StatusBadge'
import { cn } from '@/lib/utils'

/**
 * El color del punto por tono, con su halo.
 *
 * Los cinco tonos del contrato se resuelven en cuatro colores: `neutral` y
 * `unknown` comparten el gris porque **las dos son ausencia de afirmación** —una
 * no tiene nada que decir, la otra no lo pudo comprobar— y un punto no tiene
 * dónde poner el borde punteado que las distingue en un badge. Esa diferencia la
 * hace la palabra, que va al lado.
 *
 * El halo es un `ring` del mismo color al 25 %: es lo que hace que el punto se
 * lea como una luz encendida y no como una viñeta. **No parpadea**: un pulso
 * permanente en el tablero convierte en ruido justo lo que tiene que llamar la
 * atención cuando cambia, y encima es movimiento que nadie pidió.
 */
const DOT_TONES: Record<StatusTone, string> = {
  positive: 'bg-emerald-500 ring-emerald-500/25',
  attention: 'bg-amber-500 ring-amber-500/25',
  critical: 'bg-red-500 ring-red-500/25',
  neutral: 'bg-muted-foreground/40 ring-muted-foreground/15',
  unknown: 'bg-muted-foreground/40 ring-muted-foreground/15',
}

interface Props {
  tone: StatusTone
  className?: string
}

/**
 * La luz de atención de una tarjeta: verde, amarillo, rojo o gris.
 *
 * **Nunca va solo** (RT-04). Un estado dicho únicamente con color no se comunica:
 * no sobrevive a una captura en escala de grises ni a quien no distingue el verde
 * del rojo. Este punto es el refuerzo que se ve desde lejos —de un vistazo, sin
 * leer— y la palabra que lo nombra vive en el cuerpo de la misma tarjeta.
 *
 * Por eso mismo es `aria-hidden`: la palabra ya está en la tarjeta y un lector de
 * pantalla que además anuncie el punto diría el estado dos veces.
 *
 * El tono no lo elige quien lo dibuja: sale de `accessStateTone()`, que es el
 * mismo criterio que usa el badge. Con dos mapas separados, el punto puede quedar
 * verde al lado de una palabra que dice «acceso perdido».
 */
export function AttentionDot({ tone, className }: Props) {
  return (
    <span
      aria-hidden
      // El tono viaja al marcado para poder comprobar desde afuera qué familia
      // le tocó, sin leer la lista de clases.
      data-tone={tone}
      className={cn('inline-block size-2.5 shrink-0 rounded-full ring-4', DOT_TONES[tone], className)}
    />
  )
}
