TradingView Lightweight Charts integration in dApp

We design and develop full-cycle blockchain solutions: from smart contract architecture to launching DeFi protocols, NFT marketplaces and crypto exchanges. Security audits, tokenomics, integration with existing infrastructure.
Showing 1 of 1 servicesAll 1306 services
TradingView Lightweight Charts integration in dApp
Medium
from 1 business day to 3 business days
FAQ
Blockchain Development Services
Blockchain Development Stages
Latest works
  • image_website-b2b-advance_0.png
    B2B ADVANCE company website development
    1214
  • image_web-applications_feedme_466_0.webp
    Development of a web application for FEEDME
    1161
  • image_websites_belfingroup_462_0.webp
    Website development for BELFINGROUP
    852
  • image_ecommerce_furnoro_435_0.webp
    Development of an online store for the company FURNORO
    1041
  • image_logo-advance_0.png
    B2B Advance company logo design
    561
  • image_crm_enviok_479_0.webp
    Development of a web application for Enviok
    823

TradingView Lightweight Charts Integration in dApp

TradingView Lightweight Charts is an open-source library (~45 KB gzipped) used by most DEXes for price chart display. Dydx, GMX, Uniswap Info—they either use it directly or fork it. Integration into a dApp is straightforward, but there are several places where performance breaks when working with on-chain data.

Basic Initialization

import { createChart, IChartApi, CandlestickData } from 'lightweight-charts';

const chartContainer = useRef<HTMLDivElement>(null);
const chartRef = useRef<IChartApi>();

useEffect(() => {
  if (!chartContainer.current) return;

  const chart = createChart(chartContainer.current, {
    width: chartContainer.current.clientWidth,
    height: 400,
    layout: {
      background: { color: '#0d0d0d' },
      textColor: '#9ca3af',
    },
    grid: {
      vertLines: { color: '#1f2937' },
      horzLines: { color: '#1f2937' },
    },
    timeScale: {
      timeVisible: true,
      secondsVisible: false,
    },
  });

  chartRef.current = chart;
  return () => chart.remove();
}, []);

Always call chart.remove() in useEffect cleanup, otherwise hot reload or component unmount accumulates memory leaks.

Feeding Data from On-Chain Sources

This is the main problem when integrating with dApp. On-chain OHLCV candle data comes from several sources:

Subgraph (The Graph)—the most common option for DEX. Uniswap v3 subgraph provides poolHourDatas and poolDayDatas with OHLC for each pool. Query:

query GetCandles($pool: String!, $startTime: Int!) {
  poolHourDatas(
    where: { pool: $pool, periodStartUnix_gte: $startTime }
    orderBy: periodStartUnix
    first: 1000
  ) {
    periodStartUnix
    open
    high
    low
    close
    volumeUSD
  }
}

Converting to LWC format:

const candles: CandlestickData[] = data.poolHourDatas.map((d) => ({
  time: d.periodStartUnix as UTCTimestamp,
  open: parseFloat(d.open),
  high: parseFloat(d.high),
  low: parseFloat(d.low),
  close: parseFloat(d.close),
}));

candleSeries.setData(candles);

Real-time updates—poll subgraph every 30–60 seconds or WebSocket subscription to Swap events via RPC. On new event, recalculate current unclosed candle and update via candleSeries.update(newCandle) instead of setData (full data reset on every tick kills performance).

Synchronizing Multiple Charts

If you need two synchronized charts (price + volume), use chart.timeScale().subscribeVisibleTimeRangeChange() to sync viewport between instances. Standard practice for trading interfaces:

chart1.timeScale().subscribeVisibleTimeRangeChange((range) => {
  if (range) chart2.timeScale().setVisibleRange(range);
});

Responsive Resizing

LWC doesn't adapt automatically on container resize. Use ResizeObserver:

const resizeObserver = new ResizeObserver(entries => {
  const { width, height } = entries[0].contentRect;
  chart.applyOptions({ width, height });
});
resizeObserver.observe(chartContainer.current);

Custom Markers and Overlay

To display on-chain events on chart (liquidations, large trades), use series.setMarkers():

series.setMarkers([
  {
    time: timestamp as UTCTimestamp,
    position: 'belowBar',
    color: '#ef4444',
    shape: 'arrowUp',
    text: 'Liquidation $2.4M',
  },
]);

Markers display directly on candles and don't require custom rendering—much simpler than implementing overlay through canvas directly.