An indicator for crypto perpetual futures that scores each bar from trend, momentum, volume and market structure, then confirms it across four timeframes.
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
855 lines of Pine Script v6 from Symbiose_Signal_System_v1.pine, published under MIT. Keep the author's credit and licence lines when you reuse it.
Symbiose_Signal_System_v1.pine
// ============================================================================
// ███████╗██╗ ██╗███╗ ███╗██████╗ ██████╗ ███████╗███████╗
// ██╔════╝╚██╗ ██╔╝████╗ ████║██╔══██╗██╔═══██╗██╔════╝██╔════╝
// ███████╗ ╚████╔╝ ██╔████╔██║██████╔╝██║ ██║███████╗█████╗
// ╚════██║ ╚██╔╝ ██║╚██╔╝██║██╔══██╗██║ ██║╚════██║██╔══╝
// ███████║ ██║ ██║ ╚═╝ ██║██████╔╝╚██████╔╝███████║███████╗
// ╚══════╝ ╚═╝ ╚═╝ ╚═╝╚═════╝ ╚═════╝ ╚══════╝╚══════╝
// AURA v2.5.0 — Confluence Trading Signal System (Pine Script v6)
// ============================================================================
// Ebenen: 1) Technische Analyse (Trend/Momentum/Volatilität/Volumen/Struktur)
// 2) Kalibrierte Win-Probability (PAVA Isotonic Regression)
// 3) Marktmikrostruktur & Derivate-Daten (Funding, Open Interest, Basis)
// 4) Dynamisches Exit Management (TP1-3, Trailing Stop, Time-Stop)
// 5) Marktkontext (Regime-Filter, Liquiditätspools, Fear & Greed)
//
// v1.8.2 PATCH: Ehrliches /ready, Anti-Stumm-Warnung, Signal-/Ausführungspreis-Split
//
// v1.8.0 MINOR: Runner-Selbstheilung & Timeout-Härtung
// v1.7.0 MINOR: Headless Paper-Autobot (Server-Modus) & Paritäts-Metadaten
// v1.7.0 MINOR: Headless Paper-Autobot (Server-Modus) & 24/7 Signals
// v1.6.1 PATCH (Infra): Universum-Sync-Isolation & CI-Stabilität
// - AURA_UNIVERSE_PATH / AURA_DISABLE_AUTO_SYNC isoliert Daten-Sync in Tests
// - CI-Release-Gate bleibt bei sauberem Arbeitsbaum stabil (keine false positives)
//
// v2.5.0 CURRENT:
// - Server-Only Live: Browser is Viewer + Config; Docker runner never pauses for browser state.
// - JS/Pine mathematical parity and current symbiose.v2.5.0 alert contract
//
// HISTORICAL v1.0.3 NOTES:
// - These original feature notes remain historical context only.
//
// HINWEIS ZU FEAR & GREED: TradingView-Pine kann KEINE externen REST-APIs
// abfragen. Der Index wird deshalb als Input gepflegt (Zahlenwert 0-100) und
// kann via Webhook/Alert-Payload (z. B. über einen Bot) live injiziert werden.
// Das Web-Dashboard nutzt die echte Alternative.me-API (minutengenau).
//
// BITGET-VERSION: Um TradingView-Kurse möglichst nah an Bitget zu halten,
// das Chart-Symbol auf den Bitget-Feed umstellen (z. B. BITGET:BTCUSDT).
// Die Positionsgröße wird zusätzlich in BITGET-KONTRAKTEN ausgegeben —
// dafür die Kontraktgröße (ctVal) des Symbols eintragen (Bitget-API:
// /api/v2/mix/market/contracts -> sizeMultiplier, z. B. 0.0001 bei BTCUSDT).
//
// WICHTIG MTF: Die Bestätigung nutzt dieselbe volle Scoring-Engine wie die
// Chart-Ebene, aber ausschließlich über ta.*-Built-ins (kein var-State, kein
// Repaint-Leck in request.security, lookahead_off). Die Chart-Ebene nutzt die
// volle Engine inkl. Swing-Struktur, FVG und Orderflow mit var-State. Alle
// ta.*-Zustandsfunktionen werden GLOBAL berechnet (v6 Lazy-Evaluation-Falle) —
// einzige Ausnahme ist der request.security-Kontext (f_mtf), wo ta.* erlaubt ist.
// ============================================================================
//@version=6
indicator("AURA — Confluence Signal-System", "AURA", overlay=true, max_bars_back=500, max_boxes_count=500, max_labels_count=500, max_lines_count=500, dynamic_requests=false)
// ============================================================================
// EINGABEN
// ============================================================================
grpT = "1) Multi-Timeframe (MTF)"
mtfT1 = input.string("15", "MTF 1", options=["1", "3", "5", "15", "30", "60", "240", "1D", "1W"], group=grpT)
mtfT2 = input.string("60", "MTF 2", options=["1", "3", "5", "15", "30", "60", "240", "1D", "1W"], group=grpT)
mtfT3 = input.string("240", "MTF 3", options=["1", "3", "5", "15", "30", "60", "240", "1D", "1W"], group=grpT)
mtfT4 = input.string("1D", "MTF 4", options=["1", "3", "5", "15", "30", "60", "240", "1D", "1W"], group=grpT)
mtfNeed = input.int(3, "Erforderliche übereinstimmende TFs", minval=1, maxval=4, group=grpT)
grpI = "2) Indikator-Parameter"
emaF = input.int(20, "EMA fast", group=grpI)
emaM = input.int(50, "EMA mid", group=grpI)
emaS = input.int(200, "EMA slow", group=grpI)
bbLen = input.int(20, "Bollinger-Band Länge", group=grpI)
bbMul = input.float(2.0, "Bollinger Multiplikator", group=grpI)
rsiLen = input.int(14, "RSI Länge", group=grpI)
adxLen = input.int(14, "ADX Länge", group=grpI)
atrLen = input.int(14, "ATR Länge (Risk)", group=grpI)
atrSl = input.float(1.5, "Stop-Loss ATR-Multiplikator", group=grpI)
stLen = input.int(10, "SuperTrend ATR-Länge", group=grpI)
stMul = input.float(3.0, "SuperTrend Faktor", group=grpI)
pivotL = input.int(5, "Swing-Pivot Lookback", minval=2, maxval=12, group=grpI)
grpS = "3) Signal-Schwellen & Gates"
thLong = input.float(75.0, "Long-Schwelle (Score >=)", minval=50, maxval=95, step=1, group=grpS)
thShort = input.float(25.0, "Short-Schwelle (Score <=)", minval=5, maxval=50, step=1, group=grpS)
regimeGate = input.bool(true, "Regime-Gate (Trendfolge nur in Bull/Bear)", group=grpS)
showFVG = input.bool(true, "FVG-Zonen zeichnen", group=grpS)
showStr = input.bool(true, "BOS/CHoCH Labels zeichnen", group=grpS)
showHeat = input.bool(true, "Score-Heatmap (Hintergrund)", group=grpS)
grpR = "4) Risk Management"
riskPct = input.float(1.0, "Risiko pro Trade (%)", minval=0.1, maxval=5.0, step=0.1, group=grpR)
equity = input.float(10000.0, "Konto-Größe (USDT)", minval=100, step=100, group=grpR)
ctValB = input.float(0.0001, "Bitget Kontraktgröße (ctVal)", minval=0.000001, step=0.0001, tooltip="sizeMultiplier aus der Bitget-API (z. B. BTCUSDT: 0.0001, ETHUSDT: 0.01). Nur für die Kontrakt-Anzeige.", group=grpR)
timeStopN = input.int(15, "Time-Stop (Bars, 0 = aus)", minval=0, maxval=100, group=grpR)
grpF = "5) Makro & Crypto-Native Edge"
inFG = input.float(50.0, "Fear & Greed Index (0-100)", minval=0, maxval=100, step=1, tooltip="Manuell pflegbar oder per Webhook injiziert. Dashboard nutzt die Live-API (alternative.me).", group=grpF)
inFundingBias = input.float(0.0, "Funding Bias (-100..+100)", minval=-100.0, maxval=100.0, step=1.0, tooltip="Funding-Rate Z-Score Bias aus Webhook/API (-100 = überfüllte Longs/Short-Bias, +100 = überfüllte Shorts/Long-Bias).", group=grpF)
inFundingZ = input.float(0.0, "Funding Z-Score (Extremwert > 2.5 = Veto-Bereich)", minval=-5.0, maxval=5.0, step=0.1, tooltip="Z-Score der Funding Rate. |Z| > 2.5 aktiviert den Makro-Veto-Multiplier (bis 25P Abzug).", group=grpF)
inOIBias = input.float(0.0, "OI Bias (-100..+100)", minval=-100.0, maxval=100.0, step=1.0, tooltip="Open Interest Quadrant Bias (-100..+100).", group=grpF)
inOISpike = input.bool(false, "OI-Spike aktiv (Topping-Warnung)", tooltip="Aktiviert wenn OI-Quadrant = 'OI-Spike / Topping-Warnung'.", group=grpF)
inBasisBias = input.float(0.0, "Perp Basis Bias (-100..+100)", minval=-100.0, maxval=100.0, step=1.0, tooltip="Perp-Basis / Premium Bias (-100..+100).", group=grpF)
inCalibP = input.float(50.0, "Kalibrierte P(Long) % (aus Webhook)", minval=0.0, maxval=100.0, step=0.5, tooltip="Empirische Out-of-Sample Gewinnwahrscheinlichkeit P(Long) in % aus dem Walk-Forward-Backtest.", group=grpF)
grpV = "6) Darstellung"
structureLabelSize = input.string("Normal", "BOS/CHoCH Textgröße", options=["Klein", "Normal", "Groß"], group=grpV)
structureLabelOffsetAtr = input.float(0.35, "BOS/CHoCH Abstand (ATR)", minval=0.1, maxval=2.0, step=0.05, tooltip="Vertikaler Abstand der Struktur-Labels zur Kerze. Höhere Werte verhindern Überlappungen.", group=grpV)
// ============================================================================
// HILFSFUNKTIONEN
// ============================================================================
f_clamp(x, lo, hi) =>
math.max(lo, math.min(hi, x))
// Entscheidung: Score (0-100) -> Richtung (+1 bull, -1 bear, 0 neutral)
f_dirOf(s) =>
s > 55.0 ? 1 : s < 45.0 ? -1 : 0
f_fgLabel(f) =>
f >= 75 ? "Extreme Greed" : f >= 55 ? "Greed" : f > 45 ? "Neutral" : f > 25 ? "Fear" : "Extreme Fear"
// Stärke-Label aus Score & Richtung — bewusst als if/else (keine
// mehrzeiligen Ternary-Ketten, die in Pine nicht fortgesetzt werden dürfen)
f_strength(s, d) =>
string lbl = "—"
if d == 1
lbl := s >= 94.0 ? "ULTRA" : s >= 87.0 ? "STRONG" : s >= 80.0 ? "MEDIUM" : "WEAK"
else if d == -1
lbl := s <= 6.0 ? "ULTRA" : s <= 13.0 ? "STRONG" : s <= 20.0 ? "MEDIUM" : "WEAK"
lbl
// Dynamic TP1: find closest opposing level in [1R, 2R) and clamp to it.
// dir=1 -> bearish FVG bottom / EQH in [entry+1R, entry+2R)
// dir=-1 -> bullish FVG top / EQL in (entry-2R, entry-1R]
// Returns TP1 price (float). No look-ahead: all inputs are current-bar confirmed state.
f_dynTP1(dir, entry, r, fAct, fDir, fTop, fBot, eqhLv, eqlLv) =>
float tp1 = dir == 1 ? entry + 2.0 * r : entry - 2.0 * r
float best = na
float bestR = na
if dir == 1
float minR = entry + 1.0 * r
float maxR = entry + 2.0 * r
if not na(eqhLv) and eqhLv >= minR and eqhLv < maxR
float rm = (eqhLv - entry) / r
best := eqhLv
bestR := rm
if fAct and fDir == -1 and fBot >= minR and fBot < maxR
float rm = (fBot - entry) / r
if na(bestR) or rm < bestR
best := fBot
bestR := rm
else
float minR = entry - 2.0 * r
float maxR = entry - 1.0 * r
if not na(eqlLv) and eqlLv <= maxR and eqlLv > minR
float rm = (entry - eqlLv) / r
best := eqlLv
bestR := rm
if fAct and fDir == 1 and fTop <= maxR and fTop > minR
float rm = (entry - fTop) / r
if na(bestR) or rm < bestR
best := fTop
bestR := rm
na(best) ? tp1 : best
// ============================================================================
// EBENE 1 — INDIKATOREN (Chart-Timeframe, volle Engine)
// Alle ta.*-Aufrufe GLOBAL — niemals in Bedingungen (v6 Lazy-Evaluation!)
// ============================================================================
emaFast = ta.ema(close, emaF)
emaMid = ta.ema(close, emaM)
emaSlow = ta.ema(close, emaS)
rsiV = ta.rsi(close, rsiLen)
rsiLo = ta.lowest(rsiV, rsiLen)
rsiHi = ta.highest(rsiV, rsiLen)
srsiRaw = (rsiHi - rsiLo) > 0 ? (rsiV - rsiLo) / (rsiHi - rsiLo) * 100.0 : 50.0
srsiK = ta.sma(srsiRaw, 3)
srsiD = ta.sma(srsiK, 3)
[macdLine, macdSig, macdHist] = ta.macd(close, 12, 26, 9)
[diPlus, diMinus, adxV] = ta.dmi(adxLen, adxLen)
bbMid = ta.sma(close, bbLen)
bbStd = ta.stdev(close, bbLen)
bbUp = bbMid + bbMul * bbStd
bbDn = bbMid - bbMul * bbStd
bbWidth = bbMid > 0 ? (bbUp - bbDn) / bbMid : 0.0
kcMid = ta.ema(close, 20)
kcUp = kcMid + 2.0 * ta.atr(10)
kcDn = kcMid - 2.0 * ta.atr(10)
kcWidth = kcMid > 0 ? (kcUp - kcDn) / kcMid : 0.0
atrR = ta.atr(atrLen)
// --- SuperTrend (10, 3.0) — eigene Implementierung (braucht var-State) ---
stAtr = ta.atr(stLen)
stMid = (high + low) / 2.0
stUp = stMid + stMul * stAtr
stDn = stMid - stMul * stAtr
var float stFUp = na
var float stFDn = na
var float stLine = na
var int stDir = 1
stFUp := na(stFUp[1]) ? stUp : (stUp < stFUp[1] or close[1] > stFUp[1]) ? stUp : stFUp[1]
stFDn := na(stFDn[1]) ? stDn : (stDn > stFDn[1] or close[1] < stFDn[1]) ? stDn : stFDn[1]
stLine := na(stLine[1]) ? stFDn : stLine[1] == stFUp[1] ? (close > stFUp ? stFDn : stFUp) : (close < stFDn ? stFUp : stFDn)
stDir := stLine[1] != stLine ? (close > stLine ? 1 : -1) : stDir[1]
// --- OBV + VWAP (täglich verankert) ---
var float obv = 0.0
obv := nz(obv[1]) + (close > close[1] ? volume : close < close[1] ? -volume : 0.0)
emaObv = ta.ema(obv, 20)
var float vwpyPv = 0.0
var float vwpyVv = 0.0
newDay = timeframe.change("1D")
vwpyPv := newDay ? hlc3 * volume : vwpyPv + hlc3 * volume
vwpyVv := newDay ? volume : vwpyVv + volume
vwapD = vwpyVv > 0.0 ? vwpyPv / vwpyVv : hlc3
// --- Volume Delta / CVD (Approximation über Bar-Range-Position) ---
barRange = high - low
volDelta = barRange > 0.0 ? volume * (2.0 * close - high - low) / barRange : 0.0
var float cvd = 0.0
cvd := nz(cvd[1]) + volDelta
emaCvd = ta.ema(cvd, 20)
smaVol = ta.sma(volume, 20)
// --- Swing Highs/Lows (Pivots, 5/5 bestätigt) ---
ph = ta.pivothigh(pivotL, pivotL)
pl = ta.pivotlow(pivotL, pivotL)
// ============================================================================
// MARKTSTRUKTUR — BOS / CHoCH / FVG / Liquiditätspools
// ============================================================================
var float lastPH = na
var float lastPL = na
var int structTrend = 1
var int bosBullAgo = 99
var int bosBearAgo = 99
var int chBullAgo = 99
var int chBearAgo = 99
var array<float> phPool = array.new<float>(0)
var array<float> plPool = array.new<float>(0)
// Keep chart objects bounded below TradingView's hard box limit. If all retained
// zones are still active, visual history yields to continued indicator execution.
MAX_FVG_ZONES = 30
var float fvgTop = na
var float fvgBot = na
var int fvgDir = 0
var bool fvgAct = false
var int fvgAge = 99
var array<float> fvgTops = array.new<float>(0)
var array<float> fvgBots = array.new<float>(0)
var array<int> fvgDirs = array.new<int>(0)
var array<bool> fvgActives = array.new<bool>(0)
var array<box> fvgBoxes = array.new<box>(0)
var array<label> strLabels = array.new<label>(0)
// --- Level-Breaks: stateless berechnet (kein ta.crossover in Bedingungen) ---
bullBreakCl = not na(lastPH) and close > lastPH and close[1] <= lastPH
bearBreakCl = not na(lastPL) and close < lastPL and close[1] >= lastPL
// --- Counter hochzählen (vor Ereignisbehandlung, damit Ereignis-Bar = 0) ---
bosBullAgo := bosBullAgo < 99 ? bosBullAgo + 1 : bosBullAgo
bosBearAgo := bosBearAgo < 99 ? bosBearAgo + 1 : bosBearAgo
chBullAgo := chBullAgo < 99 ? chBullAgo + 1 : chBullAgo
chBearAgo := chBearAgo < 99 ? chBearAgo + 1 : chBearAgo
// --- Ereignisse: neue bestätigte Pivots (Hoch-/Tief-Sequenz => BOS) ---
if not na(ph)
prevPH = lastPH
lastPH := ph
array.push(phPool, ph)
if array.size(phPool) > 8
array.shift(phPool)
if not na(prevPH) and structTrend == 1 and ph > prevPH
bosBullAgo := 0
if not na(pl)
prevPL = lastPL
lastPL := pl
array.push(plPool, pl)
if array.size(plPool) > 8
array.shift(plPool)
if not na(prevPL) and structTrend == -1 and pl < prevPL
bosBearAgo := 0
// --- Level-Breaks: BOS (Trendrichtung) / CHoCH (gegen Trend) ---
if bullBreakCl
if structTrend == -1
structTrend := 1
chBullAgo := 0
else
bosBullAgo := 0
if bearBreakCl
if structTrend == 1
structTrend := -1
chBearAgo := 0
else
bosBearAgo := 0
// --- Fair Value Gaps (3-Kerzen-Regel) ---
fvBull = low > high[2]
fvBear = high < low[2]
if showFVG and fvBull
fvgTop := low
fvgBot := high[2]
fvgDir := 1
fvgAct := true
fvgAge := 0
b = box.new(bar_index, fvgTop, bar_index, fvgBot, border_color=color.new(#22d3ee, 40), bgcolor=color.new(#22d3ee, 88), border_width=1)
array.push(fvgBoxes, b)
array.push(fvgTops, fvgTop)
array.push(fvgBots, fvgBot)
array.push(fvgDirs, 1)
array.push(fvgActives, true)
else if showFVG and fvBear
fvgTop := low[2]
fvgBot := high
fvgDir := -1
fvgAct := true
fvgAge := 0
b = box.new(bar_index, fvgTop, bar_index, fvgBot, border_color=color.new(#f43f5e, 40), bgcolor=color.new(#f43f5e, 88), border_width=1)
array.push(fvgBoxes, b)
array.push(fvgTops, fvgTop)
array.push(fvgBots, fvgBot)
array.push(fvgDirs, -1)
array.push(fvgActives, true)
else if fvgAct
fvgAge := fvgAge < 99 ? fvgAge + 1 : fvgAge
if fvgDir == 1 and low <= fvgBot
fvgAct := false
if fvgDir == -1 and high >= fvgTop
fvgAct := false
if showFVG and array.size(fvgBoxes) > 0
for zi = array.size(fvgBoxes) - 1 to 0
zoneTop = array.get(fvgTops, zi)
zoneBot = array.get(fvgBots, zi)
zoneDir = array.get(fvgDirs, zi)
zoneActive = array.get(fvgActives, zi)
if zoneActive
box.set_right(array.get(fvgBoxes, zi), bar_index)
zoneFilled = zoneDir == 1 ? low <= zoneBot : high >= zoneTop
if zoneFilled
array.set(fvgActives, zi, false)
box.set_right(array.get(fvgBoxes, zi), bar_index)
if showFVG and array.size(fvgBoxes) > MAX_FVG_ZONES
int removeIdx = na
for ci = array.size(fvgBoxes) - 1 to 0
if not array.get(fvgActives, ci)
removeIdx := ci
break
// Prefer a mitigated zone; otherwise evict only the oldest visual zone.
// The latest scalar FVG state used by scoring and dynTP1 is unaffected.
if na(removeIdx)
removeIdx := 0
box.delete(array.get(fvgBoxes, removeIdx))
array.remove(fvgBoxes, removeIdx)
array.remove(fvgTops, removeIdx)
array.remove(fvgBots, removeIdx)
array.remove(fvgDirs, removeIdx)
array.remove(fvgActives, removeIdx)
// --- Liquiditäts-Pools: Equal Highs / Equal Lows (mit Preislevel für dynTP1) ---
eqhFound = false
eqlFound = false
float eqhLvl = na
float eqlLvl = na
if array.size(phPool) >= 2
for i = 0 to array.size(phPool) - 2
for j = i + 1 to array.size(phPool) - 1
aP = array.get(phPool, i)
bP = array.get(phPool, j)
if math.abs(aP - bP) <= 0.35 * atrR and aP > close and bP > close
eqhFound := true
eqhLvl := (aP + bP) / 2.0
if array.size(plPool) >= 2
for i = 0 to array.size(plPool) - 2
for j = i + 1 to array.size(plPool) - 1
aP = array.get(plPool, i)
bP = array.get(plPool, j)
if math.abs(aP - bP) <= 0.35 * atrR and aP < close and bP < close
eqlFound := true
eqlLvl := (aP + bP) / 2.0
// ============================================================================
// EBENE 5a — MARKT-REGIME (Bull / Bear / Sideways + Squeeze)
// ============================================================================
regimeV = close > emaSlow and emaMid > emaSlow ? 1 : close < emaSlow and emaMid < emaSlow ? -1 : 0
squeezeV = bbWidth < kcWidth
regimeTxt = regimeV == 1 ? "BULL" : regimeV == -1 ? "BEAR" : (squeezeV ? "SIDEWAYS·SQZ" : "SIDEWAYS")
// ============================================================================
// EBENE 4 — MULTI-TIMEFRAME (volle JS-Paritäts-Engine, repaint-sicher)
// Berechnet exakt denselben Trend/Momentum/Volumen/Struktur-Score wie Ebene 2.
// Pivots werden erst nach pivotL rechten Bars bestätigt; request.security läuft
// zusätzlich mit lookahead_off, daher werden keine zukünftigen Bars eingeblendet.
// ============================================================================
f_mtf() =>
e20 = ta.ema(close, emaF)
e50 = ta.ema(close, emaM)
e200 = ta.ema(close, emaS)
r1 = ta.rsi(close, rsiLen)
rLo1 = ta.lowest(r1, rsiLen)
rHi1 = ta.highest(r1, rsiLen)
sr1 = (rHi1 - rLo1) > 0.0 ? (r1 - rLo1) / (rHi1 - rLo1) * 100.0 : 50.0
srK1 = ta.sma(sr1, 3)
[dp1, dm1, adxT] = ta.dmi(adxLen, adxLen)
[m1, s1, h1] = ta.macd(close, 12, 26, 9)
[st1, stDirRaw1] = ta.supertrend(stMul, stLen)
stDir1 = close > st1 ? 1 : -1
obv1 = ta.cum(close > close[1] ? volume : close < close[1] ? -volume : 0.0)
eObv1 = ta.ema(obv1, 20)
// Stateless session VWAP (ta.vwap). No `var` state inside request.security —
// `var` is illegal in Pine function bodies and would repaint in the MTF context.
vwap1 = ta.vwap(hlc3)
range1 = high - low
delta1 = range1 > 0.0 ? volume * (2.0 * close - high - low) / range1 : 0.0
cvd1 = ta.cum(delta1)
eCvd1 = ta.ema(cvd1, 20)
smaV1 = ta.sma(volume, 20)
ph1 = ta.pivothigh(pivotL, pivotL)
pl1 = ta.pivotlow(pivotL, pivotL)
lastPH1 = ta.valuewhen(not na(ph1), ph1, 0)
prevPH1 = ta.valuewhen(not na(ph1), ph1, 1)
lastPL1 = ta.valuewhen(not na(pl1), pl1, 0)
prevPL1 = ta.valuewhen(not na(pl1), pl1, 1)
bosBull1 = not na(ph1) and not na(prevPH1) and ph1 > prevPH1
bosBear1 = not na(pl1) and not na(prevPL1) and pl1 < prevPL1
bullBreak1 = not na(lastPH1) and close > lastPH1 and close[1] <= lastPH1
bearBreak1 = not na(lastPL1) and close < lastPL1 and close[1] >= lastPL1
struct1 = ta.valuewhen(bullBreak1 or bearBreak1, bullBreak1 ? 1 : -1, 0)
struct1 := na(struct1) ? 1 : struct1
bosBullAgo1 = nz(ta.barssince(bosBull1 or (bullBreak1 and struct1 == 1)), 99)
bosBearAgo1 = nz(ta.barssince(bosBear1 or (bearBreak1 and struct1 == -1)), 99)
chBullAgo1 = nz(ta.barssince(bullBreak1 and struct1[1] == -1), 99)
chBearAgo1 = nz(ta.barssince(bearBreak1 and struct1[1] == 1), 99)
fvgBull1 = low > high[2]
fvgBear1 = high < low[2]
lastFvgDir1 = ta.valuewhen(fvgBull1 or fvgBear1, fvgBull1 ? 1 : -1, 0)
lastFvgTop1 = ta.valuewhen(fvgBull1 or fvgBear1, fvgBull1 ? low : low[2], 0)
lastFvgBot1 = ta.valuewhen(fvgBull1 or fvgBear1, fvgBull1 ? high[2] : high, 0)
fvgActive1 = lastFvgDir1 == 1 ? low > lastFvgBot1 : lastFvgDir1 == -1 ? high < lastFvgTop1 : false
atr1 = ta.atr(atrLen)
eqh1 = not na(lastPH1) and not na(prevPH1) and math.abs(lastPH1 - prevPH1) <= 0.35 * atr1 and lastPH1 > close and prevPH1 > close
eql1 = not na(lastPL1) and not na(prevPL1) and math.abs(lastPL1 - prevPL1) <= 0.35 * atr1 and lastPL1 < close and prevPL1 < close
trend1 = f_clamp(50.0 + (close > e20 ? 8.0 : -8.0) + (e20 > e50 ? 8.0 : -8.0) + (e50 > e200 ? 7.0 : -7.0) + (stDir1 == 1 ? 12.0 : -12.0) + (adxT >= 25.0 ? (e20 > e50 ? 8.0 : -8.0) : (adxT < 18.0 ? -3.0 : 0.0)), 0.0, 100.0)
mom1 = f_clamp(50.0 + f_clamp((r1 - 50.0) * 1.5, -30.0, 30.0) + (m1 > s1 ? 12.0 : -12.0) + (h1 > 0.0 ? 8.0 : -8.0) + f_clamp((srK1 - 50.0) * 0.8, -20.0, 20.0), 0.0, 100.0)
vol1 = f_clamp(50.0 + (obv1 > eObv1 ? 15.0 : -15.0) + (close > vwap1 ? 10.0 : -10.0) + f_clamp((volume / (smaV1 > 0.0 ? smaV1 : volume) - 1.0) * 20.0, -10.0, 10.0) * (close > open ? 1.0 : -1.0) + (cvd1 > eCvd1 ? 10.0 : -10.0), 0.0, 100.0)
str1 = f_clamp(50.0 + (bosBullAgo1 <= 6 ? 15.0 : bosBearAgo1 <= 6 ? -15.0 : 0.0) + (chBullAgo1 <= 6 ? 10.0 : chBearAgo1 <= 6 ? -10.0 : 0.0) + (fvgActive1 and lastFvgDir1 == 1 and close > lastFvgTop1 ? 10.0 : fvgActive1 and lastFvgDir1 == -1 and close < lastFvgBot1 ? -10.0 : 0.0) + (eqh1 ? 7.0 : eql1 ? -7.0 : 0.0) + (struct1 == 1 ? 8.0 : -8.0), 0.0, 100.0)
score1 = f_clamp(0.30 * trend1 + 0.25 * mom1 + 0.25 * vol1 + 0.20 * str1, 0.0, 100.0)
[score1, f_dirOf(score1)]
[mtfS1, mtfD1] = request.security(syminfo.tickerid, mtfT1, f_mtf(), lookahead=barmerge.lookahead_off)
[mtfS2, mtfD2] = request.security(syminfo.tickerid, mtfT2, f_mtf(), lookahead=barmerge.lookahead_off)
[mtfS3, mtfD3] = request.security(syminfo.tickerid, mtfT3, f_mtf(), lookahead=barmerge.lookahead_off)
[mtfS4, mtfD4] = request.security(syminfo.tickerid, mtfT4, f_mtf(), lookahead=barmerge.lookahead_off)
alignedBull = (mtfD1 == 1 ? 1 : 0) + (mtfD2 == 1 ? 1 : 0) + (mtfD3 == 1 ? 1 : 0) + (mtfD4 == 1 ? 1 : 0)
alignedBear = (mtfD1 == -1 ? 1 : 0) + (mtfD2 == -1 ? 1 : 0) + (mtfD3 == -1 ? 1 : 0) + (mtfD4 == -1 ? 1 : 0)
// ============================================================================
// EBENE 2 — CONFLUENCE-SCORING (Gewichtung: Trend 30 / Mom 25 / Vol 25 / Str 20)
// ============================================================================
trendScore = 50.0
trendScore += close > emaFast ? 8.0 : -8.0
trendScore += emaFast > emaMid ? 8.0 : -8.0
trendScore += emaMid > emaSlow ? 7.0 : -7.0
trendScore += stDir == 1 ? 12.0 : -12.0
trendScore += adxV >= 25.0 ? (emaFast > emaMid ? 8.0 : -8.0) : (adxV < 18.0 ? -3.0 : 0.0)
trendScore := f_clamp(trendScore, 0.0, 100.0)
momScore = 50.0
momScore += f_clamp((rsiV - 50.0) * 1.5, -30.0, 30.0)
momScore += macdLine > macdSig ? 12.0 : -12.0
momScore += macdHist > 0.0 ? 8.0 : -8.0
momScore += f_clamp((srsiK - 50.0) * 0.8, -20.0, 20.0)
momScore := f_clamp(momScore, 0.0, 100.0)
volScore = 50.0
volScore += obv > emaObv ? 15.0 : -15.0
volScore += close > vwapD ? 10.0 : -10.0
volScore += f_clamp((volume / (smaVol > 0 ? smaVol : volume) - 1.0) * 20.0, -10.0, 10.0) * (close > open ? 1.0 : -1.0)
volScore += cvd > emaCvd ? 10.0 : -10.0
volScore := f_clamp(volScore, 0.0, 100.0)
strScore = 50.0
strScore += bosBullAgo <= 6 ? 15.0 : bosBearAgo <= 6 ? -15.0 : 0.0
strScore += chBullAgo <= 6 ? 10.0 : chBearAgo <= 6 ? -10.0 : 0.0
strScore += fvgAct and fvgDir == 1 and close > fvgTop ? 10.0 : fvgAct and fvgDir == -1 and close < fvgBot ? -10.0 : 0.0
strScore += eqhFound ? 7.0 : eqlFound ? -7.0 : 0.0
strScore += structTrend == 1 ? 8.0 : -8.0
strScore := f_clamp(strScore, 0.0, 100.0)
// --- Gesamtscore (gewichtet, 0-100) ---
coreScore = f_clamp(0.30 * trendScore + 0.25 * momScore + 0.25 * volScore + 0.20 * strScore, 0.0, 100.0)
// ============================================================================
// EBENE 5b — MAKRO-VETO/MULTIPLIER (v1.0.3: Parität zu JS macroAdjust())
//
// Schwellen identisch mit JS SYM-Konstanten:
// wFunding=0.10, wOI=0.10, wBasis=0.03
// macroCap=25 (statt vorher 4)
// fundingExtreme: |Z| > 2.5 => cap erweitert auf ±25
// oiSpike: OI-Quadrant "Topping" => cap auf ±25
//
// Veto: Score erreichte thLong/thShort durch coreScore, wird aber durch
// extreme Makro-Korrektur wieder unter die Schwelle gedrückt.
// ============================================================================
fgAdj = f_clamp((inFG - 50.0) * 0.08, -4.0, 4.0)
mtfBonus = alignedBull >= 4 or alignedBear >= 4 ? 2.0 : alignedBull >= 3 or alignedBear >= 3 ? 1.0 : 0.0
fundingExtreme = math.abs(inFundingZ) > 2.5
float fundAdj = 0.0
if fundingExtreme
fundAdj := f_clamp(inFundingBias * 0.10, -25.0, 25.0)
else
fundAdj := f_clamp(inFundingBias * 0.10, -10.0, 10.0)
float oiAdj = 0.0
if inOISpike
oiAdj := f_clamp(inOIBias * 0.10, -25.0, 25.0)
else
oiAdj := f_clamp(inOIBias * 0.10, -10.0, 10.0)
basisAdj = f_clamp(inBasisBias * 0.03, -3.0, 3.0)
macroAdj = f_clamp(fundAdj + oiAdj, -25.0, 25.0)
totalScore = f_clamp(coreScore + (coreScore >= 50.0 ? fgAdj : -fgAdj) + macroAdj + basisAdj + mtfBonus, 0.0, 100.0)
// Makro-Veto: schwaches technisches Signal (knapp über Schwelle) trifft extremes Makro
weakTechLong = coreScore >= thLong and coreScore < 85.0
weakTechShort = coreScore <= thShort and coreScore > 15.0
macroVetoL = weakTechLong and totalScore < thLong
macroVetoS = weakTechShort and totalScore > thShort
dirMain = f_dirOf(totalScore)
strengthLbl = f_strength(totalScore, dirMain)
// ============================================================================
// SIGNAL-LOGIK (Gates: Score-Schwelle + MTF >= 3 von 4 aligned + Regime-Gate)
// Makro-Veto unterdrückt Signal wenn technisches Confluence zu schwach.
// ============================================================================
regimeLongOk = not regimeGate or (regimeV == 1 and not squeezeV)
regimeShortOk = not regimeGate or (regimeV == -1 and not squeezeV)
longSig = totalScore >= thLong and alignedBull >= mtfNeed and regimeLongOk and not macroVetoL
shortSig = totalScore <= thShort and alignedBear >= mtfNeed and regimeShortOk and not macroVetoS
regimeBlocked = regimeGate and ((totalScore >= thLong and not regimeLongOk) or (totalScore <= thShort and not regimeShortOk))
// ============================================================================
// EBENE 3 — RISK MANAGEMENT (Entry / SL / dynTP1 [1R-2R] / 1:3 / 1:5)
// ============================================================================
entryPx = close
riskAmt = equity * riskPct / 100.0
// Stop-Loss: Struktur-Level, wenn es NÄHER am Entry liegt als der 1.5×ATR-Stop
// (sonst ATR-Kappe); Mindestabstand 0.5×ATR zum Entry.
lngSL_t = entryPx - atrSl * atrR
if not na(lastPL) and lastPL - 0.25 * atrR > lngSL_t
lngSL_t := lastPL - 0.25 * atrR
lngSL = math.min(entryPx - 0.5 * atrR, lngSL_t)
shtSL_t = entryPx + atrSl * atrR
if not na(lastPH) and lastPH + 0.25 * atrR < shtSL_t
shtSL_t := lastPH + 0.25 * atrR
shtSL = math.max(entryPx + 0.5 * atrR, shtSL_t)
lngR = entryPx - lngSL
shtR = shtSL - entryPx
rAct = math.max(lngR, shtR)
// --- DYNAMISCHER TP1 (v1.0.3): opposing FVG / EQH / EQL im [1R, 2R]-Fenster ---
// Kein Look-ahead: alle Inputs sind close-basiert und am aktuellen Bar bestätigt.
lngTP1 = f_dynTP1(1, entryPx, lngR, fvgAct, fvgDir, fvgTop, fvgBot, eqhLvl, eqlLvl)
shtTP1 = f_dynTP1(-1, entryPx, shtR, fvgAct, fvgDir, fvgTop, fvgBot, eqhLvl, eqlLvl)
lngTP2 = entryPx + 3.0 * lngR
lngTP3 = entryPx + 5.0 * lngR
shtTP2 = entryPx - 3.0 * shtR
shtTP3 = entryPx - 5.0 * shtR
lngSize = lngR > 0.0 ? riskAmt / lngR : 0.0
shtSize = shtR > 0.0 ? riskAmt / shtR : 0.0
showLong = longSig and lngR > 0.0
showShort = shortSig and shtR > 0.0
// --- Runner-Modus: sofort aktiv bei Score > 85, sonst erst nach TP1 ---
runnerUltraL = showLong and totalScore >= 85.0
runnerUltraS = showShort and totalScore <= 15.0
// ============================================================================
// TRADE-STATE (var) — SuperTrend-Trailing + Time-Stop (v1.0.3)
// Vorwärts-only: kein Repaint. Alle Level werden beim Entry eingefroren.
// ============================================================================
var int trDir = 0
var float trEntry = na
var float trStop = na
var float trR = na
var float trTP1 = na
var int trBars = 0
var bool trTrail = false
var bool trTP1Hit = false
// Entry: neuer Trade wenn Signal-Richtung wechselt
newLong = showLong and trDir != 1
newShort = showShort and trDir != -1
if newLong
trDir := 1
trEntry := close
trStop := lngSL
trR := lngR
trTP1 := lngTP1
trBars := 0
trTrail := runnerUltraL
trTP1Hit := false
if newShort
trDir := -1
trEntry := close
trStop := shtSL
trR := shtR
trTP1 := shtTP1
trBars := 0
trTrail := runnerUltraS
trTP1Hit := false
// Bar-Counter (erst nach Entry-Bar zählen)
if trDir != 0
trBars := trBars + 1
// TP1-Touch -> Trail aktivieren + SL auf Breakeven ziehen
tp1TouchNow = trDir == 1 and high >= trTP1 and not trTP1Hit
if tp1TouchNow
trTP1Hit := true
trTrail := true
trStop := math.max(trStop, trEntry) // SL -> Breakeven
tp1TouchShNow = trDir == -1 and low <= trTP1 and not trTP1Hit
if tp1TouchShNow
trTP1Hit := true
trTrail := true
trStop := math.min(trStop, trEntry) // SL -> Breakeven
// SuperTrend-Trailing: Stop nachziehen wenn Runner aktiv
if trDir == 1 and trTrail and not na(stLine)
trStop := math.max(trStop, stLine)
if trDir == -1 and trTrail and not na(stLine)
trStop := math.min(trStop, stLine)
// Trail-Exit (StDir-Flip während Trail aktiv)
trailExit = trDir == 1 and trTrail and trTP1Hit and stDir == -1
trailExitS = trDir == -1 and trTrail and trTP1Hit and stDir == 1
// rNet: unrealisierte R seit Entry (für Time-Stop-Berechnung, fee-frei — Pine kennt keine fees)
float rNet = na
if trDir == 1 and trR > 0.0
rNet := (close - trEntry) / trR
else if trDir == -1 and trR > 0.0
rNet := (trEntry - close) / trR
// Time-Stop: nach N Bars bei rNet <= 0 (Kapital-Effizienz)
timeStopActive = timeStopN > 0 and trDir != 0 and trBars >= timeStopN and not na(rNet) and rNet <= 0.0
// Wenn Time-Stop oder Trail-Exit auslöst -> Trade-State zurücksetzen
if timeStopActive or trailExit or trailExitS
trDir := 0
trEntry := na
trStop := na
trR := na
trTP1 := na
trBars := 0
trTrail := false
trTP1Hit := false
// ============================================================================
// CHART-VISUALISIERUNG — EMAs, SuperTrend, BB, VWAP, Signale, Heatmap
// ============================================================================
plot(emaFast, "EMA 20", color=color.new(#22d3ee, 0), linewidth=1)
plot(emaMid, "EMA 50", color=color.new(#f59e0b, 0), linewidth=2)
plot(emaSlow, "EMA 200", color=color.new(#a855f7, 0), linewidth=2)
plot(stLine, "SuperTrend", color=stDir == 1 ? color.new(#22c55e, 0) : color.new(#ef4444, 0), linewidth=3, style=plot.style_linebr)
plot(bbUp, "BB Upper", color=color.new(#94a3b8, 75), linewidth=1)
plot(bbDn, "BB Lower", color=color.new(#94a3b8, 75), linewidth=1)
plot(vwapD, "VWAP (Tag)", color=color.new(#e2e8f0, 40), linewidth=1, style=plot.style_circles)
// Signal-Pfeile
plotshape(showLong, "Long Signal", shape.triangleup, location.belowbar, color.new(#22c55e, 0), size=size.small, text="L", textcolor=color.new(#22c55e, 0))
plotshape(showShort, "Short Signal", shape.triangledown, location.abovebar, color.new(#ef4444, 0), size=size.small, text="S", textcolor=color.new(#ef4444, 0))
// Time-Stop Marker
plotshape(timeStopActive, "Time-Stop Exit", shape.xcross, location.abovebar, color.new(#f59e0b, 0), size=size.tiny, text="T", textcolor=color.new(#f59e0b, 0))
// Score-Heatmap
hg = color.new(#22c55e, int(math.max(70.0, 92.0 - (totalScore - thLong) * 2.0)))
hs = color.new(#ef4444, int(math.max(70.0, 92.0 - (thShort - totalScore) * 2.0)))
bgcolor(showHeat and totalScore >= thLong ? hg : showHeat and totalScore <= thShort ? hs : na)
// Data Window diagnostics for Pine↔JS Golden-Master comparison. These plots do
// not render on the chart and do not alter signal state.
plot(trendScore, "GM Trend Score", display=display.data_window)
plot(momScore, "GM Momentum Score", display=display.data_window)
plot(volScore, "GM Volume Score", display=display.data_window)
plot(strScore, "GM Structure Score", display=display.data_window)
plot(coreScore, "GM Core Score", display=display.data_window)
plot(cvd, "GM CVD", display=display.data_window)
plot(emaCvd, "GM EMA CVD 20", display=display.data_window)
plot(cvd > emaCvd ? 1 : 0, "GM CVD Above EMA", display=display.data_window)
plot(volDelta, "GM CVD Delta", display=display.data_window)
plot(macroAdj, "GM Macro Adjustment", display=display.data_window)
plot(totalScore, "GM Total Score", display=display.data_window)
plot(math.max(alignedBull, alignedBear), "GM MTF Aligned", display=display.data_window)
plot(regimeV, "GM Regime (-1/0/1)", display=display.data_window)
plot(showLong ? 1 : 0, "GM Long Gate", display=display.data_window)
plot(showShort ? 1 : 0, "GM Short Gate", display=display.data_window)
plot(atrR, "GM ATR", display=display.data_window)
plot(showLong ? lngR : showShort ? shtR : na, "GM Stop Distance", display=display.data_window)
plot(showLong ? lngSize : showShort ? shtSize : 0, "GM Position Size", display=display.data_window)
plot(showLong ? lngSize / ctValB : showShort ? shtSize / ctValB : 0, "GM Contracts", display=display.data_window)
// BOS/CHoCH-Labels
strLabelSize = structureLabelSize == "Groß" ? size.large : structureLabelSize == "Klein" ? size.small : size.normal
strLabelOffset = math.max(syminfo.mintick * 10, atrR * structureLabelOffsetAtr)
if showStr and bosBullAgo == 0
lbl = label.new(bar_index, high + strLabelOffset, "BOS ▲", style=label.style_label_down, color=color.new(#22c55e, 0), textcolor=color.white, size=strLabelSize, tooltip="Bullischer Break of Structure")
array.push(strLabels, lbl)
if array.size(strLabels) > 40
oldL = array.shift(strLabels)
label.delete(oldL)
if showStr and bosBearAgo == 0
lbl = label.new(bar_index, low - strLabelOffset, "BOS ▼", style=label.style_label_up, color=color.new(#ef4444, 0), textcolor=color.white, size=strLabelSize, tooltip="Bärischer Break of Structure")
array.push(strLabels, lbl)
if array.size(strLabels) > 40
oldL = array.shift(strLabels)
label.delete(oldL)
if showStr and chBullAgo == 0
lbl = label.new(bar_index, high + strLabelOffset * 1.35, "CHoCH ▲", style=label.style_label_down, color=color.new(#f59e0b, 0), textcolor=color.white, size=strLabelSize, tooltip="Bullischer Change of Character · mögliche Trendwende")
array.push(strLabels, lbl)
if array.size(strLabels) > 40
oldL = array.shift(strLabels)
label.delete(oldL)
if showStr and chBearAgo == 0
lbl = label.new(bar_index, low - strLabelOffset * 1.35, "CHoCH ▼", style=label.style_label_up, color=color.new(#f59e0b, 0), textcolor=color.white, size=strLabelSize, tooltip="Bärischer Change of Character · mögliche Trendwende")
array.push(strLabels, lbl)
if array.size(strLabels) > 40
oldL = array.shift(strLabels)
label.delete(oldL)
// ============================================================================
// DASHBOARD-TABLE (Score, Signal, SL/TP, MTF-Status, Position-Size, v1.0.7)
// ============================================================================
var table dash = table.new(position.top_right, 2, 28, border_width=1, border_color=color.new(#334155, 0), frame_width=1, frame_color=color.new(#334155, 0))
f_hdr(ro, tx, vl) =>
table.cell(dash, 0, ro, tx, text_color=color.new(#0b1220, 0), text_size=size.small, bgcolor=color.new(#38bdf8, 0))
table.cell(dash, 1, ro, vl, text_color=color.new(#0b1220, 0), text_size=size.small, bgcolor=color.new(#38bdf8, 0), text_halign=text.align_right)
f_cell(ro, tx, vl, tc, bg) =>
table.cell(dash, 0, ro, tx, text_color=color.new(#94a3b8, 0), text_size=size.tiny, bgcolor=color.new(#0f172a, 0))
table.cell(dash, 1, ro, vl, text_color=tc, text_size=size.tiny, bgcolor=bg, text_halign=text.align_right)
f_hdr(0, "AURA v2.5.0", syminfo.ticker + " · " + timeframe.period)
sClr = totalScore >= thLong ? color.new(#4ade80, 0) : totalScore <= thShort ? color.new(#f87171, 0) : color.new(#e2e8f0, 0)
sigClr = showLong ? color.new(#4ade80, 0) : showShort ? color.new(#f87171, 0) : (macroVetoL or macroVetoS) ? color.new(#a855f7, 0) : regimeBlocked ? color.new(#f59e0b, 0) : color.new(#64748b, 0)
bgScr = totalScore >= thLong ? color.new(#22c55e, 82) : totalScore <= thShort ? color.new(#ef4444, 82) : color.new(#334155, 75)
mtfTxt = str.tostring(mtfT1) + ":" + str.tostring(mtfS1, "#.#") + (mtfD1 == 1 ? "▲" : mtfD1 == -1 ? "▼" : "—") + " · " + str.tostring(mtfT2) + ":" + str.tostring(mtfS2, "#.#") + (mtfD2 == 1 ? "▲" : mtfD2 == -1 ? "▼" : "—") + " · " + str.tostring(mtfT3) + ":" + str.tostring(mtfS3, "#.#") + (mtfD3 == 1 ? "▲" : mtfD3 == -1 ? "▼" : "—") + " · " + str.tostring(mtfT4) + ":" + str.tostring(mtfS4, "#.#") + (mtfD4 == 1 ? "▲" : mtfD4 == -1 ? "▼" : "—")
// Makro-Status-Text
macroStatusTxt = fundingExtreme ? "Fund Z=" + str.tostring(inFundingZ, "#.##") + " EXTREM" : inOISpike ? "OI-SPIKE" : "normal"
vetoTxt = (macroVetoL or macroVetoS) ? " ← VETO" : ""
f_cell(1, "Regime", regimeTxt + " · ADX " + str.tostring(adxV, "#.#"), color.new(#e2e8f0, 0), color.new(#334155, 60))
f_cell(2, "Score (Core / Total)", str.tostring(coreScore, "#.#") + " / " + str.tostring(totalScore, "#.#") + " · 100", sClr, bgScr)
f_cell(3, "Signal", showLong ? "LONG · " + strengthLbl : showShort ? "SHORT · " + strengthLbl : (macroVetoL or macroVetoS) ? "MAKRO-VETO" : regimeBlocked ? "REGIME-BLOCK" : "KEIN SIGNAL", sigClr, color.new(#1e293b, 0))
f_cell(4, "P(Long) / P(Win)", str.tostring(inCalibP, "#.#") + "% (OOS Kalibriert)", color.new(#38bdf8, 0), color.new(#1e293b, 0))
f_cell(5, "Trend / Momentum", str.tostring(trendScore, "#.#") + " / " + str.tostring(momScore, "#.#"), color.new(#e2e8f0, 0), color.new(#1e293b, 0))
f_cell(6, "Volumen / Struktur", str.tostring(volScore, "#.#") + " / " + str.tostring(strScore, "#.#"), color.new(#e2e8f0, 0), color.new(#1e293b, 0))
f_cell(7, "Makro-Adj / Status", str.tostring(macroAdj, "+#.##;-#.##") + "P · " + macroStatusTxt + vetoTxt, (macroVetoL or macroVetoS) ? color.new(#a855f7, 0) : fundingExtreme or inOISpike ? color.new(#f59e0b, 0) : color.new(#e2e8f0, 0), color.new(#1e293b, 0))
f_cell(8, "MTF Aligned", str.tostring(math.max(alignedBull, alignedBear)) + " / 4 " + mtfTxt, color.new(#e2e8f0, 0), color.new(#1e293b, 0))
f_cell(9, "Fear & Greed", str.tostring(inFG, "#.#") + " · " + f_fgLabel(inFG), color.new(#e2e8f0, 0), color.new(#1e293b, 0))
f_cell(10, "Struktur", (structTrend == 1 ? "HH/HL · bullisch" : "LL/LH · bärisch") + (fvgAct ? (fvgDir == 1 ? " · FVG▲ aktiv" : " · FVG▼ aktiv") : "") + (eqhFound ? " · EQH↑ " + str.tostring(eqhLvl, "#.####") : eqlFound ? " · EQL↓ " + str.tostring(eqlLvl, "#.####") : ""), color.new(#e2e8f0, 0), color.new(#1e293b, 0))
f_cell(11, "Entry", str.tostring(entryPx, "#.####"), color.new(#e2e8f0, 0), color.new(#1e293b, 0))
f_cell(12, "Stop-Loss (1.5×ATR+Struktur)", showLong ? str.tostring(lngSL, "#.####") : showShort ? str.tostring(shtSL, "#.####") : "—", color.new(#f87171, 0), color.new(#1e293b, 0))
f_cell(13, "TP1 (dyn. [1R–2R] · 50%)", showLong ? str.tostring(lngTP1, "#.####") : showShort ? str.tostring(shtTP1, "#.####") : "—", color.new(#4ade80, 0), color.new(#1e293b, 0))
f_cell(14, "TP2 (1:3 · Runner)", showLong ? str.tostring(lngTP2, "#.####") : showShort ? str.tostring(shtTP2, "#.####") : "—", color.new(#4ade80, 0), color.new(#1e293b, 0))
f_cell(15, "TP3 (1:5 · Ref)", showLong ? str.tostring(lngTP3, "#.####") : showShort ? str.tostring(shtTP3, "#.####") : "—", color.new(#4ade80, 0), color.new(#1e293b, 0))
f_cell(16, "Risk / R", (showLong or showShort) ? str.tostring(rAct, "#.##") : "—", color.new(#e2e8f0, 0), color.new(#1e293b, 0))
f_cell(17, "Positionsgröße", showLong ? str.tostring(lngSize, "#.####") + " @ " + str.tostring(lngSize * entryPx, "#,###") + " USDT · " + str.tostring(lngSize / ctValB, "#.##") + " Ktr." : showShort ? str.tostring(shtSize, "#.####") + " @ " + str.tostring(shtSize * entryPx, "#,###") + " USDT · " + str.tostring(shtSize / ctValB, "#.##") + " Ktr." : "—", color.new(#e2e8f0, 0), color.new(#1e293b, 0))
f_cell(18, "Leverage (Konto " + str.tostring(equity, "#,###") + ")", showLong ? str.tostring(lngSize * entryPx / equity, "#.##") + "x" : showShort ? str.tostring(shtSize * entryPx / equity, "#.##") + "x" : "—", color.new(#e2e8f0, 0), color.new(#1e293b, 0))
f_cell(19, "Risiko pro Trade", str.tostring(riskAmt, "#.##") + " USDT (" + str.tostring(riskPct, "#.##") + "%)", color.new(#f8fafc, 0), color.new(#1e293b, 0))
f_cell(20, "Regime-Gate Status", regimeGate ? (showLong or showShort ? "FREIGEGEBEN" : regimeBlocked ? "GESPERRT (Regime/SQZ)" : "STANDBY") : "AUS", (showLong or showShort) ? color.new(#4ade80, 0) : regimeBlocked ? color.new(#f59e0b, 0) : color.new(#94a3b8, 0), color.new(#1e293b, 0))
// Trailing-State
trailStatusTxt = trDir != 0 ? (str.tostring(trBars) + " Bars · Runner: " + (trTrail ? "ST-TRAIL" : (trTP1Hit ? "BE-Stop" : "SL-Schutz")) + " · rNet: " + str.tostring(rNet, "+#.##;-#.##") + "R") : "—"
f_cell(21, "Trade-State", trailStatusTxt, trDir == 1 ? color.new(#4ade80, 0) : trDir == -1 ? color.new(#f87171, 0) : color.new(#94a3b8, 0), color.new(#1e293b, 0))
f_cell(22, "Time-Stop", str.tostring(timeStopN) + " Bars · " + (timeStopActive ? "AUSLÖSUNG: rNet=" + str.tostring(rNet, "#.##") + "R" : "inaktiv"), timeStopActive ? color.new(#f59e0b, 0) : color.new(#94a3b8, 0), color.new(#1e293b, 0))
f_cell(23, "RSI / StochRSI", str.tostring(rsiV, "#.#") + " / " + str.tostring(srsiK, "#.#"), color.new(#e2e8f0, 0), color.new(#1e293b, 0))
f_cell(24, "CVD (kum. Delta)", str.tostring(cvd, "#.##") + (cvd > emaCvd ? " ▲" : " ▼"), color.new(#e2e8f0, 0), color.new(#1e293b, 0))
f_cell(25, "Squeeze", squeezeV ? "AKTIV (BB<KC)" : "nein", squeezeV ? color.new(#f59e0b, 0) : color.new(#e2e8f0, 0), color.new(#1e293b, 0))
f_cell(26, "Funding / OI Bias", "F:" + str.tostring(inFundingBias, "#") + " Z:" + str.tostring(inFundingZ, "#.#") + " · OI:" + str.tostring(inOIBias, "#") + " · B:" + str.tostring(inBasisBias, "#"), color.new(#e2e8f0, 0), color.new(#1e293b, 0))
f_cell(27, "Letzte Aktualisierung", str.format_time(time_close, "dd.MM HH:mm"), color.new(#64748b, 0), color.new(#1e293b, 0))
// ============================================================================
// ALERTS (kompatibel mit Webhook/Bot — JSON-Payload via alert())
// ============================================================================
alertcondition(showLong, "AURA: Long Signal", "AURA LONG | Score >= Schwelle & MTF aligned")
alertcondition(showShort, "AURA: Short Signal", "AURA SHORT | Score <= Schwelle & MTF aligned")
alertcondition(showLong and strengthLbl == "ULTRA", "AURA: Long ULTRA", "AURA LONG ULTRA (Score >= 94)")
alertcondition(showShort and strengthLbl == "ULTRA", "AURA: Short ULTRA", "AURA SHORT ULTRA (Score <= 6)")
alertcondition(bosBullAgo == 0, "AURA: Bullischer BOS", "Marktstruktur: Bullsche BOS")
alertcondition(bosBearAgo == 0, "AURA: Bärischer BOS", "Marktstruktur: Bärische BOS")
alertcondition(chBullAgo == 0, "AURA: Bullischer CHoCH", "Marktstruktur: Bullischer CHoCH (Trendwende)")
alertcondition(chBearAgo == 0, "AURA: Bärischer CHoCH", "Marktstruktur: Bärischer CHoCH (Trendwende)")
alertcondition(macroVetoL or macroVetoS, "AURA: Makro-Veto", "Makro-Veto aktiv: Funding/OI-Extrem unterdrückt technisches Signal")
alertcondition(timeStopActive, "AURA: Time-Stop Exit", "Time-Stop ausgelöst: rNet <= 0 nach eingestellter Bar-Anzahl")
tp1TouchL = showLong and high >= lngTP1
tp1TouchS = showShort and low <= shtTP1
alertcondition(tp1TouchL, "AURA: TP1 erreicht (Long)", "TP1 (dyn. 1–2R) erreicht — Long Position — Runner per ST aktiv")
alertcondition(tp1TouchS, "AURA: TP1 erreicht (Short)", "TP1 (dyn. 1–2R) erreicht — Short Position — Runner per ST aktiv")
alertcondition(trailExit or trailExitS, "AURA: SuperTrend Runner Exit", "Runner-Tranche: SuperTrend-Flip — Exit Runner-50%")
if showLong or showShort
sDir = showLong ? "LONG" : "SHORT"
sSize = showLong ? lngSize : shtSize
sSl = str.tostring(showLong ? lngSL : shtSL, "#.######")
sTp1 = str.tostring(showLong ? lngTP1 : shtTP1, "#.######")
sTp2 = str.tostring(showLong ? lngTP2 : shtTP2, "#.######")
sTp3 = str.tostring(showLong ? lngTP3 : shtTP3, "#.######")
sSiz = str.tostring(sSize, "#.######")
sNot = str.tostring(sSize * entryPx, "#.##")
sMtf = str.tostring(mtfS1, "#.#") + "," + str.tostring(mtfS2, "#.#") + "," + str.tostring(mtfS3, "#.#") + "," + str.tostring(mtfS4, "#.#")
sRunnerMode = showLong ? (runnerUltraL ? "INSTANT_ST" : "POST_TP1") : (runnerUltraS ? "INSTANT_ST" : "POST_TP1")
// JSON-Payload includes the v2.5.0 release contract; field semantics are unchanged.
jsn = '{"type":"symbiose.v2.5.0","symbol":"' + syminfo.ticker + '","tf":"' + timeframe.period + '","dir":"' + sDir + '","strength":"' + strengthLbl + '","score":' + str.tostring(totalScore, "#.##") + ',"core_score":' + str.tostring(coreScore, "#.##") + ',"p_long":' + str.tostring(inCalibP, "#.#") + ',"funding_bias":' + str.tostring(inFundingBias, "#") + ',"funding_z":' + str.tostring(inFundingZ, "#.##") + ',"oi_bias":' + str.tostring(inOIBias, "#") + ',"basis_bias":' + str.tostring(inBasisBias, "#") + ',"regime":"' + regimeTxt + '","regime_blocked":' + (regimeBlocked ? "true" : "false") + ',"macro_veto":' + ((macroVetoL or macroVetoS) ? "true" : "false") + ',"macro_adj":' + str.tostring(macroAdj, "#.#") + ',"mtf_bonus":' + str.tostring(mtfBonus, "#") + ',"mtf":"' + sMtf + '","runner_mode":"' + sRunnerMode + '","entry":' + str.tostring(entryPx, "#.####") + ',"sl":' + str.tostring(trStop, "#.####") + ',"dyn_tp1":' + str.tostring(trTP1, "#.####") + ',"tp2":' + str.tostring(sDir == "LONG" ? lngTP2 : shtTP2, "#.####") + ',"tp3":' + str.tostring(sDir == "LONG" ? lngTP3 : shtTP3, "#.####") + ',"time_stop_bars":' + str.tostring(timeStopN) + ',"ts":' + str.tostring(time_close) + '}'
alert(jsn, alert.freq_once_per_bar_close)
// ============================================================================
// ENDE — AURA v2.5.0 (Pine v6)
// Einstieg: nächster Kerzen-Open als Maker-Limit-Order.
// 50% bei dyn. TP1 ([1R,2R] · opposing FVG/EQH/EQL), 50% SuperTrend-Runner.
// Time-Stop nach N Bars wenn rNet <= 0.
// Makro-Veto: Funding Z > 2.5 / OI-Spike kann bis 25P abziehen und schwache
// Signale (Score knapp über Schwelle) blockieren.
// Kein Finanzratschlag. Handelssystem ohne Gewinngarantie.
// ============================================================================
Overview
Scores at or above a long threshold or at or below a short threshold produce signals, optionally gated by a trend regime check. It draws fair value gaps, break of structure labels and a score heat map, and shows an ATR-based stop, staged targets, a time stop and risk-based size in contracts. Fear and greed and funding values are entered by hand. Comments and labels are in German.
The inputs you can change from the gear icon on the chart. Defaults are the author's.
Setting
Type
Default
Variable
MTF 1
string
15
mtfT1
MTF 2
string
60
mtfT2
MTF 3
string
240
mtfT3
MTF 4
string
1D
mtfT4
Erforderliche übereinstimmende TFs
int
3
mtfNeed
EMA fast
int
20
emaF
EMA mid
int
50
emaM
EMA slow
int
200
emaS
Bollinger-Band Länge
int
20
bbLen
Bollinger Multiplikator
float
2.0
bbMul
RSI Länge
int
14
rsiLen
ADX Länge
int
14
adxLen
Show all 36 settings
Setting
Type
Default
Variable
ATR Länge (Risk)
int
14
atrLen
Stop-Loss ATR-Multiplikator
float
1.5
atrSl
SuperTrend ATR-Länge
int
10
stLen
SuperTrend Faktor
float
3.0
stMul
Swing-Pivot Lookback
int
5
pivotL
Long-Schwelle (Score >=)
float
75.0
thLong
Short-Schwelle (Score <=)
float
25.0
thShort
Regime-Gate (Trendfolge nur in Bull/Bear)
bool
true
regimeGate
FVG-Zonen zeichnen
bool
true
showFVG
BOS/CHoCH Labels zeichnen
bool
true
showStr
Score-Heatmap (Hintergrund)
bool
true
showHeat
Risiko pro Trade (%)
float
1.0
riskPct
Konto-Größe (USDT)
float
10000.0
equity
Bitget Kontraktgröße (ctVal)
float
0.0001
ctValB
Time-Stop (Bars, 0 = aus)
int
15
timeStopN
Fear & Greed Index (0-100)
float
50.0
inFG
Funding Bias (-100..+100)
float
0.0
inFundingBias
Funding Z-Score (Extremwert > 2.5 = Veto-Bereich)
float
0.0
inFundingZ
OI Bias (-100..+100)
float
0.0
inOIBias
OI-Spike aktiv (Topping-Warnung)
bool
false
inOISpike
Perp Basis Bias (-100..+100)
float
0.0
inBasisBias
Kalibrierte P(Long) % (aus Webhook)
float
50.0
inCalibP
BOS/CHoCH Textgröße
string
Normal
structureLabelSize
BOS/CHoCH Abstand (ATR)
float
0.35
structureLabelOffsetAtr
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.
Structural Wave Field is a market structure indicator that evaluates structural flow, internal wave energy, and structural integrity across multiple time horizons. It combines momentum, velocity, and acceleration with wave segmentation and Elliott-context sequ
This indicator identifies Smart Money Concepts market structure across higher and lower timeframes directly on the main price chart. It detects Break of Structure, Market Structure Shifts, Order Blocks, and regular or inverse Fair Value Gaps. Entry signals are
Elton's Predictions Decision Engine synthesizes thirty selectable strategy algorithms or an auto-detect mode into unified buy, sell, or wait verdicts directly on the price chart. It calculates higher-timeframe trend alignment, confidence scores, and ATR-based
Pieki Algo is an all-in-one technical analysis indicator that overlays trading signals, trend visualizers, and Smart Money Concepts onto the main price chart. It plots buy and sell signals based on configurable sensitivity settings, colors candles by trend or
Apex Signal Matrix Pro is an overlay indicator that scores long and short bias from trend, momentum, structure, participation, and risk-reward. It plots entry and strong-entry signals when a smoothed score clears thresholds and the directional spread exceeds a
This indicator evaluates gold market conditions using a multi-factor confluence model on the price chart. It combines Stochastic, RSI, triple EMAs, Fibonacci retracements, automated support and resistance levels, wick reclaims, and volume spikes into an aggreg