Skip to main content
A reference line marks a constant value — a sales target, a capacity ceiling, a zero baseline — that the rest of the chart is read against. It’s a geom like any other: geom.rule(), layered into the spec with its own value and style.

A horizontal goal line

Bind the rule to a constant y with aes: { y: { value } }. The { value } form is a constant mapping — it pins the aesthetic to a literal instead of a column:
The rule value participates in the y-scale’s auto-domain — set a target above the tallest bar and the axis grows to fit it, so the line is never clipped off the top.

Styling the line

Style the rule through its params:
label
string
Optional inline text drawn alongside the line. Omit to draw a bare line.
labelPosition
'start' | 'end'
default:"start"
Anchors the label at the start or end of the line.
color
string
Stroke color. Falls back to the theme’s reference-line token when unset.
strokeWidth
number
default:"1"
Line thickness in pixels.
lineType
'solid' | 'dashed' | 'dotted'
default:"solid"
Stroke style.

Vertical lines

Mark a constant along the x-axis with aes: { x: { value } } instead:
A vertical rule requires a numeric x-axis — it marks a constant x-value, which only has meaning when x is continuous. Categorical and date x-axes support horizontal rules only.

Multiple rules

Rules compose like any other layer, and paint in spec order — a rule added after geom.bar() draws in front of the bars. Stack as many as you need:

Flipped and secondary axes

A rule tracks the data space, not the screen. Under coord.flip() a { y: { value } } rule still marks a constant y — the renderer paints it as a vertical line because the y-axis now runs horizontally. To pin a rule to a secondary axis, add yScaleType: 'secondary':