---
name: month_heatmap
kind: component
lang: ts
domain: ui
version: "1.0.0"
framework: react
purity: pure
signature: "MonthHeatmap(props: MonthHeatmapProps): JSX.Element"
description: "Grid mensual de calor (heatmap) con inicio en lunes. Renderiza 7 columnas con header de dias de semana y celdas que muestran numero del dia, hasta dos contadores con icono, borde azul para hoy y fondo tintado segun valores primary/secondary."
tags: [calendar, heatmap, grid, month, ui, mantine, pendiente-usar]
uses_functions: [month_grid_ts_core]
uses_types: []
returns: []
returns_optional: false
error_type: ""
imports:
  - "@mantine/core"
  - "@tabler/icons-react"
  - "../core/month_grid"
tested: false
tests: []
test_file_path: ""
props:
  - name: month
    type: "Date"
    required: true
    description: "Mes a mostrar. Se usan getFullYear() y getMonth(). El dia se ignora."
  - name: cells
    type: "Map<string, MonthHeatmapCell>"
    required: true
    description: "Datos por dia. Clave YYYY-MM-DD. Valores: primary (contador azulado) y secondary (contador verdoso)."
  - name: primaryIcon
    type: "ReactNode"
    required: false
    description: "Icono junto al contador primary. Default: IconPlus de @tabler/icons-react."
  - name: secondaryIcon
    type: "ReactNode"
    required: false
    description: "Icono junto al contador secondary. Default: IconCheckbox de @tabler/icons-react."
  - name: primaryColor
    type: "string"
    required: false
    description: "Color Mantine del contador primary. Default: 'blue'."
  - name: secondaryColor
    type: "string"
    required: false
    description: "Color Mantine del contador secondary. Default: 'green'."
  - name: dayLabels
    type: "string[]"
    required: false
    description: "Array de 7 strings para el header de columnas, empezando por lunes. Default: ['Lun','Mar','Mie','Jue','Vie','Sab','Dom']."
  - name: cellMinHeight
    type: "number"
    required: false
    description: "Altura minima de cada celda en px. Default: 72."
emits: []
has_state: false
params:
  - name: month
    desc: "Mes a renderizar como objeto Date (year + month extraidos con getFullYear/getMonth)."
  - name: cells
    desc: "Map de YYYY-MM-DD a { primary?, secondary? } con los contadores de cada dia."
  - name: primaryIcon
    desc: "ReactNode opcional para el icono del contador primary (creado, pendiente, etc.)."
  - name: secondaryIcon
    desc: "ReactNode opcional para el icono del contador secondary (completado, resuelto, etc.)."
  - name: primaryColor
    desc: "Nombre de color Mantine para el contador primary y su tinte de fondo (rgba 6%)."
  - name: secondaryColor
    desc: "Nombre de color Mantine para el contador secondary y su tinte de fondo (rgba 8%)."
  - name: dayLabels
    desc: "Labels del header de dias de semana, 7 elementos, orden lunes-domingo."
  - name: cellMinHeight
    desc: "Altura minima en px de cada celda del grid."
output: "Componente React que renderiza un grid de 7 columnas con el calendario del mes indicado. Celdas de relleno vacias, celdas del mes con numero, contadores opcionales e iconos, borde azul en el dia de hoy y fondo tintado segun presencia de valores."
file_path: "frontend/functions/ui/month_heatmap.tsx"
---

## Ejemplo

```tsx
import { MonthHeatmap, type MonthHeatmapCell } from "@fn_library/ui/month_heatmap";

const cells = new Map<string, MonthHeatmapCell>([
  ["2026-05-01", { primary: 3 }],
  ["2026-05-09", { primary: 1, secondary: 2 }],
  ["2026-05-15", { secondary: 4 }],
]);

<MonthHeatmap
  month={new Date(2026, 4, 1)}
  cells={cells}
/>
```

## Ejemplo con iconos y colores custom

```tsx
import { IconBug, IconCheck } from "@tabler/icons-react";

<MonthHeatmap
  month={new Date(2026, 4, 1)}
  cells={cells}
  primaryIcon={<IconBug size={10} />}
  secondaryIcon={<IconCheck size={10} />}
  primaryColor="red"
  secondaryColor="teal"
  cellMinHeight={88}
/>
```

## Notas

Componente puro (sin estado propio, sin efectos). El calculo del grid se delega a
`month_grid_ts_core` (`monthGrid(year, month)`), que genera un array de celdas
de longitud multiplo de 7 con `date: null` para el padding.

La deteccion de "hoy" usa `Date` nativo sin dayjs para no introducir dependencias.

El fondo tintado prioriza `secondary` sobre `primary` cuando ambos son > 0,
replicando la logica del componente original en `apps/kanban`.

Compatible con Mantine v9. No usa CSS variables custom — emplea props de Mantine
(`c`, `fw`, `p`, `gap`, `radius`) y solo dos `style` inline para `minHeight`
y `borderColor` condicional (que no tienen equivalente en props Mantine).
