Chapter 03 · Dreambase ECharts
Subchapter 3.3
references/charts/candlestick.mdMarkdown5 KBView on GitHub
line or bar instead; a candlestick with fabricated open/close values misleads.boxplot (5 values, different semantics), not candlestick.Each data item is a 4-tuple in ECharts order (OCLH):
[open, close, lowest, highest]This differs from the OHLC order many libraries and data feeds use. If your source rows are [open, high, low, close], do NOT reorder the arrays by hand — remap with encode:
{ "type": "candlestick", "encode": { "x": 0, "y": [1, 4, 3, 2] } }(there, source columns are [date, open, high, low, close] and encode.y maps them into OCLH).
Items may also be objects for per-item styling: { "value": [open, close, lowest, highest], "itemStyle": { ... } }.
The x axis must be type: "category" with data holding the period labels (dates), aligned 1:1 with the series data. Direction is derived from the tuple: close >= open renders as bullish (color), close < open as bearish (color0).
{
"tooltip": {
"trigger": "axis",
"axisPointer": { "type": "cross" }
},
"legend": { "data": ["Daily", "MA5"] },
"grid": { "left": 60, "right": 20, "bottom": 60 },
"xAxis": {
"type": "category",
"data": ["2026-07-06", "2026-07-07", "2026-07-08", "2026-07-09", "2026-07-10", "2026-07-13"],
"boundaryGap": true
},
"yAxis": {
"type": "value",
"scale": true,
"splitArea": { "show": true }
},
"dataZoom": [
{ "type": "inside", "start": 0, "end": 100 },
{ "type": "slider", "start": 0, "end": 100, "bottom": 10 }
],
"series": [
{
"name": "Daily",
"type": "candlestick",
"data": [
[212.4, 218.1, 211.7, 219.3],
[218.1, 215.6, 213.9, 220.0],
[215.6, 221.8, 215.2, 222.5],
[221.8, 224.4, 220.9, 226.1],
[224.4, 219.7, 218.3, 225.0],
[219.7, 223.2, 219.1, 224.8]
],
"itemStyle": {
"color": "#ef4444",
"color0": "#22c55e",
"borderColor": "#ef4444",
"borderColor0": "#22c55e"
}
},
{
"name": "MA5",
"type": "line",
"data": [null, null, null, null, 218.42, 220.94],
"smooth": true,
"showSymbol": false,
"lineStyle": { "width": 1.5, "opacity": 0.8 }
}
]
}itemStyle.color = #eb5454 — fill of bullish (close >= open) candles; itemStyle.color0 = #47b262 — fill of bearish candles.itemStyle.borderColor = #eb5454 / itemStyle.borderColor0 = #47b262 — candle and wick outline for bullish/bearish; set these together with color/color0 or wicks keep the default colors.yAxis.scale = false (axis option, not series) — set true so the value axis does not start at 0; prices clustered around e.g. 220 render as invisible slivers otherwise.barWidth (auto) / barMinWidth / barMaxWidth — candle body width; useful to cap width when only a few periods are shown.encode — remap dataset/data columns to x and the four y dimensions; the only safe way to consume OHLC-ordered sources.large = true, largeThreshold = 600, progressive = 3000 — built-in large-dataset optimizations; leave at defaults.markLine / markPoint — annotate support/resistance levels or extremes declaratively.dataZoom (top-level) — pair {"type":"inside"} (wheel/drag zoom) with {"type":"slider"} for long histories; give both the same start/end.[open, high, low, close] data fed as-is produces candles with inverted bodies and impossible wicks — no error is thrown because the numbers are still valid. Always confirm OCLH or use encode.y.xAxis.type is "value" (or omitted with numeric labels), candlestick has no category to place bodies on and draws nothing usable. Use xAxis: { type: "category", data: [...] }.yAxis starts at 0; for prices in a narrow band the whole series compresses into a few pixels. Set yAxis.scale: true.color/borderColor green, color0/borderColor0 red — and change all four, not just the fills.itemStyle.color recolors half the candles. Bearish candles read color0/borderColor0; forgetting them leaves a mixed default/custom palette.grid entries, two xAxis/yAxis pairs (gridIndex: 1 on the second), a bar series with xAxisIndex: 1, yAxisIndex: 1, and put both x-axis indexes in dataZoom.xAxisIndex: [0, 1] so zooming stays in sync.line series shares the category axis, so pad its head with null for the periods before the window fills; shifting instead of padding plots the MA against the wrong dates.