RedK Chop & Breakout Scout (C&B_Scout)
// This source code is subject to the terms of the Mozilla Public License 2.0 at https://mozilla.org/MPL/2.0/
// © RedKTrader

//@version=5

indicator('RedK Chop & Breakout Scout ', shorttitle='C&B_Scout v2.0', overlay = false, explicit_plot_zorder = true, timeframe='', timeframe_gaps=false)

// plots a centered oscillator based on how many ATR units the source price is from a price baseline (could be a Donchian midline or another slow MA) 
// the Chop Zone is detected when the price is within a customizable ATR-based distance above or below the baseline
// a filter is then applied (using EMA - but can be other types of long-term MA) to indicate the preferred trade direction (long vs. short)
// when the CBS line is inside the chop zone, trading is not recommended for the conservative trader 
// Breakouts are found when the CBS line exits the Chop zone (in agreement with the filter direction)
// An aggressive swing trader can consider positions when the CBS line crosses the 0 line in the filter direction

// =================================================================================================
//                                  ATR Calclatioin Function
// =================================================================================================
ATR_Calc(_price, _length, _atrcalc) =>
	switch _atrcalc
		"RMA" => ta.rma(_price, _length)
		"SMA" => ta.sma(_price, _length)
		"EMA" => ta.ema(_price, _length)
		=> ta.wma(_price, _length)
		
// =================================================================================================
//                                  Inputs
// =================================================================================================

Src         = input.source(close,   title = 'Price')
Length      = input.int(10,         title = 'Baseline Length',  minval = 1)

AtrLength   = input.int(10,         title = 'TR Avg Length',    minval = 1)
ATRCalc     = input.string('RMA',   title = 'ATR Calculation',  options = ["RMA", "SMA", "EMA", "WMA"])

slevel      = input.float(0.5,      title = 'Chop Level',       step = 0.05)

smooth      = input.int(3,          title = 'Smooth',           minval = 1)
Filter      = input.int(20,         title = 'EMA Filter',       minval = 1)

// =================================================================================================
//                                  Calculations
// =================================================================================================


//calculate baseline price -- for v1.0, we'll use a Donchain midline - can add other slow MA's in future
baseline    = (ta.highest(Length) + ta.lowest(Length))/2

// Calculate ATR

ATR = ATR_Calc(ta.tr(true), Length, ATRCalc) 

// CBS value is basically how far is current price from the baseline in terms of "ATR units"
cbs         = (Src - baseline)/ATR
scbs        = ta.wma(cbs, smooth)

// check where is price wrt the filter line to determine recommended trading direction
// in v1, we use an EMA-based filter as it's most popular -- may add other MA types in future.
f_modelong  = Src > ta.ema(Src, Filter)

// =================================================================================================
//                                  Plots
// =================================================================================================

hline(0, title = 'Zero Line', color = color.blue, linestyle = hline.style_solid)
h0          = hline(slevel, "Chop Zone - Upper", color=#787B86, display=display.none)
h1          = hline(-slevel, "Chop Zone - Lower", color=#787B86, display=display.none)

c_modelong  = color.new(#1b5e20, 50)
c_modeshort = color.new(#981919, 50)
FillColor   =  f_modelong ? c_modelong : c_modeshort

fill(h0, h1, color = FillColor, title = "Background")

// Dynamic coloring of CBS line
c_cbslong   = color.new(#11ff20, 60)
c_cbsshort  = color.new(#ff1111, 60)
c_cbs_chop  = color.new(#ffee58, 50)   

// the coloring condition is based on the "CBS_Raw" value to give earliest signal regarding of smoothing
cbs_color   = f_modelong and cbs > slevel ? c_cbslong : 
  not(f_modelong) and cbs < -slevel ? c_cbsshort : 
  c_cbs_chop

plot(cbs, title = "CBS Raw", display = display.none)

// avoid dublicating the CBS "cloud" value on the status line - by default the cloud is hidden - not sure how many would visually prefer a cloud vs a line.
showcloud = input.bool(false, "Show CBS Cloud?")

plot(showcloud ? scbs : na, title = "CBS Cloud", color = cbs_color, 
  style = plot.style_area, display = not(showcloud) ? display.none : (display.all - display.status_line))

plot(scbs, title = "CBS Line", color = cbs_color, linewidth = 3)

// =================================================================================================
//                                  Alerts
// =================================================================================================

// These alerts will only trigger if a breakout to the upside happens in long mode (price above filterline)  
// or a breakout to the downside happens in short mode (price below filterline)  
// to avoid whipsaws, we can apply smoothing to the price crossing the filter - which will reduce false alerts in volatile conditions
// Thought of adding an alert when price comes back into Chop Zone.. then thought it would be too much distraction.. Feedback ?
alert_up    = f_modelong and ta.crossover(cbs, slevel)
alert_dn    = not(f_modelong) and ta.crossunder(cbs, -slevel)
alertcondition(alert_up,    "CBS Breaking Up",      "Break Up in Long Mode Detected!")
alertcondition(alert_dn,    "CBS Breaking Down",    "Break Down in Short Mode Detected!")



