Bulkowski Double Bottom Indicator for ThinkorSwim

BenTen

Administrative
Staff
VIP
This indicator was created for ThinkorSwim based on Bulkowski's Double Bottom Setup. You can learn more about the pattern, examples, and how to trade it here.

Pm0SPMF.png


The Bulkowski Double Bottom indicator highlights a few things on your chart:
  • First Pivot
  • Pivot Low
  • Double Bottom Price
  • Breakout Price

thinkScript Code

Code:
# Bulkowski Double Bottom Pattern
# TASC Aril 2019
# Nube 3.30.19
# v 0.02, unsuccessfully trying to mark the first pivot of the pattern

    # INPUTS
input pivotLength = 4;
input maxDoubleBottomWidth = 24;
input tolerancePercentage = 1.5;
input ticksAboveDoubleBottomHigh = 1;

    # VARIABLES
# Universal
def h = high;
def l = low;
def nan = Double.NaN;
def x = BarNumber();
def tick = TickSize();
# Study Specific
def lowPivotBar = if !GetMinValueOffset(l, pivotLength + 1)
                  and GetMinValueOffset(l, pivotLength + 1)[-pivotLength + 1] ==
                      pivotLength - 1
                  then x
                  else lowPivotBar[1];
def lowPivot = if x == lowPivotBar
               then x   
               else nan;
def lowPivotPrice = if x == lowPivotBar
                    then l
                    else lowPivotPrice[1];
def priorLowPivotBar = if lowPivotBar != lowPivotBar[1]
                       then lowPivotBar[1]
                       else priorLowPivotBar[1];
def priorLowPivotPrice = if x == lowPivotBar
                         then GetValue(l,  lowPivotBar - priorLowPivotBar)
                         else priorLowPivotPrice[1];
def hh = if x crosses above lowPivotBar
         then h
         else if h > hh[1]
              then h
              else hh[1];
def highBetweenPivots = if x == lowPivotBar
                        then hh
                        else highBetweenPivots[1];
# Checking for pivot lows being within tolerancePercentage
def doubleBottom = if Between(lowPivotPrice,
                              priorLowPivotPrice * (1 - tolerancePercentage * .01),
                              priorLowPivotPrice * (1 + tolerancePercentage * .01))
                   and lowPivotBar - priorLowPivotBar <= maxDoubleBottomWidth
                   then Min(lowPivotPrice,priorLowPivotPrice)
                   else nan;
# invalidating pattern when price breaks below the doubleBottom price
def valid = if IsNaN(doubleBottom[1])
            and !IsNaN(doubleBottom)
            then 1
            else if l crosses below doubleBottom
                 then 0
                 else valid[1];

    # Plots
plot
PivotLow = x == lowPivotBar;
PivotLow.SetPaintingStrategy(PaintingStrategy.BOOLEAN_WEDGE_DOWN);
PivotLow.SetDefaultColor(Color.Red);

plot
DoubleBottomPrice = if valid then doubleBottom else nan;
DoubleBottomPrice.SetDefaultColor(Color.Red);
DoubleBottomPrice.SetPaintingStrategy(PaintingStrategy.HORIZONTAL);

plot
BreakoutPrice = if DoubleBottomPrice
                then highBetweenPivots + ticksAboveDoubleBottomHigh * tick
                else nan;
BreakoutPrice.SetDefaultColor(Color.Green);
BreakoutPrice.SetPaintingStrategy(PaintingStrategy.HORIZONTAL);

AddChartBubble(DoubleBottomPrice and IsNaN(DoubleBottomPrice[-1]), DoubleBottomPrice, DoubleBottomPrice+" Bottomm Price", Color.Red, 0);
AddChartBubble(BreakoutPrice and IsNaN(BreakoutPrice[-1]), BreakOutPrice, "Breakout Price"+ BreakOutPrice, Color.Green);

# f/  Bulkowski Double Bottom Pattern from April 2019 TASC this section still incorrect. Attempting to mark first pivot
def untilDB = fold i = -maxDoubleBottomWidth + 1 to 0
              with u
              while IsNaN(doubleBottom)
              do u + GetValue(IsNaN(doubleBottom), i);
        
def firstPivot = !IsNaN(lowPivot) and
                 IsNaN(GetValue(doubleBottom, -untilDB)) and
                 Between(GetValue(doubleBottom, -untilDB -1),
                         l * (1 - tolerancePercentage * .01),
                         l * (1 + tolerancePercentage * .01));

AddChartBubble(firstPivot, l, "First Pivot", Color.Red, 0);

Shareable Link

https://tos.mx/7678EI
 
Last edited:

Gabtrader

New member
Hello, i'm just new here, and just want to know if there is any script for double top/bottom candles, thanks a lot guys !
 
Last edited by a moderator:

BenTen

Administrative
Staff
VIP
Welcome. Unfortunately there is nothing like that at the moment. I'm afraid you will have to identify the candlestick pattern yourself.
 
Last edited:

CreativiTimothy

New member
Hey, I think it works very well, and I'm able to convert it into a scan filter like I can do with other studies, but the scan filter isn't working as intended for my purposes, and I need tips.

Intention: It detects a double bottom immediately and after about 30 minutes, it should no longer show up in the scan. For example, it bottoms at 1.45 once, then it bottoms 1.45 the second time 5 hours later. It shows up in my scan immediately when that happens, which is good. However, it remains in the scan even after 3 days after the double bottom has formed (two peak lows). I don't want to be trading a stock that has already went up a ton after 3 days after the double bottom formation. I want it to be removed from the scan after a 30 minute bar or (30 1 minute bars) because I like to buy the double bottom immediately with a tight stop loss for high reward/risk ratio, like buying at 5.01 at a bottom of 5, stop loss at 4.99.

Any tips on how to restrict the scan to only show immediate double bottom formations, not double bottoms that formed a long while ago like 3 days ago?
 

CreativiTimothy

New member
use within " x " days at the end of scan code
Hi I put within 1 bar at a few parts of the code, then several parts of the code, since putting it at the end didn't seem to work, but no luck. It still shows up the same number of results. For example, I modified the plot to this:


plot
DoubleBottomPrice = (if valid then 1 else nan) within 1 bar;
 

iamgshankar

New member
Friends,

Can someone please help me to use the above script to scan within the last few bars??

@BenTen I am not seeing the Break out price and other labels in my chart when i use the sharable link.. Am i missing something?

Thanks.
 

hoojsn

New member
Hi Ben,
There is 2 Error Code:
Invalid Statement. AddChartBubble at 78:1
Invalid Statement. AddChartBubble at 82:1

Please help to fix it. Thanks In Advance.
 

CreativiTimothy

New member
@Cleartarget Sure. I basically just commented all the other plots out except the "DoubleBottomPrice" plot. That's the only plot you need for the scan (scans only allow one plot) that determines whether a double bottom exists in a stock or not.

Code:
# Bulkowski Double Bottom Pattern
# TASC Aril 2019
# Nube 3.30.19
# v 0.02, unsuccessfully trying to mark the first pivot of the pattern

    # INPUTS
input pivotLength = 1;
input maxDoubleBottomWidth = 24;
input tolerancePercentage = 1.5;
input ticksAboveDoubleBottomHigh = 1;

    # VARIABLES
        ## Universal
def h = high;
def l = low;
def nan = Double.NaN;
def x = BarNumber();
def tick = TickSize();
        ## Study Specific
def lowPivotBar = if !GetMinValueOffset(l, pivotLength + 1)
                  and GetMinValueOffset(l, pivotLength + 1)[-pivotLength + 1] ==
                      pivotLength - 1
                  then x
                  else lowPivotBar[1];
def lowPivot = if x == lowPivotBar
               then x 
               else nan;
def lowPivotPrice = if x == lowPivotBar
                    then l
                    else lowPivotPrice[1];
def priorLowPivotBar = if lowPivotBar != lowPivotBar[1]
                       then lowPivotBar[1]
                       else priorLowPivotBar[1];
def priorLowPivotPrice = if x == lowPivotBar
                         then GetValue(l,  lowPivotBar - priorLowPivotBar)
                         else priorLowPivotPrice[1];
def hh = if x crosses above lowPivotBar
         then h
         else if h > hh[1]
              then h
              else hh[1];
def highBetweenPivots = if x == lowPivotBar
                        then hh
                        else highBetweenPivots[1];
            ### Checking for pivot lows being within tolerancePercentage
def doubleBottom = if Between(lowPivotPrice,
                              priorLowPivotPrice * (1 - tolerancePercentage * .01),
                              priorLowPivotPrice * (1 + tolerancePercentage * .01))
                   and lowPivotBar - priorLowPivotBar <= maxDoubleBottomWidth
                   then Min(lowPivotPrice,priorLowPivotPrice)
                   else nan;
            ### invalidating pattern when price breaks below the doubleBottom price
def valid = if IsNaN(doubleBottom[1])
            and !IsNaN(doubleBottom)
            then 1
            else if l crosses below doubleBottom
                 then 0
                 else valid[1];

    # Plots
#plot
#PivotLow = x == lowPivotBar;
#PivotLow.SetPaintingStrategy(PaintingStrategy.BOOLEAN_WEDGE_DOWN);
#PivotLow.SetDefaultColor(Color.Red);

plot
DoubleBottomPrice = if valid then doubleBottom else nan;
DoubleBottomPrice.SetDefaultColor(Color.Red);
DoubleBottomPrice.SetPaintingStrategy(PaintingStrategy.HORIZONTAL);

#plot
#BreakoutPrice = if DoubleBottomPrice
#                then highBetweenPivots + ticksAboveDoubleBottomHigh * tick
#                else nan;
#BreakoutPrice.SetDefaultColor(Color.Green);
#BreakoutPrice.SetPaintingStrategy(PaintingStrategy.HORIZONTAL);

AddChartBubble(DoubleBottomPrice and IsNaN(DoubleBottomPrice[-1]),
               DoubleBottomPrice, DoubleBottomPrice+"\nBottomm Price\n", Color.Red, 0);
#AddChartBubble(BreakoutPrice and IsNaN(BreakoutPrice[-1]),
#               BreakOutPrice, "Breakout Price\n"+ BreakOutPrice, Color.Green);


# f/  Bulkowski Double Bottom Pattern from April 2019 TASC

                #### this section still incorrect. Attempting to mark first pivot
def untilDB = fold i = -maxDoubleBottomWidth + 1 to 0
              with u
              while IsNaN(doubleBottom)
              do u + GetValue(IsNaN(doubleBottom), i);
        
def firstPivot = !IsNaN(lowPivot) and
                 IsNaN(GetValue(doubleBottom, -untilDB)) and
                 Between(GetValue(doubleBottom, -untilDB -1),
                         l * (1 - tolerancePercentage * .01),
                         l * (1 + tolerancePercentage * .01));

AddChartBubble(firstPivot, l, "First Pivot", Color.Red, 0);
 

dmillz

Member
VIP
Does anyone know how to plot the higher double bottom for a scan using this script.

Code:
# Double Bottom

# Mobius

 

input Percent_A_to_B = 2;

input Percent_A_to_C = .1;

input nP = 13;

input ShowValues = yes;

input ShowLines = yes;

 

def AB = Percent_A_to_B / 100;

def AC = Percent_A_to_C / 100;

def h = high;

def l = low;

def bar = BarNumber();

def Ps = 1 + AC;

def Ns = 1 - AC; 

def ll = fold j = 1 to nP + 1 

         with q = 1

         while q

         do l < GetValue(low, -j);

def PivotL = if (bar > nP and 

                 l == Lowest(l, nP) and 

                 ll) 

            then l 

            else Double.NaN;

def PL1 = if !isNaN(PivotL) 

          then l 

          else PL1[1];

def PL1Bar = if !IsNaN(PivotL) 

             then bar 

             else PL1Bar[1];

 

def PL2 = if PL1 != PL1[1]

          then PL1[1]

          else PL2[1];

def PL2Bar = if PL1Bar != PL1Bar[1]

             then Pl1Bar[1] 

             else PL2Bar[1];

def Check1 = if between(PL2, PL1 * Ns, PL1 * Ps)

             then 1

             else 0;

plot Cond1 = HighestAll(if Check1

                        then PL2

                        else double.nan);

def PL3 = if PL2 != PL2[1]

          then PL2[1]

          else PL3[1];

def PL3Bar = if PL2Bar != PL2Bar[1]

             then Pl2Bar[1] 

             else PL3Bar[1];

def Check2 = if between(PL3, PL2 * Ns, PL2 * Ps)

             then 1

             else 0;

def PL4 = if PL3 != PL3[1]

          then PL3[1]

          else PL4[1];

def PL4Bar = if PL3Bar != PL3Bar[1]

             then PL3Bar[1]

             else PL4Bar[1];

def Check3 = if between(PL4, PL3 * Ns, PL3 * Ps)

             then 1

             else 0;

def PL5 = if PL4 != PL4[1]

          then PL4[1]

          else PL5[1];

def PL5Bar = if PL4Bar != PL4Bar[1]

             then PL4Bar[1]

             else PL5Bar[1];

def Check4 = if between(PL5, PL4 * Ns, PL4 * Ps)

             then 1

             else double.nan;

 

plot pivotLow = PivotL;

     pivotLow.SetDefaultColor(Color.Yellow);

     pivotLow.SetPaintingStrategy(PaintingStrategy.VALUES_BELOW);

     pivotLow.SetHiding(!ShowValues);

plot PivotDot = PivotL;

     PivotDot.SetDefaultColor(Color.Gray);

     PivotDot.SetPaintingStrategy(PaintingStrategy.POINTS);

     PivotDot.SetLineWeight(3);

 

# End Code
 

Similar threads

Top