Repaints Trend Reversal Questions

Repaints

MerryDay

Administrative
Staff member
Staff
VIP
Lifetime
Trend Reversal Indicator:
Read through this thread for answers to everything that you ever wanted to know about the Trend Reversal Indicator
https://usethinkscript.com/threads/trend-reversal-indicator-with-signals-for-thinkorswim.183/

PLEASE NOTE: THIS INDICATOR REPAINTS
Repainters use to be the FASTEST way to find and be alerted to tops and bottoms which make them the preferred indicators for shorter timeframes.
BUT
The Trend Reversal uses the function: HighestAll which ToS broke in the last update and has no plans on fixing. This function no longer calculates in real time, which will cause scripts that use it to lag to the point of being un-usable.

Also, because repainters are such prolific liars, these studies should ONLY be used to make entry by traders proficient in using them in correlation with price action, candlestick patterns, a disciplined stop-loss plan, and the fortitude to weather the losses that come with the false signals.
Read more:
https://usethinkscript.com/threads/answers-to-commonly-asked-questions.6006/#post-57833

Continue reading for answers to your most pressing questions.
 
Last edited:
What is the recommended time frame to use this indicator with? I was using on a 5 min chart and got a few false signals. Anyway to combat that? LIke using a higher time frame or something else?
This is a repainting indicator, by definition false signals abound. On higher timeframes, on TRENDING days, there will be less false signals but the false signals that do occur can result in higher losses.

Therefore, the indicator should never be used in isolation.
Read more here:
https://usethinkscript.com/threads/repainting-trend-reversal-questions.7600/#post-72193
 
Last edited:
#Trend_Reversal_Indicator_with_Signals
#2020-07-02

input usealerts = no;

def price = close;
def superfast_length = 9;
def fast_length = 14;
def slow_length = 21;
def displace = 0;

def mov_avg9 = ExpAverage(price[-displace], superfast_length);
def mov_avg14 = ExpAverage(price[-displace], fast_length);
def mov_avg21 = ExpAverage(price[-displace], slow_length);

#moving averages

def Superfast = mov_avg9;
def Fast = mov_avg14;
def Slow = mov_avg21;

def buy = mov_avg9 > mov_avg14 and mov_avg14 > mov_avg21 and low > mov_avg9;
def stopbuy = mov_avg9 <= mov_avg14;
def buynow = !buy[1] and buy;
def buysignal = CompoundValue(1, if buynow and !stopbuy then 1 else if buysignal[1] == 1 and stopbuy then 0 else buysignal[1], 0);

def Buy_Signal = buysignal[1] == 0 and buysignal == 1;

Alert(condition = buysignal[1] == 0 and buysignal == 1 and usealerts, text = "Buy Signal", sound = Sound.Bell, "alert type" = Alert.BAR);

def Momentum_Down = buysignal[1] == 1 and buysignal == 0;

#Alert(condition = buysignal[1] == 1 and buysignal == 0 and usealerts, text = "Momentum_Down", sound = Sound.Bell, "alert type" = Alert.BAR);

def sell = mov_avg9 < mov_avg14 and mov_avg14 < mov_avg21 and high < mov_avg9;
def stopsell = mov_avg9 >= mov_avg14;
def sellnow = !sell[1] and sell;
def sellsignal = CompoundValue(1, if sellnow and !stopsell then 1 else if sellsignal[1] == 1 and stopsell then 0 else sellsignal[1], 0);

def Sell_Signal = sellsignal[1] == 0 and sellsignal;

Alert(condition = sellsignal[1] == 0 and sellsignal == 1 and usealerts, text = "Sell Signal", sound = Sound.Bell, "alert type" = Alert.BAR);

def Momentum_Up = sellsignal[1] == 1 and sellsignal == 0;

#Alert(condition = sellsignal[1] == 1 and sellSignal == 0 and usealerts, text = "Momentum_Up", sound = Sound.Bell, "alert type" = Alert.BAR);

plot Colorbars = if buysignal == 1 then 1 else if sellsignal == 1 then 2 else if buysignal == 0 or sellsignal == 0 then 3 else 0;
Colorbars.Hide();
Colorbars.DefineColor("Buy_Signal_Bars", CreateColor(0,128,0));
Colorbars.DefineColor("Sell_Signal_Bars", CreateColor(128,0,0));
Colorbars.DefineColor("Neutral", CreateColor(0,0,128));
#___________________________________________________________________________

input method = {default average, high_low};
def bubbleoffset = .0005;
def percentamount = .01;
def revAmount = .05;
def atrreversal = 2.0;
def atrlength = 5;
def pricehigh = high;
def pricelow = low;
def averagelength = 5;
def averagetype = AverageType.EXPONENTIAL;
def mah = MovingAverage(averagetype, pricehigh, averagelength);
def mal = MovingAverage(averagetype, pricelow, averagelength);
def priceh = if method == method.high_low then pricehigh else mah;
def pricel = if method == method.high_low then pricelow else mal;
def EI = ZigZagHighLow("price h" = priceh, "price l" = pricel, "percentage reversal" = percentamount, "absolute reversal" = revAmount, "atr length" = atrlength, "atr reversal" = atrreversal);
def reversalAmount = if (close * percentamount / 100) > Max(revAmount < atrreversal * reference ATR(atrlength), revAmount) then (close * percentamount / 100) else if revAmount < atrreversal * reference ATR(atrlength) then atrreversal * reference ATR(atrlength) else revAmount;
rec EISave = if !IsNaN(EI) then EI else GetValue(EISave, 1);
def chg = (if EISave == priceh then priceh else pricel) - GetValue(EISave, 1);
def isUp = chg >= 0;
rec isConf = AbsValue(chg) >= reversalAmount or (IsNaN(GetValue(EI, 1)) and GetValue(isConf, 1));
def EId = if isUp then 1 else 0;

#plot EnhancedLines = if EId <= 1 then EI else Double.NaN;
#EnhancedLines.AssignValueColor(if EId == 1 then Color.GREEN else if EId == 0 then Color.RED else Color.DARK_ORANGE);
#EnhancedLines.SetStyle(Curve.FIRM);
#EnhancedLines.EnableApproximation();
#EnhancedLines.HideBubble();

#Price Change between Enhanceds

def xxhigh = if EISave == priceh then priceh else xxhigh[1];
def chghigh = priceh - xxhigh[1];
def xxlow = if EISave == pricel then pricel else xxlow[1];
def chglow = pricel - xxlow[1];
def showBubbleschange = no;
AddChartBubble(showBubbleschange and !IsNaN(EI) and BarNumber() != 1, if isUp then priceh * (1 + bubbleoffset) else pricel * (1 - bubbleoffset) , "$" + chg , if isUp and chghigh > 0 then Color.GREEN else if isUp and chghigh < 0 then Color.RED else if isUp then Color.YELLOW else if !isUp and chglow > 0 then Color.GREEN else if !isUp and chglow < 0 then Color.RED else Color.YELLOW, isUp);

#Price at High/Low

def showBubblesprice = no;
AddChartBubble(showBubblesprice and !IsNaN(EI) and BarNumber() != 1, if isUp then priceh * (1 + bubbleoffset) else pricel * (1 - bubbleoffset) , if isUp then "$" + priceh else "$" + pricel , if isUp and chghigh > 0 then Color.GREEN else if isUp and chghigh < 0 then Color.RED else if isUp then Color.YELLOW else if !isUp and chglow > 0 then Color.GREEN else if !isUp and chglow < 0 then Color.RED else Color.YELLOW, isUp);

#Label for Confirmed/Unconfirmed Status of Current Enhanced

#Bar Count between Enhanceds

rec EIcount = if EISave[1] != EISave then 1 else if EISave[1] == EISave then EIcount[1] + 1 else 0;
def EIcounthilo = if EIcounthilo[1] == 0 and (EISave == priceh or EISave == pricel) then 1 else if EISave == priceh or EISave == pricel then EIcounthilo[1] + 1 else EIcounthilo[1];
def EIhilo = if EISave == priceh or EISave == pricel then EIcounthilo else EIcounthilo + 1;
def EIcounthigh = if EISave == priceh then EIcount[1] else Double.NaN;
def EIcountlow = if EISave == pricel then EIcount[1] else Double.NaN;
def showBubblesbarcount = no;
AddChartBubble(showBubblesbarcount and !IsNaN(EI) and BarNumber() != 1, if isUp then priceh * (1 + bubbleoffset) else pricel * (1 - bubbleoffset) , if EISave == priceh then EIcounthigh else EIcountlow, if isUp and chghigh > 0 then Color.GREEN else if isUp and chghigh < 0 then Color.RED else if isUp then Color.YELLOW else if !isUp and chglow > 0 then Color.GREEN else if !isUp and chglow < 0 then Color.RED else Color.YELLOW, if isUp then yes else no );

#Arrows

def EIL = if !IsNaN(EI) and !isUp then pricel else GetValue(EIL, 1);
def EIH = if !IsNaN(EI) and isUp then priceh else GetValue(EIH, 1);
def dir = CompoundValue(1, if EIL != EIL[1] or pricel == EIL[1] and pricel == EISave then 1 else if EIH != EIH[1] or priceh == EIH[1] and priceh == EISave then -1 else dir[1], 0);
def signal = CompoundValue(1, if dir > 0 and pricel > EIL then if signal[1] <= 0 then 1 else signal[1] else if dir < 0 and priceh < EIH then if signal[1] >= 0 then -1 else signal[1] else signal[1], 0);
def showarrows = yes;
def U1 = showarrows and signal > 0 and signal[1] <= 0;
#U1.SetPaintingStrategy(PaintingStrategy.BOOLEAN_ARROW_UP);
#U1.SetDefaultColor(Color.GREEN);
#U1.SetLineWeight(4);
def D1 = showarrows and signal < 0 and signal[1] >= 0;
#D1.SetPaintingStrategy(PaintingStrategy.BOOLEAN_ARROW_DOWN);
#D1.SetDefaultColor(Color.RED);
#D1.SetLineWeight(4);
def barnumber = BarNumber()[10];

AddChartBubble((barnumber and U1), if isUp then low else high, if showarrows and signal > 0 and signal[1] <= 0 then "" + low else "" , if Colorbars == 3 then Color.LIGHT_GREEN else Color.UPTICK, no);

AddChartBubble((barnumber and D1), if isUp then low else high, if showarrows and signal < 0 and signal[1] >= 0 then "" + high else "" , if Colorbars == 3 then Color.LIGHT_RED else Color.DOWNTICK, yes);


def revLineTop;
def revLineBot;

if barnumber and D1 {
revLineBot = Double.NaN;
revLineTop = high[1];
} else if barnumber and U1 {
revLineTop = Double.NaN;
revLineBot = low[1];
} else if !IsNaN(revLineBot[1]) and (Colorbars[2] == 2 or Colorbars[1] == 2) {
revLineBot = revLineBot[1];
revLineTop = Double.NaN;
} else if !IsNaN(revLineTop[1]) and (Colorbars[2] == 1 or Colorbars[1] == 1) {
revLineTop = revLineTop[1];
revLineBot = Double.NaN;
} else {
revLineTop = Double.NaN;
revLineBot = Double.NaN;
}

#plot botLine = revLineBot[-1];
#botLine.SetDefaultColor(Color.LIGHT_GREEN);
#plot topLine = revLineTop[-1];
#topLine.SetDefaultColor(Color.LIGHT_RED);

#Alerts

#def usealerts = no;
Alert(usealerts and U1, "EI-UP", Alert.BAR, Sound.Bell);
Alert(usealerts and D1, "EI-DOWN", Alert.BAR, Sound.Chimes);

#Supply Demand Areas

rec data1 = CompoundValue(1, if (EISave == priceh or EISave == pricel) then data1[1] + 1 else data1[1], 0);
def datacount1 = (HighestAll(data1) - data1[1]);
def numbersuppdemandtoshow = 0;
input showSupplyDemand = {default Pivot, Arrow, None};
def idx = if showSupplyDemand == showSupplyDemand.Pivot then 1 else 0;
def rLow;
def rHigh;

if signal crosses 0 {
rLow = pricel[idx];
rHigh = priceh[idx];
} else {
rLow = rLow[1];
rHigh = rHigh[1];
}

def HighLine = if datacount1 <= numbersuppdemandtoshow and showSupplyDemand != showSupplyDemand.None and !IsNaN(close) and rHigh != 0 then rHigh else Double.NaN;

def LowLine = if datacount1 <= numbersuppdemandtoshow and showSupplyDemand != showSupplyDemand.None and !IsNaN(close) and rLow != 0 then rLow else Double.NaN;

def hlUp = if signal > 0 then HighLine else Double.NaN;
def hlDn = if signal < 0 then HighLine else Double.NaN;

def showsupplydemandcloud = no;
AddCloud(if showsupplydemandcloud then hlUp else Double.NaN, LowLine, Color.LIGHT_GREEN, Color.LIGHT_GREEN);
AddCloud(if showsupplydemandcloud then hlDn else Double.NaN, LowLine, Color.LIGHT_RED, Color.LIGHT_RED);

#Store Previous Data

def EIsave1 = if !IsNaN(EISave) then EISave else EIsave1[1];
def EIsave2 = EIsave1;
rec priorEI1 = if EIsave2 != EIsave2[1] then EIsave2[1] else priorEI1[1];
rec priorEI2 = if priorEI1 != priorEI1[1] then priorEI1[1] else priorEI2[1];
rec priorEI3 = if priorEI2 != priorEI2[1] then priorEI2[1] else priorEI3[1];

#Fibonacci Extensions

rec data = CompoundValue(1, if (EISave == priceh or EISave == pricel) then data[1] + 1 else data[1], 0);
def datacount = (HighestAll(data) - data[1]);
def numberextfibstoshow = 2;
rec cpo = if dir[1] != dir then 0 else 1;
def showFibExtLines = no;
def showtodayonly = no;
def today = if showtodayonly == yes then GetDay() == GetLastDay() else GetDay();
def extfib1 = if EISave == priceh then priceh - AbsValue(priorEI2 - priorEI1) * 1
else extfib1[1];
def extfib100 = if datacount <= numberextfibstoshow and today and showFibExtLines and !IsNaN(extfib1) and dir < 0 and cpo != 0 then extfib1[1] else Double.NaN;

def extfib1a = if EISave == priceh then priceh - AbsValue(priorEI2 - priorEI1) * 0.382
else extfib1a[1];
def extfib382 = if datacount <= numberextfibstoshow and today and showFibExtLines and !IsNaN(extfib1a) and dir < 0 and cpo != 0 then extfib1a[1] else Double.NaN;

def extfib2 = if EISave == priceh then priceh - AbsValue(priorEI2 - priorEI1) *
0.618 else extfib2[1];
def extfib618 = if datacount <= numberextfibstoshow and today and showFibExtLines and !IsNaN(extfib2) and dir < 0 and cpo != 0 then extfib2[1] else Double.NaN;

def extfib3 = if EISave == priceh then priceh - AbsValue(priorEI2 - priorEI1) *
1.618 else extfib3[1];
def extfib1618 = if datacount <= numberextfibstoshow and today and showFibExtLines and !IsNaN(extfib3) and dir < 0 and cpo != 0 then extfib3[1] else Double.NaN;

def extfib3a = if EISave == priceh then priceh - AbsValue(priorEI2 - priorEI1) *
2.000 else extfib3a[1];
def extfib2000 = if datacount <= numberextfibstoshow and today and showFibExtLines and !IsNaN(extfib3a) and dir < 0 and cpo != 0 then extfib3a[1] else Double.NaN;

def extfib4 = if EISave == priceh then priceh - AbsValue(priorEI2 - priorEI1) *
2.618 else extfib4[1];
def extfib2618 = if datacount <= numberextfibstoshow and today and showFibExtLines and !IsNaN(extfib4) and dir < 0 and cpo != 0 then extfib4[1] else Double.NaN;

def extfib5 = if EISave == priceh then priceh - AbsValue(priorEI2 - priorEI1) *
3.618 else extfib5[1];
def extfib3618 = if datacount <= numberextfibstoshow and today and showFibExtLines and !IsNaN(extfib5) and dir < 0 and cpo != 0 then extfib5[1] else Double.NaN;

def extfib1_ = if EISave == pricel then pricel + AbsValue(priorEI2 - priorEI1) * 1
else extfib1_[1];
def extfib100_ = if datacount <= numberextfibstoshow and today and showFibExtLines and !IsNaN(extfib1_) and dir > 0 and cpo != 0 then extfib1_[1] else Double.NaN;

def extfib1a_ = if EISave == pricel then pricel + AbsValue(priorEI2 - priorEI1) * 0.382
else extfib1a_[1];
def extfib382_ = if datacount <= numberextfibstoshow and today and showFibExtLines and !IsNaN(extfib1a_) and dir > 0 and cpo != 0 then extfib1a_[1] else Double.NaN;

def extfib2_ = if EISave == pricel then pricel + AbsValue(priorEI2 - priorEI1) *
0.618 else extfib2_[1];
def extfib618_ = if datacount <= numberextfibstoshow and today and showFibExtLines and !IsNaN(extfib2_) and dir > 0 and cpo != 0 then extfib2_[1] else Double.NaN;

def extfib3_ = if EISave == pricel then pricel + AbsValue(priorEI2 - priorEI1) *
1.618 else extfib3_[1];
def extfib1618_ = if datacount <= numberextfibstoshow and today and showFibExtLines and !IsNaN(extfib3_) and dir > 0 and cpo != 0 then extfib3_[1] else Double.NaN;

def extfib3a_ = if EISave == pricel then pricel + AbsValue(priorEI2 - priorEI1) *
2.000 else extfib3a_[1];
def extfib2000_ = if datacount <= numberextfibstoshow and today and showFibExtLines and !IsNaN(extfib3a_) and dir > 0 and cpo != 0 then extfib3a_[1] else Double.NaN;

def extfib4_ = if EISave == pricel then pricel + AbsValue(priorEI2 - priorEI1) *
2.618 else extfib4_[1];
def extfib2618_ = if datacount <= numberextfibstoshow and today and showFibExtLines and !IsNaN(extfib4_) and dir > 0 and cpo != 0 then extfib4_[1] else Double.NaN;

def extfib5_ = if EISave == pricel then pricel + AbsValue(priorEI2 - priorEI1) *
3.618 else extfib5_[1];
def extfib3618_ = if datacount <= numberextfibstoshow and today and showFibExtLines and !IsNaN(extfib5_) and dir > 0 and cpo != 0 then extfib5_[1] else Double.NaN;

def fibextbubblespacesinexpansion = 8;
def b = fibextbubblespacesinexpansion;
def direction = if !isUp then 1 else 0;

AddChartBubble( direction[b + 1] == 1 and showFibExtLines and !IsNaN(close[b + 1]) and IsNaN(close), extfib1[b + 2], "100%", Color.RED, no);
AddChartBubble( direction[b + 1] == 1 and showFibExtLines and !IsNaN(close[b + 1]) and IsNaN(close), extfib1a[b + 2], "38.2%", Color.RED, no);
AddChartBubble( direction[b + 1] == 1 and showFibExtLines and !IsNaN(close[b + 1]) and IsNaN(close), extfib2[b + 2], "61.8%", Color.RED, no);
AddChartBubble( direction[b + 1] == 1 and showFibExtLines and !IsNaN(close[b + 1]) and IsNaN(close), extfib3[b + 2], "161.8%", Color.RED, no);
AddChartBubble( direction[b + 1] == 1 and showFibExtLines and !IsNaN(close[b + 1]) and IsNaN(close), extfib3a[b + 2], "200%", Color.RED, no);
AddChartBubble( direction[b + 1] == 1 and showFibExtLines and !IsNaN(close[b + 1]) and IsNaN(close), extfib4[b + 2], "261.8%", Color.RED, no);
AddChartBubble( direction[b + 1] == 1 and showFibExtLines and !IsNaN(close[b + 1]) and IsNaN(close), extfib5[b + 2], "361.8%", Color.RED, no);
AddChartBubble( direction[b + 1] == 0 and showFibExtLines and !IsNaN(close[b + 1]) and IsNaN(close), extfib1_[b + 2], "100%", Color.GREEN, yes);
AddChartBubble( direction[b + 1] == 0 and showFibExtLines and !IsNaN(close[b + 1]) and IsNaN(close), extfib1a_[b + 2], "38.2%", Color.GREEN, yes);
AddChartBubble( direction[b + 1] == 0 and showFibExtLines and !IsNaN(close[b + 1]) and IsNaN(close), extfib2_[b + 2], "61.8%", Color.GREEN, yes);
AddChartBubble( direction[b + 1] == 0 and showFibExtLines and !IsNaN(close[b + 1]) and IsNaN(close), extfib3_[b + 2], "161.8%", Color.GREEN, yes);
AddChartBubble( direction[b + 1] == 0 and showFibExtLines and !IsNaN(close[b + 1]) and IsNaN(close), extfib3a_[b + 2], "200%", Color.GREEN, yes);
AddChartBubble( direction[b + 1] == 0 and showFibExtLines and !IsNaN(close[b + 1]) and IsNaN(close), extfib4_[b + 2], "261.8%", Color.GREEN, yes);
AddChartBubble( direction[b + 1] == 0 and showFibExtLines and !IsNaN(close[b + 1]) and IsNaN(close), extfib5_[b + 2], "361.8%", Color.GREEN, yes);

#Volume at Reversals

def vol = if BarNumber() == 0 then 0 else volume + vol[1];
def vol1 = if BarNumber() == 1 then volume else vol1[1];
def xxvol = if EISave == priceh or EISave == pricel then TotalSum(volume) else xxvol[1];
def chgvol = if xxvol - xxvol[1] + vol1 == vol then vol else xxvol - xxvol[1];
def showBubblesVolume = no;
AddChartBubble(showBubblesVolume and !IsNaN(EI) and BarNumber() != 1, if isUp then priceh * (1 + bubbleoffset) else pricel * (1 - bubbleoffset), chgvol, if isUp and chghigh > 0 then Color.GREEN else if isUp and chghigh < 0 then Color.RED else if isUp then Color.YELLOW else if !isUp and chglow > 0 then Color.GREEN else if !isUp and chglow < 0 then Color.RED else Color.YELLOW, if isUp then yes else no );

input usemanualfibskip = no;#Hint usemanualfibskip: Select no to use preprogrammed fibskip amounts. Select no, to use the amount entered at input fibskip.
input fibskip = .50;#Hint fibskip: Set input usemanualfibskip == yes to use this amount versus preprogrammed amounts. Standard is 1.0. This is percentage difference between fib high and low before a new fib grid created.

def showBubblesfibratio = no;
def showFibLabel = no;#Hint showfibLabel: Select yes to show label of current fib level as of last price
def showfiblines = no;
def fib1level = .236;
def fib2level = .382;
def fibMlevel = .500;
def fib3level = .618;
def fib4level = .786;

#Fibs

def datacount2 = (HighestAll(data1) - data1[1]);
def numberfibretracementstoshow = 2;
def fibskipit = if usemanualfibskip == no then if close > 800 then .25 else .5 else fibskip;
def EIfibh = if EISave == priceh and AbsValue(EISave - EISave[1]) > priceh * fibskipit * .01 then priceh else EIfibh[1];
def EIfibl = if EISave == pricel and AbsValue(EISave - EISave[1]) > priceh * fibskipit * .01 then pricel else EIfibl[1];
def range = EIfibh - EIfibl;
def fibH = if showfiblines == no then Double.NaN else if datacount2 <= numberfibretracementstoshow then EIfibh else Double.NaN;
def fibL = if showfiblines == no then Double.NaN else if datacount2 <= numberfibretracementstoshow then EIfibl else Double.NaN;
def fibM = if showfiblines == no then Double.NaN else if datacount2 <= numberfibretracementstoshow then EIfibl + range * fibMlevel else Double.NaN;
def fib1 = if showfiblines == no then Double.NaN else if datacount2 <= numberfibretracementstoshow then EIfibl + range * fib1level else Double.NaN;
def fib2 = if showfiblines == no then Double.NaN else if datacount2 <= numberfibretracementstoshow then EIfibl + range * fib2level else Double.NaN;
def fib3 = if showfiblines == no then Double.NaN else if datacount2 <= numberfibretracementstoshow then EIfibl + range * fib3level else Double.NaN;
def fib4 = if showfiblines == no then Double.NaN else if datacount2 <= numberfibretracementstoshow then EIfibl + range * fib4level else Double.NaN;

AddLabel(showFibLabel, Concat( "Current Fib Level ", AsPercent((close - EIfibl) / (range))), if close > EIfibl then Color.GREEN else if EIfibh == close then Color.WHITE else Color.RED);

AddChartBubble(showBubblesfibratio and !IsNaN(EI) and BarNumber() != 1, if isUp then priceh * (1 + bubbleoffset) else pricel * (1 - bubbleoffset) , if isUp then AsPercent((priceh - EIfibl) / (range)) else AsPercent((pricel - EIfibl) / range), if isUp and chghigh > 0 then Color.GREEN else if isUp and chghigh < 0 then Color.RED else if isUp then Color.GREEN else if !isUp and chglow > 0 then Color.GREEN else if !isUp and chglow < 0 then Color.RED else Color.RED, isUp);

Replace these 2 bubbles (highlighted in bold) in the above code with the following:

Ruby:
AddChartBubble((barnumber and U1), if isUp then low else high, if showarrows and signal > 0 and signal[1] <= 0 then "L" else "" , if Colorbars == 3 then Color.LIGHT_GREEN else Color.UPTICK, no);

AddChartBubble((barnumber and D1), if isUp then low else high, if showarrows and signal < 0 and signal[1] >= 0 then "S" else "" , if Colorbars == 3 then Color.LIGHT_RED else Color.DOWNTICK, yes);
 
Maybe this can help - it removes a lot of unnecessary fluff from the indicator. The EMAs (the 9, 14, and 21) and fib retracements are extra for the indicator and are not shown. For instance, the three EMAs are only used for the color of the reversal bubbles, and the fib code itself is just dead weight, nothing is even plotted from the calculations. There are also a lot of bubbles and labels in the code that are turned off by default in the original indicator. There's a bunch of stuff that isnt being used in the original. I uncovered a few plots and added a bit to make the visuals easier. Not an expert, but hope this helps

Code:
# used to switch between "zigzag based on high/low of price" and "zigzag based on then high/low of moving averages"
input method = {default average, high_low};

# data for the built-in zigzag indicator which is referenced in the study. To see the ZigZagHighLow() code, look for it in the built-in TOS studies
def bubbleoffset = .0005;
def percentamount = .01;
def revAmount = .05;
def atrreversal = 2.0;
def atrlength = 5;

# data for the moving averages
def pricehigh = high;
def pricelow = low;
def averagelength = 5;
def averagetype = AverageType.EXPONENTIAL;

# here are the moving averages used for the signals - changed to plots and given colors
plot mah = MovingAverage(averagetype, pricehigh, averagelength);
plot mal = MovingAverage(averagetype, pricelow, averagelength);
mah.setdefaultcolor(color.cyan);
mal.setdefaultcolor(color.cyan);

# continues the switch between the two different zigzag data points
def priceh = if method == method.high_low then pricehigh else mah;
def pricel = if method == method.high_low then pricelow else mal;

# references the built-in zigzag indicator
def EI = ZigZagHighLow("price h" = priceh, "price l" = pricel, "percentage reversal" = percentamount, "absolute reversal" = revAmount, "atr length" = atrlength, "atr reversal" = atrreversal);

# not very clear on how this exactly works - but the end result is to plot the zigzag lines
def reversalAmount = if (close * percentamount / 100) > Max(revAmount < atrreversal * reference ATR(atrlength), revAmount) then (close * percentamount / 100) else if revAmount < atrreversal * reference ATR(atrlength) then atrreversal * reference ATR(atrlength) else revAmount;
rec EISave = if !IsNaN(EI) then EI else GetValue(EISave, 1);
def chg = (if EISave == priceh then priceh else pricel) - GetValue(EISave, 1);
def isUp = chg >= 0;
rec isConf = AbsValue(chg) >= reversalAmount or (IsNaN(GetValue(EI, 1)) and GetValue(isConf, 1));
def EId = if isUp then 1 else 0;

# zigzag plot and colors
plot EnhancedLines = if EId <= 1 then EI else Double.NaN;
EnhancedLines.AssignValueColor(if EId == 1 then Color.GREEN else if EId == 0 then Color.RED else Color.DARK_ORANGE);
EnhancedLines.SetStyle(Curve.FIRM);
EnhancedLines.EnableApproximation();
EnhancedLines.HideBubble();

# calculates and plots the arrows
def EIL = if !IsNaN(EI) and !isUp then pricel else GetValue(EIL, 1);
def EIH = if !IsNaN(EI) and isUp then priceh else GetValue(EIH, 1);
def dir = CompoundValue(1, if EIL != EIL[1] or pricel == EIL[1] and pricel == EISave then 1 else if EIH != EIH[1] or priceh == EIH[1] and priceh == EISave then -1 else dir[1], 0);
def signal = CompoundValue(1, if dir > 0 and pricel > EIL then if signal[1] <= 0 then 1 else signal[1] else if dir < 0 and priceh < EIH then if signal[1] >= 0 then -1 else signal[1] else signal[1], 0);
def showarrows = yes;
plot U1 = showarrows and signal > 0 and signal[1] <= 0;
U1.SetPaintingStrategy(PaintingStrategy.BOOLEAN_ARROW_UP);
U1.SetDefaultColor(Color.GREEN);
U1.SetLineWeight(4);
plot D1 = showarrows and signal < 0 and signal[1] >= 0;
D1.SetPaintingStrategy(PaintingStrategy.BOOLEAN_ARROW_DOWN);
D1.SetDefaultColor(Color.RED);
D1.SetLineWeight(4);

As you can see, the 9, 14, and 21 EMAs are not even needed.

Edit: If you look at the code I posted, you can see the line def showarrows = yes;. The original code is full of these "defs" that probably were originally meant to be inputs instead. Someone has either changed the original code a lot before @BenTen found and posted it here in the forum, or its just a incomplete mish-mash of different codes. I have no idea

example-pic.png
I added band color changes so that it is easier to follow the trend changes.
Ruby:
# used to switch between "zigzag based on high/low of price" and "zigzag based on then high/low of moving averages"
input method = {default average, high_low};

# data for the built-in zigzag indicator which is referenced in the study. To see the ZigZagHighLow() code, look for it in the built-in TOS studies
def bubbleoffset = .0005;
def percentamount = .01;
def revAmount = .05;
def atrreversal = 2.0;
def atrlength = 5;

# data for the moving averages
def pricehigh = high;
def pricelow = low;
def averagelength = 5;
def averagetype = AverageType.EXPONENTIAL;
def nan  =  Double.NaN;
input fill = yes;
# here are the moving averages used for the signals - changed to plots and given colors
plot UpperBand = MovingAverage(averagetype, pricehigh, averagelength);
plot LowerBand = MovingAverage(averagetype, pricelow, averagelength);
UpperBand.AssignValueColor(if UpperBand > UpperBand[1] then Color.UPTICK else Color.RED);
LowerBand.AssignValueColor(if LowerBand > LowerBand[1] then Color.UPTICK else Color.RED);

# continues the switch between the two different zigzag data points
def priceh = if method == method.high_low then pricehigh else UpperBand;
def pricel = if method == method.high_low then pricelow else LowerBand;

# references the built-in zigzag indicator
def EI = ZigZagHighLow("price h" = priceh, "price l" = pricel, "percentage reversal" = percentamount, "absolute reversal" = revAmount, "atr length" = atrlength, "atr reversal" = atrreversal);

# not very clear on how this exactly works - but the end result is to plot the zigzag lines
def reversalAmount = if (close * percentamount / 100) > Max(revAmount < atrreversal * reference ATR(atrlength), revAmount) then (close * percentamount / 100) else if revAmount < atrreversal * reference ATR(atrlength) then atrreversal * reference ATR(atrlength) else revAmount;
rec EISave = if !IsNaN(EI) then EI else GetValue(EISave, 1);
def chg = (if EISave == priceh then priceh else pricel) - GetValue(EISave, 1);
def isUp = chg >= 0;
rec isConf = AbsValue(chg) >= reversalAmount or (IsNaN(GetValue(EI, 1)) and GetValue(isConf, 1));
def EId = if isUp then 1 else 0;

# zigzag plot and colors
plot EnhancedLines = if EId <= 1 then EI else Double.NaN;
EnhancedLines.AssignValueColor(if EId == 1 then Color.GREEN else if EId == 0 then Color.RED else Color.DARK_ORANGE);
EnhancedLines.SetStyle(Curve.FIRM);
EnhancedLines.EnableApproximation();
EnhancedLines.HideBubble();

# calculates and plots the arrows
def EIL = if !IsNaN(EI) and !isUp then pricel else GetValue(EIL, 1);
def EIH = if !IsNaN(EI) and isUp then priceh else GetValue(EIH, 1);
def dir = CompoundValue(1, if EIL != EIL[1] or pricel == EIL[1] and pricel == EISave then 1 else if EIH != EIH[1] or priceh == EIH[1] and priceh == EISave then -1 else dir[1], 0);
def signal = CompoundValue(1, if dir > 0 and pricel > EIL then if signal[1] <= 0 then 1 else signal[1] else if dir < 0 and priceh < EIH then if signal[1] >= 0 then -1 else signal[1] else signal[1], 0);
def showarrows = yes;
plot U1 = showarrows and signal > 0 and signal[1] <= 0;
U1.SetPaintingStrategy(PaintingStrategy.BOOLEAN_ARROW_UP);
U1.SetDefaultColor(Color.GREEN);
U1.SetLineWeight(4);
plot D1 = showarrows and signal < 0 and signal[1] >= 0;
D1.SetPaintingStrategy(PaintingStrategy.BOOLEAN_ARROW_DOWN);
D1.SetDefaultColor(Color.RED);
D1.SetLineWeight(4);
 
I added band color changes so that it is easier to follow the trend changes.
Ruby:
# used to switch between "zigzag based on high/low of price" and "zigzag based on then high/low of moving averages"
input method = {default average, high_low};

# data for the built-in zigzag indicator which is referenced in the study. To see the ZigZagHighLow() code, look for it in the built-in TOS studies
def bubbleoffset = .0005;
def percentamount = .01;
def revAmount = .05;
def atrreversal = 2.0;
def atrlength = 5;

# data for the moving averages
def pricehigh = high;
def pricelow = low;
def averagelength = 5;
def averagetype = AverageType.EXPONENTIAL;
def nan  =  Double.NaN;
input fill = yes;
# here are the moving averages used for the signals - changed to plots and given colors
plot UpperBand = MovingAverage(averagetype, pricehigh, averagelength);
plot LowerBand = MovingAverage(averagetype, pricelow, averagelength);
UpperBand.AssignValueColor(if UpperBand > UpperBand[1] then Color.UPTICK else Color.RED);
LowerBand.AssignValueColor(if LowerBand > LowerBand[1] then Color.UPTICK else Color.RED);

# continues the switch between the two different zigzag data points
def priceh = if method == method.high_low then pricehigh else UpperBand;
def pricel = if method == method.high_low then pricelow else LowerBand;

# references the built-in zigzag indicator
def EI = ZigZagHighLow("price h" = priceh, "price l" = pricel, "percentage reversal" = percentamount, "absolute reversal" = revAmount, "atr length" = atrlength, "atr reversal" = atrreversal);

# not very clear on how this exactly works - but the end result is to plot the zigzag lines
def reversalAmount = if (close * percentamount / 100) > Max(revAmount < atrreversal * reference ATR(atrlength), revAmount) then (close * percentamount / 100) else if revAmount < atrreversal * reference ATR(atrlength) then atrreversal * reference ATR(atrlength) else revAmount;
rec EISave = if !IsNaN(EI) then EI else GetValue(EISave, 1);
def chg = (if EISave == priceh then priceh else pricel) - GetValue(EISave, 1);
def isUp = chg >= 0;
rec isConf = AbsValue(chg) >= reversalAmount or (IsNaN(GetValue(EI, 1)) and GetValue(isConf, 1));
def EId = if isUp then 1 else 0;

# zigzag plot and colors
plot EnhancedLines = if EId <= 1 then EI else Double.NaN;
EnhancedLines.AssignValueColor(if EId == 1 then Color.GREEN else if EId == 0 then Color.RED else Color.DARK_ORANGE);
EnhancedLines.SetStyle(Curve.FIRM);
EnhancedLines.EnableApproximation();
EnhancedLines.HideBubble();

# calculates and plots the arrows
def EIL = if !IsNaN(EI) and !isUp then pricel else GetValue(EIL, 1);
def EIH = if !IsNaN(EI) and isUp then priceh else GetValue(EIH, 1);
def dir = CompoundValue(1, if EIL != EIL[1] or pricel == EIL[1] and pricel == EISave then 1 else if EIH != EIH[1] or priceh == EIH[1] and priceh == EISave then -1 else dir[1], 0);
def signal = CompoundValue(1, if dir > 0 and pricel > EIL then if signal[1] <= 0 then 1 else signal[1] else if dir < 0 and priceh < EIH then if signal[1] >= 0 then -1 else signal[1] else signal[1], 0);
def showarrows = yes;
plot U1 = showarrows and signal > 0 and signal[1] <= 0;
U1.SetPaintingStrategy(PaintingStrategy.BOOLEAN_ARROW_UP);
U1.SetDefaultColor(Color.GREEN);
U1.SetLineWeight(4);
plot D1 = showarrows and signal < 0 and signal[1] >= 0;
D1.SetPaintingStrategy(PaintingStrategy.BOOLEAN_ARROW_DOWN);
D1.SetDefaultColor(Color.RED);
D1.SetLineWeight(4);
I add cloud colors to follow the trends.
Ruby:
# used to switch between "zigzag based on high/low of price" and "zigzag based on then high/low of moving averages"
input method = {default average, high_low};

# data for the built-in zigzag indicator which is referenced in the study. To see the ZigZagHighLow() code, look for it in the built-in TOS studies
def bubbleoffset = .0005;
def percentamount = .01;
def revAmount = .05;
def atrreversal = 2.0;
def atrlength = 5;

# data for the moving averages
def pricehigh = high;
def pricelow = low;
def averagelength = 5;
def averagetype = AverageType.EXPONENTIAL;
def nan  =  Double.NaN;
input fill = yes;
# here are the moving averages used for the signals - changed to plots and given colors
plot UpperBand = MovingAverage(averagetype, pricehigh, averagelength);
plot LowerBand = MovingAverage(averagetype, pricelow, averagelength);
UpperBand.AssignValueColor(if UpperBand > UpperBand[1] then Color.UPTICK else Color.RED);
LowerBand.AssignValueColor(if LowerBand > LowerBand[1] then Color.UPTICK else Color.RED);

# continues the switch between the two different zigzag data points
def priceh = if method == method.high_low then pricehigh else UpperBand;
def pricel = if method == method.high_low then pricelow else LowerBand;

# references the built-in zigzag indicator
def EI = ZigZagHighLow("price h" = priceh, "price l" = pricel, "percentage reversal" = percentamount, "absolute reversal" = revAmount, "atr length" = atrlength, "atr reversal" = atrreversal);

# not very clear on how this exactly works - but the end result is to plot the zigzag lines
def reversalAmount = if (close * percentamount / 100) > Max(revAmount < atrreversal * reference ATR(atrlength), revAmount) then (close * percentamount / 100) else if revAmount < atrreversal * reference ATR(atrlength) then atrreversal * reference ATR(atrlength) else revAmount;
rec EISave = if !IsNaN(EI) then EI else GetValue(EISave, 1);
def chg = (if EISave == priceh then priceh else pricel) - GetValue(EISave, 1);
def isUp = chg >= 0;
rec isConf = AbsValue(chg) >= reversalAmount or (IsNaN(GetValue(EI, 1)) and GetValue(isConf, 1));
def EId = if isUp then 1 else 0;

# zigzag plot and colors
plot EnhancedLines = if EId <= 1 then EI else Double.NaN;
EnhancedLines.AssignValueColor(if EId == 1 then Color.GREEN else if EId == 0 then Color.RED else Color.DARK_ORANGE);
EnhancedLines.SetStyle(Curve.FIRM);
EnhancedLines.EnableApproximation();
EnhancedLines.HideBubble();

# calculates and plots the arrows
def EIL = if !IsNaN(EI) and !isUp then pricel else GetValue(EIL, 1);
def EIH = if !IsNaN(EI) and isUp then priceh else GetValue(EIH, 1);
def dir = CompoundValue(1, if EIL != EIL[1] or pricel == EIL[1] and pricel == EISave then 1 else if EIH != EIH[1] or priceh == EIH[1] and priceh == EISave then -1 else dir[1], 0);
def signal = CompoundValue(1, if dir > 0 and pricel > EIL then if signal[1] <= 0 then 1 else signal[1] else if dir < 0 and priceh < EIH then if signal[1] >= 0 then -1 else signal[1] else signal[1], 0);
def showarrows = yes;
plot U1 = showarrows and signal > 0 and signal[1] <= 0;
U1.SetPaintingStrategy(PaintingStrategy.BOOLEAN_ARROW_UP);
U1.SetDefaultColor(Color.GREEN);
U1.SetLineWeight(4);
plot D1 = showarrows and signal < 0 and signal[1] >= 0;
D1.SetPaintingStrategy(PaintingStrategy.BOOLEAN_ARROW_DOWN);
D1.SetDefaultColor(Color.RED);
D1.SetLineWeight(4);

UpperBand.AssignValueColor(if UpperBand > UpperBand[1] then Color.UPTICK else Color.RED);
LowerBand.AssignValueColor(if LowerBand > LowerBand[1] then Color.UPTICK else Color.RED);
AddCloud(UpperBand, LowerBand, Color.GREEN, Color.RED);
def Chg1      =   If((UpperBand > UpperBand[1] and LowerBand > LowerBand[1]), 1, If((UpperBand < UpperBand[1] and LowerBand < LowerBand[1]), -1, 0));
def Hold     =   CompoundValue(1, If(Hold[1] == Chg1 or Chg1 == 0, Hold[1], If(Chg1 == 1, 1, -1)), 0);
def LBUp     =   if fill and Hold[0] == 1 then lowerBand else nan;
def UBUp     =   if fill and Hold[0] == 1 then upperband else nan;
def LBDn     =   if fill and Hold[0] == -1 then lowerband else nan;
def UBDn     =   if fill and Hold[0] == -1 then upperband else nan;
DefineGlobalColor("Cloud Up", Color.magenta);
DefineGlobalColor("Cloud Dn", Color.green);
AddCloud(LBUp, UBUp, GlobalColor("Cloud Up"), GlobalColor("Cloud Dn"));
AddCloud(LBDn, UBDn, GlobalColor("Cloud Dn"), GlobalColor("Cloud Up"));
 
hey guys. i have been using this and understand it has issues. My question is what is a similar indicator that does not have the problems. thanks
i have been using on 5 minute charts and seems to work pretty well. i may need to give it more time to see if it works longer term
 
Last edited by a moderator:
hey guys. i have been using this and understand it has issues. My question is what is a similar indicator that does not have the problems. thanks
Any indicator plotting high / lows will repaint. It is part of the definition. The high this minute is $10. It goes up to $12. so it erases the $10 high signal and now calls $12 the high. So on and so forth all day long. There is no way to predict when a trend is done until it is long done.
This is true for trend reversals, zigzags, swing high swing low, COG, Hurst, HoHo, DansArrows, etc...

Repainting indicators are used by scalpers on the minute chart. Their trades only last 2-5 ticks. They are in and out, disciplined with their stop losses, and never use the indicator in isolation.
Read more:
https://usethinkscript.com/threads/repainting-trend-reversal-questions.7600/#post-72193

@dcosper repainters do work well on trending days, trending markets, with a trending stock.
Where day traders lose their portfolios with repainters is making the mistake of thinking a volatile stock in a volatile market reversed just because they got a repainting signal.

Repainters make no guarantee that the stock won't head lower. On a 5-min chart, there can be significant downward movement. Waiting 5-min to find out the stock tanked could be calamitous.

To hedge your bets. Use multiple timeframes:
Keep a 2-min chart open also and review the multiple indicators

On the VIP forum read more about what timeframes and what other indicators:
https://usethinkscript.com/threads/...cators-of-for-swinging-and-day-trading.10766/
 
Last edited:
Trend Reversal Indicator: Scanner
Scanning using this indicator is not always successful.
It works best when run against a smaller selection of stocks (for example: S&P100 or one of your watchlists)
This is a repainting indicator so the results returned in the scanner are be based on signals that exist in the moment but subsequently may not.

Copy the code from here --> https://usethinkscript.com/threads/...signals-for-thinkorswim.183/page-18#post-8617 and paste into the Studies Tab
or
Copy Shared Scanner Link: https://tos.mx/vlVadom Click here for --> Easiest way to load shared links

Click on the scanner.
  1. Click on +Add filter
  2. Click on the pencil icon next to the filter you just added
  3. Click edit
  4. In the left column, click on the 1st pull-down window, click study
  5. Type in the name of your study
  6. Under Plot, click on the pull-down window, choose upArrow
  7. In the middle column, choose is true
  8. Save
Sorry I am asking a very rookie question: "Click on the scanner.". Exactly where to click? Is it a button or something? where is it? Thanks.
 
Sorry I am asking a very rookie question: "Click on the scanner.". Exactly where to click? Is it a button or something? where is it? Thanks.
@wshao8 , You need to provide a name when u copy the code and saved as an indicator, eg Trend Reversal Indicator.

https%3A//i.imgur.com/GN4FwcC.jpg[/img]']
GN4FwcC.jpg


https%3A//i.imgur.com/S7oMT7P.jpg[/img]']
S7oMT7P.jpg


https%3A//i.imgur.com/uz2ikgI.jpg[/img]']
uz2ikgI.jpg
 
Still one question: how can this scanner be used for DT? #22 seems doe not answer the question which #21 asked. Thanks again.
If your question is how to use MTF indicators in the ToS Scan Hacker, the answer is that you don't.
The ToS Scan Hacker does not provide for MTF scanning.

You can scan for one timeframe and then feed those results into another scan for another timeframe.
read more here:
https://usethinkscript.com/threads/is-there-a-way-to-use-two-time-aggregations.11122/#post-97446
 
Last edited:
Below code is from theelderwant - but what im unable to understand is what is the role of Buy_Signal / buysignal and Sell_Signal / sellsignal

i dont see these 2 being used in the code below -- but when i remove code lines from 20-32 it stops painting the up and down arrow - but if I comment only just buy_signal section or sell_signal section then it continues to paint the UP anbd DOWN arrows -- whats the mystry here

Rich (BB code):
# Trend Reversal Scanner
# Scanner by https://usethinkscript.com/u/theelderwand
# Discuss https://usethinkscript.com/d/183-trend-reversal-indicator-with-signals-for-thinkorswim

def price = close;
def superfast_length = 9;
def fast_length = 14;
def slow_length = 21;
def displace = 0;

def mov_avg9 = ExpAverage(price[-displace], superfast_length);
def mov_avg14 = ExpAverage(price[-displace], fast_length);
def mov_avg21 = ExpAverage(price[-displace], slow_length);

#moving averages
def Superfast = mov_avg9;
def Fast = mov_avg14;
def Slow = mov_avg21;

def buy = mov_avg9 > mov_avg14 and mov_avg14 > mov_avg21 and low > mov_avg9;
def stopbuy = mov_avg9 <= mov_avg14;
def buynow = !buy[1] and buy;
def buysignal = CompoundValue(1, if buynow and !stopbuy then 1 else if buysignal[1] == 1 and stopbuy then 0 else buysignal[1], 0);

def Buy_Signal = buysignal[1] == 0 and buysignal == 1;
def Momentum_Down = buysignal[1] == 1 and buysignal == 0;

def sell = mov_avg9 < mov_avg14 and mov_avg14 < mov_avg21 and high < mov_avg9;
def stopsell = mov_avg9 >= mov_avg14;
def sellnow = !sell[1] and sell;
def sellsignal = CompoundValue(1, if sellnow and !stopsell then 1 else if sellsignal[1] == 1 and stopsell then 0 else sellsignal[1], 0);
def Sell_Signal = sellsignal[1] == 0 and sellsignal;


input method = {default average, high_low};
def bubbleoffset = .0005;
def percentamount = .01;
def revAmount = .05;
def atrreversal = 2.0;
def atrlength = 5;
def pricehigh = high;
def pricelow = low;
def averagelength = 5;
def averagetype = AverageType.EXPONENTIAL;
def mah = MovingAverage(averagetype, pricehigh, averagelength);
def mal = MovingAverage(averagetype, pricelow, averagelength);
def priceh = if method == method.high_low then pricehigh else mah;
def pricel = if method == method.high_low then pricelow else mal;
def EI = ZigZagHighLow("price h" = priceh, "price l" = pricel, "percentage reversal" = percentamount, "absolute reversal" = revAmount, "atr length" = atrlength, "atr reversal" = atrreversal);
rec EISave = if !IsNaN(EI) then EI else GetValue(EISave, 1);
def chg = (if EISave == priceh then priceh else pricel) - GetValue(EISave, 1);
def isUp = chg >= 0;
def EIL = if !IsNaN(EI) and !isUp then pricel else GetValue(EIL, 1);
def EIH = if !IsNaN(EI) and isUp then priceh else GetValue(EIH, 1);
def dir = CompoundValue(1, if EIL != EIL[1] or pricel == EIL[1] and pricel == EISave then 1 else if EIH != EIH[1] or priceh == EIH[1] and priceh == EISave then -1 else dir[1], 0);
def signal = CompoundValue(1, if dir > 0 and pricel > EIL then if signal[1] <= 0 then 1 else signal[1] else if dir < 0 and priceh < EIH then if signal[1] >= 0 then -1 else signal[1] else signal[1], 0);

def bullish2 = signal > 0 and signal[1] <= 0;
plot upArrow = bullish2;
upArrow.SetPaintingStrategy(PaintingStrategy.BOOLEAN_ARROW_UP);
upArrow.SetDefaultColor(CreateColor(145, 210, 144));

def bearish2 = signal < 0 and signal[1] >= 0;
plot downArrow = bearish2;
downArrow.SetPaintingStrategy(PaintingStrategy.BOOLEAN_ARROW_DOWN);
downArrow.SetDefaultColor(CreateColor(255, 15, 10));
 
Below code is from theelderwant - but what im unable to understand is what is the role of Buy_Signal / buysignal and Sell_Signal / sellsignal

i dont see these 2 being used in the code below -- but when i remove code lines from 20-32 it stops painting the up and down arrow - but if I comment only just buy_signal section or sell_signal section then it continues to paint the UP anbd DOWN arrows -- whats the mystry here

Rich (BB code):
# Trend Reversal Scanner
# Scanner by https://usethinkscript.com/u/theelderwand
# Discuss https://usethinkscript.com/d/183-trend-reversal-indicator-with-signals-for-thinkorswim

def price = close;
def superfast_length = 9;
def fast_length = 14;
def slow_length = 21;
def displace = 0;

def mov_avg9 = ExpAverage(price[-displace], superfast_length);
def mov_avg14 = ExpAverage(price[-displace], fast_length);
def mov_avg21 = ExpAverage(price[-displace], slow_length);

#moving averages
def Superfast = mov_avg9;
def Fast = mov_avg14;
def Slow = mov_avg21;

def buy = mov_avg9 > mov_avg14 and mov_avg14 > mov_avg21 and low > mov_avg9;
def stopbuy = mov_avg9 <= mov_avg14;
def buynow = !buy[1] and buy;
def buysignal = CompoundValue(1, if buynow and !stopbuy then 1 else if buysignal[1] == 1 and stopbuy then 0 else buysignal[1], 0);

def Buy_Signal = buysignal[1] == 0 and buysignal == 1;
def Momentum_Down = buysignal[1] == 1 and buysignal == 0;

def sell = mov_avg9 < mov_avg14 and mov_avg14 < mov_avg21 and high < mov_avg9;
def stopsell = mov_avg9 >= mov_avg14;
def sellnow = !sell[1] and sell;
def sellsignal = CompoundValue(1, if sellnow and !stopsell then 1 else if sellsignal[1] == 1 and stopsell then 0 else sellsignal[1], 0);
def Sell_Signal = sellsignal[1] == 0 and sellsignal;


input method = {default average, high_low};
def bubbleoffset = .0005;
def percentamount = .01;
def revAmount = .05;
def atrreversal = 2.0;
def atrlength = 5;
def pricehigh = high;
def pricelow = low;
def averagelength = 5;
def averagetype = AverageType.EXPONENTIAL;
def mah = MovingAverage(averagetype, pricehigh, averagelength);
def mal = MovingAverage(averagetype, pricelow, averagelength);
def priceh = if method == method.high_low then pricehigh else mah;
def pricel = if method == method.high_low then pricelow else mal;
def EI = ZigZagHighLow("price h" = priceh, "price l" = pricel, "percentage reversal" = percentamount, "absolute reversal" = revAmount, "atr length" = atrlength, "atr reversal" = atrreversal);
rec EISave = if !IsNaN(EI) then EI else GetValue(EISave, 1);
def chg = (if EISave == priceh then priceh else pricel) - GetValue(EISave, 1);
def isUp = chg >= 0;
def EIL = if !IsNaN(EI) and !isUp then pricel else GetValue(EIL, 1);
def EIH = if !IsNaN(EI) and isUp then priceh else GetValue(EIH, 1);
def dir = CompoundValue(1, if EIL != EIL[1] or pricel == EIL[1] and pricel == EISave then 1 else if EIH != EIH[1] or priceh == EIH[1] and priceh == EISave then -1 else dir[1], 0);
def signal = CompoundValue(1, if dir > 0 and pricel > EIL then if signal[1] <= 0 then 1 else signal[1] else if dir < 0 and priceh < EIH then if signal[1] >= 0 then -1 else signal[1] else signal[1], 0);

def bullish2 = signal > 0 and signal[1] <= 0;
plot upArrow = bullish2;
upArrow.SetPaintingStrategy(PaintingStrategy.BOOLEAN_ARROW_UP);
upArrow.SetDefaultColor(CreateColor(145, 210, 144));

def bearish2 = signal < 0 and signal[1] >= 0;
plot downArrow = bearish2;
downArrow.SetPaintingStrategy(PaintingStrategy.BOOLEAN_ARROW_DOWN);
downArrow.SetDefaultColor(CreateColor(255, 15, 10));
This is a scan script to be used in the Scan Hacker
 
Maybe this can help - it removes a lot of unnecessary fluff from the indicator. The EMAs (the 9, 14, and 21) and fib retracements are extra for the indicator and are not shown. For instance, the three EMAs are only used for the color of the reversal bubbles, and the fib code itself is just dead weight, nothing is even plotted from the calculations. There are also a lot of bubbles and labels in the code that are turned off by default in the original indicator. There's a bunch of stuff that isnt being used in the original. I uncovered a few plots and added a bit to make the visuals easier. Not an expert, but hope this helps

Code:
# used to switch between "zigzag based on high/low of price" and "zigzag based on then high/low of moving averages"
input method = {default average, high_low};

# data for the built-in zigzag indicator which is referenced in the study. To see the ZigZagHighLow() code, look for it in the built-in TOS studies
def bubbleoffset = .0005;
def percentamount = .01;
def revAmount = .05;
def atrreversal = 2.0;
def atrlength = 5;

# data for the moving averages
def pricehigh = high;
def pricelow = low;
def averagelength = 5;
def averagetype = AverageType.EXPONENTIAL;

# here are the moving averages used for the signals - changed to plots and given colors
plot mah = MovingAverage(averagetype, pricehigh, averagelength);
plot mal = MovingAverage(averagetype, pricelow, averagelength);
mah.setdefaultcolor(color.cyan);
mal.setdefaultcolor(color.cyan);

# continues the switch between the two different zigzag data points
def priceh = if method == method.high_low then pricehigh else mah;
def pricel = if method == method.high_low then pricelow else mal;

# references the built-in zigzag indicator
def EI = ZigZagHighLow("price h" = priceh, "price l" = pricel, "percentage reversal" = percentamount, "absolute reversal" = revAmount, "atr length" = atrlength, "atr reversal" = atrreversal);

# not very clear on how this exactly works - but the end result is to plot the zigzag lines
def reversalAmount = if (close * percentamount / 100) > Max(revAmount < atrreversal * reference ATR(atrlength), revAmount) then (close * percentamount / 100) else if revAmount < atrreversal * reference ATR(atrlength) then atrreversal * reference ATR(atrlength) else revAmount;
rec EISave = if !IsNaN(EI) then EI else GetValue(EISave, 1);
def chg = (if EISave == priceh then priceh else pricel) - GetValue(EISave, 1);
def isUp = chg >= 0;
rec isConf = AbsValue(chg) >= reversalAmount or (IsNaN(GetValue(EI, 1)) and GetValue(isConf, 1));
def EId = if isUp then 1 else 0;

# zigzag plot and colors
plot EnhancedLines = if EId <= 1 then EI else Double.NaN;
EnhancedLines.AssignValueColor(if EId == 1 then Color.GREEN else if EId == 0 then Color.RED else Color.DARK_ORANGE);
EnhancedLines.SetStyle(Curve.FIRM);
EnhancedLines.EnableApproximation();
EnhancedLines.HideBubble();

# calculates and plots the arrows
def EIL = if !IsNaN(EI) and !isUp then pricel else GetValue(EIL, 1);
def EIH = if !IsNaN(EI) and isUp then priceh else GetValue(EIH, 1);
def dir = CompoundValue(1, if EIL != EIL[1] or pricel == EIL[1] and pricel == EISave then 1 else if EIH != EIH[1] or priceh == EIH[1] and priceh == EISave then -1 else dir[1], 0);
def signal = CompoundValue(1, if dir > 0 and pricel > EIL then if signal[1] <= 0 then 1 else signal[1] else if dir < 0 and priceh < EIH then if signal[1] >= 0 then -1 else signal[1] else signal[1], 0);
def showarrows = yes;
plot U1 = showarrows and signal > 0 and signal[1] <= 0;
U1.SetPaintingStrategy(PaintingStrategy.BOOLEAN_ARROW_UP);
U1.SetDefaultColor(Color.GREEN);
U1.SetLineWeight(4);
plot D1 = showarrows and signal < 0 and signal[1] >= 0;
D1.SetPaintingStrategy(PaintingStrategy.BOOLEAN_ARROW_DOWN);
D1.SetDefaultColor(Color.RED);
D1.SetLineWeight(4);

As you can see, the 9, 14, and 21 EMAs are not even needed.

Edit: If you look at the code I posted, you can see the line def showarrows = yes;. The original code is full of these "defs" that probably were originally meant to be inputs instead. Someone has either changed the original code a lot before @BenTen found and posted it here in the forum, or its just a incomplete mish-mash of different codes. I have no idea

example-pic.png

Nice work on this study ,works great and has a clean look to the chart too!!! Waited 3 years to get rid of bubbles .......Thank you @Pensar !!!!
 
Last edited by a moderator:
I am getting script complexity error

low crosses below TrendReversalIndicatorSignalBars()."botLine"
yes, the Trend Reversal is too complex for the scan hacker.

There is a version that has been extremely modified and may not give you the results you want:
https://usethinkscript.com/threads/repainting-trend-reversal-questions.7600/#post-72210

1. You should read through the whole thread for the caveats
2. You should not attempt to scan the whole universe of stocks. Limit your scan to something that won't timeout IE: S&P500, NASDAQ 100, etc...

Trades based on repainting indicators can result in significant losses.
 
Last edited:
This question is for this popular indicator found here: https://usethinkscript.com/threads/repainting-trend-reversal-for-thinkorswim.183/

I would like to create a label that displays the reversal price. Here's what I have so far and here's a screen shot.


def Low_1 = if signal > 0 and signal[1] then low else double.nan;
def High_1 = if signal < 0 and signal[1] then high else double.nan;

AddLabel(yes, if signal > 0 and signal[1] then "Bullish Reversal: " + Concat(low_1, 0) else "", color.Green);
AddLabel(yes, if signal < 0 and signal[1] then "Bearish Reversal: " + Concat(high_1, 0) else "", color.Red);

1. labels display a value from the last bar. you aren't storing previous values, so there is no number to display.

2. you aren't including the time component of when to read data, the first parameter in a bubble.

3. you used ...and signal[1]
instead of ...and signal[1] <= 0


These 2 lines seem to be the bubble code that you want to copy.

AddChartBubble(
(barnumber and U1),
if isUp then low else high,
if showarrows and signal > 0 and signal[1] <= 0 then "Reversal:" + low else "" ,
if Colorbars == 3 then Color.PLUM else Color.UPTICK,
no);

AddChartBubble(
(barnumber and D1),
if isUp then low else high,
if showarrows and signal < 0 and signal[1] >= 0 then "Reversal:" + high else "" ,
if Colorbars == 3 then Color.PLUM else Color.DOWNTICK,
yes);


ref,
the signal formula , 1 or -1 or 0
def signal = CompoundValue(1, if dir > 0 and pricel > EIL then if signal[1] <= 0 then 1 else signal[1] else if dir < 0 and priceh < EIH then if signal[1] >= 0 then -1 else signal[1] else signal[1], 0);


------------

add this to the end of the original code

Code:
# add labels to show recent bubble values.
# ..copy trigger signals from bubble formulas
# ..keep recent values

# ref , in original
# def barnumber = BarNumber()[10];
# bubble formulas use barnumber as a logical value, so i guess if the bar# is 10 or less then it equals nan or false. otherwise it is a valid number, which is interpretted as true...

def Low_1 = if (barnumber and U1 and signal > 0 and signal[1] <= 0)  then low else Low_1[1];

def High_1 = if (barnumber and D1 and signal < 0 and signal[1] >= 0) then high else High_1[1];

AddLabel(1, "Bullish Reversal: " + low_1, color.Green);

AddLabel(1, "Bearish Reversal: " + high_1, color.Red);
#
 
Hey everyone,

. I grabbed this code off this site and have been trying to modify it with a buddy added in an ema cross for an additional confluence. Total newb when it comes to coding, so I am probably messing something up here. I am attempting to add in the float but seem to be struggling getting it correct can anyone help?

Side note: I also saw an old thread you can't use options, but there's code within ToS to pull from options. Is this still the case?

https://tlc.thinkorswim.com/center/reference/thinkScript/Functions/Option-Related

Reversal Code
http://tos.mx/LVJSEkW

Thanks in advance for all your help!
 
Hey everyone,

. I grabbed this code off this site and have been trying to modify it with a buddy added in an ema cross for an additional confluence. Total newb when it comes to coding, so I am probably messing something up here. I am attempting to add in the float but seem to be struggling getting it correct can anyone help?

Side note: I also saw an old thread you can't use options, but there's code within ToS to pull from options. Is this still the case?

https://tlc.thinkorswim.com/center/reference/thinkScript/Functions/Option-Related

Reversal Code
http://tos.mx/LVJSEkW

Thanks in advance for all your help!
1. No, you cannot add a repainter to a strategy to get the P&L float. All the false signals are erased, only perfect signals are left resulting in a perfect P&L that is meaningless.

This will be true regardless of how many other indicators that you add to it. This theory was tested by hundreds of traders in this thread:
https://usethinkscript.com/threads/supertrend-with-reversal-for-thinkorswim.8259/ Where several indicators were added to the reversal and still it repainted.

Unfortunately, that is the definition of repainting. That is why repainting indicators can not be used in strategies nor back tested.
You can read more here:
https://usethinkscript.com/threads/answers-to-commonly-asked-questions.6006/#post-57833

2. Not sure what you mean with this statement: "you can't use options, but there's code within ToS to pull from options. Is this still the case?"
 

Join useThinkScript to post your question to a community of 21,000+ developers and traders.

Similar threads

Not the exact question you're looking for?

Start a new thread and receive assistance from our community.

87k+ Posts
521 Online
Create Post

Similar threads

Similar threads

The Market Trading Game Changer

Join 2,500+ subscribers inside the useThinkScript VIP Membership Club
  • Exclusive indicators
  • Proven strategies & setups
  • Private Discord community
  • ‘Buy The Dip’ signal alerts
  • Exclusive members-only content
  • Add-ons and resources
  • 1 full year of unlimited support

Frequently Asked Questions

What is useThinkScript?

useThinkScript is the #1 community of stock market investors using indicators and other tools to power their trading strategies. Traders of all skill levels use our forums to learn about scripting and indicators, help each other, and discover new ways to gain an edge in the markets.

How do I get started?

We get it. Our forum can be intimidating, if not overwhelming. With thousands of topics, tens of thousands of posts, our community has created an incredibly deep knowledge base for stock traders. No one can ever exhaust every resource provided on our site.

If you are new, or just looking for guidance, here are some helpful links to get you started.

What are the benefits of VIP Membership?
VIP members get exclusive access to these proven and tested premium indicators: Buy the Dip, Advanced Market Moves 2.0, Take Profit, and Volatility Trading Range. In addition, VIP members get access to over 50 VIP-only custom indicators, add-ons, and strategies, private VIP-only forums, private Discord channel to discuss trades and strategies in real-time, customer support, trade alerts, and much more. Learn all about VIP membership here.
How can I access the premium indicators?
To access the premium indicators, which are plug and play ready, sign up for VIP membership here.
Back
Top