Interface IndicatorDescriptor

interface IndicatorDescriptor {
    alerts?: readonly IndicatorAlertSpec[];
    category?: string;
    fills?: readonly IndicatorFillSpec[];
    id: string;
    inputs: readonly IndicatorInput[];
    name: string;
    placement: "onchart" | "pane";
    plots: readonly IndicatorPlot[];
    attach(ctx: IndicatorAttachContext): void | () => void;
    background(
        ctx: {
            bars: readonly Bar[];
            settings: Readonly<IndicatorSettings>;
            values: IndicatorValues;
        },
    ): readonly (null | string)[];
    barColors(
        ctx: {
            bars: readonly Bar[];
            settings: Readonly<IndicatorSettings>;
            values: IndicatorValues;
        },
    ): readonly (null | string)[];
    calc(
        bars: readonly Bar[],
        settings: Readonly<IndicatorSettings>,
        store: IndicatorStore,
        ctx?: IndicatorCalcContext,
    ): IndicatorValues;
    calcTail(
        bars: readonly Bar[],
        settings: Readonly<IndicatorSettings>,
        fromIndex: number,
        previous: IndicatorValues,
        store: IndicatorStore,
        ctx?: IndicatorCalcContext,
    ): null | IndicatorValues;
    draws(
        ctx: {
            bars: readonly Bar[];
            settings: Readonly<IndicatorSettings>;
            values: IndicatorValues;
        },
    ): readonly IndicatorDrawing[];
    levels(ctx: IndicatorLevelContext): readonly IndicatorLevel[];
    markers(
        ctx: {
            bars: readonly Bar[];
            settings: Readonly<IndicatorSettings>;
            values: IndicatorValues;
        },
    ): readonly SeriesMarker[];
    range(
        settings: Readonly<IndicatorSettings>,
    ): null | { max: number; min: number };
    table(
        ctx: {
            bars: readonly Bar[];
            settings: Readonly<IndicatorSettings>;
            values: IndicatorValues;
        },
    ): | null
    | {
        options?: Partial<ChartTableOptions>;
        rows: readonly (readonly TableCell[])[];
    };
}

Properties

alerts?: readonly IndicatorAlertSpec[]

Optional conditions the runtime watches on the descriptor's behalf, emitted as 'indicator:alert' on the chart's event bus with an IndicatorAlertPayload. See IndicatorAlertSpec.

category?: string

Grouping for a picker UI ('Trend', 'Momentum', 'Volume', 'Volatility').

fills?: readonly IndicatorFillSpec[]

Shaded bands between pairs of plots — the Ichimoku cloud, a Bollinger channel. A pair of lines is not the same picture as a filled region: the fill is what makes "price is above the cloud" readable at a glance, and which side leads is itself the signal, hence the two colours.

id: string

Registry key, e.g. 'macd'.

inputs: readonly IndicatorInput[]
name: string

Display name, e.g. 'MACD'.

placement: "onchart" | "pane"

'onchart' overlays the price pane; 'pane' gets its own pane.

plots: readonly IndicatorPlot[]

Methods

  • Optional per-instance lifecycle, for indicators whose data is not derived from the chart's bars (open interest, CVD, an external feed). Called once when the instance is created; return a teardown function.

    Fetch into ctx.store, then call ctx.requestRecompute()calc runs again and reads what you stored.

    Parameters

    Returns void | () => void

  • Optional per-bar shading behind everything else in the indicator's pane: a full-height column per bar, null where nothing should be shaded.

    A regime study answers "which state is the market in right now", and that is a property of the whole bar, not a price. Drawn as a plot it would need a value to sit at and would fight the pane's autoscale; as a column behind the candles it reads at a glance and costs the scale nothing.

    Runs after every calc. Return [] to clear the layer.

    Parameters

    Returns readonly (null | string)[]

  • Optional recolouring of the main price candles, one entry per bar, null to leave that bar with its own colour.

    Distinct from a plot's colorBy, which paints the indicator's own series: a trend filter, a volatility regime or a higher-timeframe bias is a statement about the price bars themselves, and drawing it as a second series beside them says something weaker.

    Only one indicator's colours can be on the candles at a time; the most recent publisher wins, and publishers run in addIndicator order, so the winner is the same one from frame to frame. Removing it, or hiding it, restores the bars' own colours.

    Parameters

    Returns readonly (null | string)[]

  • Optional bar-anchored signal markers — a named "Buy"/"Sell" plate, an arrow at a crossover. Runs after every calc, so it reads the values it just produced rather than recomputing anything.

    A plot cannot express this: a plot is a column of prices drawn as a line or histogram, whereas a signal is a discrete event with a label. Returning [] (when a showLabels-style input is off, say) clears the layer.

    Parameters

    Returns readonly SeriesMarker[]

  • Optional fixed price range for the indicator's own pane (RSI 0..100). Applied only when the indicator creates its pane — two indicators sharing a pane would otherwise fight over it.

    Parameters

    Returns null | { max: number; min: number }

  • Optional summary grid pinned to a corner of the pane.

    Some studies are not a value per bar at all: a seasonality heatmap is a matrix of monthly returns, a scoreboard is a handful of statistics. Those have no place in calc, whose contract is one column per plot aligned to the bars, so they come back through here instead. Runs after every calc.

    Return null (or a zero-row grid) to draw nothing, which is how a showTable-style input should switch it off.

    Parameters

    Returns
        | null
        | {
            options?: Partial<ChartTableOptions>;
            rows: readonly (readonly TableCell[])[];
        }