feature

Bull bar

Marks every bar that closes above its open. Payload carries bar range for later studies.

What it defines

A Collectable event bull_bar whenever close > open.

Key decisions

Piece

Why it matters

kind: "flow"

Enables emit / Collect (not an indicator).

events.declare + payload schema

Contract for Collect and studies.

Required label on ctx.emit

Events without labels are dropped at runtime.

Early return on bear bars

Keep onBar cheap when the setup is false.

Full script

meta({
  name: "Bull bar",
  kind: "flow",
  slug: "bull-bar",
  shortName: "BullBar",
});

events.declare({
  id: "bull_bar",
  intent: "Mark closes above open",
  payload: {
    range: { type: "number", description: "High minus low" },
    close: { type: "number", description: "Close price" },
  },
  paint: "pin",
});

outputs.declare({
  id: "close_line",
  kind: "line",
  name: "Close",
  color: "#64b5f6",
});

export function onBar(ctx) {
  ctx.plot("close_line", ctx.close);

  if (ctx.close <= ctx.open) return;

  const range = ctx.high - ctx.low;
  ctx.emit(
    "bull_bar",
    { range, close: ctx.close },
    {
      label: `Bull · R=${range.toFixed(2)}`,
      subtitle: `close ${ctx.close.toFixed(2)}`,
      price: ctx.close,
      timeStart: ctx.time,
    }
  );
}

Next

  1. Examples

  2. EMA cross

  3. Emit and labels