Sigma Expected Movement [D/W/M]
// This source code is subject to the terms of the Mozilla Public License 2.0 at https://mozilla.org/MPL/2.0/
// © seba34e

//@version=5
indicator("Sigma Expected Movement [D/W/M]", overlay=true)

period = input.string("DAY", title="Period", options = ["DAY", "WEEK", "MONTH"])
FirstDeviation = input.float (68, title = "First Deviation (%)")
SecondDeviation = input.float (90, title = "Second Deviation (%)")
roundIt = input.bool(false, title = "Round to Integer", inline = "Round")
spread = input.int(5, title="", inline = "Round")
tablePosition = input.string(title = 'Table Position', defval="Top right", options = ["Top right", "Top left", "Bottom right", "Bottom left"], tooltip='Position of the table')

operableDays = 0
var yy1= 0.0
var table TheTable = table.new(tablePosition == "Top right" ? position.top_right : tablePosition == "Top left" ? position.top_left : tablePosition == "Bottom right" ? position.bottom_right : position.bottom_left, 2, 20, border_width=2)

fill_Cell(_table, _column, _row, _title, _value, _bgcolor, _txtcolor) =>
    _cellText = _title + '' + _value
    table.cell(_table, _column, _row, _cellText, bgcolor=_bgcolor, text_color=_txtcolor, text_halign=text.align_right)

if period == "DAY"
    operableDays :=252
if period == "WEEK"
    operableDays :=52
if period == "MONTH"
    operableDays :=12

//Geting data
previousClose = nz(request.security(syminfo.tickerid, "D", close[1]))
vixClose = nz(request.security("TVC:VIX",timeframe.period, close))

raizCuadrada = math.sqrt(operableDays)
d = vixClose / raizCuadrada
ME = previousClose * (d / 100)
ME_sup = previousClose + ME
ME_inf = previousClose - ME
ME_inv = previousClose

RangoUp1   = ME_inv + ((ME_sup - ME_inv) * (FirstDeviation/100))
RangoDown1 = ME_inv + ((ME_inv - ME_sup) * (FirstDeviation/100))

RangoUp2 =   ME_inv + ((ME_sup - ME_inv) * (SecondDeviation/100))
RangoDown2 = ME_inv + ((ME_inv - ME_sup) * (SecondDeviation/100))

if roundIt // round to integer (default 5)
    yy1 := ME_sup % spread 
    if yy1 > spread / 2
        ME_sup := ME_sup + (spread-yy1)
    else
        ME_sup := ME_sup - yy1
    
    yy1 := ME_inf % spread 
    if yy1 > spread / 2
        ME_inf := ME_inf + (spread-yy1)
    else
        ME_inf := ME_inf - yy1

    yy1 := RangoUp1 % spread 
    if yy1 > spread / 2
        RangoUp1 := RangoUp1 + (spread-yy1)
    else
        RangoUp1 := RangoUp1 - yy1

    yy1 := RangoDown1 % spread 
    if yy1 > spread / 2
        RangoDown1 := RangoDown1 + (spread-yy1)
    else
        RangoDown1 := RangoDown1 - yy1
    
    yy1 := RangoUp2 % spread 
    if yy1 > spread / 2
        RangoUp2 := RangoUp2 + (spread-yy1)
    else
        RangoUp2 := RangoUp2 - yy1
    
    yy1 := RangoDown2 % spread 
    if yy1 > spread / 2
        RangoDown2 := RangoDown2 + (spread-yy1)
    else
        RangoDown2 := RangoDown2 - yy1

// Draw lines
line_inf = line.new(bar_index,ME_inf,bar_index+10,ME_inf, color=color.purple, width = 2)
line_sup = line.new(bar_index,ME_sup,bar_index+10,ME_sup, color=color.purple, width = 2)
label_sup = label.new(bar_index,ME_sup, "EM+  " + str.tostring(ME_sup, "0.00"),  style=label.style_label_down, textcolor = color.white)
label_inf = label.new(bar_index,ME_inf, "EM-  " + str.tostring(ME_inf, "0.00"), style=label.style_label_up, textcolor = color.white)

line_sup1 = line.new(bar_index,RangoUp1,bar_index+10,RangoUp1, color=color.yellow, style=line.style_dashed, width = 1)
line_inf1 = line.new(bar_index,RangoDown1,bar_index+10,RangoDown1, color=color.yellow,style=line.style_dashed, width = 1)
label_firstSup = label.new(bar_index+10,RangoUp1,str.tostring(RangoUp1, "0.00"),  style=label.style_none, textcolor = color.yellow)
label_firstDown = label.new(bar_index+10,RangoDown1,str.tostring(RangoDown1, "0.00"),  style=label.style_none, textcolor = color.yellow)

line_sup2 = line.new(bar_index,RangoUp2,bar_index+10,RangoUp2, color=color.blue, style=line.style_dashed, width = 1)
line_inf2 = line.new(bar_index,RangoDown2,bar_index+10,RangoDown2, color=color.blue, style=line.style_dashed, width = 1)
label_secondSup = label.new(bar_index+10,RangoUp2,str.tostring(RangoUp2, "0.00"),  style=label.style_none, textcolor = color.blue)
label_secondDown = label.new(bar_index+10,RangoDown2,str.tostring(RangoDown2, "0.00"),  style=label.style_none, textcolor = color.blue)

line_previousClose = line.new(bar_index,previousClose,bar_index+10, previousClose, color=color.white, style=line.style_dashed, width = 1)
label_previousClose = label.new(bar_index, previousClose, "Previous Close",  style=label.style_none, textcolor = color.white)

//Delete prevous lines
line.delete(line_inf[1])
line.delete(line_sup[1])

line.delete(line_inf1[1])
line.delete(line_inf2[1])

line.delete(line_sup1[1])
line.delete(line_sup2[1])
line.delete(line_previousClose[1])

label.delete(label_sup[1])
label.delete(label_inf[1])
label.delete(label_firstSup[1])
label.delete(label_secondSup[1])
label.delete(label_firstDown[1])
label.delete(label_secondDown[1])
label.delete(label_previousClose[1])

// Shows Table
if barstate.islast
    fill_Cell(TheTable, 0, 0, "", 'Period' , color.black, color.yellow)
    fill_Cell(TheTable, 1, 0, "", period , color.black, color.yellow)

    fill_Cell(TheTable, 0, 1, "", 'EM' , color.black, color.yellow)
    fill_Cell(TheTable, 1, 1, "", str.tostring(ME,"± 0.00") , color.black, color.yellow)

    fill_Cell(TheTable, 0, 2, "", 'Expected Movement UP' , color.black, color.yellow)
    fill_Cell(TheTable, 1, 2, "", str.tostring(ME_sup,"0.00") , color.black, color.yellow)
    
    fill_Cell(TheTable, 0, 3, "", 'Expected Movement DOWN' , color.black, color.yellow)
    fill_Cell(TheTable, 1, 3, "", str.tostring(ME_inf,"0.00") , color.black, color.yellow)

    fill_Cell(TheTable, 0, 4, "", 'VIX' , color.black, color.yellow)
    fill_Cell(TheTable, 1, 4, "", str.tostring(vixClose,"0.00") , color.black, color.yellow)

    fill_Cell(TheTable, 0, 5, "", 'Previous Close' , color.black, color.yellow)
    fill_Cell(TheTable, 1, 5, "", str.tostring(previousClose,"0.00") , color.black, color.yellow)
    
