TanStack
Mark Reference

Hexbin Mark

hexbin aggregates raw numeric x/y observations after the chart resolves its positional scales and inner bounds. Import it from the optional spatial subpath; it is not included in the root or universal barrel.

ts
import { hexbin } from '@tanstack/charts/spatial/hexbin'

const mark = hexbin(rows, {
  x: 'weight',
  y: 'economy',
  binWidth: 24,
  color: 'count',
  r: 11,
  stroke: '#fff',
})
ts
function hexbin<TDatum, TOutputs extends TransformOutputs<TDatum>>(
  source: Iterable<TDatum>,
  options: HexbinOptions<TDatum, TOutputs>,
): ChartMark<HexbinDatum<TDatum, TOutputs>, number, number>

Without outputs, each bin receives a numeric count output.

Options

OptionTypeDefaultMeaning
xTransformValue<TDatum, number?>RequiredRaw horizontal observation
yTransformValue<TDatum, number?>RequiredRaw vertical observation
binWidthnumber20Horizontal pixel distance between bin centers
outputsTransformOutputs<TDatum>Count reducerNamed reducers evaluated over each bin
idstringLayer-derivedStable mark ID
zChannel<HexbinDatum, ChartKey?>No groupInteraction group
colorChannel<HexbinDatum, ChartKey?>zDerived value sent to the color scale
rnumber | Channel<HexbinDatum, number?>Bin radius minus 1pxRendered hexagon circumradius
rScaleChartNumericScaleIdentityMaps a radius channel to pixels
fillVisualChannel<HexbinDatum, string>Resolved colorFinal fill override
strokeVisualChannel<HexbinDatum, string>NoneFinal stroke override
fillOpacity, strokeOpacity, and strokeWidthnumberSVG defaultHexagon presentation

binWidth must be positive and finite. Both positional scales must support invert; continuous D3 scales and the compact TanStack linear scale do. A band scale is not a valid hexbin position scale.

Reducers and lineage

outputs uses the same reducer contract as eager transforms. Count, sum, mean, minimum, maximum, and custom reducers are available:

ts
hexbin(rows, {
  x: 'x',
  y: 'y',
  outputs: {
    count: { reduce: 'count' },
    total: { value: 'revenue', reduce: 'sum' },
  },
  color: 'total',
})

The margin solver may evaluate reducers during multiple resolved-layout passes. Custom reducers must be synchronous, pure, deterministic, and must not mutate source rows.

HexbinDatum<TDatum, TOutputs> contains:

  • semantic x and y values obtained by inverting the lattice center;
  • every named reducer output;
  • source, retaining the original row objects in input order; and
  • sourceIndexes, retaining their original indexes.

Rows with nonfinite or missing x/y values are omitted without renumbering the remaining lineage. Every valid input row belongs to exactly one bin. The interaction point datum is the complete HexbinDatum, so tooltips can show counts, custom outputs, or source records without case-owned lookup tables.

Responsive behavior

Initial raw x/y channels establish the positional domains. The mark then bins their mapped pixel coordinates inside the final plot and contributes its derived color channel before color-scale and legend resolution. Resizing may change bin membership; repeated compilation at the same size is deterministic.