# Triple Exhaustion Indicator
##
##
## CREDITS
## Requested by @Chence27 from criteria listed here https://usethinkscript.com/threads/triple-exhaustion-indicator.9001/
##
##
## Removing the header Credit credits and description is not permitted, any modification needs to be shared.
##
## V 1.0 : @cos251 - Initial release per request from www.usethinkscript.com forum thread:
## : https://usethinkscript.com/threads/triple-exhaustion-indicator.9001/
##
##
## adding MTF labels @irishgold 08/22/2022
declare upper;
input agperiod1 = { "1 min", default "2 min", "3 min", "5 min", "10 min", "15 min", "30 min", "1 hour", "2 hours", "4 hours", "Day", "Week", "Month"};
input agperiod2 = {"1 min", "2 min", "3 min", default "5 min", "10 min", "15 min", "30 min", "1 hour", "2 hours", "4 hours", "Day", "Week", "Month"};
input agperiod3 = {"1 min", "2 min", "3 min", "5 min", default "10 min", "15 min", "30 min", "1 hour", "2 hours", "4 hours", "Day", "Week", "Month"};
input agperiod4 = {"1 min", "2 min", "3 min", "5 min", "10 min", default "15 min", "30 min", "1 hour", "2 hours", "4 hours", "Day", "Week", "Month"};
input DI_Length = 14;
# --- Inputs
input over_bought = 80;
input over_sold = 20;
input KPeriod = 10;
input DPeriod = 10;
# --- Def
def currentPeriod = GetAggregationPeriod();
def priceH1 = high(period = agperiod1);
def priceH2 = high(period = agperiod2);
def priceH3 = high(period = agperiod3);
def priceH4 = high(period = agperiod4);
def priceL1 = low(period = agperiod1);
def priceL2 = low(period = agperiod2);
def priceL3 = low(period = agperiod3);
def priceL4 = low(period = agperiod4);
def priceC1 = close(period = agperiod1);
def priceC2 = close(period = agperiod2);
def priceC3 = close(period = agperiod3);
def priceC4 = close(period = agperiod4);
input priceH = high;
input priceL = low;
input priceC = close;
input averageType = AverageType.SIMPLE;
input length = 500;
input paintBars = yes;
input showLabels = yes;
input percentGain = .005;
# --- Indicators - StochasticSlow / MACD / MACD StDev / DMI+/-
def SlowK = reference StochasticFull(over_bought, over_sold, KPeriod, DPeriod, priceH, priceL, priceC, 3, averageType).FullK;
def SlowK1 = reference StochasticFull(over_bought, over_sold, KPeriod, DPeriod, priceH1, priceL1, priceC1, 3, averageType).FullK;
def SlowK2 = reference StochasticFull(over_bought, over_sold, KPeriod, DPeriod, priceH2, priceL2, priceC2, 3, averageType).FullK;
def SlowK3 = reference StochasticFull(over_bought, over_sold, KPeriod, DPeriod, priceH3, priceL3, priceC3, 3, averageType).FullK;
def SlowK4 = reference StochasticFull(over_bought, over_sold, KPeriod, DPeriod, priceH4, priceL4, priceC4, 3, averageType).FullK;
def MACD = reference MACD()."Value";
# This section is for the aggregations term MACD
def MACD1 = (ExpAverage(priceC1[1], 12)) - (ExpAverage(priceC1[1], 26));
def MACD2 = (ExpAverage(priceC2[1], 12)) - (ExpAverage(priceC2[1], 26));
def MACD3 = (ExpAverage(priceC3[1], 12)) - (ExpAverage(priceC3[1], 26));
def MACD4 = (ExpAverage(priceC4[1], 12)) - (ExpAverage(priceC4[1], 26));
def priceMean1 = SimpleMovingAvg(MACD1, length);
def priceMean2 = SimpleMovingAvg(MACD2, length);
def priceMean3 = SimpleMovingAvg(MACD3, length);
def priceMean4 = SimpleMovingAvg(MACD4, length);
def MACD_stdev1 = (MACD1 - priceMean1) / StDev(MACD1, length);
def MACD_stdev2 = (MACD2 - priceMean2) / StDev(MACD2, length);
def MACD_stdev3 = (MACD3 - priceMean3) / StDev(MACD3, length);
def MACD_stdev4 = (MACD4 - priceMean4) / StDev(MACD4, length);
def priceMean = SimpleMovingAvg(MACD, length);
def MACD_stdev = (MACD - priceMean) / StDev(MACD, length);
def dPlus = reference DMI()."DI+";
def dMinus = reference DMI()."DI-";
# DMI computations
def hiDiff1 = priceH1 - priceH1[1];
def loDiff1 = priceL1[1] - priceL1;
def plusDM1 = if hiDiff1 > loDiff1 and hiDiff1 > 0 then hiDiff1 else 0;
def minusDM1 = if loDiff1 > hiDiff1 and loDiff1 > 0 then loDiff1 else 0;
def ATR1 = MovingAverage(averageType, TrueRange(priceH1, priceC1, priceL1), DI_Length);
def dPlus1 = 100 * MovingAverage(AverageType.WILDERS, plusDM1, DI_Length) / ATR1;
def dMinus1 = 100 * MovingAverage(AverageType.WILDERS, minusDM1, DI_Length) / ATR1;
def hiDiff2 = priceH2 - priceH2[1];
def loDiff2 = priceL2[1] - priceL2;
def plusDM2 = if hiDiff2 > loDiff2 and hiDiff2 > 0 then hiDiff2 else 0;
def minusDM2 = if loDiff2 > hiDiff2 and loDiff2 > 0 then loDiff2 else 0;
def ATR2 = MovingAverage(averageType, TrueRange(priceH2, priceC2, priceL2),
DI_Length);
def dPlus2 = 100 * MovingAverage(AverageType.WILDERS, plusDM2, DI_Length) / ATR2;
def dMinus2 = 100 * MovingAverage(AverageType.WILDERS, minusDM2, DI_Length) / ATR2;
def hiDiff3 = priceH3 - priceH3[1];
def loDiff3 = priceL3[1] - priceL3;
def plusDM3 = if hiDiff3 > loDiff3 and hiDiff3 > 0 then hiDiff3 else 0;
def minusDM3 = if loDiff3 > hiDiff3 and loDiff3 > 0 then loDiff3 else 0;
def ATR3 = MovingAverage(averageType, TrueRange(priceH3, priceC3, priceL3), DI_Length);
def dPlus3 = 100 * MovingAverage(AverageType.WILDERS, plusDM3, DI_Length) /
ATR3;
def dMinus3 = 100 * MovingAverage(AverageType.WILDERS, minusDM3, DI_Length) / ATR3;
def hiDiff4 = priceH4 - priceH4[1];
def loDiff4 = priceL4[1] - priceL4;
def plusDM4 = if hiDiff4 > loDiff4 and hiDiff4 > 0 then hiDiff4 else 0;
def minusDM4 = if loDiff4 > hiDiff4 and loDiff4 > 0 then loDiff4 else 0;
def ATR4 = MovingAverage(averageType, TrueRange(priceH4, priceC4, priceL4), DI_Length);
def dPlus4 = 100 * MovingAverage(AverageType.WILDERS, plusDM4, DI_Length) / ATR4;
def dMinus4 = 100 * MovingAverage(AverageType.WILDERS, minusDM4, DI_Length) / ATR4;
# --- End Indicators
# --- Conditions
def sellerRegular = SlowK < 20 and MACD_stdev < -1 and dPlus < 15;
def sellerRegular1 = SlowK1 < 20 and MACD_stdev1 < -1 and dPlus1 < 15;
def sellerRegular2 = SlowK2 < 20 and MACD_stdev2 < -1 and dPlus2 < 15;
def sellerRegular3 = SlowK3 < 20 and MACD_stdev3 < -1 and dPlus3 < 15;
def sellerRegular4 = SlowK4 < 20 and MACD_stdev4 < -1 and dPlus4 < 15;
def sellerExtreme = SlowK < 20 and MACD_stdev < -2 and dPlus < 15;
def sellerExtreme1 = SlowK1 < 20 and MACD_stdev1 < -2 and dPlus1 < 15;
def sellerExtreme2 = SlowK2 < 20 and MACD_stdev2 < -2 and dPlus2 < 15;
def sellerExtreme3 = SlowK3 < 20 and MACD_stdev3 < -2 and dPlus3 < 15;
def sellerExtreme4 = SlowK4 < 20 and MACD_stdev4 < -2 and dPlus4 < 15;
def buyerRegular = SlowK > 80 and MACD_stdev > 1 and dMinus < 15;
def buyerRegular1 = SlowK1 > 80 and MACD_stdev1 > 1 and dMinus1 < 15;
def buyerRegular2 = SlowK2 > 80 and MACD_stdev2 > 1 and dMinus2 < 15;
def buyerRegular3 = SlowK3 > 80 and MACD_stdev3 > 1 and dMinus3 < 15;
def buyerRegular4 = SlowK4 > 80 and MACD_stdev4 > 1 and dMinus4 < 15;
def buyerExtreme = SlowK > 80 and MACD_stdev > 2 and dMinus < 15;
def buyerExtreme1 = SlowK1 > 80 and MACD_stdev1 > 2 and dMinus1 < 15;
def buyerExtreme2 = SlowK2 > 80 and MACD_stdev2 > 2 and dMinus2 < 15;
def buyerExtreme3 = SlowK3 > 80 and MACD_stdev3 > 2 and dMinus3 < 15;
def buyerExtreme4 = SlowK4 > 80 and MACD_stdev4 > 2 and dMinus4 < 15;
def priceJump = if close[1] > (open[5] + open[5] * percentGain) then 1 else 0;
# --- End Conditions
# calc vertical placement for arrows
#def arrow3dwn = if !x3d then na else high + (.001 * high);
#def arrow2dwn = if !x2d then na else high + (.0005 * high);
#def arrow1dwn = if !x1d then na else high + (.0001 * high);
#def arrow1up = if !x1u then na else low - (.0001 * high);
#def arrow2up = if !x2u then na else low - (.0005 * high);
#def arrow3up = if !x3u then na else low - (.001 * high);
declare once_per_bar;
input LW1 = 2;
input LW2 = 2;
input LW3 = 2;
input LW4 = 2;
# define distance away from low/high to plot signal
def AvgBarHeight_LN = Power(Double.E, Average(Log(Max(high - low, TickSize())), 5));
def AvgBarHeight = Average(Max(high - low, TickSize()), 5);
#plot graph_BarInfo_Up = AvgBarHeight_LN;
#graph_BarInfo_Up.SetPaintingStrategy(PaintingStrategy.arrow_down);
#plot graph_BarInfo_Dn = AvgBarHeight;
#graph_BarInfo_Dn.SetPaintingStrategy(PaintingStrategy.arrow_up);
#+ (.001 * high);
#def arrow2dwn = if !x2d then na else high + (.0005 * high);
#def arrow1dwn = if !x1d then na else high + (.0001 * high);
# --- Plot
plot RegularBuy = if sellerRegular[1] and !sellerRegular then low else Double.NaN;
plot ExtremeBuy = if sellerExtreme[1] and !sellerExtreme then low else Double.NaN;
plot RegularSell = if buyerRegular[1] and !buyerRegular then high else Double.NaN;
plot ExtremeSell = if buyerExtreme[1] and !buyerExtreme then high else Double.NaN;
plot RegularBuy1 = if sellerRegular1[1] and !sellerRegular1 then low else Double.NaN;
plot ExtremeBuy1 = if sellerExtreme1[1] and !sellerExtreme1 then low else Double.NaN;
plot RegularSell1 = if buyerRegular1[1] and !buyerRegular1 then high else Double.NaN;
plot ExtremeSell1 = if buyerExtreme1[1] and !buyerExtreme1 then high else Double.NaN;
plot RegularBuy2 = if sellerRegular2[1] and !sellerRegular2 then low else Double.NaN;
plot ExtremeBuy2 = if sellerExtreme2[1] and !sellerExtreme2 then low else Double.NaN;
plot RegularSell2 = if buyerRegular2[1] and !buyerRegular2 then high else Double.NaN;
plot ExtremeSell2 = if buyerExtreme2[1] and !buyerExtreme2 then high else Double.NaN;
plot RegularBuy3 = if sellerRegular3[1] and !sellerRegular3 then low else Double.NaN;
plot ExtremeBuy3 = if sellerExtreme3[1] and !sellerExtreme3 then low else Double.NaN;
plot RegularSell3 = if buyerRegular3[1] and !buyerRegular3 then high else Double.NaN;
plot ExtremeSell3 = if buyerExtreme3[1] and !buyerExtreme3 then high else Double.NaN;
plot RegularBuy4 = if sellerRegular4[1] and !sellerRegular4 then low else Double.NaN;
plot ExtremeBuy4 = if sellerExtreme4[1] and !sellerExtreme4 then low else Double.NaN;
plot RegularSell4 = if buyerRegular4[1] and !buyerRegular4 then high else Double.NaN;
plot ExtremeSell4 = if buyerExtreme4[1] and !buyerExtreme4 then high else Double.NaN;
# --- Arrows
#RegularBuy.SetPaintingStrategy(PaintingSTrategy.ARROW_UP);
#ExtremeBuy.SetPaintingSTrategy(paintingSTrategy.Arrow_UP);
#RegularSell.SetPaintingStrategy(PaintingSTrategy.ARROW_down);
#ExtremeSell.SetPaintingSTrategy(paintingSTrategy.Arrow_DOWN);
#RegularBuy1.SetPaintingStrategy(PaintingSTrategy.ARROW_UP);
#ExtremeBuy1.SetPaintingStrategy(PaintingSTrategy.ARROW_UP);
#RegularSell1.SetPaintingStrategy(PaintingSTrategy.ARROW_down);
#ExtremeSell1.SetPaintingSTrategy(paintingSTrategy.Arrow_DOWN);
AddVerticalLine(RegularBuy1, " 1", Color.Green, curve.short_DASH);
AddVerticalLine(ExtremeBuy1, " 1X", Color.Green, curve.short_DASH);
AddVerticalLine(RegularSell1, " 1", Color.Red, curve.short_DASH);
AddVerticalLine(ExtremeSell1, " 1X", Color.Red, curve.short_DASH);
#RegularBuy2.SetPaintingStrategy(PaintingSTrategy.ARROW_UP);
#ExtremeBuy2.SetPaintingStrategy(PaintingSTrategy.ARROW_UP);
#RegularSell2.SetPaintingStrategy(PaintingSTrategy.ARROW_down);
#ExtremeSell2.SetPaintingSTrategy(paintingSTrategy.Arrow_DOWN);
AddVerticalLine(RegularBuy2, " 2", Color.Green, curve.firm);
AddVerticalLine(ExtremeBuy2, " 2X", Color.Green, curve.firm);
AddVerticalLine(RegularSell2, " 2", Color.Red, curve.firm);
AddVerticalLine(ExtremeSell2, " 2X", Color.Red, curve.firm);
#RegularBuy3.SetPaintingStrategy(PaintingSTrategy.ARROW_UP);
#ExtremeBuy3.SetPaintingStrategy(PaintingSTrategy.ARROW_UP);
#RegularSell3.SetPaintingStrategy(PaintingSTrategy.ARROW_down);
#ExtremeSell3.SetPaintingSTrategy(paintingSTrategy.Arrow_DOWN);
AddVerticalLine(RegularBuy3, " 3", Color.Green, curve.LONG_DASH);
AddVerticalLine(ExtremeBuy3, " 3X", Color.Green, curve.LONG_DASH);
AddVerticalLine(RegularSell3, " 3", Color.Red, curve.LONG_DASH);
AddVerticalLine(ExtremeSell3, " 3X", Color.red, curve.LONG_DASH);
#RegularSell4.SetPaintingStrategy(PaintingSTrategy.ARROW_down);
#ExtremeSell4.SetPaintingSTrategy(paintingSTrategy.Arrow_DOWN);
#RegularBuy4.SetPaintingStrategy(PaintingSTrategy.ARROW_UP);
#ExtremeBuy4.SetPaintingStrategy(PaintingSTrategy.ARROW_UP);
AddVerticalLine(RegularBuy4, " 4", Color.Green, curve.FIRM);
AddVerticalLine(ExtremeBuy4, " 4X", Color.Green, curve.FIRM);
AddVerticalLine(RegularSell4, " 4", Color.Light_Red, curve.FIRM);
AddVerticalLine(ExtremeSell4, " 4X", Color.Light_Red, curve.FIRM);
RegularBuy1.Setlineweight(LW1);
ExtremeBuy1.Setlineweight(LW1);
RegularSell1.Setlineweight(LW1);
ExtremeSell1.Setlineweight(LW1);
RegularBuy2.Setlineweight(LW2);
ExtremeBuy2.Setlineweight(LW2);
RegularSell2.Setlineweight(LW2);
ExtremeSell2.Setlineweight(LW2);
RegularBuy3.Setlineweight(LW3);
ExtremeBuy3.Setlineweight(LW3);
RegularSell3.Setlineweight(LW3);
ExtremeSell3.Setlineweight(LW3);
RegularBuy4.Setlineweight(LW4);
ExtremeBuy4.Setlineweight(LW4);
RegularSell4.Setlineweight(LW4);
ExtremeSell4.Setlineweight(LW4);
# --- Default Colors
#RegularBuy.SetDefaultColor(Color.Green);
#ExtremeBuy.SetDefaultColor(Color.Red);
#RegularSell.SetDefaultColor(Color.Green);
#ExtremeSell.SetDefaultColor(Color.Red);
RegularBuy1.SetDefaultColor(CreateColor(0, 205, 1));
ExtremeBuy1.SetDefaultColor(CreateColor(102, 255, 135));
RegularSell1.SetDefaultColor(CreateColor(205, 0, 1));
ExtremeSell1.SetDefaultColor(CreateColor(205, 51, 51));
RegularBuy2.SetDefaultColor(CreateColor(0, 155, 1));
ExtremeBuy2.SetDefaultColor(CreateColor(102, 255, 105));
RegularSell2.SetDefaultColor(CreateColor(155, 0, 1));
ExtremeSell2.SetDefaultColor(CreateColor(155, 51, 51));
RegularBuy3.SetDefaultColor(CreateColor(0, 105, 1));
ExtremeBuy3.SetDefaultColor(CreateColor(102, 255, 75));
RegularSell3.SetDefaultColor(CreateColor(105, 0, 1));
ExtremeSell3.SetDefaultColor(CreateColor(105, 51, 51));
RegularBuy4.SetDefaultColor(Color.Gray);
ExtremeBuy4.SetDefaultColor(Color.Light_red);
RegularSell4.SetDefaultColor(Color.Gray);
ExtremeSell4.SetDefaultColor(Color.Light_Red);
# --- Bubbles
#AddChartBubble((RegularBuy and ExtremeBuy), low, "Buy", Color.Dark_green, no);
#AddChartBubble((RegularSell and ExtremeSell), High, "Sell", Color.Dark_red, no);
#AddChartBubble((RegularSell and ExtremeSell)and ExtremeSell1[5], High, "Sell", Color.Dark_red, no);
# -- Price Color
AssignPriceColor( if paintBars and sellerExtreme then Color.Dark_red else if buyerExtreme and paintBars then Color.GREEN else if paintBars and sellerRegular then Color.red else if buyerRegular and paintBars then Color.DARK_GREEN else if paintBars and sellerExtreme1 then Color.Dark_red else if buyerExtreme1 and paintBars then Color.GREEN else if paintBars and sellerRegular1 then Color.red else if buyerRegular1 and paintBars then Color.DARK_GREEN else if paintBars and sellerExtreme2 then Color.Dark_red else if buyerExtreme2 and paintBars then Color.GREEN else if paintBars and sellerRegular2 then Color.red else if buyerRegular2 and paintBars then Color.DARK_GREEN else if paintBars and sellerExtreme3 then Color.Dark_red else if buyerExtreme3 and paintBars then Color.Green else if paintBars and sellerRegular3 then Color.red else if buyerRegular3 and paintBars then Color.Light_GREEN else if paintBars and sellerExtreme4 then Color.Dark_Red else if buyerExtreme4 and paintBars then Color.GREEN else if paintBars and sellerRegular4 then Color.red else if buyerRegular4 and paintBars then Color.DARK_GREEN else if paintBars then Color.GRAY else Color.current);
# -- Labels
#AddLabel(yes, if buyerRegular[2] and !buyerRegular[1] then "TF: " + currentPeriod/60000 + " min Sell " else if sellerRegular[1] and !sellerRegular then "TF: " + currentPeriod/60000 + " min Buy " else "TF: " + currentPeriod/60000 + " min", if buyerRegular[2] and !buyerRegular[1] then Color.RED else if sellerRegular[2] and !sellerRegular[1] then Color.GREEN else Color.GRAY);
#AddLabel(yes, if buyerRegular1[2] and !buyerRegular1[1] then "TF: " + agperiod1 + " Sell " else if sellerRegular1[1] and !sellerRegular1 then "TF: " + agperiod1 + " Buy " else "TF: " + agperiod1, if buyerRegular1[2] and !buyerRegular1[1] then Color.RED else if sellerRegular1[2] and !sellerRegular1[1] then Color.GREEN else Color.GRAY);
#AddLabel(yes, if buyerRegular2[2] and !buyerRegular2[1] then "TF: " + agperiod2 + " Sell " else if sellerRegular2[1] and !sellerRegular2 then "TF: " + agperiod2 + " Buy " else "TF: " + agperiod2, if buyerRegular2[2] and !buyerRegular2[1] then Color.RED else if sellerRegular2[2] and !sellerRegular2[1] then Color.GREEN else Color.GRAY);
#AddLabel(yes, if buyerRegular3[2] and !buyerRegular3[1] then "TF: " + agperiod3 + " Sell " else if sellerRegular3[1] and !sellerRegular3 then "TF: " + agperiod3 + " Buy " else "TF: " + agperiod3, if buyerRegular3[2] and !buyerRegular3[1] then Color.RED else if sellerRegular3[2] and !sellerRegular3[1] then Color.GREEN else Color.GRAY);
#AddLabel(yes, if buyerRegular4[2] and !buyerRegular4[1] then "TF: " + agperiod4 + " Sell " else if sellerRegular4[1] and !sellerRegular4 then "TF: " + agperiod4 + " Buy " else "TF: " + agperiod4, if buyerRegular4[2] and !buyerRegular4[1] then Color.RED else if sellerRegular4[2] and !sellerRegular4[1] then Color.GREEN else Color.GRAY);
#AddLabel(yes, if buyerExtreme[2] and !buyerExtreme[1] then "TF: " + currentPeriod/60000 + " min Sell " else if sellerExtreme[1] and !sellerExtreme then "TF: " + currentPeriod/60000 + " min Buy " else "TF: " + currentPeriod/60000 + " min", if buyerExtreme[2] and !buyerExtreme[1] then Color.RED else if sellerExtreme[2] and !sellerExtreme[1] then Color.GREEN else Color.GRAY);
#AddLabel(yes, if buyerExtreme1[2] and !buyerExtreme1[1] then "TF: " + agperiod1 + " Sell " else if sellerExtreme1[1] and !sellerExtreme1 then "TF: " + agperiod1 + " Buy " else "TF: " + agperiod1, if buyerExtreme1[2] and !buyerExtreme1[1] then Color.RED else if sellerExtreme1[2] and !sellerExtreme1[1] then Color.GREEN else Color.GRAY);
#AddLabel(yes, if buyerExtreme2[2] and !buyerExtreme2[1] then "TF: " + agperiod2 + " Sell " else if sellerExtreme2[1] and !sellerExtreme2 then "TF: " + agperiod2 + " Buy " else "TF: " + agperiod2, if buyerExtreme2[2] and !buyerExtreme2[1] then Color.RED else if sellerExtreme2[2] and !sellerExtreme2[1] then Color.GREEN else Color.GRAY);
#AddLabel(yes, if buyerExtreme3[2] and !buyerExtreme3[1] then "TF: " + agperiod3 + " Sell " else if sellerExtreme3[1] and !sellerExtreme3 then "TF: " + agperiod3 + " Buy " else "TF: " + agperiod3, if buyerExtreme3[2] and !buyerExtreme3[1] then Color.RED else if sellerExtreme3[2] and !sellerExtreme3[1] then Color.GREEN else Color.GRAY);
#AddLabel(yes, if buyerExtreme4[2] and !buyerExtreme4[1] then "TF: " + agperiod4 + " Sell " else if sellerExtreme4[1] and !sellerExtreme4 then "TF: " + agperiod4 + " Buy " else "TF: " + agperiod4, if buyerExtreme4[2] and !buyerExtreme4[1] then Color.RED else if sellerExtreme4[2] and !sellerExtreme4[1] then Color.GREEN else Color.GRAY);
# --- VERTICLE LINE DAILY ---
#AddVerticalLine(( GetDay() <> GetDay()[1]), "", Color.DARK_GRAY, Curve.SHORT_DASH);
#--- END ---