OPEN-SOURCE SCRIPT
gex levels Rafael

//version=5
indicator("GEX Levels (10-slot, symbol-specific)", overlay=true, max_lines_count=500, max_labels_count=500)
//===========================
// User inputs (10 slots)
//===========================
slotSym1 = input.string("IREN", "Slot 1 Symbol")
slotDat1 = input.string('IREN: Key Delta, 20.0, Implied Movement -2σ, 43.83, Implied Movement -σ, 47.97, Implied Movement +2σ, 62.15, Put Dominate , 41.0, Large Gamma 1 & Gamma Field CE & Call Wall & Call Wall CE, 55.0, Put Wall & Large Gamma 2 & Gamma Field, 50.0, Implied Movement +σ, 58.01, Call Dominate , 57.0, Put Wall CE & Gamma Flip & Gamma Flip CE, 43.5,', "Slot 1 Data")
slotSym2 = input.string("", "Slot 2 Symbol")
slotDat2 = input.string("", "Slot 2 Data")
slotSym3 = input.string("", "Slot 3 Symbol")
slotDat3 = input.string("", "Slot 3 Data")
slotSym4 = input.string("", "Slot 4 Symbol")
slotDat4 = input.string("", "Slot 4 Data")
slotSym5 = input.string("", "Slot 5 Symbol")
slotDat5 = input.string("", "Slot 5 Data")
slotSym6 = input.string("", "Slot 6 Symbol")
slotDat6 = input.string("", "Slot 6 Data")
slotSym7 = input.string("", "Slot 7 Symbol")
slotDat7 = input.string("", "Slot 7 Data")
slotSym8 = input.string("", "Slot 8 Symbol")
slotDat8 = input.string("", "Slot 8 Data")
slotSym9 = input.string("", "Slot 9 Symbol")
slotDat9 = input.string("", "Slot 9 Data")
slotSym10 = input.string("", "Slot 10 Symbol")
slotDat10 = input.string("", "Slot 10 Data")
showOnlyOnMatch = input.bool(true, "Show only when chart symbol matches a slot?")
labelOnRight = input.bool(true, "Show labels on right")
extendRight = input.bool(true, "Extend lines to the right")
lineWidth = input.int(2, "Line width", minval=1, maxval=4)
labelOffsetBars = input.int(30, "Label offset (bars to the right)", minval=5, maxval=300)
//===========================
// Helpers
//===========================
trim(s) =>
// Safe trim
str.trim(s)
containsCI(hay, needle) =>
str.contains(str.lower(hay), str.lower(needle))
// Decide color based on label keywords
levelColor(lbl) =>
// You can tune this mapping to match your old indicator’s palette
containsCI(lbl, "key delta") ? color.new(color.red, 0) :
containsCI(lbl, "gamma flip") ? color.new(color.fuchsia, 0) :
containsCI(lbl, "put wall") ? color.new(color.purple, 0) :
containsCI(lbl, "call wall") ? color.new(color.orange, 0) :
containsCI(lbl, "put dominate") ? color.new(color.yellow, 0) :
containsCI(lbl, "call dominate") ? color.new(color.teal, 0) :
containsCI(lbl, "implied movement") ? color.new(color.blue, 0) :
color.new(color.gray, 0)
//===========================
// Pick active slot by chart symbol
//===========================
chartSym = syminfo.ticker // e.g. "IREN" on most US stocks
getSlotData() =>
string sym = ""
string dat = ""
if chartSym == trim(slotSym1) and trim(slotSym1) != ""
sym := trim(slotSym1), dat := slotDat1
else if chartSym == trim(slotSym2) and trim(slotSym2) != ""
sym := trim(slotSym2), dat := slotDat2
else if chartSym == trim(slotSym3) and trim(slotSym3) != ""
sym := trim(slotSym3), dat := slotDat3
else if chartSym == trim(slotSym4) and trim(slotSym4) != ""
sym := trim(slotSym4), dat := slotDat4
else if chartSym == trim(slotSym5) and trim(slotSym5) != ""
sym := trim(slotSym5), dat := slotDat5
else if chartSym == trim(slotSym6) and trim(slotSym6) != ""
sym := trim(slotSym6), dat := slotDat6
else if chartSym == trim(slotSym7) and trim(slotSym7) != ""
sym := trim(slotSym7), dat := slotDat7
else if chartSym == trim(slotSym8) and trim(slotSym8) != ""
sym := trim(slotSym8), dat := slotDat8
else if chartSym == trim(slotSym9) and trim(slotSym9) != ""
sym := trim(slotSym9), dat := slotDat9
else if chartSym == trim(slotSym10) and trim(slotSym10) != ""
sym := trim(slotSym10), dat := slotDat10
[sym, dat]
//===========================
// Parse "label, value, label, value, ..."
//===========================
parsePairs(raw) =>
// Split by comma, then step through tokens 2 at a time.
// Expect format: label, number, label, number, ...
string[] t = str.split(raw, ",")
int n = array.size(t)
string[] outLabels = array.new_string()
float[] outValues = array.new_float()
for i = 0 to n - 1
array.set(t, i, trim(array.get(t, i)))
for i = 0 to n - 2
if i % 2 == 0
string lbl = array.get(t, i)
string valS = array.get(t, i + 1)
// Skip empty label/value
if lbl != "" and valS != ""
float v = str.tonumber(valS)
if not na(v)
// Optional: remove leading "SYMBOL:" prefix from label
// e.g. "IREN: Key Delta" -> "Key Delta"
string cleaned = lbl
int colonPos = str.pos(cleaned, ":")
if colonPos != -1
cleaned := trim(str.substring(cleaned, colonPos + 1, str.length(cleaned)))
array.push(outLabels, cleaned)
array.push(outValues, v)
[outLabels, outValues]
//===========================
// Drawing state
//===========================
var line[] lines = array.new_line()
var label[] labels = array.new_label()
var string lastRaw = ""
// Delete all existing drawings
clearAll() =>
for i = 0 to array.size(lines) - 1
line.delete(array.get(lines, i))
for i = 0 to array.size(labels) - 1
label.delete(array.get(labels, i))
array.clear(lines)
array.clear(labels)
// Draw levels
drawLevels(sym, raw) =>
[lbls, vals] = parsePairs(raw)
int m = array.size(lbls)
// Build on last bar only to reduce clutter and avoid heavy redraw
if barstate.islast
clearAll()
// If user wants strict symbol match, and no slot matched, show nothing
bool ok = (sym != "")
if not showOnlyOnMatch
ok := true
if ok
int x1 = bar_index
int x2 = bar_index + (extendRight ? 200 : 1)
for i = 0 to m - 1
string lbl = array.get(lbls, i)
float y = array.get(vals, i)
color c = levelColor(lbl)
// Line
line ln = line.new(x1, y, x2, y, extend=extendRight ? extend.right : extend.none, color=c, width=lineWidth)
array.push(lines, ln)
// Label (right side)
if labelOnRight
int lx = bar_index + labelOffsetBars
string text = lbl + " (" + str.tostring(y) + ")"
label la = label.new(lx, y, text=text, style=label.style_label_left, textcolor=color.white, color=color.new(c, 0))
array.push(labels, la)
//===========================
// Main
//===========================
[sym, raw] = getSlotData()
// If not matched but user wants to still show something, fallback to slot1
if not showOnlyOnMatch and sym == ""
sym := trim(slotSym1)
raw := slotDat1
// Redraw only when raw changes (or first run); still rebuild on last bar to keep labels aligned
if raw != lastRaw
lastRaw := raw
drawLevels(sym, raw)
indicator("GEX Levels (10-slot, symbol-specific)", overlay=true, max_lines_count=500, max_labels_count=500)
//===========================
// User inputs (10 slots)
//===========================
slotSym1 = input.string("IREN", "Slot 1 Symbol")
slotDat1 = input.string('IREN: Key Delta, 20.0, Implied Movement -2σ, 43.83, Implied Movement -σ, 47.97, Implied Movement +2σ, 62.15, Put Dominate , 41.0, Large Gamma 1 & Gamma Field CE & Call Wall & Call Wall CE, 55.0, Put Wall & Large Gamma 2 & Gamma Field, 50.0, Implied Movement +σ, 58.01, Call Dominate , 57.0, Put Wall CE & Gamma Flip & Gamma Flip CE, 43.5,', "Slot 1 Data")
slotSym2 = input.string("", "Slot 2 Symbol")
slotDat2 = input.string("", "Slot 2 Data")
slotSym3 = input.string("", "Slot 3 Symbol")
slotDat3 = input.string("", "Slot 3 Data")
slotSym4 = input.string("", "Slot 4 Symbol")
slotDat4 = input.string("", "Slot 4 Data")
slotSym5 = input.string("", "Slot 5 Symbol")
slotDat5 = input.string("", "Slot 5 Data")
slotSym6 = input.string("", "Slot 6 Symbol")
slotDat6 = input.string("", "Slot 6 Data")
slotSym7 = input.string("", "Slot 7 Symbol")
slotDat7 = input.string("", "Slot 7 Data")
slotSym8 = input.string("", "Slot 8 Symbol")
slotDat8 = input.string("", "Slot 8 Data")
slotSym9 = input.string("", "Slot 9 Symbol")
slotDat9 = input.string("", "Slot 9 Data")
slotSym10 = input.string("", "Slot 10 Symbol")
slotDat10 = input.string("", "Slot 10 Data")
showOnlyOnMatch = input.bool(true, "Show only when chart symbol matches a slot?")
labelOnRight = input.bool(true, "Show labels on right")
extendRight = input.bool(true, "Extend lines to the right")
lineWidth = input.int(2, "Line width", minval=1, maxval=4)
labelOffsetBars = input.int(30, "Label offset (bars to the right)", minval=5, maxval=300)
//===========================
// Helpers
//===========================
trim(s) =>
// Safe trim
str.trim(s)
containsCI(hay, needle) =>
str.contains(str.lower(hay), str.lower(needle))
// Decide color based on label keywords
levelColor(lbl) =>
// You can tune this mapping to match your old indicator’s palette
containsCI(lbl, "key delta") ? color.new(color.red, 0) :
containsCI(lbl, "gamma flip") ? color.new(color.fuchsia, 0) :
containsCI(lbl, "put wall") ? color.new(color.purple, 0) :
containsCI(lbl, "call wall") ? color.new(color.orange, 0) :
containsCI(lbl, "put dominate") ? color.new(color.yellow, 0) :
containsCI(lbl, "call dominate") ? color.new(color.teal, 0) :
containsCI(lbl, "implied movement") ? color.new(color.blue, 0) :
color.new(color.gray, 0)
//===========================
// Pick active slot by chart symbol
//===========================
chartSym = syminfo.ticker // e.g. "IREN" on most US stocks
getSlotData() =>
string sym = ""
string dat = ""
if chartSym == trim(slotSym1) and trim(slotSym1) != ""
sym := trim(slotSym1), dat := slotDat1
else if chartSym == trim(slotSym2) and trim(slotSym2) != ""
sym := trim(slotSym2), dat := slotDat2
else if chartSym == trim(slotSym3) and trim(slotSym3) != ""
sym := trim(slotSym3), dat := slotDat3
else if chartSym == trim(slotSym4) and trim(slotSym4) != ""
sym := trim(slotSym4), dat := slotDat4
else if chartSym == trim(slotSym5) and trim(slotSym5) != ""
sym := trim(slotSym5), dat := slotDat5
else if chartSym == trim(slotSym6) and trim(slotSym6) != ""
sym := trim(slotSym6), dat := slotDat6
else if chartSym == trim(slotSym7) and trim(slotSym7) != ""
sym := trim(slotSym7), dat := slotDat7
else if chartSym == trim(slotSym8) and trim(slotSym8) != ""
sym := trim(slotSym8), dat := slotDat8
else if chartSym == trim(slotSym9) and trim(slotSym9) != ""
sym := trim(slotSym9), dat := slotDat9
else if chartSym == trim(slotSym10) and trim(slotSym10) != ""
sym := trim(slotSym10), dat := slotDat10
[sym, dat]
//===========================
// Parse "label, value, label, value, ..."
//===========================
parsePairs(raw) =>
// Split by comma, then step through tokens 2 at a time.
// Expect format: label, number, label, number, ...
string[] t = str.split(raw, ",")
int n = array.size(t)
string[] outLabels = array.new_string()
float[] outValues = array.new_float()
for i = 0 to n - 1
array.set(t, i, trim(array.get(t, i)))
for i = 0 to n - 2
if i % 2 == 0
string lbl = array.get(t, i)
string valS = array.get(t, i + 1)
// Skip empty label/value
if lbl != "" and valS != ""
float v = str.tonumber(valS)
if not na(v)
// Optional: remove leading "SYMBOL:" prefix from label
// e.g. "IREN: Key Delta" -> "Key Delta"
string cleaned = lbl
int colonPos = str.pos(cleaned, ":")
if colonPos != -1
cleaned := trim(str.substring(cleaned, colonPos + 1, str.length(cleaned)))
array.push(outLabels, cleaned)
array.push(outValues, v)
[outLabels, outValues]
//===========================
// Drawing state
//===========================
var line[] lines = array.new_line()
var label[] labels = array.new_label()
var string lastRaw = ""
// Delete all existing drawings
clearAll() =>
for i = 0 to array.size(lines) - 1
line.delete(array.get(lines, i))
for i = 0 to array.size(labels) - 1
label.delete(array.get(labels, i))
array.clear(lines)
array.clear(labels)
// Draw levels
drawLevels(sym, raw) =>
[lbls, vals] = parsePairs(raw)
int m = array.size(lbls)
// Build on last bar only to reduce clutter and avoid heavy redraw
if barstate.islast
clearAll()
// If user wants strict symbol match, and no slot matched, show nothing
bool ok = (sym != "")
if not showOnlyOnMatch
ok := true
if ok
int x1 = bar_index
int x2 = bar_index + (extendRight ? 200 : 1)
for i = 0 to m - 1
string lbl = array.get(lbls, i)
float y = array.get(vals, i)
color c = levelColor(lbl)
// Line
line ln = line.new(x1, y, x2, y, extend=extendRight ? extend.right : extend.none, color=c, width=lineWidth)
array.push(lines, ln)
// Label (right side)
if labelOnRight
int lx = bar_index + labelOffsetBars
string text = lbl + " (" + str.tostring(y) + ")"
label la = label.new(lx, y, text=text, style=label.style_label_left, textcolor=color.white, color=color.new(c, 0))
array.push(labels, la)
//===========================
// Main
//===========================
[sym, raw] = getSlotData()
// If not matched but user wants to still show something, fallback to slot1
if not showOnlyOnMatch and sym == ""
sym := trim(slotSym1)
raw := slotDat1
// Redraw only when raw changes (or first run); still rebuild on last bar to keep labels aligned
if raw != lastRaw
lastRaw := raw
drawLevels(sym, raw)
Mã nguồn mở
Theo đúng tinh thần TradingView, tác giả của tập lệnh này đã công bố nó dưới dạng mã nguồn mở, để các nhà giao dịch có thể xem xét và xác minh chức năng. Chúc mừng tác giả! Mặc dù bạn có thể sử dụng miễn phí, hãy nhớ rằng việc công bố lại mã phải tuân theo Nội quy.
Thông báo miễn trừ trách nhiệm
Thông tin và các ấn phẩm này không nhằm mục đích, và không cấu thành, lời khuyên hoặc khuyến nghị về tài chính, đầu tư, giao dịch hay các loại khác do TradingView cung cấp hoặc xác nhận. Đọc thêm tại Điều khoản Sử dụng.
Mã nguồn mở
Theo đúng tinh thần TradingView, tác giả của tập lệnh này đã công bố nó dưới dạng mã nguồn mở, để các nhà giao dịch có thể xem xét và xác minh chức năng. Chúc mừng tác giả! Mặc dù bạn có thể sử dụng miễn phí, hãy nhớ rằng việc công bố lại mã phải tuân theo Nội quy.
Thông báo miễn trừ trách nhiệm
Thông tin và các ấn phẩm này không nhằm mục đích, và không cấu thành, lời khuyên hoặc khuyến nghị về tài chính, đầu tư, giao dịch hay các loại khác do TradingView cung cấp hoặc xác nhận. Đọc thêm tại Điều khoản Sử dụng.