### App.tsx (Manual Setup) Source: https://percept.one/docs/getting-started/installation For production apps where bundle size is critical, use the main entrypoint and manually import CSS and register indicators. This example shows a basic chart setup with sample data. ```tsx import '@titancharts/react/style.css'; import { TitanProvider, TitanChart, type IOHLCV, type ITitanChartAPI, } from '@titancharts/react'; export default function App() { const data: IOHLCV[] = [ { time: 1704067200, open: 42000, high: 42500, low: 41800, close: 42300, volume: 1000 }, { time: 1704070800, open: 42300, high: 42800, low: 42100, close: 42600, volume: 1200 }, // ... more candles ]; const handleReady = (api: ITitanChartAPI) => { console.log('Chart ready:', api); api.on('crosshair:move', (e) => { console.log('Price:', e.price); }); }; return (
); } ``` -------------------------------- ### App.tsx (using /auto) Source: https://percept.one/docs/getting-started/installation Use the /auto entrypoint for the fastest setup, which auto-injects CSS and registers built-in indicators. This is ideal for quick starts and prototypes. ```tsx import { TitanProvider, TitanChart } from '@titancharts/react/auto'; import { DataFeed } from '@titancharts/data'; const dataFeed = new DataFeed({ licenseKey: "your-license-key", }); export default function App() { return (
); } ``` -------------------------------- ### Full Multi-spline Chart Setup Example Source: https://percept.one/docs/api-reference/chart-methods Demonstrates a complete end-to-end setup for a custom multi-spline chart using the public API. Includes series color and label configuration, live merge, data fetching, initial data seeding, mode switching, and constraint application. ```typescript import { multiSplineMergeLiveDataPoint } from '@titancharts/react'; // A custom N-series source through the public API alone: chart.setSeriesColors(series.map((s) => s.color)); chart.setSeriesLabels(() => series.map((s) => ({ name: s.name, color: s.color }))); chart.setLiveMerge(multiSplineMergeLiveDataPoint); // optional — installed by default chart.setFetchRawMainData(async ({ from, to, interval, signal }) => feed.fetchMatrix(series.map((s) => s.id), from, to, interval, signal), ); chart.setRawData(initialMatrix); // rows: [time_ms, v1, …, vN] chart.updateAdapterMode('multi-spline'); chart.applyAdapterConstraints(); // hide single-asset chrome (run last) feed.onTick((row) => chart.updateRawData(row)); // tick: [time_seconds, v1, …, vN] // A custom hover tooltip: the per-series values arrive on the event — no need to // interpolate your own data. chart.on('crosshair:move', ({ time, values }) => { if (values) showTooltip(time, values); // values[i] aligns with series[i] }); ``` -------------------------------- ### Zero-Config Setup with Auto Entrypoint Source: https://percept.one/docs/frameworks/react The 'Auto' entrypoint provides a batteries-included experience for quick starts and prototypes, automatically injecting CSS and pre-registering all built-in indicators. ```tsx import { TitanChart } from '@titancharts/react/auto'; // No CSS import needed - styles are auto-injected at runtime! // All built-in indicators are already registered ``` -------------------------------- ### DialogProvider Setup Source: https://percept.one/docs/features/dialogs/hooks-reference Wrap your application with DialogProvider to enable dialog customization. This example shows basic setup with a Dialog component. ```tsx import { DialogProvider } from '@titancharts/react'; function App() { return ( ); } ``` -------------------------------- ### Direct Authentication Setup Source: https://percept.one/docs/datafeed-api/titancharts-datafeed/authentication Initialize the DataFeed with your enterprise license key for direct authentication. This is the simplest setup. ```typescript const dataFeed = new DataFeed({ licenseKey: 'your-enterprise-license-key', }); ``` -------------------------------- ### Event Handling Examples Source: https://percept.one/docs/api-reference/events Code examples demonstrating how to subscribe to and handle various trading events. ```typescript chart.on('trading:order_create', async ({ side, type, price, size, attachedTp, attachedSl }) => { console.log(`New ${side} ${type} order at ${price}`); // Send to exchange API await exchange.placeOrder({ side, type, price, size, tp: attachedTp, sl: attachedSl }); }); chart.on('trading:order_modify', async ({ orderId, newPrice, previousPrice }) => { console.log(`Order ${orderId} moved from ${previousPrice} to ${newPrice}`); await exchange.modifyOrder(orderId, { price: newPrice }); }); chart.on('trading:position_close', async ({ positionId }) => { await exchange.closePosition(positionId); }); chart.on('trading:bracket_create', async ({ parentId, bracketRole, price }) => { console.log(`New ${bracketRole.toUpperCase()} bracket on ${parentId} at ${price}`); await exchange.createBracket(parentId, bracketRole, price); }); chart.on('trading:drag_move', ({ dragType, price }) => { if (dragType === 'bracket') updateRiskPanel(price); }); ``` -------------------------------- ### Install Optional Dependency for Screenshots Source: https://percept.one/docs/getting-started/installation Install the 'html2canvas' package if you need to use the screenshot feature. ```bash npm install html2canvas ``` -------------------------------- ### Virtual Input Example with get/set Source: https://percept.one/docs/features/indicators/tier2-advanced Illustrates using 'get' and 'set' for a virtual input 'barHeightMultiplier'. The 'get' function reads from a per-interval dictionary, and 'set' updates this dictionary, preserving other settings. ```typescript createTier2Control({ inputs: [{ key: 'barHeightMultiplier', label: 'Ticks per bar', type: 'number', default: 15, min: 1, max: 500, step: 1, affectsData: true, get: (settings, context) => { const dict = settings.multipliersByInterval as Record ?? {}; return dict[context.interval] ?? 15; }, set: (value, settings, context) => { return { ...settings, multipliersByInterval: { ...(settings.multipliersByInterval as Record), [context.interval]: value as number, }, }; }, }], }); ``` -------------------------------- ### Production Chart with Real-time Data Source: https://percept.one/docs/features/data-loading This example demonstrates a complete production setup for a chart component. It includes fetching historical data via an API and handling real-time price updates through a WebSocket connection to dynamically update the chart. ```tsx import { useRef, useCallback, useEffect } from 'react'; import { TitanChart, TitanProvider, intervalToMs, type ITitanChartAPI, type IOHLCV, } from '@titancharts/react'; interface WebSocketTick { price: number; volume: number; timestamp: number; } function ProductionChart({ symbol }: { symbol: string }) { const chartRef = useRef(null); const wsRef = useRef(null); // Fetch historical data const fetchData = useCallback(async ({ from, to, interval }) => { const response = await fetch( `/api/candles?symbol=${symbol}&interval=${interval}&from=${from}&to=${to}` ); return response.json(); }, [symbol]); // Handle real-time updates useEffect(() => { const ws = new WebSocket(`wss://stream.example.com/${symbol}`); wsRef.current = ws; ws.onmessage = (event) => { const tick: WebSocketTick = JSON.parse(event.data); if (!chartRef.current) return; const data = chartRef.current.getData(); if (data.length === 0) return; const lastCandle = data[data.length - 1]; const intervalMs = intervalToMs(chartRef.current.getInterval()); const currentCandleStart = Math.floor(tick.timestamp / intervalMs) * intervalMs; if (tick.timestamp >= lastCandle.time * 1000 + intervalMs) { // New candle started chartRef.current.appendData([{ time: currentCandleStart / 1000, open: tick.price, high: tick.price, low: tick.price, close: tick.price, volume: tick.volume, }]); } else { // Update current candle chartRef.current.updateLast({ ...lastCandle, high: Math.max(lastCandle.high, tick.price), low: Math.min(lastCandle.low, tick.price), close: tick.price, volume: (lastCandle.volume || 0) + tick.volume, }); } }; return () => ws.close(); }, [symbol]); return ( ); } ``` -------------------------------- ### Volume Profile Example Data Source: https://percept.one/docs/features/indicators/volume-profile-guide An example of how IProfileCandle data is structured, showing a timestamp followed by multiple price buckets, each represented as a flat tuple of [priceBottom, priceTop, buyVolume, sellVolume]. ```typescript [1700000000000, [100, 100.5, 50, 30], [100.5, 101, 80, 20], [101, 101.5, 10, 60]] ``` -------------------------------- ### Advanced TitanChart Setup with TitanProvider for Multi-Chart Apps Source: https://percept.one/docs/frameworks/react For multi-chart applications, use `TitanProvider` to share license keys and configurations across multiple charts. This example also demonstrates event handling for 'crosshair:move' and 'interval:change', and custom data fetching. ```tsx import { useCallback, useRef } from 'react'; import { TitanProvider, TitanChart, type ITitanChartAPI, type IOHLCV, type Market, } from '@titancharts/react'; function App({ data, market }: { data: IOHLCV[]; market: Market }) { const chartRef = useRef(null); const handleReady = useCallback((api: ITitanChartAPI) => { chartRef.current = api; api.on('crosshair:move', (e) => { if (e.price) console.log('Price:', e.price); }); api.on('interval:change', ({ interval, previous }) => { console.log('Interval changed:', { interval, previous }); }); }, []); return (
{ // Handles initial load, lazy loading, and interval changes // If data prop is omitted, this is called on mount for initial data const data = await fetchHistorical(market.symbol, interval, from, to); return data; }} />
); } ``` -------------------------------- ### Basic Polymarket Chart Setup Source: https://percept.one/docs/features/polymarket This component demonstrates the minimal setup for Polymarket support, including a chart and symbol picker. It registers the PolymarketPlatform and configures localization for probability formatting. ```tsx import { useState, useMemo } from 'react'; import { TitanProvider, TitanChart, PolymarketPlatform, formatProbabilityPrice, type Market, type ISymbolMetadata, } from '@titancharts/react/auto'; import { DataFeed, DEFAULT_MARKET } from '@titancharts/data'; const dataFeed = new DataFeed({ licenseKey: 'YOUR_LICENSE_KEY' }); export function Chart() { const [market, setMarket] = useState(DEFAULT_MARKET); const [preloadedMeta, setPreloadedMeta] = useState(); // Switch Y-axis formatter for prediction markets const isPolymarket = market.exchange === 'polymarket'; const localization = useMemo( () => (isPolymarket ? { priceFormatter: formatProbabilityPrice } : undefined), [isPolymarket] ); return (
{ setPreloadedMeta(meta); setMarket(m); }} />
); } ``` -------------------------------- ### Example Usage of resolveColorToken Source: https://percept.one/docs/api-reference/chart-methods Illustrates how to use `resolveColorToken()` to get actual hex colors for theme tokens like `$bullish`, and shows that valid hex codes are returned directly. Handles `undefined` input. ```typescript // Resolve a token to the current theme color const bullish = chart.resolveColorToken('$bullish'); // '#D97757' (Percept dark theme) // Hex colors pass through unchanged const red = chart.resolveColorToken('#ff0000'); // '#ff0000' // Undefined returns white const fallback = chart.resolveColorToken(undefined); // '#ffffff' ``` -------------------------------- ### Composability Example Source: https://percept.one/docs/features/indicators/calc-helpers Demonstrates how indicator calculation functions can be chained together for complex indicator logic. ```APIDOC ## Composability Example ### Description Because all helpers operate on `number[]`, you can chain them. ### Request Example ```ts import { calcEma, extractSeries } from '@titancharts/react'; calc: (data, settings, ctx) => { const series = extractSeries(data, ctx.getSource, 'close'); // Step 1: Compute RSI values (your own logic) const rsiValues = computeRsi(series, 14); // Step 2: Smooth RSI with an EMA const smoothedRsi = calcEma(rsiValues, 9); return data.map((candle, i) => [candle.time * 1000, smoothedRsi[i]]); }, ``` ``` -------------------------------- ### Example WebSocket Subscription Implementation Source: https://percept.one/docs/datafeed-api/interface-reference An example implementation of `subscribeLive` using WebSockets. It parses incoming JSON messages and formats the tick data for the `onTick` callback. Includes a basic unsubscribe function. ```typescript subscribeLive(params, onTick) { const { dataType, market, interval } = params; const ws = new WebSocket( `wss://stream.example.com/${market.exchange}/${market.symbol}/${interval}` ); ws.onmessage = (event) => { const tick = JSON.parse(event.data); onTick([tick.time, tick.price, tick.volume, tick.high, tick.low, tick.open]); }; // Return unsubscribe function return () => { ws.close(); }; } ``` -------------------------------- ### Create Tier 3 Control Example Source: https://percept.one/docs/api-reference/types Example demonstrating how to create a Tier 3 control using a data source that implements `ITier3DataSource`. Ensure the `dataSource` object conforms to the interface. ```typescript import type { ITier3DataSource } from '@titancharts/react'; const control = createTier3Control({ dataSource: myDataFeed, // DataFeed implements ITier3DataSource dataType: 'HEATMAP', // ... }); ``` -------------------------------- ### Rich Picker Item Example Source: https://percept.one/docs/features/dialogs/picker-dialogs An example demonstrating how to structure a rich item for a picker dialog, including title, subtitle, icon, category, metadata with color, and custom data. ```typescript const items: IPickerItem[] = [ { id: 'btc-usd', title: 'BTC/USD', subtitle: 'Bitcoin / US Dollar', icon: 'bitcoin', category: 'crypto', metadata: [ { key: 'price', value: '$45,230', color: '#26a69a' }, { key: 'change', value: '+2.5%', color: '#26a69a' }, ], data: { exchange: 'binance', pair: 'BTCUSDT' }, }, ]; ``` -------------------------------- ### useTPO Hook Example Source: https://percept.one/docs/features/indicators/tpo-guide Example demonstrating how to use the useTPO hook to interact with TPO periods within a React component. ```APIDOC ```tsx import { useTPO } from '@titancharts/react'; function TPOControls({ instanceId }: { instanceId: string }) { const { getPeriodState, expandPeriod, collapsePeriod, mergePeriod, restorePeriod, isReady, version, } = useTPO(); const handlePeriodAction = (periodStartMs: number) => { if (!isReady) return; const state = getPeriodState(instanceId, periodStartMs); if (state.isExpanded) { collapsePeriod(instanceId, periodStartMs); } else { expandPeriod(instanceId, periodStartMs); } }; return (
TPO version: {version} {/* Render period controls */}
); } ``` ``` -------------------------------- ### Legacy Live Data Streaming Example Source: https://percept.one/docs/api-reference/chart-methods This example demonstrates a legacy approach to live data streaming using manual updates for existing candles and appending new ones via WebSocket events. It requires explicit handling of 'tick' and 'newCandle' events. ```typescript websocket.on('tick', (tick) => { chart.updateLast({ time: tick.time, open: tick.open, high: tick.high, low: tick.low, close: tick.close, volume: tick.volume, }); }); websocket.on('newCandle', (candle) => { chart.appendData([candle]); }); ``` -------------------------------- ### Custom Navigation Bar Example Source: https://percept.one/docs/api-reference/chart-methods Example of implementing custom navigation controls using chart viewport methods. It includes buttons for zoom, pan, and conditionally showing a 'go to live' button based on scroll position. ```typescript // Step controls for a custom nav bar // Show a "back to live" affordance only when the user has scrolled away if (chart.isScrolledAwayFromLatest()) { showGoToLatestButton(); } ``` -------------------------------- ### Set Visible Range Example Source: https://percept.one/docs/api-reference/chart-methods Example demonstrating how to set the visible time range to a specific calendar day. It also shows how to pair `setVisibleRange` with `setClamping` to fill a clamp window with a clean default view. ```typescript // Snap to a calendar day const startOfDay = new Date('2024-06-01T00:00:00Z').getTime(); const endOfDay = startOfDay + 24 * 60 * 60 * 1000; chart.setVisibleRange(startOfDay, endOfDay); // Pair with setClamping to fill a clamp window with a clean default view chart.setClamping({ x: { before, after } }); chart.setVisibleRange(before, after); ``` -------------------------------- ### Usage Examples Source: https://percept.one/docs/api-reference/constants Examples demonstrating how to use the DataTypes constants in different parts of the TitanCharts library, such as Tier 2 Indicator Configuration, DataFeed Routing, and Live Subscription Source Identities. ```APIDOC ### Usage Examples #### Tier 2 Indicator Config ```ts import { createTier2Control, DataTypes } from '@titancharts/react'; export const OPEN_INTEREST_CONTROL = createTier2Control({ id: 'open-interest', name: 'Open Interest', dataType: DataTypes.OPEN_INTEREST, placement: 'offchart', overlayType: 'candle', // ... }); ``` #### DataFeed Routing ```ts import { DataTypes } from '@titancharts/react'; async fetchHistoricalData(params) { switch (params.dataType) { case DataTypes.OHLCV: return this.fetchOHLCV(params); case DataTypes.OPEN_INTEREST: return this.fetchOpenInterest(params); case DataTypes.FUNDING_RATE: return this.fetchFundingRate(params); case DataTypes.VOLUME_FOOTPRINT: case DataTypes.SESSION_VOLUME_PROFILE: return this.fetchVolumeProfile(params); case DataTypes.ORDERBOOK_HEATMAP: return this.fetchOrderbookHeatmap(params); default: return { data: [], noData: true }; } } ``` #### Live Subscription Source Identities ```ts import { DataTypes } from '@titancharts/react'; getSourceIdentities(settings) { return [{ type: DataTypes.OPEN_INTEREST, exchange: settings.exchange, symbol: settings.symbol, }]; } ``` ``` -------------------------------- ### formatLegendItems Example Implementation Source: https://percept.one/docs/features/indicators/tier1-schema An example implementation of formatLegendItems that formats a single value and displays a title based on settings. It handles NaN values by displaying a hyphen. ```javascript formatLegendItems: (values, settings, plots) => { const value = values[0]; const formatted = isNaN(value) ? '-' : value.toFixed(2); return [ { id: 'title', text: `SMA(${settings.length})`, color: '$text', isStatic: true }, { id: 'value', text: `: ${formatted}`, color: plots[0]?.color || '#2196F3' }, ]; } ``` -------------------------------- ### Example: Programmatically Move Floating Toolbar Source: https://percept.one/docs/api-reference/chart-methods Illustrates how to reposition the floating toolbar using `updateToolbarState`. ```typescript // Programmatically move the floating toolbar chart.updateToolbarState({ position: { x: 100, y: 200 } }); ``` -------------------------------- ### Example: Unpin Floating Toolbar Source: https://percept.one/docs/api-reference/chart-methods Demonstrates how to unpin the floating toolbar, allowing it to be freely moved. ```typescript // Unpin the floating toolbar chart.updateToolbarState({ pinned: false }); ``` -------------------------------- ### Get Chart State Source: https://percept.one/docs/api-reference/chart-methods Retrieves the complete serializable state of the chart. This state can be saved, for example, to local storage. ```typescript const state = chart.getState(); localStorage.setItem('chart-state', JSON.stringify(state)); ``` -------------------------------- ### Getting Visible Chart Data Source: https://percept.one/docs/api-reference/types Retrieve the portion of the dataset currently visible in the chart, along with its start and end indices. ```typescript getVisibleData(): { data: IOHLCV[]; from: number; to: number }; ``` -------------------------------- ### Configuring Picker Dialog with Item Actions Source: https://percept.one/docs/features/dialogs/picker-dialogs Example of setting up a picker dialog schema with item-specific actions like 'Add' and a stepper for increment/decrement. This demonstrates how to define actions for different item types and handle them via the `onItemAction` callback. ```tsx import { Dialog, PICKER_ACTION, type IPickerSchema, type IPickerItem } from '@titancharts/react'; const schema: IPickerSchema = { // ... data: { items: [ { id: 'sma', title: 'Simple Moving Average', actions: [ { id: PICKER_ACTION.ADD, icon: 'plus', label: 'Add' }, ], }, { id: 'ema-instance', title: 'EMA(20)', actionsLayout: 'stepper', actions: [ { id: PICKER_ACTION.DECREMENT, icon: 'minus', ariaLabel: 'Decrement' }, { id: PICKER_ACTION.INCREMENT, icon: 'plus', ariaLabel: 'Increment' }, ], }, ], }, selection: { mode: 'multi' }, }; save(items)} onItemAction={(itemId, actionId) => { if (actionId === PICKER_ACTION.ADD) addIndicator(itemId); if (actionId === PICKER_ACTION.INCREMENT) increment(itemId); if (actionId === PICKER_ACTION.DECREMENT) decrement(itemId); }} /> ``` -------------------------------- ### Chart Layout Configuration Example Source: https://percept.one/docs/api-reference/chart-methods Demonstrates setting both padding and minimum width for the price scale gutter to achieve a tight mobile layout. This configuration allows the gutter to closely follow label width without a fixed minimum. ```typescript // Tight mobile recipe — gutter follows label width + 2px, no minimum chart.setPriceScalePadding(2); chart.setPriceScaleMinWidth(0); // Spacious dashboard look — leave defaults (10 / 70) ``` -------------------------------- ### Get Visible OHLCV Data Range Source: https://percept.one/docs/api-reference/chart-methods Retrieves the subset of OHLCV data currently visible in the chart's viewport, along with the start and end indices. ```typescript // Get visible data range chart.getVisibleData(): { data: IOHLCV[]; from: number; to: number } ``` -------------------------------- ### Layout Configuration Usage Examples Source: https://percept.one/docs/api-reference/types Demonstrates how to apply layout configurations, including hiding entire sections, granular control over header elements, and specifying visible toolbar tools. Also shows headless mode. ```tsx import type { ILayoutConfig, ToolGroup } from '@titancharts/react'; // Hide entire header const layout: ILayoutConfig = { header: false }; // Granular header control const layout: ILayoutConfig = { header: { screenshot: false, plotType: false } }; // Show only specific tool groups const layout: ILayoutConfig = { toolbar: { tools: ['lines', 'shapes', 'measurement'] } }; // Headless mode (canvas only) ``` -------------------------------- ### TPO Period Management with useTPO Hook Source: https://percept.one/docs/features/indicators/tpo-guide Example of using the useTPO hook to manage TPO periods. It demonstrates checking readiness, getting period state, and toggling expansion/collapse. ```tsx import { useTPO } from '@titancharts/react'; function TPOControls({ instanceId }: { instanceId: string }) { const { getPeriodState, expandPeriod, collapsePeriod, mergePeriod, restorePeriod, isReady, version, } = useTPO(); const handlePeriodAction = (periodStartMs: number) => { if (!isReady) return; const state = getPeriodState(instanceId, periodStartMs); if (state.isExpanded) { collapsePeriod(instanceId, periodStartMs); } else { expandPeriod(instanceId, periodStartMs); } }; return (
TPO version: {version} {/* Render period controls */}
); } ``` -------------------------------- ### Start Draft Order on Right-Click Source: https://percept.one/docs/quick-examples An example of triggering the `startOrderDraft` function programmatically in response to a chart event. This specific snippet initiates an order draft when the user right-clicks on the chart. ```typescript chart.on('click', (payload) => { if (payload.event?.button === 2) { const { price } = payload.payload['main']; trading.startOrderDraft(price); } }); ``` -------------------------------- ### Source Buckets Example Source: https://percept.one/docs/trading/api-methods Demonstrates writing to different source buckets. Host code writes to the default bucket, while modules can write to their own buckets. Getters return the union of all buckets. ```typescript // Host writes to default bucket trading.setPositions([{ id: 'my-pos', side: 'long', ... }]); // Module writes to its own bucket — host position survives trading.setPositions([{ id: 'hl:position:BTC', side: 'short', ... }], 'hyperliquid'); // Both render side-by-side trading.getPositions(); // → [my-pos, hl:position:BTC] ``` -------------------------------- ### Configure Floating Toolbar with Collapsed State and Custom Position Source: https://percept.one/docs/features/shell/layout Example of configuring the floating toolbar to start in a collapsed (pinned: false) state and with a custom default position. This allows for a tailored initial user experience. ```tsx // Floating toolbar starting collapsed and positioned lower ``` -------------------------------- ### Manage Chart Intervals Source: https://percept.one/docs/api-reference/chart-methods Provides methods to change, get, and configure the chart's interval. It also shows an example of setting a specific interval and retrieving the current one. The built-in `IntervalSelector` component uses these methods. ```typescript // Change interval (triggers interval:change event) chart.setInterval(interval: Interval): void // Get current interval chart.getInterval(): Interval // Get available intervals chart.getIntervals(): Interval[] // Configure available intervals chart.setIntervals(intervals: Interval[]): void // Example chart.setInterval('4h'); const currentInterval = chart.getInterval(); // '1h' chart.setIntervals(['1m', '5m', '15m', '1h', '4h', '1d']); ``` -------------------------------- ### Start Order Draft - With Pre-filled Size Source: https://percept.one/docs/trading/api-methods Initiates the order creation UI at a specific price for a buy order with a pre-filled quantity. ```typescript trading.startOrderDraft(49500, 'buy', 1.5); ``` -------------------------------- ### Configure Responsive Price Scale Gutter with ResizeObserver Source: https://percept.one/docs/advanced/patterns This pattern uses `ResizeObserver` to dynamically adjust the price scale minimum width based on the container's viewport size. This allows the gutter to shrink gracefully on small screens and grow back on larger ones. Remember to disconnect the observer on unmount. ```typescript const ro = new ResizeObserver((entries) => { const w = entries[0].contentRect.width; chart.setPriceScaleMinWidth(w < 480 ? 40 : w < 768 ? 50 : 70); }); ro.observe(chartContainer); // remember to ro.disconnect() on unmount ``` -------------------------------- ### React Quick Start with Hyperliquid Account Source: https://percept.one/docs/features/hyperliquid Enable the Hyperliquid account feature in the layout configuration to automatically mount the address selector and inspector drawer. Ensure you have a valid license key for the data feed and provider. ```tsx import { TitanProvider, TitanChart } from '@titancharts/react'; import { DataFeed, DEFAULT_MARKET } from '@titancharts/data'; const dataFeed = new DataFeed({ licenseKey: 'YOUR_LICENSE_KEY' }); export function Chart() { return ( ); } ``` -------------------------------- ### Install TitanCharts Data Package Source: https://percept.one/docs/datafeed-api/titancharts-datafeed/README Install the TitanCharts data package using npm. This command fetches and installs the necessary libraries for managing chart data. ```bash npm install @titancharts/data ``` -------------------------------- ### Example: Toggle Toolbar with Button Source: https://percept.one/docs/api-reference/chart-methods Shows how to link a button click to the `toggleToolbar` method for interactive control. ```typescript // Toggle with a custom button ``` -------------------------------- ### Using useDialogCompact Hook Source: https://percept.one/docs/features/dialogs/hooks-reference Demonstrates how to import and use the useDialogCompact hook. It requires the dialog's open state, a reference to the dialog element, and optionally a reference for constraining observations and a pixel threshold for compact mode. ```tsx import { useDialogCompact } from '@titancharts/react'; const { isCompact } = useDialogCompact({ open, dialogRef, constrainRef: shellRef, threshold: 600, }); ``` -------------------------------- ### Key Path Notation Examples Source: https://percept.one/docs/features/dialogs/schema-reference Illustrates how to use dot notation for accessing nested settings within the dialog input keys. ```typescript // Flat key { key: 'length', ... } // settings.length ``` ```typescript // Nested key { key: 'style.line.color', ... } // settings.style.line.color ``` -------------------------------- ### Cross-Field Validation Example Source: https://percept.one/docs/features/dialogs/schema-reference An example demonstrating cross-field validation, comparing a value against a maximum length setting. ```typescript // Cross-field validation validate: (value, settings) => { if (value > settings.maxLength) { return `Cannot exceed ${settings.maxLength}`; } return null; } ``` -------------------------------- ### Simple Validation Example Source: https://percept.one/docs/features/dialogs/schema-reference A basic example of a validation function that checks if a numeric value is at least 1. ```typescript // Simple validation validate: (value) => { if (value < 1) return 'Must be at least 1'; return null; } ``` -------------------------------- ### Heatmap Control Skeleton Source: https://percept.one/docs/features/indicators/tier2-advanced A skeleton example demonstrating how to implement the heatmap control methods within `createTier2Control`. ```APIDOC ## Skeleton ```ts createTier2Control({ overlayType: 'heatmap', async fetchHeatmapData(params) { // Return { data, effectiveFrom, effectiveTo } // data: Float64Array (packed) or ISimpleHeatmapPoint[] (auto-converted) }, processHeatmapData(overlayId, data, settings, context) { // data is always Float64Array here (auto-converted if needed) // Return { float64Data, thresholds, outerRange, tileHeightInPrice, colorSchemeColors } }, async streamHeatmapData(params) { // params.onChunk(chunkData) called per chunk // Return { data: new Float64Array(0), effectiveFrom, effectiveTo } }, }); ``` ``` -------------------------------- ### Install TitanCharts Packages (yarn) Source: https://percept.one/docs/quickstart Use yarn to install the necessary TitanCharts packages for React integration and data handling. ```bash yarn add @titancharts/react @titancharts/data ``` -------------------------------- ### Example searchMarket API Call Source: https://percept.one/docs/datafeed-api/interface-reference Demonstrates how to call the searchMarket API and process the response to extract relevant market details. ```typescript async searchMarket(params) { const response = await fetch( `/api/markets?q=${params.query}&exchange=${params.exchange || ''}&limit=${params.pageSize || 20}` ); const results = await response.json(); return results.map(r => ({ symbol: r.symbol, exchange: r.exchange, name: r.displayName, type: r.marketType, })); } ``` -------------------------------- ### Install TitanCharts Packages (pnpm) Source: https://percept.one/docs/quickstart Use pnpm to install the necessary TitanCharts packages for React integration and data handling. ```bash pnpm add @titancharts/react @titancharts/data ``` -------------------------------- ### Initialize and Control Viewport Clamping Source: https://percept.one/docs/features/clamping Demonstrates setting an initial clamp configuration, updating it at runtime, and clearing it. Use `ITitanChartConfig.clamping` for initial setup and `setClamping(null)` to remove all bounds. ```typescript const chart = await TitanChartController.create(container, { market: { symbol: 'BTCUSDT', exchange: 'BINANCE' }, clamping: { x: { before: Date.parse('2024-01-01'), after: Date.parse('2024-12-31') }, y: { low: 30_000, high: 80_000 }, }, }); // Narrow the right edge at runtime chart.setClamping({ x: { after: Date.now() } }); // Clear all bounds chart.setClamping(null); // Read the active config const current = chart.getClamping(); // IClamping | null ``` -------------------------------- ### Install TitanCharts Packages (npm) Source: https://percept.one/docs/quickstart Use npm to install the necessary TitanCharts packages for React integration and data handling. ```bash npm install @titancharts/react @titancharts/data ``` -------------------------------- ### Configure License Key with Environment Variables Source: https://percept.one/docs/quickstart For production, configure your license key using environment variables. The example shows access patterns for Vite, Create React App, and Next.js. The license key is used for both local validation and API authentication. ```tsx const LICENSE_KEY = import.meta.env.VITE_TITAN_CHARTS_LICENSE_KEY; const dataFeed = new DataFeed({ licenseKey: LICENSE_KEY, }); ... ``` -------------------------------- ### Polling Control Example - TypeScript Source: https://percept.one/docs/api-reference/chart-methods Example of pausing data polling before a bulk update operation and resuming it afterward to prevent interruptions. ```typescript // Pause polling during bulk operations chart.stopPolling(); await performBulkUpdate(); chart.startPolling(); ``` -------------------------------- ### Start Order Draft - With Icon Source: https://percept.one/docs/trading/api-methods Initiates the order creation UI at a specific price for a buy order with a pre-filled quantity and an optional icon, such as an exchange logo. ```typescript trading.startOrderDraft(49500, 'buy', 1, 'https://example.com/exchange-logo.svg'); ``` -------------------------------- ### Example IOHLCV Candle Data Source: https://percept.one/docs/getting-started/core-concepts An example of a single candlestick data point conforming to the IOHLCV interface, including time, OHLC, and volume. ```typescript const candle = { time: 1704067200, // 2024-01-01 00:00:00 UTC open: 42000, high: 42500, low: 41800, close: 42300, volume: 1500, }; ``` -------------------------------- ### Multiple Conditions Validation Example Source: https://percept.one/docs/features/dialogs/schema-reference An example of a validation function with multiple conditions, checking for required input, minimum length, and allowed characters. ```typescript // Multiple conditions validate: (value) => { if (value === '') return 'Required'; if (value.length < 3) return 'Minimum 3 characters'; if (!/^[a-zA-Z]+$/.test(value)) return 'Letters only'; return null; } ``` -------------------------------- ### Example Usage of getAvailableThemes Source: https://percept.one/docs/api-reference/chart-methods Demonstrates how to call `getAvailableThemes()` and the expected structure of the returned array, showing theme keys, labels, and preview colors. ```typescript const themes = chart.getAvailableThemes(); // [ // { key: 'percept', label: 'Percept', colors: { bullish: '#D97757', bearish: '#CECECE' } }, // { key: 'classic', label: 'Classic', colors: { bullish: '#26a69a', bearish: '#ef5350' } }, // ... // ] ``` -------------------------------- ### Form Dialog Schema Example with Groups Source: https://percept.one/docs/features/dialogs/form-dialogs An example of a form dialog schema demonstrating the use of sections and nested groups to organize inputs. ```tsx const schema: IFormDialogSchema = { id: 'grouped-settings', title: 'Settings', layout: 'single', sections: [{ id: 'main', title: 'Main', groups: [ { id: 'calculation', title: 'Calculation', inputs: [ { key: 'length', label: 'Length', type: 'number', default: 20 }, { key: 'source', label: 'Source', type: 'source', default: 'close' }, ], }, { id: 'appearance', title: 'Appearance', defaultCollapsed: true, inputs: [ { key: 'color', label: 'Color', type: 'color', default: '#2196F3' }, { key: 'width', label: 'Width', type: 'number', default: 2 }, ], }, ], }], }; ``` -------------------------------- ### Handle Bracket Order Creation Source: https://percept.one/docs/api-reference/events Listen for 'trading:bracket_create' to handle the creation of Take Profit (TP) or Stop Loss (SL) brackets. This example logs the bracket details and creates it on the exchange. ```typescript chart.on('trading:bracket_create', async ({ parentId, bracketRole, price }) => { console.log(`New ${bracketRole.toUpperCase()} bracket on ${parentId} at ${price}`); await exchange.createBracket(parentId, bracketRole, price); }); ``` -------------------------------- ### Example: React to Toolbar Toggles Source: https://percept.one/docs/api-reference/chart-methods Listen for the 'toolbar:toggle' event to perform actions when the toolbar's visibility changes. ```typescript // React to visibility changes chart.on('toolbar:toggle', ({ visible }) => { console.log('Toolbar is now:', visible ? 'visible' : 'hidden'); }); ``` -------------------------------- ### Create Custom Volume Profile with createTier2Control Source: https://percept.one/docs/features/indicators/volume-profile-guide Use `createTier2Control` with `overlayType: 'profile'` for maximum control over custom data feeds or non-standard processing. The `initializeOverlay` settings are the minimum required for rendering a profile. ```typescript import { createTier2Control, type IProfileBucket } from '@titancharts/react'; export const RAW_PROFILE_CONTROL = createTier2Control({ id: 'raw-profile', name: 'Raw Profile', description: 'Profile from custom data source', category: 'Volume', dataType: 'RAW_PROFILE', placement: 'onchart', overlayType: 'profile', allowMultiple: false, legendPreset: 'none', inputs: [ { key: 'exchange', type: 'select', label: 'Exchange', default: 'binance', affectsData: true }, { key: 'symbol', type: 'text', label: 'Symbol', default: 'BTCUSDT', affectsData: true }, ], overlaySettings: { variant: 'session', stickToLeft: true, hideLegendValues: true, verticalPadding: 0.1, }, extractors: { getX1: (d: unknown) => (d as number[])[0], getX2: (d: unknown) => (d as number[])[0], getHigh: () => null as unknown as number, getLow: () => null as unknown as number, getData: (d: unknown) => d, }, async initializeOverlay(params) { const blockSize = params.symbolMetadata?.blockSizes?.[0] ?? 0.01; return { side: 'onchart', template: { name: 'Raw Profile', type: 'profile', data: [], settings: { colors: ['$bullish', '$bearish'], width: 0.7, minimumBarHeight: blockSize, barHeight: blockSize * 15, barHeightMultiplier: 15, session: 3600000, // 1 hour sessions showPOC: true, pocColor: '$text', showValueArea: false, valueArea: 0.7, showVAH: false, vahColor: '$text', showVAL: false, valColor: '$text', }, }, }; }, async fetchData(params) { // Your custom data source const response = await fetch( `/api/profile?symbol=${params.market.symbol}&from=${params.from}&to=${params.to}` ); const data: number[][] = await response.json(); // Data must be [[timestamp, [pB, pT, buy, sell], [pB, pT, buy, sell], ...], ...] return data; }, }); ``` -------------------------------- ### Full CVD Indicator Example Source: https://percept.one/docs/features/indicators/multi-symbol-guide An example demonstrating the configuration for a Cumulative Volume Delta (CVD) indicator, including multi-symbol settings, color modes, and custom data processing functions. ```typescript import { createTier2Control } from '@titancharts/react'; export const CVD_CONTROL = createTier2Control({ id: 'cvd', name: 'Cumulative Volume Delta', dataType: 'CVD', placement: 'offchart', overlayType: 'momentumFillSpline', gridHeight: 0.2, smooth: true, horizontalLine: { price: 0 }, multiSymbol: { mirrorMainChart: true, colorMode: 'dual', maxSymbols: 8, columnsPerSymbol: 2, fillStrategy: 'locf', expandColors: (entries, { alpha }) => entries.flatMap((e) => { const [bull, bear] = e.colors!; return [bull, bear, alpha(bull, 0.3), alpha(bear, 0.3)]; }), processSymbolData(data) { let cum = 0; return data.map(([t, buy, sell]) => { cum += (buy ?? 0) - (sell ?? 0); return [t, cum, /* sma */]; }); }, mergeSymbolLiveData(lastValues, tick, _interval, settings) { const delta = parseTradeDelta(tick, settings); const [cum, sma] = lastValues; const newCum = cum + delta; return [newCum, updateSma(sma, cum, newCum)]; }, }, inputs: [ { key: 'currency', label: 'Unit', type: 'select', default: 'USD', options: [{ label: 'USD', value: 'USD' }, { label: 'Coin', value: 'Coin' }], group: 'Parameters', affectsData: true }, ], getQueryModifiers: (s) => ({ quoteCurrency: s.currency === 'USD' ? 'USD' : 'COIN', }), }); ``` -------------------------------- ### Configure Price Scale Gutter via Init-time Prop Source: https://percept.one/docs/advanced/patterns Apply `priceScaleAutoPadding` and `priceScaleMinWidth` as props during component initialization for static, deploy-time defaults. This method prevents a visual flash or resize on mount. ```tsx ```