Loading source
Pulling the file list, source metadata, and syntax-aware rendering for this listing.
Source from repo
Generate TradingView-style dark-theme candlestick charts with RSI, MACD, Bollinger Bands, and EMA/SMA using mplfinance.
Files
Skill
Size
Entrypoint
Format
Open file
Syntax-highlighted preview of this file as included in the skill package.
templates/multi-panel.html
1<!DOCTYPE html>2<html lang="en">3<head>4<meta charset="UTF-8">5<meta name="viewport" content="width=device-width, initial-scale=1.0">6<title>Multi Panel Chart</title>7<script src="https://cdn.jsdelivr.net/npm/echarts@5/dist/echarts.min.js"></script>8<style>{{BASE_STYLES}}</style>9</head>10<body>11<div class="toolbar">12<div>13<h1>{{TITLE}}</h1>14<div class="subtitle">{{SUBTITLE}}</div>15</div>16<div class="actions">17<button onclick="downloadPNG(this)">๐ฅ Download PNG</button>18<button onclick="copyToClipboard(this)">๐ Copy Image</button>19<button onclick="saveToProject(this)">๐พ Save Image</button>20</div>21</div>2223<!--24Multi-panel layout: all panels share ONE ECharts instance.25This enables tooltip sync / dataZoom linkage across panels automatically.26Panel height ratios: price 55% | volume 25% | indicator 20%27-->28<div id="chart-area">29<div id="main-chart" style="width:100%;height:600px;"></div>30</div>3132<script>{{BASE_EXPORT_JS}}</script>33<script>34// === DATA ===35const dates = ['2024-01','2024-02','2024-03','2024-04','2024-05','2024-06',36'2024-07','2024-08','2024-09','2024-10','2024-11','2024-12'];37// [open, close, low, high]38const ohlc = [39[42000,43500,41000,44000],[43500,41000,40000,44500],[41000,52000,40500,53000],40[52000,60000,51000,62000],[60000,57000,55000,61000],[57000,62000,56000,63500],41[62000,65000,61000,66000],[65000,58000,57000,67000],[58000,61000,57500,62000],42[61000,68000,60000,69000],[68000,72000,67000,73000],[72000,95000,71000,96000],43];44const volume = [12000,15000,25000,30000,18000,22000,19000,35000,21000,28000,32000,55000];45// RSI (14) โ mock values46const rsi = [52,44,68,72,58,65,67,48,55,63,70,78];4748// Derived MA49function ma(data, n) {50return data.map((_, i) => i < n - 1 ? null : data.slice(i - n + 1, i + 1).reduce((s, v) => s + v, 0) / n);51}52const closes = ohlc.map(d => d[1]);53const ma7 = ma(closes, 3); // 3-period as proxy for short-window demo54const ma25 = ma(closes, 6);5556// === CHART (single instance, 3 grids) ===57window.CHART_INSTANCES = [];58const chart = echarts.init(document.getElementById('main-chart'), 'dark');5960chart.setOption({61backgroundColor: 'transparent',62animation: false,63tooltip: {64trigger: 'axis',65axisPointer: { type: 'cross', link: [{ xAxisIndex: 'all' }] },66},67axisPointer: { link: [{ xAxisIndex: 'all' }] },68dataZoom: [69{ type: 'inside', xAxisIndex: [0, 1, 2] },70{ type: 'slider', xAxisIndex: [0, 1, 2], height: 18, bottom: 4 },71],72grid: [73{ top: 40, left: 70, right: 30, height: '52%' }, // price74{ top: '62%', left: 70, right: 30, height: '16%' }, // volume75{ top: '82%', left: 70, right: 30, height: '10%' }, // RSI76],77xAxis: [78{ type: 'category', data: dates, gridIndex: 0, axisLabel: { show: false }, boundaryGap: false },79{ type: 'category', data: dates, gridIndex: 1, axisLabel: { show: false }, boundaryGap: false },80{ type: 'category', data: dates, gridIndex: 2, boundaryGap: false },81],82yAxis: [83{ type: 'value', gridIndex: 0, scale: true, splitLine: { lineStyle: { color: '#2a2d3a' } }, axisLabel: { formatter: v => `$${(v/1000).toFixed(0)}k` } },84{ type: 'value', gridIndex: 1, splitLine: { show: false }, axisLabel: { formatter: v => `${(v/1000).toFixed(0)}k` } },85{ type: 'value', gridIndex: 2, min: 0, max: 100, splitLine: { lineStyle: { color: '#2a2d3a', type: 'dashed' } },86axisLabel: { formatter: v => `${v}` },87splitArea: {88show: true,89areaStyle: { color: ['rgba(255,80,80,0.04)', 'rgba(80,255,80,0.04)'] },90},91},92],93series: [94// Candlestick95{96name: 'BTC', type: 'candlestick', xAxisIndex: 0, yAxisIndex: 0,97data: ohlc,98itemStyle: {99color: '#26a69a', color0: '#ef5350',100borderColor: '#26a69a', borderColor0: '#ef5350',101},102},103// MA7104{ name: 'MA7', type: 'line', xAxisIndex: 0, yAxisIndex: 0, data: ma7,105smooth: true, symbol: 'none', lineStyle: { width: 1.5, color: '#f6c768' } },106// MA25107{ name: 'MA25', type: 'line', xAxisIndex: 0, yAxisIndex: 0, data: ma25,108smooth: true, symbol: 'none', lineStyle: { width: 1.5, color: '#ee6666' } },109// Volume110{111name: 'Volume', type: 'bar', xAxisIndex: 1, yAxisIndex: 1, data: volume,112itemStyle: {113color: p => ohlc[p.dataIndex][1] >= ohlc[p.dataIndex][0] ? '#26a69a' : '#ef5350',114opacity: 0.7,115},116},117// RSI118{119name: 'RSI(14)', type: 'line', xAxisIndex: 2, yAxisIndex: 2, data: rsi,120smooth: true, symbol: 'none',121lineStyle: { width: 1.5, color: '#7b68ee' },122markLine: {123silent: true,124lineStyle: { color: '#555', type: 'dashed' },125data: [{ yAxis: 70 }, { yAxis: 30 }],126},127},128],129});130131CHART_INSTANCES.push(chart);132</script>133</body>134</html>135