Full Volatility Statistics and Forecast
// This source code is subject to the terms of the Mozilla Public License 2.0 at https://mozilla.org/MPL/2.0/
// © exlux99

//@version=5
indicator("Full Volatility Statistics and Forecast", overlay=true)


 ////////////////////////
// FUNCTIONS
source = input.source(open, title="Source of the Candle", group="Source", group="Candle")
candle_point = 0//input.int(0, title="Candle Calculation", group="Candle")
volatility_source = input.symbol("TVC:VIX", title= "External Source Volatility", group="Volatility")



coeficient = input.float(1.0, step=0.25, title="Coefficient", group="Volatility")
vix = request.security(volatility_source, timeframe.period, open)
vix_close = request.security(volatility_source, timeframe.period, close[1])

vix_length = 1//input.int(1)
vix_sma_hv = ta.sma(vix_close,(vix_length))
vix_sma = ta.sma(vix,(vix_length))



// label Panel Function
_label(T, color_PnL) =>
    label PnL_Label = na
    label.delete(PnL_Label[1])
    PnL_Label := label.new(time, 0, text=T, color=color_PnL, textcolor=color.white, size=size.normal, style=label.style_label_lower_left, xloc=xloc.bar_time, textalign=text.align_left)
    label.set_x(PnL_Label, label.get_x(PnL_Label) + math.round(ta.change(time) * 3))

// Round Function
Round(src, digits) =>
    p = math.pow(10, digits)
    math.round(math.abs(src) * p) / p * math.sign(src)


sqrt_movement = input.float(252, title="Timeframe Adaptation", group="Volatility")

// Historical Volatiity Models
Hv_zero =  vix_sma_hv*coeficient


var int min_hv_iv_plus =0
var int max_hv_iv_plus =0
var int min_temp_hv_iv_plus =0
var int max_temp_hv_iv_plus =0

var int min_hv_iv_minus =0
var int max_hv_iv_minus =0
var int min_temp_hv_iv_minus =0
var int max_temp_hv_iv_minus =0

var float avg_distance_top_hv_iv_plus = 0
var float daily_bull_movement_hv_iv_plus = 0

var float avg_distance_bot_hv_iv_plus = 0
var float daily_bear_movement_hv_iv_plus = 0

var float avg_distance_top_hv_iv_minus = 0
var float daily_bull_movement_hv_iv_minus = 0

var float avg_distance_bot_hv_iv_minus = 0
var float daily_bear_movement_hv_iv_minus = 0


var float daily_bull_movement = 0
var int count_bull = 0
var float daily_bear_movement = 0
var int count_bear = 0



Hv = Hv_zero/ math.sqrt(sqrt_movement) 
top_channel = source + (source*Hv)/100
bot_channel = source - (source*Hv)/100

plot(top_channel)
plot(bot_channel)



var bool data_top_cross = false
var bool data_bot_cross = false
var bool suma_velas = false

var bool data_top_cross_partial_high = false
var bool data_bot_cross_partial_high = false
var bool suma_velas_partial_high = false




fromDay = input.int(defval=1, title='From Day', minval=1, maxval=31, group='Time Condition')
fromMonth = input.int(defval=1, title='From Month', minval=1, maxval=12, group='Time Condition')
fromYear = input.int(defval=2000, title='From Year', minval=1970, group='Time Condition')
//monday and session 
// To Date Inputs
toDay = input.int(defval=31, title='To Day', minval=1, maxval=31, group='Time Condition')
toMonth = input.int(defval=12, title='To Month', minval=1, maxval=12, group='Time Condition')
toYear = input.int(defval=2029, title='To Year', minval=1970, group='Time Condition')

startDate = timestamp(fromYear, fromMonth, fromDay, 00, 00)
finishDate = timestamp(toYear, toMonth, toDay, 00, 00)
time_cond = time >= startDate and time <= finishDate


data_top_cross := close >= top_channel[candle_point] and time_cond   
data_bot_cross := close <=  bot_channel[candle_point] and time_cond  
suma_velas := close!=0 

plotshape(data_top_cross, style=shape.xcross, location=location.abovebar, color=color.yellow)
plotshape(data_bot_cross, style=shape.xcross, location=location.belowbar, color=color.yellow)


data_top_cross_partial_high := high >= top_channel[candle_point] and time_cond   
data_bot_cross_partial_high := low <=  bot_channel[candle_point] and time_cond  
suma_velas_partial_high := close!=0 
    



var int count_top_crosses_hv_iv_plus = 0
var int count_bot_crosses_hv_iv_plus = 0


if(data_top_cross and Hv<= vix_sma)
    count_top_crosses_hv_iv_plus:=count_top_crosses_hv_iv_plus+1

if(data_bot_cross and Hv<= vix_sma )
    count_bot_crosses_hv_iv_plus:=count_bot_crosses_hv_iv_plus+1


var int count_candles_hv_iv_plus = 0

if(suma_velas and time_cond and Hv <= vix_sma)
    count_candles_hv_iv_plus := count_candles_hv_iv_plus+1
    
    
    
ratio_hv_iv_plus = (count_top_crosses_hv_iv_plus + count_bot_crosses_hv_iv_plus) / count_candles_hv_iv_plus

///////////////////////////////////////////////

var int count_top_crosses_hv_iv_plus_partial_high = 0
var int count_bot_crosses_hv_iv_plus_partial_high = 0

if(data_top_cross_partial_high and Hv<= vix_sma)
    count_top_crosses_hv_iv_plus_partial_high:=count_top_crosses_hv_iv_plus_partial_high+1

if(data_bot_cross_partial_high and Hv<= vix_sma )
    count_bot_crosses_hv_iv_plus_partial_high:=count_bot_crosses_hv_iv_plus_partial_high+1

var int count_candles_hv_iv_plus_partial_high = 0

if(suma_velas_partial_high and time_cond and Hv <= vix_sma)
    count_candles_hv_iv_plus_partial_high := count_candles_hv_iv_plus_partial_high+1
    
    
ratio_hv_iv_plus_partial_high = (count_top_crosses_hv_iv_plus_partial_high + count_bot_crosses_hv_iv_plus_partial_high) / count_candles_hv_iv_plus_partial_high




if(time_cond and (data_top_cross or data_bot_cross) and Hv <= vix_sma )  
    min_temp_hv_iv_plus:=0
    max_temp_hv_iv_plus := max_temp_hv_iv_plus+1
    if(max_temp_hv_iv_plus>max_hv_iv_plus )
        max_hv_iv_plus:=max_temp_hv_iv_plus
            
if(time_cond and Hv <= vix_sma and not (data_top_cross or data_bot_cross ) )
    max_temp_hv_iv_plus:=0
    min_temp_hv_iv_plus := min_temp_hv_iv_plus+1
    if(min_temp_hv_iv_plus > min_hv_iv_plus )
        min_hv_iv_plus:=min_temp_hv_iv_plus


var int count_top_crosses_hv_iv_minus = 0
var int count_bot_crosses_hv_iv_minus = 0

if(data_top_cross and Hv > vix_sma)
    count_top_crosses_hv_iv_minus:=count_top_crosses_hv_iv_minus+1

if(data_bot_cross and Hv > vix_sma)
    count_bot_crosses_hv_iv_minus:=count_bot_crosses_hv_iv_minus+1

var int count_candles_hv_iv_minus = 0

if(suma_velas and time_cond and Hv > vix_sma)
    count_candles_hv_iv_minus := count_candles_hv_iv_minus+1
    
ratio_hv_iv_minus = (count_top_crosses_hv_iv_minus + count_bot_crosses_hv_iv_minus) / count_candles_hv_iv_minus

//////////////////////////////////////////////////////////////////

var int count_top_crosses_hv_iv_minus_partial_high = 0
var int count_bot_crosses_hv_iv_minus_partial_high = 0

if(data_top_cross_partial_high and Hv > vix_sma)
    count_top_crosses_hv_iv_minus_partial_high:=count_top_crosses_hv_iv_minus_partial_high+1

if(data_bot_cross_partial_high and Hv > vix_sma)
    count_bot_crosses_hv_iv_minus_partial_high:=count_bot_crosses_hv_iv_minus_partial_high+1

var int count_candles_hv_iv_minus_partial_high = 0

if(suma_velas_partial_high and time_cond and Hv > vix_sma)
    count_candles_hv_iv_minus_partial_high := count_candles_hv_iv_minus_partial_high+1
    
ratio_hv_iv_minus_partial_high = (count_top_crosses_hv_iv_minus_partial_high + count_bot_crosses_hv_iv_minus_partial_high) / count_candles_hv_iv_minus_partial_high




  
if(time_cond and (data_top_cross or data_bot_cross) and Hv> vix_sma )  
    min_temp_hv_iv_minus:=0
    max_temp_hv_iv_minus := max_temp_hv_iv_minus+1
    if(max_temp_hv_iv_minus>max_hv_iv_minus)
        max_hv_iv_minus:=max_temp_hv_iv_minus
            
if(time_cond and Hv > vix_sma and not (data_top_cross or data_bot_cross ) )
    max_temp_hv_iv_minus:=0
    min_temp_hv_iv_minus := min_temp_hv_iv_minus+1
    if(min_temp_hv_iv_minus > min_hv_iv_minus )
        min_hv_iv_minus:=min_temp_hv_iv_minus



total_candles = count_candles_hv_iv_minus + count_candles_hv_iv_plus
avg_Occurence = ((ratio_hv_iv_minus * count_candles_hv_iv_minus) + (ratio_hv_iv_plus *count_candles_hv_iv_plus ))  / total_candles
avg_Occurence_max_loss =  ((max_hv_iv_minus * count_candles_hv_iv_minus) + (max_hv_iv_plus *count_candles_hv_iv_plus ))  / total_candles 
avg_Occurence_max_win =  ((min_hv_iv_minus * count_candles_hv_iv_minus) + (min_hv_iv_plus *count_candles_hv_iv_plus ))  / total_candles

////////////////////////////////////////////////////////////////////////////
if (data_top_cross and Hv> vix_sma)
    avg_distance_top_hv_iv_minus:=avg_distance_top_hv_iv_minus+ ((close - top_channel[candle_point])/top_channel[candle_point])
    //daily_bull_movement_hv_iv_minus:=daily_bull_movement_hv_iv_minus+((close-open)/open)
if (data_bot_cross and Hv > vix_sma )
    avg_distance_bot_hv_iv_minus:=avg_distance_bot_hv_iv_minus+ ((bot_channel[candle_point] - close)/close)
    //daily_bear_movement_hv_iv_minus:=daily_bear_movement_hv_iv_minus+((open-close)/close)


if (data_top_cross and Hv<= vix_sma)
    avg_distance_top_hv_iv_plus:=avg_distance_top_hv_iv_plus+ ((close - top_channel[candle_point])/top_channel[candle_point])
    //daily_bull_movement_hv_iv_plus:=daily_bull_movement_hv_iv_plus+((close-open)/open)
if (data_bot_cross and Hv<= vix_sma )
    avg_distance_bot_hv_iv_plus:=avg_distance_bot_hv_iv_plus+((bot_channel[candle_point] - close)/close)
    //daily_bear_movement_hv_iv_plus:=daily_bear_movement_hv_iv_plus+((open-close)/close)


////////////////////////////////////////////////////////////////////////////

if(close > open and time_cond )
    count_bull:=count_bull+1
    daily_bull_movement:=daily_bull_movement+((close-open)/open)

if(close < open and time_cond)
    count_bear:=count_bear+1
    daily_bear_movement:=daily_bear_movement+((open-close)/close)



////////////////////////////////////////////////////////////////////////////
posInput = input.string(title='Position', defval='Middle Right', options=['Bottom Left', 'Bottom Right', 'Top Left', 'Top Right', 'Middle Right'])
var pos = posInput == 'Bottom Left' ? position.bottom_left : posInput == 'Bottom Right' ? position.bottom_right : posInput == 'Top Left' ? position.top_left : posInput == 'Top Right' ? position.top_right : posInput == 'Middle Right' ? position.middle_right: na


var table table_atr = table.new(pos, 15, 15, border_width=1)


table_fillCell(_table, _column, _row, _value, _timeframe, _c_color) =>
    _transp = 70  
    _cellText = str.tostring(_value, '#.###')
    table.cell(_table, _column, _row, _cellText, bgcolor=color.new(_c_color, _transp), text_color=_c_color, width=5)
    //table.cell_set_text_size(table_atr, 0, 2, text)


if barstate.islast


    table.cell(table_atr, 0, 0, 'Total C', text_color=color.white, text_size=size.normal, bgcolor=color.purple)
    table_fillCell(table_atr, 0, 1, count_top_crosses_hv_iv_plus+ count_bot_crosses_hv_iv_plus, 'Text', color.white)
    table.cell(table_atr, 1, 0, 'BOT Ψ C', text_color=color.white, text_size=size.normal, bgcolor=color.purple)
    table_fillCell(table_atr, 1, 1, count_bot_crosses_hv_iv_plus, 'Text', color.white)
    table.cell(table_atr, 2, 0, 'TOP Ψ C', text_color=color.white, text_size=size.normal, bgcolor=color.purple)
    table_fillCell(table_atr, 2, 1, count_top_crosses_hv_iv_plus, 'Text', color.white)
    table.cell(table_atr, 3, 0, 'Candles Ψ C', text_color=color.white, text_size=size.normal, bgcolor=color.purple)
    table_fillCell(table_atr, 3, 1, count_candles_hv_iv_plus, 'Text', color.white)
    table.cell(table_atr, 4, 0, 'Occurence Ψ C', text_color=color.white, text_size=size.normal, bgcolor=color.purple)
    table_fillCell(table_atr, 4, 1, ratio_hv_iv_plus, 'Text HV<IV', color.white)
    table.cell(table_atr, 5, 0, 'OUT', text_color=color.white, text_size=size.normal, bgcolor= coeficient < 1?color.lime: color.red)
    table_fillCell(table_atr, 5, 1, max_hv_iv_plus, 'Text HV<IV', color.white)
    table.cell(table_atr, 6, 0, 'IN ', text_color=color.white, text_size=size.normal, bgcolor= coeficient < 1? color.red : color.lime)
    table_fillCell(table_atr, 6, 1, min_hv_iv_plus, 'Text HV<IV', color.white)
    table.cell(table_atr, 7, 0, '% D top', text_color=color.white, text_size=size.normal, bgcolor=color.orange)
    table_fillCell(table_atr, 7, 1, (avg_distance_top_hv_iv_plus/count_top_crosses_hv_iv_plus)*100, 'AVG Distance HV<IV', color.white)
    table.cell(table_atr, 8, 0, '% D bot', text_color=color.white, text_size=size.normal, bgcolor=color.orange)
    table_fillCell(table_atr, 8, 1, (avg_distance_bot_hv_iv_plus/count_bot_crosses_hv_iv_plus)*100, 'AVG Distance HV<IV', color.white)
    // table.cell(table_atr, 9, 0, 'AVG Bull', text_color=color.white, text_size=size.normal, bgcolor=color.lime)
    // table_fillCell(table_atr, 9, 1, (daily_bull_movement_hv_iv_plus/count_top_crosses_hv_iv_plus)*100, 'AVG Distance HV<IV', color.white)
    // table.cell(table_atr, 10, 0, 'AVG Bear', text_color=color.white, text_size=size.normal, bgcolor=color.red)
    // table_fillCell(table_atr, 10, 1, (daily_bear_movement_hv_iv_plus/count_bot_crosses_hv_iv_plus)*100, 'AVG Distance HV<IV', color.white)

   
    // table.cell(table_atr, 0, 4, 'Total Ω C', text_color=color.white, text_size=size.normal, bgcolor=color.aqua)
    // table_fillCell(table_atr, 0, 5, count_top_crosses_hv_iv_minus + count_bot_crosses_hv_iv_minus, 'Text', color.white)
    // table.cell(table_atr, 1, 4, 'BOT Ω C', text_color=color.white, text_size=size.normal, bgcolor=color.aqua)
    // table_fillCell(table_atr, 1, 5, count_bot_crosses_hv_iv_minus, 'Text', color.white)
    // table.cell(table_atr, 2, 4, 'TOP Ω C', text_color=color.white, text_size=size.normal, bgcolor=color.aqua)
    // table_fillCell(table_atr, 2, 5, count_top_crosses_hv_iv_minus, 'Text', color.white)
    // table.cell(table_atr, 3, 4, 'Candles Ω C', text_color=color.white, text_size=size.normal, bgcolor=color.aqua)
    // table_fillCell(table_atr, 3, 5, count_candles_hv_iv_minus, 'Text', color.white)
    // table.cell(table_atr, 4, 4, 'Occurence Ω C', text_color=color.white, text_size=size.normal, bgcolor=color.aqua)
    // table_fillCell(table_atr, 4, 5, ratio_hv_iv_minus, 'Text', color.white)
    // table.cell(table_atr, 5, 4, 'OUT', text_color=color.white, text_size=size.normal, bgcolor=color.red)
    // table.cell(table_atr, 6, 4, 'IN', text_color=color.white, text_size=size.normal, bgcolor=color.lime)
    // table_fillCell(table_atr, 5, 5, max_hv_iv_minus, 'Text', color.white)   
    // table_fillCell(table_atr, 6, 5, min_hv_iv_minus, 'Text', color.white)
    // table.cell(table_atr, 7, 4, '% D top', text_color=color.white, text_size=size.normal, bgcolor=color.orange)
    // table_fillCell(table_atr, 7, 5, (avg_distance_top_hv_iv_minus/count_top_crosses_hv_iv_minus)*100, 'AVG Distance HV>IV', color.white)
    // table.cell(table_atr, 8, 4, '% D bot', text_color=color.white, text_size=size.normal, bgcolor=color.orange)
    // table_fillCell(table_atr, 8, 5, (avg_distance_bot_hv_iv_minus/count_bot_crosses_hv_iv_minus)*100, 'AVG Distance HV>IV', color.white)
    // // table.cell(table_atr, 9, 2, 'AVG Bull', text_color=color.white, text_size=size.normal, bgcolor=color.lime)
    // // table_fillCell(table_atr, 9, 3, (daily_bull_movement_hv_iv_minus/count_top_crosses_hv_iv_minus)*100, 'AVG Distance HV>IV', color.white)
    // // table.cell(table_atr, 10, 2, 'AVG Bear', text_color=color.white, text_size=size.normal, bgcolor=color.red)
    // // table_fillCell(table_atr, 10, 3, (daily_bear_movement_hv_iv_minus/count_bot_crosses_hv_iv_minus)*100, 'AVG Distance HV>IV', color.white)


    
    table.cell(table_atr, 0, 8, '∑', text_color=color.white, text_size=size.normal, bgcolor=color.blue)
    table_fillCell(table_atr, 0, 9, close*(vix_sma/ math.sqrt(sqrt_movement))/100, 'Text', color.white)   
    table.cell(table_atr, 1, 8, 'TOP ∑', text_color=color.white, text_size=size.normal, bgcolor=color.lime)
    table_fillCell(table_atr, 1, 9, top_channel[candle_point], 'Text', color.white)
    table.cell(table_atr, 2, 8, 'BOT ∑', text_color=color.white, text_size=size.normal, bgcolor=color.orange)
    table_fillCell(table_atr, 2, 9, bot_channel[candle_point], 'Text', color.white)
    table.cell(table_atr, 3, 8, 'Total Candles', text_color=color.white, text_size=size.normal, bgcolor=color.navy)
    table_fillCell(table_atr, 3, 9, total_candles, 'Text', color.white)
    table.cell(table_atr, 4, 8, 'AVG Occurence', text_color=color.white, text_size=size.normal, bgcolor=color.navy)
    table_fillCell(table_atr, 4, 9, avg_Occurence, 'Text', color.white)
    table.cell(table_atr, 5, 8, 'AVG OUT', text_color=color.white, text_size=size.normal, bgcolor=color.navy)
    table_fillCell(table_atr, 5, 9, avg_Occurence_max_loss, 'Text', color.white)   
    table.cell(table_atr, 6, 8, 'AVG IN', text_color=color.white, text_size=size.normal, bgcolor=color.navy)
    table_fillCell(table_atr, 6, 9, avg_Occurence_max_win, 'Text', color.white)
    table.cell(table_atr, 7, 8, 'AVG Bull', text_color=color.white, text_size=size.normal, bgcolor=color.lime)
    table_fillCell(table_atr, 7, 9, (daily_bull_movement/count_bull)*100, 'Text', color.white)   
    table.cell(table_atr, 8, 8, 'AVG Bear', text_color=color.white, text_size=size.normal, bgcolor=color.red)
    table_fillCell(table_atr, 8, 9, (daily_bear_movement/count_bear)*100, 'Text', color.white)





