Documentation Index
Fetch the complete documentation index at: https://docs.polynode.dev/llms.txt
Use this file to discover all available pages before exploring further.
API Reference
createChart
import { createChart } from 'polynode-charts'
const chart = createChart(container, options?)
| Parameter | Type | Description |
|---|
container | HTMLElement | string | DOM element or CSS selector |
options | ChartOptions | Optional configuration |
ChartOptions
interface ChartOptions {
width?: number // fixed width (px)
height?: number // fixed height (px)
autoSize?: boolean // auto-resize to container (default: true)
layout?: LayoutOptions
grid?: GridOptions
crosshair?: CrosshairOptions
timeScale?: TimeScaleOptions
rightPriceScale?: PriceScaleOptions
}
LayoutOptions
interface LayoutOptions {
background?: string // default: '#080d16'
textColor?: string // default: '#556'
fontFamily?: string // default: '"SF Mono", "Fira Code", monospace'
fontSize?: number // default: 10
}
GridOptions
interface GridOptions {
vertLines?: { color?: string; visible?: boolean }
horzLines?: { color?: string; visible?: boolean }
}
PriceScaleOptions
interface PriceScaleOptions {
mode?: 'normal' | 'probability' // 'probability' clamps axis to 0-100%
autoScale?: boolean
scaleMargins?: { top?: number; bottom?: number }
}
Chart
Series Methods
chart.addCandleSeries(opts?: CandleSeriesOptions): CandleSeries
chart.addLineSeries(opts?: LineSeriesOptions): LineSeries
chart.addAreaSeries(opts?: AreaSeriesOptions): AreaSeries
chart.addVolumeSeries(opts?: VolumeSeriesOptions): VolumeSeries
chart.removeSeries(series): void
Scale Access
chart.timeScale(): TimeScale
Events
// Subscribe to crosshair movement — returns unsubscribe function
const unsub = chart.subscribeCrosshairMove((params) => {
console.log(params.time, params.point)
})
unsub() // stop listening
// Subscribe to chart clicks
const unsub2 = chart.subscribeClick((params) => {
console.log('Clicked at time:', params.time)
})
CrosshairMoveParams:
interface CrosshairMoveParams {
time: number | null
point: { x: number; y: number } | null
seriesData: Map<string, OhlcData | LineData>
}
ClickParams:
interface ClickParams {
time: number | null
point: { x: number; y: number }
}
Utility
chart.getContainer(): HTMLElement // returns the chart's parent DOM element
Lifecycle
chart.resize(width, height): void // manual resize
chart.remove(): void // cleanup everything
Series
All series share these common methods:
series.setData(data[]): void // replace all data
series.update(item): void // append or update last point
series.setMaxLength(n): void // cap buffer size (drops oldest)
CandleSeries
const series = chart.addCandleSeries({
upColor: '#22c55e',
downColor: '#ef4444',
wickUpColor: '#22c55e', // optional, defaults to upColor
wickDownColor: '#ef4444', // optional, defaults to downColor
borderVisible: true,
})
Data shape:
interface OhlcData {
time: number // epoch milliseconds
open: number
high: number
low: number
close: number
volume?: number
}
LineSeries
const series = chart.addLineSeries({
color: '#f7931a',
lineWidth: 2,
smooth: true, // bezier curve interpolation
showDot: true, // pulsing dot at last point
dotColor: '#f7931a',
})
Data shape:
interface LineData {
time: number // epoch milliseconds
value: number
}
Live mode:
series.setLive(true) // phantom point + smooth lerp
series.isLive() // check live state
Price line overlay:
series.setPriceLine(72822.50, {
color: '#3b82f6',
dash: [6, 4],
label: 'PRICE TO BEAT',
labelColor: '#fff',
})
series.clearPriceLine()
series.getPriceLine() // returns PriceLineConfig | null
The price line renders as a dashed horizontal line across the chart with a label on the left and a price badge on the right axis. The Y-axis auto-expands to keep the price line visible.
AreaSeries
Extends LineSeries with a gradient fill beneath the line.
const series = chart.addAreaSeries({
color: '#6ea8fe', // line color
topColor: '#6ea8fe33', // gradient top
bottomColor: '#6ea8fe00', // gradient bottom (transparent)
lineWidth: 2,
smooth: true,
})
Uses the same LineData shape as LineSeries.
VolumeSeries
Automatically creates a separate pane at 22% of chart height.
const series = chart.addVolumeSeries({
upColor: 'rgba(34, 197, 94, 0.4)',
downColor: 'rgba(239, 68, 68, 0.4)',
opacity: 0.4,
})
Data shape:
interface VolumeData {
time: number
value: number
color?: string // override per-bar color
}
TimeScale
const ts = chart.timeScale()
| Method | Description |
|---|
goLive() | Enable live mode. Auto-scrolls to newest data. Snaps back after 4s idle. |
isLive() | Returns true if in live mode |
setVisibleRange(start, end) | Set visible time range (epoch ms) |
animateToRange(start, end) | Animated zoom to range |
zoomAt(factor, mouseXFrac) | Zoom around a point (scroll wheel) |
getVisibleStart() | Left edge time (epoch ms) |
getVisibleEnd() | Right edge time (epoch ms) |
getVisibleWindow() | Duration of visible range (ms) |
Live mode behavior: When live, the chart auto-scrolls to show the latest data. If the user pans or zooms away, the chart remembers and snaps back to live after 4 seconds of idle. This gives users freedom to explore history while keeping the default view current.
Orderbook
import { createOrderbook } from 'polynode-charts'
const ob = createOrderbook('#orderbook', {
colorBid: '#22c55e',
colorAsk: '#ef4444',
depthFillOpacity: 0.08,
labelCount: 8,
})
ob.update({
bids: [{ price: 0.54, size: 1200 }, { price: 0.53, size: 800 }],
asks: [{ price: 0.55, size: 900 }, { price: 0.56, size: 1500 }],
})
OrderbookOptions
interface OrderbookOptions {
colorBid?: string // default: '#22c55e'
colorAsk?: string // default: '#ef4444'
depthFillOpacity?: number // default: 0.08
labelCount?: number // price labels on axis
background?: string
textColor?: string
}
BookData
interface BookData {
bids: PriceLevel[]
asks: PriceLevel[]
}
interface PriceLevel {
price: number
size: number
}
| Method | Description |
|---|
ob.update(data) | Replace book data and re-render |
ob.destroy() | Remove DOM and stop rendering |
One-liner to add Polymarket short-form price-to-beat overlays to any live chart. Adds interval buttons, auto-discovers markets, draws a dashed price-to-beat line, and shows live odds with a countdown timer.
import { createChart, createShortFormOverlay } from 'polynode-charts'
const chart = createChart('#btc', { layout: { background: '#0c1220' } })
const series = chart.addLineSeries({ color: '#f7931a', showDot: true })
series.setLive(true)
chart.timeScale().goLive()
// One line: buttons + discovery + price line + odds + countdown
const overlay = createShortFormOverlay(chart, series, { coin: 'btc' })
interface ShortFormOverlayOptions {
coin: ShortFormCoin // 'btc' | 'eth' | 'sol' | 'xrp' | 'doge' | 'hype'
intervals?: ShortFormInterval[] // default: ['5m', '15m', '1h']
defaultInterval?: ShortFormInterval // if set, auto-starts on creation
onRotation?: (event: RotationEvent) => void // callback on each poll/rotation
}
| Method | Description |
|---|
overlay.setInterval('15m') | Switch to a different interval |
overlay.stop() | Stop polling, remove price line, clear display |
overlay.destroy() | Full cleanup: stop + remove DOM |
overlay.getActiveInterval() | Returns current interval or null |
What it renders
- Interval buttons (5m, 15m, 1h) — click to toggle on/off
- Price-to-beat line — horizontal dashed blue line on the chart
- Odds display — “24% up · 77% down · 1m35s” with live countdown
- Auto-rotation — discovers the next market window when the current one expires
PolynodeProvider — MarketInfo
The outcome field tells you which side of a binary market this token represents.
interface MarketInfo {
token_id: string
question: string // the market question (e.g. "US x Iran ceasefire by April 7?")
slug: string
image: string
last_price: number
volume_24h: number
outcomes: string[] // e.g. ['Yes', 'No']
outcome: string // which outcome THIS token is ('Yes' or 'No')
condition_id?: string
neg_risk?: boolean // true for multi-outcome events (elections, championships)
}
The neg_risk field indicates a multi-outcome event on Polymarket. When provider.event() searches for multi-outcome markets, it prioritizes neg_risk: true markets to find genuine events (elections, World Cup, NBA Finals) rather than binary matches.