//@version=5
indicator(title="Combined Range Filter + Impulse Safezone", shorttitle="Range +
Impulse", overlay=true)
// Color variables for Range Filter
upColor = color.white
midColor = #90bff9
downColor = color.blue
// Source
src = input(defval=close, title="Source")
// Sampling Period for Range Filter
per = input.int(defval=100, minval=1, title="Sampling Period")
// Range Multiplier for Range Filter
mult = input.float(defval=3.0, minval=0.1, title="Range Multiplier")
// Smooth Average Range function
smoothrng(x, t, m) =>
wper = t * 2 - 1
avrng = ta.ema(math.abs(x - x[1]), t)
smoothrng = ta.ema(avrng, wper) * m
smoothrng
// Calculating smoothed range for Range Filter
smrng = smoothrng(src, per, mult)
// Range Filter logic
rngfilt(x, r) =>
rngfilt = x
rngfilt := x > nz(rngfilt[1]) ? x - r < nz(rngfilt[1]) ? nz(rngfilt[1]) : x - r
:
x + r > nz(rngfilt[1]) ? nz(rngfilt[1]) : x + r
rngfilt
filt = rngfilt(src, smrng)
// Filter Direction
upward = 0.0
upward := filt > filt[1] ? nz(upward[1]) + 1 : filt < filt[1] ? 0 : nz(upward[1])
downward = 0.0
downward := filt < filt[1] ? nz(downward[1]) + 1 : filt > filt[1] ? 0 :
nz(downward[1])
// Target Bands
hband = filt + smrng
lband = filt - smrng
// Colors for Range Filter
filtcolor = upward > 0 ? upColor : downward > 0 ? downColor : midColor
barcolor1 = src > filt and src > src[1] and upward > 0 ? upColor :
src > filt and src < src[1] and upward > 0 ? upColor :
src < filt and src < src[1] and downward > 0 ? downColor :
src < filt and src > src[1] and downward > 0 ? downColor : midColor
// Plot Range Filter
filtplot = plot(filt, color=filtcolor, linewidth=2, title="Range Filter")
// Plot Target Bands
hbandplot = plot(hband, color=color.new(upColor, 70), title="High Target")
lbandplot = plot(lband, color=color.new(downColor, 70), title="Low Target")
// Fill Target Bands
fill(hbandplot, filtplot, color=color.new(upColor, 90), title="High Target Range")
fill(lbandplot, filtplot, color=color.new(downColor, 90), title="Low Target Range")
// Bar Color for Range Filter
barcolor(barcolor1)
// Break Outs
longCond = bool(na)
shortCond = bool(na)
longCond := src > filt and src > src[1] and upward > 0 or
src > filt and src < src[1] and upward > 0
shortCond := src < filt and src < src[1] and downward > 0 or
src < filt and src > src[1] and downward > 0
CondIni = 0
CondIni := longCond ? 1 : shortCond ? -1 : CondIni[1]
longCondition = longCond and CondIni[1] == -1
shortCondition = shortCond and CondIni[1] == 1
// Alerts for Range Filter
plotshape(longCondition, title="Buy Signal", text="Buy", textcolor=color.white,
style=shape.labelup, size=size.small, location=location.belowbar,
color=color.new(#aaaaaa, 20))
plotshape(shortCondition, title="Sell Signal", text="Sell", textcolor=color.white,
style=shape.labeldown, size=size.small, location=location.abovebar,
color=color.new(downColor, 20))
alertcondition(longCondition, title="Buy alert on Range Filter", message="Buy alert
on Range Filter")
alertcondition(shortCondition, title="Sell alert on Range Filter", message="Sell
alert on Range Filter")
alertcondition(longCondition or shortCondition, title="Buy and Sell alert on Range
Filter", message="Buy and Sell alert on Range Filter")
// Impulse + Safezone
source = close
out22 = ta.ema(source, 13)
out3 = ta.ema(source, 26)
plot(out22, color=out22 > out22[1] ? color.green : color.red, linewidth=1,
title='Ema fast', transp=0)
plot(out3, color=color.new(#cc9900, 0), linewidth=1, title='Ema slow')
// Calculating for Impulse + Safezone
fast_ma = ta.ema(source, 12)
slow_ma = ta.ema(source, 26)
macd = fast_ma - slow_ma
signal = ta.ema(macd, 9)
hist = macd - signal
ema = ta.ema(source, 12)
elder_bulls = ema[0] > ema[1] and hist[0] > hist[1]
elder_bears = ema[0] < ema[1] and hist[0] < hist[1]
elder_color = elder_bulls ? color.green : elder_bears ? color.red : color.blue
// Bar Color for Impulse + Safezone
barcolor(elder_color)
// Safezone Calculations
lookbackLength = input(99, 'LookBackLength')
coeff = input.float(2, 'CoEff short stop', step=0.25)
countShort = high > high[1] ? 1 : 0
diffShort = high > high[1] ? high - high[1] : 0
totalCountShort = math.sum(countShort, lookbackLength)
totalSumShort = math.sum(diffShort, lookbackLength)
penAvgShort = totalSumShort / totalCountShort
safetyShort = high[1] + penAvgShort[1] * coeff
short_stop = math.min(math.min(safetyShort, safetyShort[1]), safetyShort[2])
count = low < low[1] ? 1 : 0
diff = low < low[1] ? low[1] - low : 0
totalCount = math.sum(count, lookbackLength)
totalSum = math.sum(diff, lookbackLength)
penAvg = totalSum / totalCount
safety = low[1] - penAvg[1] * coeff
long_stop = math.max(math.max(safety, safety[1]), safety[2])
shortvs = 0.0
shortvs := na(shortvs[1]) ? short_stop : close > shortvs[1] ? short_stop :
math.min(short_stop, shortvs[1])
longvs = 0.0
longvs := na(longvs[1]) ? long_stop : close < longvs[1] ? long_stop :
math.max(long_stop, longvs[1])
// Plot Safezone Stops
plot(longvs[1], color=color.new(color.red, 0), style=plot.style_circles,
linewidth=1, title='Stop for Longs-Sell Signal')
plot(shortvs[1], color=color.new(color.blue, 0), style=plot.style_circles,
linewidth=1, title='Stop for Shorts-Buy Signal')