Dynamic Zone Range on PDFMA [Loxx]
// This source code is subject to the terms of the Mozilla Public License 2.0 at https://mozilla.org/MPL/2.0/
// © loxx

//@version=5
indicator("Dynamic Zone Range on PDFMA [Loxx]",
     shorttitle='DDZRPDFMA [Loxx]', 
     overlay = false, 
     timeframe="", 
     timeframe_gaps = true)
     
import loxx/loxxdynamiczone/3

greencolor = #2DD204
redcolor = #D2042D
lightgreencolor = #96E881 
lightredcolor =  #DF4F6C

SM02 = 'Slope'
SM03 = 'Middle Crossover'
SM04 = 'Inner Crossover'
SM05 = 'Outer Crossover'

_calcBaseUnit() =>
    bool isForexSymbol = syminfo.type == "forex"
    bool isYenPair = syminfo.currency == "JPY"
    float out = isForexSymbol ? isYenPair ? 0.01 : 0.0001 : syminfo.mintick
    out
    
_stepSizeCalc(type, per, sense, size)=>
    float stma = 0.
    float ATR0 = 0.
    float ATRmax = -1e10
    float ATRmin = 1e10
    float out = 0
    float alfa = 0
    if (size == 0) 
        float avgrng = 0
        float Weight = 0
        for i = per-1 to 0 
            if (type == "SMA")
                alfa := 1.0
            else
                alfa := 1.0 * (per - i) / per
            avgrng += alfa * (nz(high[i]) - nz(low[i]))
            Weight += alfa
        ATR0 := avgrng / Weight
        if (ATR0 > ATRmax) 
            ATRmax := ATR0
        if (ATR0 < ATRmin) 
            ATRmin := ATR0
        out := math.round(0.5 * sense * (ATRmax + ATRmin) / _calcBaseUnit())
    else
        out := sense * size
    out

_pdf(x, vari, mean)=>
    out = (1.0/math.sqrt(2 * math.pi * math.pow(vari,2)) * math.exp(-math.pow(x-mean, 2)/(2 * math.pow(vari, 2))))
    out

_pdfma(src, per, vari, mean)=>
    maxx = 3.5
    step = math.pi/(per-1)
    coeff = array.new_float(per, 0)
    for k = 0 to per - 1
        array.set(coeff, k, _pdf(k * step, vari, mean * math.pi))
    sumw = array.get(coeff, 0)
    sum  = array.get(coeff, 0) * src
    for k = 1 to per -1  
        weight = nz(array.get(coeff, k)) * src
        sumw += weight 
        sum += weight * nz(src)
    out = sum/sumw
    out
    
HLR_Range = input.int(25, "HLR Range", group = "Basic Settings")

per = input.int(10, "Period", group = "Basic Settings") 
MA_Mode = input.string("SMA", "MA Type", options = ["SMA", "LWMA"], group = "Basic Settings")
Percentage = input.float(0, "Percentage", step = 0.1, group = "Basic Settings", tooltip = "Percentage of Up/Down Moving")
stepsize = input.int(20, "Step Size", group = "Basic Settings") 
sense = input.float(5, "Sensivity", step = 0.1, minval = 0.1, group = "Basic Settings") 
vari = input.float(1, "variance", step = 0.1, minval = 0.1, group = "Basic Settings") 
mean = input.float(0, "Mean", step = 0.1, minval = -1, maxval = 1, group = "Basic Settings")
HighLow = input.bool(false, "High/Low mode?", group = "Basic Settings") 

dzper = input.int(70, "Dynamic Zone Period", group = "Levels Settings") 
buy1  = input.float(0.2, "Dynamic Zone Buy Probability Level 1", group = "Levels Settings", maxval = 0.49)
buy2  = input.float(0.06, "Dynamic Zone Buy Probability Level 2", group = "Levels Settings", maxval = 0.49)
sell1 = input.float(0.2, "Dynamic Zone Sell Probability Level 1", group = "Levels Settings", maxval = 0.49)
sell2 = input.float(0.06, "Dynamic Zone Sell Probability Level 2", group = "Levels Settings", maxval = 0.49)

sigtype = input.string(SM03, "Signal type", options = [SM02, SM03, SM04, SM05], group = "Signal Settings")

colorbars = input.bool(false, "Color bars?", group= "UI Options")
ShowMiddleLine  = input.bool(true, "Show middle line?", group = "UI Options")  
filllevels  = input.bool(false, "Show fill colors?", group = "UI Options")  
showsignals = input.bool(false, "Show signals?", group = "UI Options")

size = _stepSizeCalc(MA_Mode, per, sense, stepsize)
smax = 0., smin = 0.
hhv = 0., llv = 0., m_pr = 0.
if HighLow
    hhv  := _pdfma(ta.highest(high, HLR_Range), per, vari, mean) + 2.0 * size * _calcBaseUnit()
    llv  := _pdfma(ta.lowest(low, HLR_Range), per, vari, mean) - 2.0 * size * _calcBaseUnit()
    m_pr := _pdfma(hl2, per, vari, mean) 
else 
    hhv  := _pdfma(ta.highest(close, HLR_Range), per, vari, mean) + 2.0 * size * _calcBaseUnit()
    llv  := _pdfma(ta.lowest(close, HLR_Range), per, vari, mean) - 2.0 * size * _calcBaseUnit()
    m_pr := _pdfma(hl2, per, vari, mean) 
    
HLR_Buffer = 100.0 * (m_pr - llv) / (hhv - llv) 
 
bl1 = loxxdynamiczone.dZone("buy", HLR_Buffer, buy1,  dzper)
bl2 = loxxdynamiczone.dZone("buy", HLR_Buffer, buy2,  dzper)
sl1 = loxxdynamiczone.dZone("sell", HLR_Buffer, sell1, dzper)
sl2 = loxxdynamiczone.dZone("sell", HLR_Buffer, sell2, dzper)
zli = loxxdynamiczone.dZone("sell", HLR_Buffer, 0.5 , dzper)

state = 0.

if sigtype == SM02
    if (HLR_Buffer<nz(HLR_Buffer[1])) 
        state :=-1
    if (HLR_Buffer>nz(HLR_Buffer[1])) 
        state := 1
else if sigtype == SM03
    if (HLR_Buffer<zli) 
        state :=-1
    if (HLR_Buffer>zli)
        state := 1
else if sigtype == SM04
    if (HLR_Buffer<bl1) 
        state :=-1
    if (HLR_Buffer>sl1)
        state := 1
else if sigtype == SM05
    if (HLR_Buffer<bl2) 
        state :=-1
    if (HLR_Buffer>sl2)
        state := 1

colorout = state == -1 ? redcolor : state == 1 ? greencolor : color.gray

plot(HLR_Buffer, "PDFMA", color = colorout, linewidth = 3)
bl1pl = plot(bl1, "buy lvl 1", color = bar_index % 3 ? lightgreencolor: na)
bl2pl = plot(bl2, "buy lvl 2", color = bar_index % 2 ? greencolor: na)
sl1pl = plot(sl1, "sell lvl 1", color = bar_index % 3 ? lightredcolor: na)
sl2pl = plot(sl2, "sell lvl 1", color = bar_index % 2 ? redcolor: na)

midpl = plot(ShowMiddleLine ? zli : na, "mid lvl", color = bar_index % 4 ? color.white : na)

fill(bl1pl, bl2pl, color = filllevels ? color.new(greencolor, 85) : na)
fill(bl2pl, midpl, color = filllevels ? color.new(greencolor, 95): na)
fill(sl1pl, sl2pl, color = filllevels ? color.new(redcolor, 85): na)
fill(sl2pl, midpl, color = filllevels ? color.new(redcolor, 95): na)

barcolor(colorbars ? colorout : na)

goLong = colorout == greencolor and colorout[1] == redcolor
goShort = colorout == redcolor and colorout[1] == greencolor
plotshape(goLong and showsignals, title = "Long", color = greencolor, textcolor = greencolor, text = "L", style = shape.triangleup, location = location.bottom, size = size.auto)
plotshape(goShort and showsignals, title = "Short", color = redcolor, textcolor = redcolor, text = "S", style = shape.triangledown, location = location.top, size = size.auto)

alertcondition(goLong, title="Long", message="Dynamic Zone Range on PDFMA [Loxx]: Long\nSymbol: {{ticker}}\nPrice: {{close}}")
alertcondition(goShort, title="Short", message="Dynamic Zone Range on PDFMA [Loxx]: Short\nSymbol: {{ticker}}\nPrice: {{close}}")














