Drawing and marks
Plots, levels, shading, labels, boxes, lines, tables and marks drawn on the chart, in tested programs.
Everything a script shows is drawn by a call: lines and levels, shaded areas, marks on bars, and objects such as labels, boxes, lines and tables.
RSI zones#
The built-in RSI with levels, a shaded band and marks when it leaves a zone.
Cuprel
// The built-in RSI with two levels, a shaded middle band and a mark each time it leaves a zone.
indicator "RSI zones"
edition = 1
display = pane
input length: int = 14, name = "Length", min = 2
input upper: float = 70, name = "Upper level"
input lower: float = 30, name = "Lower level"
let value = tech.rsi(close, length)
let top = level(upper, name = "Upper", color = color.red, style = dashed)
let bottom = level(lower, name = "Lower", color = color.green, style = dashed)
shade(top, bottom, color = color.fade(color.purple, 92), name = "Middle band")
plot(value, name = "RSI", color = color.purple, width = 2)
mark.shape(
tech.crosses_below(value, upper),
name = "Leaves overbought",
shape = triangle_down,
place = above,
color = color.red,
)
mark.shape(
tech.crosses_above(value, lower),
name = "Leaves oversold",
shape = triangle_up,
place = below,
color = color.green,
)Swing pivots#
Swing highs and lows found with a left and a right window, labelled on the bar where they happened.
Cuprel
// Swing structure: a swing high is a bar whose high is the highest of `left` bars before it and `right` bars after it.
// The pivot is only known `right` bars later, so the label is placed back on the bar where the swing happened.
indicator "Swing pivots"
edition = 1
display = price
max_labels = 200
input left: int = 5, name = "Bars on the left", min = 1
input right: int = 5, name = "Bars on the right", min = 1
let swing_high = tech.pivot_high(high, left, right)
let swing_low = tech.pivot_low(low, left, right)
if not is_na(swing_high)
label.new(
bar.index - right,
swing_high,
f"{swing_high:price}",
style = label_down,
color = color.red,
)
if not is_na(swing_low)
label.new(
bar.index - right,
swing_low,
f"{swing_low:price}",
style = label_up,
color = color.green,
)
plot(close, name = "Close", color = color.gray)Status table#
A table written on the last bar, with formatted numbers and a fallback text.
Cuprel
// A small table in the corner of the chart, written on the last bar only.
indicator "Status table"
edition = 1
display = price
input length: int = 14, name = "Length", min = 2
let strength = tech.rsi(close, length)
let volatility = tech.atr(length)
if bar.is_last
let t = table.new(
top_right,
2,
3,
background = color.fade(color.black, 70),
border_color = color.gray,
border_width = 1,
)
table.cell(t, 0, 0, "Close", text_color = color.silver, h_align = left)
table.cell(t, 1, 0, f"{close:price}", text_color = color.white)
table.cell(t, 0, 1, "RSI", text_color = color.silver, h_align = left)
table.cell(t, 1, 1, f"{strength:.1f?'n/a'}", text_color = color.white)
table.cell(t, 0, 2, "ATR", text_color = color.silver, h_align = left)
table.cell(t, 1, 2, f"{volatility:price?'n/a'}", text_color = color.white)
plot(close, name = "Close", color = color.gray)Recent range drawing#
A box, a dashed line and a label drawn on the last bar.
Cuprel
// Drawing objects on the last bar: a box around the recent range, a dashed line at the close and a label at the high.
indicator "Recent range"
edition = 1
display = price
input length: int = 30, name = "Length", min = 2
let top = tech.highest(high, length)
let bottom = tech.lowest(low, length)
if bar.is_last
box.new(
bar.index - length + 1,
top,
bar.index,
bottom,
border_color = color.blue,
background = color.fade(color.blue, 90),
)
line.new(
bar.index - length + 1,
close,
bar.index,
close,
extend = right,
style = dashed,
color = color.orange,
)
label.new(bar.index, top, f"High {top:price}", style = label_down)
plot(close, name = "Close", color = color.gray)Trend background#
A chart background coloured by the side of a moving average.
Cuprel
// A background that follows the trend: green above the moving average, red below it, nothing while it is not known yet.
indicator "Trend background"
edition = 1
display = price
input length: int = 50, name = "Length", min = 2
let trend = tech.sma(close, length)
let tint = if close > trend then color.fade(color.green, 88) else color.fade(color.red, 88)
chart.background(if is_na(trend) then na else tint, name = "Trend")
plot(trend, name = "Trend line", color = color.gray)Swing high path#
Swing highs collected as chart points in an array and drawn as one polyline on the last bar.
Cuprel
// A polyline through the latest swing highs. Each confirmed swing high becomes a chart point (a bar number and a price) kept in an array,
// and on the last bar polyline.new draws one line through the twelve most recent points.
indicator "Swing high path"
edition = 1
display = price
max_polylines = 5
input side: int = 5, name = "Bars on each side", min = 1
let pivot = tech.pivot_high(high, side, side)
state points: array<chart.point> = array<chart.point>()
if not is_na(pivot)
points.push(chart.point.at_index(bar.index - side, pivot))
if points.size() > 12
points.shift()
if bar.is_last and points.size() > 1
polyline.new(points, color = color.orange, width = 2)
plot(close, name = "Close", color = color.gray)