Skip to content

mplchart.primitives

mplchart drawing primitives.

Primitives are the drawing building blocks passed to chart.plot(...): price renderers (Candlesticks, OHLC, Renko, ...), generic renderers that bind an indicator or expression via @ or a positional argument (LinePlot, AreaPlot, BarPlot, Bands), overlays (Markers, Stripes, VLine, HLine), and layout controls (Pane). Plot order matters: primitives land on the current pane, and Pane creates a new one for the primitives that follow.


AutoPlot

AutoPlot(indicator=None, *, label: str | None = None)

Default plotter primitive.

Auto-plots an expression or indicator by dispatching each output to a renderer primitive: band results (upperband/lowerband) go to Bands wholesale; otherwise *hist columns go to BarPlot and everything else to LinePlot, column by column. Styling lives in the renderers (keyed by series name). Used implicitly when plotting anything that is not already a Primitive; can also be applied explicitly to override the legend label.

Arguments:

  • indicator: indicator or expression to plot. Can also be bound via @.
  • label (str): override the legend label. When None, the label is derived from the expression/indicator via get_label.

Examples:

chart.plot(SMA(20))                                # implicit AutoPlot
chart.plot(AutoPlot(SMA(20), label="short_ma"))    # explicit override
chart.plot(MACD() @ AutoPlot(label="macd"))        # operator form

Candlesticks

Candlesticks(
    indicator=None,
    *,
    label: str | None = None,
    width: float = 0.8,
    alpha: float | None = None,
    color: str | None = None,
    colorup: str | None = None,
    colordn: str | None = None,
    hollow: bool | None = None,
    use_prev_close: bool | None = None,
    use_bars: bool = False,
)

Candlesticks primitive.

Plots OHLC prices as a candlestick chart. Up-bars are close ≥ open. An optional indicator supplies alternative OHLC data — any indicator or expression producing open/high/low/close columns; without one the chart prices are plotted. See HeikinAshi for a subclass bound to such an indicator. The color kwargs declare a complete scheme — schemes are atomic:

  • no color kwargs — style-driven: palette from the candle.* color settings, falling back to the default look (mono hollow: up-bars hollow, down-bars filled, in text.color)
  • color= — mono hollow in the given color
  • colorup= / colordn= — filled bicolor
  • colorup= / colordn= with hollow=True — colored hollow (TradingView hollow candles)

In the no-kwargs path, candle.up.color / candle.down.color select the filled bicolor family (missing side falls to text.color), edge.up.color / edge.down.color override the body outlines, wicks.up.color / wicks.down.color color the wicks (which otherwise follow the edges — set both to one color for yahoo-style neutral wicks), and candle.off.color sets the hollow-body fill (default axes.facecolor). Color kwargs bypass settings entirely.

Arguments:

  • indicator: indicator or expression producing OHLC data — a frame with open, high, low, close columns aligned with prices. @ binds as an equivalent alternative. Defaults to None — plot the chart prices.
  • label (str): legend label override. When None, derived from the indicator, else the class name.
  • width (float): Width of each candlestick body as a fraction of bar spacing. Defaults to 0.8.
  • alpha (float): Opacity of the candle body fills, between 0.0 and 1.0 — edges and wicks stay opaque, the mplfinance rendering. Defaults to the candle.alpha setting, else 1.0.
  • color (str): Single color for the mono hollow scheme. Mutually exclusive with colorup/colordn.
  • colorup (str): Color for up-bars (bicolor scheme). Defaults to the current text.color matplotlib parameter.
  • colordn (str): Color for down-bars (bicolor scheme). Defaults to the current text.color matplotlib parameter.
  • hollow (bool): Fill up-bodies with the background color (axes.facecolor) instead of the up color. Default (None) defers to the candle.hollow setting, else resolves from the palette — hollow when the resolved faces are mono, filled when they differ. False with an explicit mono color= raises at plot time (direction-blind). Combine with use_prev_close for the StockCharts look.
  • use_prev_close (bool): Color bars by close vs previous close (interbar) instead of close vs open (intrabar). Default (None) defers to the candle.use_prev_close setting, else False. Meaningless for a mono palette — True with an explicit color= raises at plot time.
  • use_bars (bool): Deprecated and ignored — the legacy bar renderer was removed (sample code preserved in playground/prototypes/candlesticks-as-bars.ipynb).

HeikinAshi

HeikinAshi(
    *,
    label: str = 'HeikinAshi',
    width: float = 0.8,
    alpha: float | None = None,
    color: str | None = None,
    colorup: str | None = None,
    colordn: str | None = None,
    hollow: bool | None = None,
)

Heikin-Ashi primitive.

Plots Heikin-Ashi ("average bar") candles computed from the chart prices — a Candlesticks specialization bound to calc_heikin_ashi. Accepts the Candlesticks styling arguments (color schemes, candle.* settings, label) except use_prev_close, which is pinned intrabar: Heikin-Ashi bars define their direction as ha close vs ha open.

OHLC

OHLC(
    *,
    width: float = 0.8,
    alpha: float | None = None,
    colorup: str | None = None,
    colordn: str | None = None,
)

Open High Low Close primitive.

Plots OHLC prices as traditional bar charts with horizontal tick marks for the open (left tick) and close (right tick) prices.

Arguments:

  • width (float): Width of each bar as a fraction of bar spacing. Defaults to 0.8.
  • alpha (float): Opacity of the bars, between 0.0 and 1.0. Defaults to the ohlc.alpha setting, else 1.0.
  • colorup (str): Color for up-bars (close ≥ previous close). Defaults to the ohlc.up.color setting, else text.color.
  • colordn (str): Color for down-bars. Defaults to the ohlc.down.color setting, else text.color.

Renko

Renko(
    brick_size: float | None = None,
    *,
    label: str = 'Renko',
    width: float = 1.0,
    alpha: float | None = None,
    color: str | None = None,
    colorup: str | None = None,
    colordn: str | None = None,
    hollow: bool | None = None,
)

Renko primitive.

Plots Renko bricks computed from the chart prices — binds calc_renko as the chart prices transform via chart.get_view(transform=...), then renders through Candlesticks with touching, full-width bodies (bricks have no wicks).

Must be the first primitive to touch the chart view — plot it first; anything plotted before it fixes the untransformed view and the late transform raises. The chart windowing (max_bars etc.) operates in brick space. Incompatible with raw_dates.

Accepts the Candlesticks styling arguments (color schemes, candle.* settings, label) except use_prev_close, which is pinned intrabar: brick direction is close vs open by construction.

Arguments:

  • brick_size (float): Brick height in price units. Defaults to the mean true range of the data.

PointFigure

PointFigure(
    box_size: float | None = None,
    reversal: int = 3,
    *,
    width: float = 0.8,
    alpha: float | None = None,
    colorup: str | None = None,
    colordn: str | None = None,
    label: str = 'PnF',
)

Point & Figure primitive.

Plots Point & Figure columns computed from the chart prices — binds calc_pnf as the chart prices transform via chart.get_view(transform=...), then draws X's (rising columns) and O's (falling columns) on the box grid.

Must be the first primitive to touch the chart view — plot it first; anything plotted before it fixes the untransformed view and the late transform raises. The chart windowing (max_bars etc.) operates in column space. Incompatible with raw_dates.

Arguments:

  • box_size (float): Box height in price units. Defaults to the mean true range of the data. Also sizes the glyph grid — when None, the render grid is inferred from the column levels.
  • reversal (int): Boxes of adverse movement required to reverse the column. Defaults to 3.
  • width (float): Glyph width as a fraction of column spacing. Defaults to 0.8.
  • alpha (float): Opacity of the glyphs.
  • colorup (str): X-column color. Defaults to the pnf.up setting, else green.
  • colordn (str): O-column color. Defaults to the pnf.down setting, else red.
  • label (str): legend label. Defaults to "PnF".

Volume

Volume(
    sma: int | None = None,
    *,
    width: float = 0.8,
    alpha: float | None = None,
    colorup: str | None = None,
    colordn: str | None = None,
    colorma: str | None = None,
    edgeup: str | None = None,
    edgedn: str | None = None,
    use_prev_close: bool | None = None,
)

Volume primitive.

Plots volume bars colored by bar direction — close ≥ open, matching the candlesticks, or close vs previous close with use_prev_close. When the current pane already has content, volume rides a twinx overlay squashed at the bottom so it does not affect the price axis; an empty current pane (volume-only chart, or right after Pane) is owned outright — full height, visible scale. An optional SMA of volume can be overlaid.

Arguments:

  • sma (int): Period for the volume SMA overlay. Omit to skip the moving average line.
  • width (float): Width of each volume bar as a fraction of bar spacing. Defaults to 0.8.
  • alpha (float): Opacity of the bars and ma line, between 0.0 and 1.0. Defaults to the volume.alpha setting, else 0.5.
  • colorup (str): Color for up-bars. Defaults to the volume.up.color setting, else green (prop-cycle snapped).
  • colordn (str): Color for down-bars. Defaults to the volume.down.color setting, else red (prop-cycle snapped).
  • colorma (str): Color for the SMA overlay line. Defaults to the volume.ma.color setting, else gray (prop-cycle snapped).
  • edgeup (str): Outline color for up-bars. Defaults to the volume.edge.up.color setting; with neither side set the bars are unoutlined, and setting only one side leaves the other following its face color.
  • edgedn (str): Outline color for down-bars. Defaults to the volume.edge.down.color setting (see edgeup).
  • use_prev_close (bool): Color bars by close vs previous close (interbar) instead of close vs open (intrabar). Default (None) defers to the volume.use_prev_close setting, else False. Mirrors the flag of the same name on Candlesticks.

LinePlot

LinePlot(
    indicator=None,
    *,
    label: str | None = None,
    legend: bool = True,
    pane: PaneTarget | None = None,
    style: str | None = None,
    marker: str | None = None,
    width: float | None = None,
    color: str | None = None,
    alpha: float | None = None,
    overbought: float | None = None,
    oversold: float | None = None,
)

Line Plot Primitive

Plot any indicator or expression as a line plot. Use @ to bind.

Arguments:

  • indicator: indicator, expression, or already-computed series data (full-length prices-aligned; pandas date-indexed data aligns by date). @ binds indicators/expressions only — pass data via the constructor.
  • label (str): legend label override. When None, derived from the indicator (the series name for data) — also the styling key for color settings.
  • style (str): line style like 'solid', 'dashed', 'dotted', 'dashdot', 'marker'
  • marker (str): marker character like '.' or 'o'
  • width (float): line width override
  • color (str): color name or value
  • alpha (float): opacity value between 0.0 and 1.0
  • legend (bool): include in the legend. Defaults to True — the label still names the plot for styling either way.
  • pane (str): pane to draw on — "main" or "twinx". Default the current pane. Selection only, never sticky — pane creation goes through the Pane primitive.
  • overbought (float): level above which to shade a fill-between band
  • oversold (float): level below which to shade a fill-between band

Examples:

LinePlot(SMA(50), style="dashdot", color="red")
LinePlot(RSI(14), overbought=70, oversold=30)
SMA(50) @ LinePlot(style="dashdot", color="red")

AreaPlot

AreaPlot(
    indicator=None,
    *,
    color: str | None = None,
    alpha: float | None = None,
    label: str | None = None,
    legend: bool = True,
    pane: PaneTarget | None = None,
)

Area Plot Primitive

Plot any indicator or expression as an area plot. Use @ to bind.

Arguments:

  • indicator: indicator, expression, or already-computed series data (full-length prices-aligned; pandas date-indexed data aligns by date). @ binds indicators/expressions only — pass data via the constructor.
  • color (str): color name or value
  • alpha (float): opacity value between 0.0 and 1.0
  • legend (bool): include in the legend. Defaults to True — the label still names the plot for styling either way.
  • label (str): plot label

Examples:

AreaPlot(SMA(50), color="red", alpha=0.5)
SMA(50) @ AreaPlot(color="red", alpha=0.5)

BarPlot

BarPlot(
    indicator=None,
    *,
    color: str | None = None,
    alpha: float | None = None,
    width: float | None = None,
    label: str | None = None,
    legend: bool = True,
    pane: PaneTarget | None = None,
)

Bar Plot Primitive

Plot any indicator or expression as a bar plot. Use @ to bind.

Arguments:

  • indicator: indicator, expression, or already-computed series data (full-length prices-aligned; pandas date-indexed data aligns by date). @ binds indicators/expressions only — pass data via the constructor.
  • color (str): color name or value
  • alpha (float): opacity value between 0.0 and 1.0
  • legend (bool): include in the legend. Defaults to True — the label still names the plot for styling either way.
  • width (float): bar width setting
  • label (str): plot label

Examples:

BarPlot(SMA(50), color="red", alpha=0.5)
SMA(50) @ BarPlot(color="red", alpha=0.5)

Bands

Bands(
    indicator=None,
    *,
    upper: str = 'upperband',
    middle: str = 'middleband',
    lower: str = 'lowerband',
    label: str | None = None,
    legend: bool = True,
    color: str | None = None,
    pane: PaneTarget | None = None,
)

Band renderer for upper/lower(/middle) multi-output results.

Renders the band columns as dotted upper/lower lines with a translucent fill between, and an optional dashed middle line — the rendering behind auto-plotted BBANDS/KELTNER/DONCHIAN.

Arguments:

  • indicator: indicator, expression, or already-computed frame with the band columns.
  • upper (str): name of the upper-band column. Defaults to "upperband".
  • middle (str): name of the middle-band column, drawn when present. Defaults to "middleband".
  • lower (str): name of the lower-band column. Defaults to "lowerband".
  • label (str): legend label override; derived from the indicator when None.
  • legend (bool): include in the legend. Defaults to True.
  • color (str): explicit band color; defaults to the bands.color setting, else the next line color.

Examples:

Bands(BBANDS(20))
chart.plot(KELTNER(20) @ Bands())

Markers

Markers(
    indicator=None,
    *,
    label: str | None = None,
    color=None,
    marker: str = '.',
    alpha: float = 0.6,
)

Markers primitive.

Plots scatter markers on the main pane at the close price whenever a condition changes. Bind a condition indicator via @ or as the first positional argument. Compose the condition externally before binding.

Arguments:

  • indicator: indicator or expression returning a boolean/numeric signal. Markers appear at transition points (off→on, on→off). Can also be bound via @.
  • label (str): Legend label. Omit to skip the legend entry.
  • color (str or list of str): Marker color. Pass a two-element list [color_off, color_on] to use different colors for signal transitions. Defaults to the matplotlib default color cycle.
  • marker (str): Matplotlib marker symbol. Defaults to ".".
  • alpha (float): Opacity of the markers, between 0.0 and 1.0. Defaults to 0.6.

Examples:

Markers(MACD().as_expr("macdhist") > 0, color=["red", "green"])

Stripes

Stripes(indicator=None, *, label: str | None = None, color=None, alpha: float = 0.2)

Stripes primitive.

Shades vertical bands across all chart panes during periods when a condition is active. Bind a condition indicator via @ or as the first positional argument.

Arguments:

  • indicator: indicator or expression returning a boolean/numeric signal. Positive values shade the band; zero or negative do not. Can also be bound via @.
  • label (str): Legend label. Omit to skip the legend entry.
  • color (str): Fill color for the shaded regions.
  • alpha (float): Opacity of the shaded regions, between 0.0 and 1.0. Defaults to 0.2.

Examples:

Stripes(MACD().as_expr("macdhist") > 0, color="green", alpha=0.15)

Swings

Swings(indicator=None, span=1, *, color: str | None = None)

Swings primitive.

Plots local peak (high) and valley (low) points as scatter markers on the chart. A point is considered a local peak or valley if it is the highest high (or lowest low) within a window of 2 * span + 1 bars centered on that bar.

Two explicit modes, decided by the bound indicator:

  • OHLC mode — no indicator: peaks on the high column and valleys on the low column of the prices DataFrame.
  • Series mode — an indicator is bound (Swings(SMA(50)) or via @): peaks and valleys both on the indicator's series. The indicator must yield a single series — compose a single-output expression to target one column of a multi-output result.

Arguments:

  • indicator: single-output indicator or expression to find peaks on. None (default) selects OHLC mode.
  • span (int): Minimum number of bars required on each side of a local extremum for it to qualify as a peak or valley. Defaults to 1.
  • color (str): Marker color. Defaults to the current text.color matplotlib parameter.

ZigZag

ZigZag(threshold=5.0, *, color: str | None = None)

ZigZag primitive.

Plots a line connecting successive swing highs and lows, filtering out moves smaller than a percentage threshold. Rendered on the same scale as the price series.

Arguments:

  • threshold (float): Minimum percentage reversal required to register a new pivot. Defaults to 5.0.
  • color (str): Line color. Defaults to the next cycled line color.

TrendLines

TrendLines(
    span: int = DEFAULT_SPAN,
    *,
    max_gap: float = DEFAULT_MAX_GAP,
    max_bars: int = DEFAULT_MAX_BARS,
    max_legs: int = DEFAULT_MAX_LEGS,
    colors: tuple[str, str] = ('green', 'red'),
)

Walkback trendlines: a support and a resistance ladder per chart.

EXPERIMENTAL: heuristics, parameters, and output are likely to change; developed in playground/prototypes/trend-lines-proto.ipynb.

Thin drawing wrapper over trend_lines — run that function on raw high/low arrays for debugging. Draws the ladder: the winning leg and the runner-ups newer than it extend to now; older legs stop at their arrival point. Touch points are marked.

Arguments:

  • span (int): swing filter width — only swings (extrema within +/- span bars, with span bars on each side) qualify as touch points. span=0 degrades to the raw walk: every bar is a touch point, anchored at the last bar.
  • max_gap (float): fold-gate horizon knob, in average moves (avg_move over the surveyed range). A fold bridging structure further away from the tail is rejected and the walk stops at the regime boundary. 0 disables the gate.
  • max_bars (int): time safety net for the walk.
  • max_legs (int): leg budget — stop once the stack holds this many legs (peak depth runs ~9-12 empirically, 17 max). 0 disables.
  • colors (tuple[str, str]): (support, resistance) line colors.

Pane

Pane(
    position: PanePosition = 'below',
    *,
    height_ratio: float | None = None,
    yticks: tuple | None = None,
)

Pane Primitive

Create a new pane inline within a plot() call. Mirrors the chart.pane() method.

Creation is sticky: the new pane becomes current and the primitives that follow land on it. Pane is the only pane creator — to draw a single primitive on an existing pane use the renderers' pane= parameter instead (e.g. LinePlot(x, pane="main")).

Arguments:

  • position (str): "below" (default) or "above" — where the new pane is inserted in the vertical stack
  • height_ratio (float): relative height of the new pane
  • yticks (tuple): y-axis tick values (also draws heavy grid lines)

Examples:

chart.plot(Pane("below", yticks=(30, 50, 70)), LinePlot(RSI(14)))

VLine

VLine(date, *, color=None, linestyle=None)

Vertical line across all panes at a given date.

Arguments:

  • date: date or date string for the vertical line position
  • color: line color (default: matplotlib grid.color)
  • linestyle: line style (default: matplotlib grid.linestyle)

Examples:

chart.plot(Candlesticks(), VLine("2024-01-15"))
chart.vline("2024-01-15", color="red")

HLine

HLine(value, *, color=None, linestyle=None)

Horizontal line on the current pane at a given value.

Arguments:

  • value: y-axis value for the horizontal line position
  • color: line color (default: matplotlib grid.color)
  • linestyle: line style (default: matplotlib grid.linestyle)

Examples:

chart.plot(Pane("below"), RSI(14), HLine(70, color="red"), HLine(30, color="green"))
chart.hline(70, color="red")

Primitive

Primitive()

Abstract base class for chart primitives.

Primitives act directly on the chart without going through the indicator calculation pipeline. They implement apply_to_chart which is invoked before any indicator calculation takes place.

Binding primitives take an indicator or expression as first argument; the @ operator is an equivalent alternative:

LinePlot(SMA(50), style="dashed", color="blue")    # constructor form
SMA(50) @ LinePlot(style="dashed", color="blue")   # operator form

BindingPrimitive

BindingPrimitive(indicator=None)

Base class for primitives that bind to an indicator or expression via @.

Provides the indicator attribute, a positional indicator argument, and the @ binding operator.