1Copy the scriptPress Copy script above, or the copy button on the code below.
2Open the Pine EditorOpen a TradingView chart and choose Pine Editor at the bottom of the screen.
3Paste over the templateCreate a new indicator, select all of the template text and paste. Press Save and give it a name.
4Add it to the chartPress Add to chart, then adjust the settings with the gear icon next to its name.
Source Code
760 lines of Pine Script v5 from src/harmonic-pattern-v5.pine, published under MIT. Keep the author's credit and licence lines when you reuse it.
harmonic-pattern-v5.pine
//@version=5
indicator("Harmonik Desen - Manuel ve Otomatik", overlay=true, max_lines_count=500, max_labels_count=500, max_bars_back=500)
// =========================================
// TÜR TANIMLARI
// =========================================
type userPoint
float price
int time
int bar
type HarmonicPattern
string name
float xab_min
float xab_max
float abc_min
float abc_max
float bcd_min
float bcd_max
float xad_min
float xad_max
type DPrediction
string pattern_name
float d_price
float confidence
color pattern_color
float xad_ratio
type AutoPattern
int xBar
float xPrice
int aBar
float aPrice
int bBar
float bPrice
int cBar
float cPrice
int dBar
float dPrice
bool isBullish
string patternType
float score
bool isComplete
// =========================================
// GLOBAL DEĞİŞKENLER
// =========================================
var line[] lines = array.new_line(0)
var label[] labels = array.new_label(0)
var box[] boxes = array.new_box(0)
var table infoTable = table.new(position.top_right, 2, 16, bgcolor=color.new(color.black, 80))
var AutoPattern[] autoPatterns = array.new<AutoPattern>()
var line[] autoLines = array.new_line(0)
var label[] autoLabels = array.new_label(0)
// =========================================
// GİRDİLER
// =========================================
mode = input.string("Otomatik", "Çalışma Modu", options=["Manuel", "Otomatik", "Her İkisi"], group="Genel Ayarlar")
xP = input.price(0, "X", group="Manuel XABC Noktaları", inline="X", confirm=true)
xT = input.time(0, "", group="Manuel XABC Noktaları", inline="X", confirm=true)
aP = input.price(0, "A", group="Manuel XABC Noktaları", inline="A", confirm=true)
aT = input.time(0, "", group="Manuel XABC Noktaları", inline="A", confirm=true)
bP = input.price(0, "B", group="Manuel XABC Noktaları", inline="B", confirm=true)
bT = input.time(0, "", group="Manuel XABC Noktaları", inline="B", confirm=true)
cP = input.price(0, "C", group="Manuel XABC Noktaları", inline="C", confirm=true)
cT = input.time(0, "", group="Manuel XABC Noktaları", inline="C", confirm=true)
dP = input.price(0, "D", group="Manuel XABC Noktaları", inline="D", confirm=true)
dT = input.time(0, "", group="Manuel XABC Noktaları", inline="D", confirm=true)
auto_lookback = input.int(100, "Geriye Bakış Periyodu", minval=50, maxval=500, group="Otomatik Tespit")
auto_min_score = input.float(60.0, "Minimum Skor %", minval=0, maxval=100, group="Otomatik Tespit")
auto_show_potential = input.bool(true, "Potansiyel Desenleri Göster", group="Otomatik Tespit")
pivot_length = input.int(5, "Pivot Uzunluğu", minval=3, maxval=20, group="Otomatik Tespit")
use_manual_d = input.bool(false, "D Noktasını Manuel Kullan", group="D Noktası Ayarları")
show_all_d_predictions = input.bool(true, "Tüm D Tahminlerini Göster", group="D Noktası Ayarları")
min_confidence = input.float(50.0, "Minimum Güven Skoru %", minval=0, maxval=100, group="D Noktası Ayarları")
show_d_zone = input.bool(true, "D Hedef Bölgesini Göster", group="Görüntüleme")
show_projections = input.bool(true, "C'den D'ye İzdüşüm Çizgileri", group="Görüntüleme")
show_ratios = input.bool(true, "Harmonik Oranları Göster", group="Görüntüleme")
show_pattern_info = input.bool(true, "Desen Bilgi Tablosunu Göster", group="Görüntüleme")
highlight_best_d = input.bool(true, "En İyi D Tahminini Vurgula", group="Görüntüleme")
tolerance = input.float(0.15, "Desen Toleransı", minval=0.01, maxval=0.3, step=0.01, group="Desen Tanıma")
pctAsym = input.float(250.0, "İzin verilen bacak uzunluğu asimetrisi %", step=1.0, minval=0.0, maxval=1000.0, group="Desen Tanıma")
c_bull_manual = input.color(color.new(color.green, 20), "Manuel Boğa Rengi", group="Renkler")
c_bear_manual = input.color(color.new(color.red, 20), "Manuel Ayı Rengi", group="Renkler")
c_bull_auto = input.color(color.new(color.blue, 40), "Otomatik Boğa Rengi", group="Renkler")
c_bear_auto = input.color(color.new(color.orange, 40), "Otomatik Ayı Rengi", group="Renkler")
// =========================================
// HARMONİK DESEN TANIMLARI
// =========================================
f_define_patterns() =>
patterns = array.new<HarmonicPattern>()
array.push(patterns, HarmonicPattern.new("Gartley", 0.618, 0.618, 0.382, 0.886, 1.13, 1.618, 0.786, 0.786))
array.push(patterns, HarmonicPattern.new("Bat", 0.382, 0.50, 0.382, 0.886, 1.618, 2.618, 0.886, 0.886))
array.push(patterns, HarmonicPattern.new("Butterfly", 0.786, 0.786, 0.382, 0.886, 1.618, 2.24, 1.27, 1.27))
array.push(patterns, HarmonicPattern.new("Crab", 0.382, 0.618, 0.382, 0.886, 2.618, 3.618, 1.618, 1.618))
array.push(patterns, HarmonicPattern.new("Deep Crab", 0.886, 0.886, 0.382, 0.886, 2.0, 3.618, 1.618, 1.618))
array.push(patterns, HarmonicPattern.new("Shark", 0.446, 0.618, 1.13, 1.618, 1.618, 2.24, 0.886, 1.13))
array.push(patterns, HarmonicPattern.new("Cypher", 0.382, 0.618, 1.13, 1.41, 1.27, 2.00, 0.786, 0.786))
patterns
f_get_pattern_color(pattern_name) =>
switch pattern_name
"Gartley" => color.green
"Bat" => color.blue
"Butterfly" => color.orange
"Crab" => color.red
"Deep Crab" => color.maroon
"Shark" => color.purple
"Cypher" => color.teal
=> color.gray
// =========================================
// TEMİZLEME
// =========================================
f_clear_all() =>
for l in lines
line.delete(l)
for lbl in labels
label.delete(lbl)
for b in boxes
box.delete(b)
array.clear(lines)
array.clear(labels)
array.clear(boxes)
f_clear_auto() =>
for l in autoLines
line.delete(l)
for lbl in autoLabels
label.delete(lbl)
array.clear(autoLines)
array.clear(autoLabels)
// =========================================
// ORAN HESAPLAMA
// =========================================
f_calculate_ratios(x, a, b, c, d) =>
xa = math.abs(a - x)
ab = math.abs(b - a)
bc = math.abs(c - b)
cd = math.abs(d - c)
ad = math.abs(d - a)
xab = xa != 0 ? ab / xa : 0
abc = ab != 0 ? bc / ab : 0
bcd = bc != 0 ? cd / bc : 0
xad = xa != 0 ? ad / xa : 0
[xab, abc, bcd, xad]
// =========================================
// OTOMATİK DESEN TESPİT FONKSİYONLARI
// =========================================
f_isPivotHigh(src, left, right, index) =>
isHigh = true
for i = 1 to left
if index + i <= bar_index and src[index + i] >= src[index]
isHigh := false
break
if isHigh
for i = 1 to right
if index - i >= 0 and src[index - i] >= src[index]
isHigh := false
break
isHigh
f_isPivotLow(src, left, right, index) =>
isLow = true
for i = 1 to left
if index + i <= bar_index and src[index + i] <= src[index]
isLow := false
break
if isLow
for i = 1 to right
if index - i >= 0 and src[index - i] <= src[index]
isLow := false
break
isLow
f_test_symmetry(leg1, leg2, leg3, leg4, asymPct) =>
legs = array.from(leg1, leg2, leg3, leg4)
avgLen = array.avg(legs)
valid = true
if avgLen > 0
for i = 0 to 3
legLen = array.get(legs, i)
if math.abs(legLen - avgLen) / avgLen > asymPct / 100
valid := false
break
valid
f_check_harmonic_ratios(xab, abc, bcd, xad, pattern, tol) =>
xab_valid = xab >= pattern.xab_min * (1 - tol) and xab <= pattern.xab_max * (1 + tol)
abc_valid = abc >= pattern.abc_min * (1 - tol) and abc <= pattern.abc_max * (1 + tol)
bcd_valid = bcd >= pattern.bcd_min * (1 - tol) and bcd <= pattern.bcd_max * (1 + tol)
xad_valid = xad >= pattern.xad_min * (1 - tol) and xad <= pattern.xad_max * (1 + tol)
score = 0.0
if xab_valid
score += 25
if abc_valid
score += 25
if bcd_valid
score += 25
if xad_valid
score += 25
[xab_valid and abc_valid and bcd_valid and xad_valid, score]
f_validate_pattern(xBar, xPrice, aBar, aPrice, bBar, bPrice, cBar, cPrice, dBar, dPrice, isBullish) =>
patterns = f_define_patterns()
validPatterns = array.new<string>()
patternScores = array.new<float>()
[xab, abc, bcd, xad] = f_calculate_ratios(xPrice, aPrice, bPrice, cPrice, dPrice)
for pattern in patterns
[isValid, score] = f_check_harmonic_ratios(xab, abc, bcd, xad, pattern, tolerance)
if isValid and score >= auto_min_score
array.push(validPatterns, pattern.name)
array.push(patternScores, score)
[validPatterns, patternScores]
f_find_auto_patterns() =>
lookback = math.min(auto_lookback, 500)
highs = array.new<int>()
lows = array.new<int>()
for i = pivot_length to lookback - pivot_length
if i <= bar_index
if f_isPivotHigh(high, pivot_length, pivot_length, i)
array.push(highs, i)
if f_isPivotLow(low, pivot_length, pivot_length, i)
array.push(lows, i)
// Debug: Pivot sayılarını tabloya ekle
if barstate.islast
table.cell(infoTable, 0, 15, "Pivot Highs/Lows", bgcolor=color.new(color.gray, 80), text_color=color.white)
table.cell(infoTable, 1, 15, str.tostring(array.size(highs)) + "/" + str.tostring(array.size(lows)), text_color=color.white)
// Pivot sayısı kontrolü
if array.size(lows) >= 3 and array.size(highs) >= 2
// Boğa desenleri (X=low, A=high, B=low, C=high, D=low)
for d = 0 to math.min(array.size(lows) - 1, 10)
dIdx = array.get(lows, d)
dBar = bar_index - dIdx
dPrice = low[dIdx]
for c = 0 to math.min(array.size(highs) - 1, 10)
cIdx = array.get(highs, c)
if cIdx > dIdx
cBar = bar_index - cIdx
cPrice = high[cIdx]
for b = d + 1 to math.min(array.size(lows) - 2, 15)
if b >= array.size(lows)
break
bIdx = array.get(lows, b)
if bIdx > cIdx
bBar = bar_index - bIdx
bPrice = low[bIdx]
xa = math.abs(cPrice - bPrice)
ab = math.abs(bPrice - cPrice)
xab = xa != 0 ? ab / xa : 0
if not (xab >= 0.382 * (1 - tolerance) and xab <= 1.618 * (1 + tolerance))
continue
for a = c + 1 to math.min(array.size(highs) - 2, 15)
if a >= array.size(highs)
break
aIdx = array.get(highs, a)
if aIdx > bIdx
aBar = bar_index - aIdx
aPrice = high[aIdx]
for x = b + 1 to math.min(array.size(lows) - 2, 20)
if x >= array.size(lows)
break
xIdx = array.get(lows, x)
if xIdx > aIdx
xBar = bar_index - xIdx
xPrice = low[xIdx]
if not f_test_symmetry(aBar-xBar, bBar-aBar, cBar-bBar, dBar-cBar, pctAsym)
continue
[validPatterns, patternScores] = f_validate_pattern(xBar, xPrice, aBar, aPrice, bBar, bPrice, cBar, cPrice, dBar, dPrice, true)
if array.size(validPatterns) > 0
maxScore = array.max(patternScores)
bestPattern = array.get(validPatterns, array.indexof(patternScores, maxScore))
pattern = AutoPattern.new()
pattern.xBar := xBar
pattern.xPrice := xPrice
pattern.aBar := aBar
pattern.aPrice := aPrice
pattern.bBar := bBar
pattern.bPrice := bPrice
pattern.cBar := cBar
pattern.cPrice := cPrice
pattern.dBar := dBar
pattern.dPrice := dPrice
pattern.isBullish := true
pattern.patternType := bestPattern
pattern.score := maxScore
pattern.isComplete := true
exists = false
for p in autoPatterns
if p.xBar == xBar and p.aBar == aBar and p.bBar == bBar and p.cBar == cBar and p.dBar == dBar
exists := true
break
if not exists
array.push(autoPatterns, pattern)
// Ayı desenleri (X=high, A=low, B=high, C=low, D=high)
for d = 0 to math.min(array.size(highs) - 1, 10)
dIdx = array.get(highs, d)
dBar = bar_index - dIdx
dPrice = high[dIdx]
for c = 0 to math.min(array.size(lows) - 1, 10)
cIdx = array.get(lows, c)
if cIdx > dIdx
cBar = bar_index - cIdx
cPrice = low[cIdx]
for b = d + 1 to math.min(array.size(highs) - 2, 15)
if b >= array.size(highs)
break
bIdx = array.get(highs, b)
if bIdx > cIdx
bBar = bar_index - bIdx
bPrice = high[bIdx]
xa = math.abs(cPrice - bPrice)
ab = math.abs(bPrice - cPrice)
xab = xa != 0 ? ab / xa : 0
if not (xab >= 0.382 * (1 - tolerance) and xab <= 1.618 * (1 + tolerance))
continue
for a = c + 1 to math.min(array.size(lows) - 2, 15)
if a >= array.size(lows)
break
aIdx = array.get(lows, a)
if aIdx > bIdx
aBar = bar_index - aIdx
aPrice = low[aIdx]
for x = b + 1 to math.min(array.size(highs) - 2, 20)
if x >= array.size(highs)
break
xIdx = array.get(highs, x)
if xIdx > aIdx
xBar = bar_index - xIdx
xPrice = high[xIdx]
if not f_test_symmetry(aBar-xBar, bBar-aBar, cBar-bBar, dBar-cBar, pctAsym)
continue
[validPatterns, patternScores] = f_validate_pattern(xBar, xPrice, aBar, aPrice, bBar, bPrice, cBar, cPrice, dBar, dPrice, false)
if array.size(validPatterns) > 0
maxScore = array.max(patternScores)
bestPattern = array.get(validPatterns, array.indexof(patternScores, maxScore))
pattern = AutoPattern.new()
pattern.xBar := xBar
pattern.xPrice := xPrice
pattern.aBar := aBar
pattern.aPrice := aPrice
pattern.bBar := bBar
pattern.bPrice := bPrice
pattern.cBar := cBar
pattern.cPrice := cPrice
pattern.dBar := dBar
pattern.dPrice := dPrice
pattern.isBullish := false
pattern.patternType := bestPattern
pattern.score := maxScore
pattern.isComplete := true
exists = false
for p in autoPatterns
if p.xBar == xBar and p.aBar == aBar and p.bBar == bBar and p.cBar == cBar and p.dBar == dBar
exists := true
break
if not exists
array.push(autoPatterns, pattern)
// Potansiyel desenler
if auto_show_potential
for c = 0 to math.min(array.size(highs) - 1, 5)
cIdx = array.get(highs, c)
cBar = bar_index - cIdx
cPrice = high[cIdx]
for b = 0 to math.min(array.size(lows) - 1, 10)
bIdx = array.get(lows, b)
if bIdx > cIdx
bBar = bar_index - bIdx
bPrice = low[bIdx]
xa = math.abs(cPrice - bPrice)
ab = math.abs(bPrice - cPrice)
xab = xa != 0 ? ab / xa : 0
if not (xab >= 0.382 * (1 - tolerance) and xab <= 1.618 * (1 + tolerance))
continue
for a = c + 1 to math.min(array.size(highs) - 2, 15)
if a >= array.size(highs)
break
aIdx = array.get(highs, a)
if aIdx > bIdx
aBar = bar_index - aIdx
aPrice = high[aIdx]
for x = b + 1 to math.min(array.size(lows) - 2, 20)
if x >= array.size(lows)
break
xIdx = array.get(lows, x)
if xIdx > aIdx
xBar = bar_index - xIdx
xPrice = low[xIdx]
xa = math.abs(aPrice - xPrice)
ab = math.abs(bPrice - aPrice)
bc = math.abs(cPrice - bPrice)
xab = xa != 0 ? ab / xa : 0
abc = ab != 0 ? bc / ab : 0
if xab > 0 and abc > 0
patterns = f_define_patterns()
for pat in patterns
xab_valid = xab >= pat.xab_min * (1 - tolerance) and xab <= pat.xab_max * (1 + tolerance)
abc_valid = abc >= pat.abc_min * (1 - tolerance) and abc <= pat.abc_max * (1 + tolerance)
if xab_valid and abc_valid
pattern = AutoPattern.new()
pattern.xBar := xBar
pattern.xPrice := xPrice
pattern.aBar := aBar
pattern.aPrice := aPrice
pattern.bBar := bBar
pattern.bPrice := bPrice
pattern.cBar := cBar
pattern.cPrice := cPrice
pattern.dBar := na
pattern.dPrice := na
pattern.isBullish := true
pattern.patternType := pat.name
pattern.score := 50.0
pattern.isComplete := false
exists = false
for p in autoPatterns
if p.xBar == xBar and p.aBar == aBar and p.bBar == bBar and p.cBar == cBar and not p.isComplete
exists := true
break
if not exists
array.push(autoPatterns, pattern)
break
// =========================================
// GÜVEN SKORU HESAPLAMA
// =========================================
f_calculate_pattern_confidence(xab, abc, pattern) =>
xab_mid = (pattern.xab_min + pattern.xab_max) / 2
xab_range = pattern.xab_max - pattern.xab_min
xab_deviation = xab_range > 0 ? math.abs(xab - xab_mid) / (xab_range / 2) : 1
xab_score = math.max(0, 100 * (1 - xab_deviation))
abc_mid = (pattern.abc_min + pattern.abc_max) / 2
abc_range = pattern.abc_max - pattern.abc_min
abc_deviation = abc_range > 0 ? math.abs(abc - abc_mid) / (abc_range / 2) : 1
abc_score = math.max(0, 100 * (1 - abc_deviation))
confidence = (xab_score * 0.6 + abc_score * 0.4)
confidence
// =========================================
// ÇOKLU D TAHMİNİ
// =========================================
f_calculate_multiple_d_predictions(x, a, b, c) =>
predictions = array.new<DPrediction>()
patterns = f_define_patterns()
xa = math.abs(a - x)
ab = math.abs(b - a)
bc = math.abs(c - b)
xab = xa != 0 ? ab / xa : 0
abc = ab != 0 ? bc / ab : 0
trend_up = a > x
for pattern in patterns
confidence = f_calculate_pattern_confidence(xab, abc, pattern)
if confidence >= min_confidence
ideal_xad = (pattern.xad_min + pattern.xad_max) / 2
ad_distance = xa * ideal_xad
d_price = trend_up ? a - ad_distance : a + ad_distance
prediction = DPrediction.new(pattern.name, d_price, confidence, f_get_pattern_color(pattern.name), ideal_xad)
array.push(predictions, prediction)
n = array.size(predictions)
if n > 1
for i = 0 to n - 2
for j = 0 to n - i - 2
if array.get(predictions, j).confidence < array.get(predictions, j + 1).confidence
temp = array.get(predictions, j)
array.set(predictions, j, array.get(predictions, j + 1))
array.set(predictions, j + 1, temp)
predictions
// =========================================
// OTOMATİK DESEN ÇİZİMİ
// =========================================
f_draw_auto_pattern(pattern) =>
lineColor = pattern.isBullish ? c_bull_auto : c_bear_auto
xa_line = line.new(pattern.xBar, pattern.xPrice, pattern.aBar, pattern.aPrice, color=lineColor, width=2)
ab_line = line.new(pattern.aBar, pattern.aPrice, pattern.bBar, pattern.bPrice, color=lineColor, width=2)
bc_line = line.new(pattern.bBar, pattern.bPrice, pattern.cBar, pattern.cPrice, color=lineColor, width=2)
array.push(autoLines, xa_line)
array.push(autoLines, ab_line)
array.push(autoLines, bc_line)
if pattern.isComplete
cd_line = line.new(pattern.cBar, pattern.cPrice, pattern.dBar, pattern.dPrice, color=lineColor, width=2)
array.push(autoLines, cd_line)
xb_line = line.new(pattern.xBar, pattern.xPrice, pattern.bBar, pattern.bPrice, color=color.new(lineColor, 50), width=1, style=line.style_dashed)
ac_line = line.new(pattern.aBar, pattern.aPrice, pattern.cBar, pattern.cPrice, color=color.new(lineColor, 50), width=1, style=line.style_dotted)
array.push(autoLines, xb_line)
array.push(autoLines, ac_line)
if pattern.isComplete
bd_line = line.new(pattern.bBar, pattern.bPrice, pattern.dBar, pattern.dPrice, color=color.new(lineColor, 50), width=1, style=line.style_dashed)
xd_line = line.new(pattern.xBar, pattern.xPrice, pattern.dBar, pattern.dPrice, color=color.new(lineColor, 50), width=1, style=line.style_dotted)
array.push(autoLines, bd_line)
array.push(autoLines, xd_line)
x_label = label.new(pattern.xBar, pattern.xPrice, "X", style=label.style_circle, color=color.white, textcolor=color.black, size=size.tiny)
a_label = label.new(pattern.aBar, pattern.aPrice, "A", style=label.style_circle, color=color.white, textcolor=color.black, size=size.tiny)
b_label = label.new(pattern.bBar, pattern.bPrice, "B", style=label.style_circle, color=color.white, textcolor=color.black, size=size.tiny)
c_label = label.new(pattern.cBar, pattern.cPrice, "C", style=label.style_circle, color=color.white, textcolor=color.black, size=size.tiny)
array.push(autoLabels, x_label)
array.push(autoLabels, a_label)
array.push(autoLabels, b_label)
array.push(autoLabels, c_label)
if pattern.isComplete
d_label = label.new(pattern.dBar, pattern.dPrice, "D", style=label.style_circle, color=color.white, textcolor=color.black, size=size.tiny)
array.push(autoLabels, d_label)
labelText = pattern.patternType + " (" + str.tostring(pattern.score, "#.#") + "%)"
if not pattern.isComplete
labelText := "Potansiyel " + labelText
pattern_label = label.new(pattern.cBar, pattern.cPrice, labelText, style=label.style_label_down, color=color.new(lineColor, 80), textcolor=color.white, size=size.small)
array.push(autoLabels, pattern_label)
if not pattern.isComplete and auto_show_potential
predictions = f_calculate_multiple_d_predictions(pattern.xPrice, pattern.aPrice, pattern.bPrice, pattern.cPrice)
if array.size(predictions) > 0
best_pred = array.get(predictions, 0)
d_line = line.new(pattern.cBar, pattern.cPrice, pattern.cBar + 20, best_pred.d_price, color=color.new(lineColor, 50), width=2, style=line.style_dashed)
array.push(autoLines, d_line)
d_label = label.new(pattern.cBar + 20, best_pred.d_price, "D?", style=label.style_circle, color=color.purple, textcolor=color.white, size=size.tiny)
array.push(autoLabels, d_label)
// =========================================
// BAR İNDEKS BULMA
// =========================================
f_resolveBarIndex(array<userPoint> pts) =>
for offset = 0 to 999
for p in pts
if na(p.bar) and time[offset] == p.time
p.bar := bar_index - offset
// =========================================
// D BÖLGESİ ÇİZİMİ - ÇOKLU
// =========================================
f_draw_multiple_d_zones(predictions, cBar, c) =>
if array.size(predictions) > 0
best_prediction = array.get(predictions, 0)
all_d_prices = array.new<float>()
for pred in predictions
array.push(all_d_prices, pred.d_price)
d_min = array.min(all_d_prices)
d_max = array.max(all_d_prices)
if show_d_zone
box_left = cBar + 5
box_right = cBar + 30
prz_box = box.new(box_left, d_max, box_right, d_min, border_color=color.purple, border_width=2, bgcolor=color.new(color.purple, 95))
box.set_text(prz_box, "D Hedef Bölgesi\n" + str.tostring(d_min, "#.##") + " - " + str.tostring(d_max, "#.##"))
box.set_text_color(prz_box, color.white)
box.set_text_halign(prz_box, text.align_center)
box.set_text_size(prz_box, size.small)
array.push(boxes, prz_box)
max_predictions_to_show = show_all_d_predictions ? array.size(predictions) : math.min(3, array.size(predictions))
for i = 0 to max_predictions_to_show - 1
pred = array.get(predictions, i)
line_width = (i == 0 and highlight_best_d) ? 3 : 1
line_style = i == 0 ? line.style_solid : line.style_dashed
level_line = line.new(cBar + 5, pred.d_price, cBar + 30, pred.d_price, color=pred.pattern_color, width=line_width, style=line_style)
array.push(lines, level_line)
label_text = pred.pattern_name + "\n" + str.tostring(pred.confidence, "#") + "%" + "\n" + "XAD: " + str.tostring(pred.xad_ratio, "#.###")
level_label = label.new(cBar + 32, pred.d_price, label_text, style=label.style_label_left, color=color.new(pred.pattern_color, 80), textcolor=color.white, size=size.small)
array.push(labels, level_label)
if show_projections
proj_line = line.new(cBar, c, cBar + 5, pred.d_price, color=color.new(pred.pattern_color, 70), width=1, style=line.style_dotted)
array.push(lines, proj_line)
// =========================================
// MANUEL DESEN ÇİZİMİ
// =========================================
f_draw_pattern(x, a, b, c, d, xBar, aBar, bBar, cBar, dBar, isAutoD) =>
lineColor = a > x ? c_bull_manual : c_bear_manual
array.push(lines, line.new(xBar, x, aBar, a, color=lineColor, width=2))
array.push(lines, line.new(aBar, a, bBar, b, color=lineColor, width=2))
array.push(lines, line.new(bBar, b, cBar, c, color=lineColor, width=2))
cd_line_style = isAutoD ? line.style_dashed : line.style_solid
array.push(lines, line.new(cBar, c, dBar, d, color=lineColor, width=2, style=cd_line_style))
array.push(lines, line.new(xBar, x, bBar, b, color=color.new(lineColor, 50), width=1, style=line.style_dashed))
array.push(lines, line.new(aBar, a, cBar, c, color=color.new(lineColor, 50), width=1, style=line.style_dotted))
if not na(d)
array.push(lines, line.new(bBar, b, dBar, d, color=color.new(lineColor, 50), width=1, style=line.style_dashed))
array.push(lines, line.new(xBar, x, dBar, d, color=color.new(lineColor, 50), width=1, style=line.style_dotted))
array.push(labels, label.new(xBar, x, "X", style=label.style_circle, color=color.white, textcolor=color.black, size=size.tiny))
array.push(labels, label.new(aBar, a, "A", style=label.style_circle, color=color.white, textcolor=color.black, size=size.tiny))
array.push(labels, label.new(bBar, b, "B", style=label.style_circle, color=color.white, textcolor=color.black, size=size.tiny))
array.push(labels, label.new(cBar, c, "C", style=label.style_circle, color=color.white, textcolor=color.black, size=size.tiny))
d_color = isAutoD ? color.purple : color.yellow
d_text = isAutoD ? "D\n(Auto)" : "D"
array.push(labels, label.new(dBar, d, d_text, style=label.style_circle, color=d_color, textcolor=color.white, size=size.tiny))
// =========================================
// ORAN ETİKETLERİ
// =========================================
f_draw_ratio_labels(x, a, b, c, d, xBar, aBar, bBar, cBar, dBar) =>
if show_ratios
[xab, abc, bcd, xad] = f_calculate_ratios(x, a, b, c, d)
xab_x = math.round((xBar + bBar) / 2)
xab_y = (x + b) / 2
xab_label = label.new(xab_x, xab_y, "XAB\n" + str.tostring(xab, "#.###"), style=label.style_label_center, color=color.new(color.gray, 80), textcolor=color.white, size=size.tiny)
array.push(labels, xab_label)
abc_x = math.round((aBar + cBar) / 2)
abc_y = (a + c) / 2
abc_label = label.new(abc_x, abc_y, "ABC\n" + str.tostring(abc, "#.###"), style=label.style_label_center, color=color.new(color.gray, 80), textcolor=color.white, size=size.tiny)
array.push(labels, abc_label)
bcd_x = math.round((bBar + dBar) / 2)
bcd_y = (b + d) / 2
bcd_label = label.new(bcd_x, bcd_y, "BCD\n" + str.tostring(bcd, "#.###"), style=label.style_label_center, color=color.new(color.gray, 80), textcolor=color.white, size=size.tiny)
array.push(labels, bcd_label)
xad_x = math.round((xBar + dBar) / 2)
xad_y = (x + d) / 2
xad_label = label.new(xad_x, xad_y, "XAD\n" + str.tostring(xad, "#.###"), style=label.style_label_center, color=color.new(color.gray, 80), textcolor=color.white, size=size.tiny)
array.push(labels, xad_label)
// =========================================
// ANA MANTIK
// =========================================
if (mode == "Otomatik" or mode == "Her İkisi") and barstate.isconfirmed
f_clear_auto()
array.clear(autoPatterns)
f_find_auto_patterns()
n = array.size(autoPatterns)
if n > 1
for i = 0 to n - 2
for j = 0 to n - i - 2
if array.get(autoPatterns, j).score < array.get(autoPatterns, j + 1).score
temp = array.get(autoPatterns, j)
array.set(autoPatterns, j, array.get(autoPatterns, j + 1))
array.set(autoPatterns, j + 1, temp)
maxPatterns = math.min(10, array.size(autoPatterns))
if maxPatterns > 0
for i = 0 to maxPatterns - 1
pattern = array.get(autoPatterns, i)
f_draw_auto_pattern(pattern)
if (mode == "Manuel" or mode == "Her İkisi") and barstate.islast
if xP > 0 and aP > 0 and bP > 0 and cP > 0
f_clear_all()
xPoint = userPoint.new(xP, xT, na)
aPoint = userPoint.new(aP, aT, na)
bPoint = userPoint.new(bP, bT, na)
cPoint = userPoint.new(cP, cT, na)
points = array.new<userPoint>(0)
array.push(points, xPoint)
array.push(points, aPoint)
array.push(points, bPoint)
array.push(points, cPoint)
userPoint dPoint = na
if dP > 0 and use_manual_d
dPoint := userPoint.new(dP, dT, na)
array.push(points, dPoint)
f_resolveBarIndex(points)
isAutoD = not use_manual_d or dP == 0
float finalD = dP
int dBar = na
predictions = f_calculate_multiple_d_predictions(xP, aP, bP, cP)
if isAutoD
if array.size(predictions) > 0
best_pred = array.get(predictions, 0)
finalD := best_pred.d_price
dBar := cPoint.bar + 20
if not na(cPoint.bar) and not use_manual_d
f_draw_multiple_d_zones(predictions, cPoint.bar, cP)
else
xa = math.abs(aP - xP)
trend_up = aP > xP
finalD := trend_up ? aP - xa * 0.786 : aP + xa * 0.786
dBar := cPoint.bar + 20
else
if not na(dPoint) and dP > 0
dBar := dPoint.bar
finalD := dP
if not na(xPoint.bar) and not na(aPoint.bar) and not na(bPoint.bar) and not na(cPoint.bar) and not na(dBar)
f_draw_pattern(xP, aP, bP, cP, finalD, xPoint.bar, aPoint.bar, bPoint.bar, cPoint.bar, dBar, isAutoD)
f_draw_ratio_labels(xP, aP, bP, cP, finalD, xPoint.bar, aPoint.bar, bPoint.bar, cPoint.bar, dBar)
if show_pattern_info and barstate.islast
table.clear(infoTable, 0, 0, 1, 15)
table.cell(infoTable, 0, 0, "Harmonik Analiz", bgcolor=color.new(color.blue, 50), text_color=color.white)
table.cell(infoTable, 1, 0, mode, bgcolor=color.new(color.blue, 50), text_color=color.white)
if mode == "Otomatik" or mode == "Her İkisi"
table.cell(infoTable, 0, 1, "Bulunan Desenler", bgcolor=color.new(color.gray, 80), text_color=color.white)
table.cell(infoTable, 1, 1, str.tostring(array.size(autoPatterns)), bgcolor=color.new(color.gray, 80), text_color=color.white)
if array.size(autoPatterns) > 0
table.cell(infoTable, 0, 2, "Desen", text_color=color.white)
table.cell(infoTable, 1, 2, "Skor %", text_color=color.white)
maxShow = math.min(10, array.size(autoPatterns))
for i = 0 to maxShow - 1
if i < array.size(autoPatterns)
pattern = array.get(autoPatterns, i)
row = 3 + i
dirSymbol = pattern.isBullish ? "↑" : "↓"
statusText = pattern.isComplete ? "" : " (P)"
table.cell(infoTable, 0, row, dirSymbol + " " + pattern.patternType + statusText, text_color=pattern.isBullish ? color.green : color.red)
table.cell(infoTable, 1, row, str.tostring(pattern.score, "#.#"), text_color=color.white)
else
table.cell(infoTable, 0, 2, "Desen bulunamadı", text_color=color.orange)
table.cell(infoTable, 1, 2, "-", text_color=color.orange)
if mode == "Manuel" or mode == "Her İkisi"
startRow = mode == "Her İkisi" ? 14 : 1
if xP > 0 and aP > 0 and bP > 0 and cP > 0
xa = math.abs(aP - xP)
ab = math.abs(bP - aP)
bc = math.abs(cP - bP)
xab = xa != 0 ? ab / xa : 0
abc = ab != 0 ? bc / ab : 0
table.cell(infoTable, 0, startRow, "Manuel Oranlar", bgcolor=color.new(color.gray, 80), text_color=color.white)
table.cell(infoTable, 1, startRow, "", bgcolor=color.new(color.gray, 80))
table.cell(infoTable, 0, startRow + 1, "XAB", text_color=color.white)
table.cell(infoTable, 1, startRow + 1, str.tostring(xab, "#.###"), text_color=color.yellow)
table.cell(infoTable, 0, startRow + 2, "ABC", text_color=color.white)
table.cell(infoTable, 1, startRow + 2, str.tostring(abc, "#.###"), text_color=color.yellow)
if dP > 0 or not use_manual_d
predictions = f_calculate_multiple_d_predictions(xP, aP, bP, cP)
finalD = dP
if not use_manual_d and array.size(predictions) > 0
best_pred = array.get(predictions, 0)
finalD := best_pred.d_price
if finalD > 0
cd = math.abs(finalD - cP)
ad = math.abs(finalD - aP)
bcd = bc != 0 ? cd / bc : 0
xad = xa != 0 ? ad / xa : 0
table.cell(infoTable, 0, startRow + 3, "BCD", text_color=color.white)
table.cell(infoTable, 1, startRow + 3, str.tostring(bcd, "#.###"), text_color=color.yellow)
table.cell(infoTable, 0, startRow + 4, "XAD", text_color=color.white)
table.cell(infoTable, 1, startRow + 4, str.tostring(xad, "#.###"), text_color=color.yellow)
patterns = f_define_patterns()
detectedPatterns = array.new<string>()
for pattern in patterns
xab_valid = xab >= pattern.xab_min * (1 - tolerance) and xab <= pattern.xab_max * (1 + tolerance)
abc_valid = abc >= pattern.abc_min * (1 - tolerance) and abc <= pattern.abc_max * (1 + tolerance)
bcd_valid = bcd >= pattern.bcd_min * (1 - tolerance) and bcd <= pattern.bcd_max * (1 + tolerance)
xad_valid = xad >= pattern.xad_min * (1 - tolerance) and xad <= pattern.xad_max * (1 + tolerance)
if xab_valid and abc_valid and bcd_valid and xad_valid
array.push(detectedPatterns, pattern.name)
if array.size(detectedPatterns) > 0
table.cell(infoTable, 0, startRow + 5, "Tespit:", text_color=color.white)
detectedText = ""
for i = 0 to math.min(array.size(detectedPatterns) - 1, 2)
if i > 0
detectedText += ", "
detectedText += array.get(detectedPatterns, i)
table.cell(infoTable, 1, startRow + 5, detectedText, text_color=color.lime)
else
table.cell(infoTable, 0, startRow, "Manuel nokta yok", text_color=color.orange)
table.cell(infoTable, 1, startRow, "-", text_color=color.orange)
// Uyarılar
if barstate.islast and array.size(autoPatterns) > 0
for i = 0 to math.min(array.size(autoPatterns) - 1, 5)
pattern = array.get(autoPatterns, i)
if pattern.isComplete
d_distance = math.abs(close - pattern.dPrice)
d_percent = d_distance / pattern.dPrice * 100
if d_percent < 1.0
alert_message = (pattern.isBullish ? "BOĞA " : "AYI ") + pattern.patternType + " deseni D noktasına yakın! Fiyat: " + str.tostring(close)
alert(alert_message, alert.freq_once_per_bar)
Overview
In automatic mode it scans pivots over a lookback window and scores each match against a minimum percentage; in manual mode the user picks the X, A, B, C and D points. It can draw projected D target zones with Fibonacci ratios, ratio labels and an information table, and raise alerts near point D.
The inputs you can change from the gear icon on the chart. Defaults are the author's.
Setting
Type
Default
Variable
Çalışma Modu
string
Otomatik
mode
X
price
0
xP
xT
time
0
xT
A
price
0
aP
aT
time
0
aT
B
price
0
bP
bT
time
0
bT
C
price
0
cP
cT
time
0
cT
D
price
0
dP
dT
time
0
dT
Geriye Bakış Periyodu
int
100
auto_lookback
Show all 29 settings
Setting
Type
Default
Variable
Minimum Skor %
float
60.0
auto_min_score
Potansiyel Desenleri Göster
bool
true
auto_show_potential
Pivot Uzunluğu
int
5
pivot_length
D Noktasını Manuel Kullan
bool
false
use_manual_d
Tüm D Tahminlerini Göster
bool
true
show_all_d_predictions
Minimum Güven Skoru %
float
50.0
min_confidence
D Hedef Bölgesini Göster
bool
true
show_d_zone
C'den D'ye İzdüşüm Çizgileri
bool
true
show_projections
Harmonik Oranları Göster
bool
true
show_ratios
Desen Bilgi Tablosunu Göster
bool
true
show_pattern_info
En İyi D Tahminini Vurgula
bool
true
highlight_best_d
Desen Toleransı
float
0.15
tolerance
İzin verilen bacak uzunluğu asimetrisi %
float
250.0
pctAsym
Manuel Boğa Rengi
color
color.new(color.green, 20)
c_bull_manual
Manuel Ayı Rengi
color
color.new(color.red, 20)
c_bear_manual
Otomatik Boğa Rengi
color
color.new(color.blue, 40)
c_bull_auto
Otomatik Ayı Rengi
color
color.new(color.orange, 40)
c_bear_auto
Third-party code. ForexR did not write, test or endorse this script, and the summary above was generated automatically from its code and README. Indicators describe the past, and a strategy's backtest can look better than live trading, especially when a script repaints. Check it in the Strategy Tester and on a demo account before you rely on it.
Moving Average Channel plots separate simple moving averages for upper and lower bands on the price chart. It fills the space between bands with semi-transparent color and colors bars green above the upper band, red below the lower band, or gray in between. Us
This overlay indicator finds pivot highs and lows on the price chart and compares the last two highs and the last two lows. When the percentage difference between a pair is below the Equal HL threshold, it treats them as equal levels and draws a box. Left and
This indicator monitors multiple cryptocurrency symbols for trading signals. It calculates and plots entry prices, take profit, and stop loss levels for each symbol including BTCUSDT, ETHUSDT, BNBUSDT and others. Price crossovers trigger buy, sell or close ale
This overlay indicator draws a fixed-range volume profile on the price chart, splitting traded activity into up and down volume at each price level. It also plots a sentiment profile, a developing point of control, and value-area high and low around a configur
The BZ-tracker indicator marks ARK Invest buy and sell transactions on stock charts with labels. It plots green labels for purchases and red labels for sales, each annotated with a multiplier such as X1 or X2 to show the number of ARK ETFs trading the stock on
This indicator fits a linear regression through stored pivot highs and lows and draws the resulting channel on the price chart. A function returns predicted values, maximum and minimum deviations, and the average absolute deviation. Confirmed two-bar pivots up