Heatmap Chart
Documentation Index
Fetch the complete documentation index at: /llms.txt. Use this file to discover all available pages before exploring further.
A GitHub-style calendar heatmap — one cell per day, colored by intensity — powered by Apache ECharts
Installation
Usage
The heatmap is the GitHub contribution graph shape: a calendar year laid out as week columns, one square per day, with color intensity standing in for the value. <EChartsHeatmapChart> is the container, and every part hangs off it as a compound member — <EChartsHeatmapChart.Cell>, <EChartsHeatmapChart.MonthLabel>, <EChartsHeatmapChart.DayLabel>, <EChartsHeatmapChart.Tooltip>, and <EChartsHeatmapChart.Legend> — so a single import gives you the whole chart. The cells are intrinsic to the data, so <Cell> always renders and just configures the grid; the labels, tooltip, and legend follow presence semantics — omit one and it does not render.
import { EChartsHeatmapChart, type ChartConfig, type HeatmapDatum } from "@/components/evilcharts/charts/echarts-heatmap-chart";// One entry per day that has a value. Days you leave out render as empty cells.
const data: HeatmapDatum[] = [
{ date: "2025-01-06", value: 3 },
{ date: "2025-01-07", value: 11 },
{ date: "2025-01-09", value: 1 },
// ...
];
// The color array IS the intensity ramp — lightest first, strongest last.
const chartConfig = {
contributions: {
label: "Contributions",
colors: {
light: ["#9be9a8", "#40c463", "#30a14e", "#216e39"],
dark: ["#0e4429", "#006d32", "#26a641", "#39d353"],
},
},
} satisfies ChartConfig;
<EChartsHeatmapChart className="h-48" data={data} config={chartConfig}>
<EChartsHeatmapChart.Cell dataKey="contributions" />
<EChartsHeatmapChart.MonthLabel />
<EChartsHeatmapChart.DayLabel />
<EChartsHeatmapChart.Tooltip />
<EChartsHeatmapChart.Legend />
</EChartsHeatmapChart>Under the hood these compound children are declarative configuration slots rather than visual React DOM nodes. The root reads their props and compiles an ECharts option — a calendar coordinate system for the date math, and a custom series for the cells so they can carry a gap, rounded corners, and a per-day color — which ECharts paints with Canvas by default or SVG when renderer="svg".
config is the same contract as every EvilCharts chart — a key maps to a label and a per-theme colors array. See Chart Config for the full shape. Here the array does double duty: its length is the number of intensity levels, and each entry is that level's color. Colors resolve from CSS variables at runtime, so dark mode just works.
With no range, the chart shows the trailing year ending on the latest date in data, so a
feed of recent activity lays out the way GitHub does without any date math on your side.
SVG Renderer
Pass renderer="svg" to the chart root to opt into ECharts' SVG renderer. Omit it to use the default Canvas renderer.
Interactive Selection
Set isClickable on <Cell> to make days selectable. The selected day keeps full strength and wears a ring while the rest soften. Handle selection events with the root's onSelectionChange callback:
<EChartsHeatmapChart
data={data}
config={chartConfig}
onSelectionChange={(selection) => {
if (selection) {
console.log("Selected:", selection.date, "Value:", selection.value);
} else {
console.log("Deselected");
}
}}
>
<EChartsHeatmapChart.Cell dataKey="contributions" isClickable />
<EChartsHeatmapChart.Tooltip />
</EChartsHeatmapChart>Loading State
Pass isLoading to <EChartsHeatmapChart> to show an animated gray skeleton of the grid
while data loads. The intro sweep replays once the data lands.
Examples
Examples of the heatmap in different configurations. Customize the root range, weekStart, and scale, the <Cell> radius and gap, and more.
Calendar Year
Pass a year to range for January through December. scale="linear" spreads the levels
evenly between the smallest and largest value instead of by quantile.
Monday Start
weekStart="monday" puts Monday on the top row. <DayLabel labels> takes seven names,
Sunday first — pass an empty string to leave a row unlabeled.
Rounded Cells
A shorter range — here one quarter — gives the cells room, so a larger radius and gap
read as tiles rather than pixels.
Explicit Thresholds
thresholds pins the level boundaries. Zero stays empty; positive values below 3 are the
first level, 3 up to 10 the second, 10 and up the third. Two cuts make three levels, so
the config needs three colors — one per level.
API Reference
A root container plus a small set of composible parts. Render the root, then compose the parts you need as children. Each part is declarative config the root compiles into the ECharts option.
The root container. It owns the date window, the value → level mapping, shared selection state, the loading skeleton, and the intro sweep. Everything visual is composed as children and compiled into the ECharts option.
Configures the day cells. Always renders — it names the config key to color the grid with and shapes each cell.
Shows month names above the grid, each over the column where the month begins. Its presence enables it; omit it and none show.
Shows weekday names beside the grid. Its presence enables it; omit it and none show.
The hover tooltip. Its presence enables it; omit it and none shows. Hovering a day shows the formatted date as the title and the series label with that day's value beneath it. Hidden automatically while loading.
The "Less → More" ramp rendered under the grid, one swatch per level plus the empty cell. Its presence enables it; omit it and none shows. Hidden while loading.