John Carter's Squeeze Pro Indicator for ThinkorSwim (FREE)

New Indicator: Buy the Dip

Check out our Buy the Dip indicator and see how it can help you find profitable swing trading ideas. Scanner, watchlist columns, and add-ons are included.

Download the indicator

@Shooters_Gotta_Shoot Nice work. What is the good time frame to use this indicator?
@whats up I was trying to use it on the 1000 tick chart but the indicator just wasn't quick enough to keep up. I'd at least bump it up to 5 minutes. I've seen the best results with the higher time frames for this indicator. Figured it was worth sharing, even though it doesn't match my trading style. Thought others would enjoy the concept.
 
@whats up I was trying to use it on the 1000 tick chart but the indicator just wasn't quick enough to keep up. I'd at least bump it up to 5 minutes. I've seen the best results with the higher time frames for this indicator. Figured it was worth sharing, even though it doesn't match my trading style. Thought others would enjoy the concept.
thank you i did tested on a one minutes and 5min chart
i find it good on a one min chart using stochastic
 
Hi All - this is great - but is there a way to make the dots bigger? They are tiny on the histogram - I've noticed that on other charts they are about 3x larger - very difficult to see on this. I checked the TOS painting strategy docs, but not seeing a solution there.
 
Hi All - this is great - but is there a way to make the dots bigger? They are tiny on the histogram - I've noticed that on other charts they are about 3x larger - very difficult to see on this. I checked the TOS painting strategy docs, but not seeing a solution there.
You can edit dot size in the Study Settings panel... In the default TTM_Squeeze that comes in TOS you would change the VolComp dots... I think they are set to 3 by default but can be increased to 5...
 
@salehz94 Throw this below code into a scan and you should get what you are looking for.

Code:
input price = close;
input length = 20;
input Num_Dev_Dn = -2.0;
input Num_Dev_up = 2.0;
input averageType = AverageType.SIMPLE;
input displace = 0;
def sDev = StDev(data = price[-displace], length = length);
def MidLineBB = MovingAverage(averageType, data = price[-displace], length = length);
def LowerBandBB = MidLineBB + Num_Dev_Dn * sDev;
def UpperBandBB = MidLineBB + Num_Dev_up * sDev;
input factorhigh = 1.0;
input factormid = 1.5;
input factorlow = 2.0;
input trueRangeAverageType = AverageType.SIMPLE;
def shifthigh = factorhigh * MovingAverage(trueRangeAverageType, TrueRange(high, close, low), length);
def shiftMid = factormid * MovingAverage(trueRangeAverageType, TrueRange(high, close, low), length);
def shiftlow = factorlow * MovingAverage(trueRangeAverageType, TrueRange(high, close, low), length);
def average = MovingAverage(averageType, price, length);

def Avg = average[-displace];


def UpperBandKCLow = average[-displace] + shiftlow[-displace];
def LowerBandKCLow = average[-displace] - shiftlow[-displace];

def UpperBandKCMid = average[-displace] + shiftMid[-displace];
def LowerBandKCMid = average[-displace] - shiftMid[-displace];

def UpperBandKCHigh = average[-displace] + shifthigh[-displace];
def LowerBandKCHigh = average[-displace] - shifthigh[-displace];

def K = (Highest(high, length) + Lowest(low, length)) /
2 + ExpAverage(close, length);
def momo = Inertia(price - K / 2, length);

def pos         = momo>= 0;
def neg         = momo< 0;
def up         = momo >= momo[1];
def dn         = momo < momo[1];


def presqueeze      = LowerBandBB > LowerBandKCLow and UpperBandBB < UpperBandKCLow;
def originalSqueeze     = LowerBandBB > LowerBandKCMid and UpperBandBB < UpperBandKCMid;
def ExtrSqueeze     = LowerBandBB > LowerBandKCHigh and UpperBandBB < UpperBandKCHigh;

plot scan = presqueeze or originalSqueeze or extrSqueeze within 1 bar;
 
This works amazingly. I'm currently using a wl column ttm status using the standard ttm. Do you have a wl column for this pro replica? @Sneaky_Swings

Here is a watchlist column for those interested: http://tos.mx/c6kSvbk

Code:
input price = close;
input length = 20;
input Num_Dev_Dn = -2.0;
input Num_Dev_up = 2.0;
input averageType = AverageType.SIMPLE;
input displace = 0;
def sDev = StDev(data = price[-displace], length = length);
def MidLineBB = MovingAverage(averageType, data = price[-displace], length = length);
def LowerBandBB = MidLineBB + Num_Dev_Dn * sDev;
def UpperBandBB = MidLineBB + Num_Dev_up * sDev;
input factorhigh = 1.0;
input factormid = 1.5;
input factorlow = 2.0;
input trueRangeAverageType = AverageType.SIMPLE;
def shifthigh = factorhigh * MovingAverage(trueRangeAverageType, TrueRange(high, close, low), length);
def shiftMid = factormid * MovingAverage(trueRangeAverageType, TrueRange(high, close, low), length);
def shiftlow = factorlow * MovingAverage(trueRangeAverageType, TrueRange(high, close, low), length);
def average = MovingAverage(averageType, price, length);

def Avg = average[-displace];


def UpperBandKCLow = average[-displace] + shiftlow[-displace];
def LowerBandKCLow = average[-displace] - shiftlow[-displace];

def UpperBandKCMid = average[-displace] + shiftMid[-displace];
def LowerBandKCMid = average[-displace] - shiftMid[-displace];

def UpperBandKCHigh = average[-displace] + shifthigh[-displace];
def LowerBandKCHigh = average[-displace] - shifthigh[-displace];

def K = (Highest(high, length) + Lowest(low, length)) /
2 + ExpAverage(close, length);
def momo = Inertia(price - K / 2, length);

def pos         = momo>= 0;
def neg         = momo< 0;
def up         = momo >= momo[1];
def dn         = momo < momo[1];


def presqueeze      = LowerBandBB > LowerBandKCLow and UpperBandBB < UpperBandKCLow;
def originalSqueeze     = LowerBandBB > LowerBandKCMid and UpperBandBB < UpperBandKCMid;
def ExtrSqueeze     = LowerBandBB > LowerBandKCHigh and UpperBandBB < UpperBandKCHigh;

addlabel(yes, if extrSqueeze then "extraSqueeze" else if presqueeze then "preSqueeze" else if originalSqueeze then "squeeze" else if preSqueeze then "preSqueeze" else "noSqueeze");
assignBackgroundColor(if ExtrSqueeze then Color.red else if originalSqueeze then Color.blue else if presqueeze then color.white else Color.gray);
 
I decided to create a quick strategy to test TTM_Squeeze (not Pro) and the related TTM indicators combined into a single strategy as John Carter described near the end of Mastering the Trade. It actually works better than I saw when I just added the studies and looked at some charts. Though, the exits are often terrible, missing half or two thirds of a run.

Put this on a chart along with the FloatingPL study to see the results. Carter recommends daily and 5m charts for this strategy.

Ruby:
input risk = 100;

def inSqueeze = reference TTM_Squeeze.SqueezeAlert == 0;

def momo = reference TTM_Squeeze.Histogram;

def waveHigh = reference TTM_Wave.Wave2High;
def waveLow = reference TTM_Wave.Wave2Low;
def waveIsLong = waveHigh >= waveHigh[1] and waveLow >= waveLow[1];

def upTrend = reference TTM_Trend.TrendUp;
def downTrend = reference TTM_Trend.TrendDown;

def isTrigger = !inSqueeze and inSqueeze[1] and momo > momo[1] and waveIsLong and upTrend;

AddOrder(OrderType.BUY_TO_OPEN, isTrigger, open[-1], RoundDown(Max(risk / (high - low + .02), 1), 0), GetColor(8), GetColor(8), "Squeeze LE");

def isExit = downTrend;
AddOrder(OrderType.SELL_TO_CLOSE, isExit, open[-1], 0, GetColor(8), GetColor(8), "Trend LX");
 
Last edited:
@Slippage Whether it works better than TTM Squeeze or not I cannot give an opinion on. I do not use TTM Squeeze enough to be able to give any kind of fair comparison. That being said, I think both of those indicators (TTM vs RAF) are doing different things. As to the RAF and its use. I think it works great, but I also look at it every day. As with any indicator the trick is to understand what the signal is telling you in relation to the price action. I find the signals on the RAF to correlate with each other when viewed on multiple TF's.

Perhaps trying both indicators together would yield insight into where the price action may be headed.

Quick Edit

I have a basic understanding of the RAF, but my basic interpretation is that a Stochastic is calculated (3 of them technically in the original 3xStochastic indicator). The Stochastic is telling you whether there is a trend in price action over x period. As the Stochastic (K Line in this) case crosses certain levels, those are taken as indications of a trend (or not). This calculation is then put through the Fisher Transform equation to find extremes in distribution. I won't attempt to explain this but see link below for more information. The idea is that as price enters the calculation, extremes outside the mean can be caught and used to trade against. The link below has a nice write up on how this works. In my opinion, this is what is needed to understand the indicators. The more you understand what the indicator is telling you the better you can analyze and formulate trading plans around that information.

https://www.mql5.com/en/articles/303
 
Last edited:
To scan for a specific squeeze level it's easiest to treat it as a number instead of a bunch of booleans. Just update the last line with whatever level of squeeze you want to scan for. Someone can rework the watchlist column code this way as well.

Ruby:
def bb = reference BollingerBands.LowerBand;
def squeezeLevel =
  if bb > reference KeltnerChannels(factor = 1.0).Lower_Band then 3
  else if bb > reference KeltnerChannels(factor = 1.5).Lower_Band then 2
  else if bb > reference KeltnerChannels(factor = 2.0).Lower_Band then 1
  else 0
;
# 0 = gray / no squeeze, 1 = dark orange / low squeeze, 2 = yellow / normal squeeze, 3 = red / high squeeze
plot scan = squeezeLevel > 0;
 
Last edited by a moderator:
how does one use this study? Can someone using it successfully comment on what they look for, entry and exit signals etc?

It's not as simple as Entry and Exit signals, it's part of an overall system of your liking... The TTM_Squeeze is all about momentum... "The Squeeze" is a term for when price movement is in consolidation, meaning it is "choppy" or in a "range"... Knowing when price is in a "Squeeze" tells you it's better to not take a trade right then... Once price action exits or is exiting "The Squeeze" you watch for price to "fire" in a given direction...

You use other indicators to tell you that, like Moving Averages or other indicators... If Moving averages indicate an Uptrend, and the TTM_Squeeze Histogram is above the zero line (Green), that is an indication to go Long or buy Call Options... The default color of the Histogram in upward positive momentum in the first post is Green... The opposite would be Short or Put Options when the Histogram fires down, or Dark Orange, and the Moving Averages are moving downward... There are many ways to use other indicators along with TTM_Squeeze_Pro... Colors can vary but the concept remains the same...

Things to remember are the default dot colors... Gray means no squeeze... Dark Orange means entering or exiting a Pre-Squeeze... Yellow is mid-level original squeeze... Red is maximum squeeze or greatest level of consolidation...

So to look for a good fire Long would be Gray dots and Green Histogram... A weakening Long would be Gray dots and a Dark Green Histogram... A good fire Short would be Gray dots and Dark Orange histogram... A weakening Short would be Gray Dots and a Yellow Histogram...

That's just a quick overview... There is more to it than that but it gives a good starting point... I hope this helps...
 
Hello All,

@BenTen/Others ; Please move this question to appropriate thread if there is one.

Recently began looking at TTM Squeeze indicators, watch list, studies, there are so many threads to confuse a new person like me. Is there a post or process which allows us to predict how big will be the Squeeze uptrend (light blue colors) will be.

Thanks

I trade primarily with the squeeze all the time, there is no way to accurately predict, but on average it lasts 4-5 bars, keep in mind the higher the timeframe the longer it will fire, so if you daytrade or scalp options like I do, then you are only in maybe 5-15 minutes at best since I trade on the 2 min timeframe. The hardest thing about the squeeze is figuring out the direction, if you wait too long after it fires to confirm the direction you missed the move, so you need to get in right before it fires with a stop loss in case it goes the wrong direction. One tip I like to use is add the momentum indicator on the same window of the squeeze, stacked EMA, and MACD to figure out the direction.
 
Im trying to scan for when the extra squeeze is valid. I thought a simple line "plot extrsqueezein or extrsqueezeout is true" but it doesn't seem to work. I tried different variations but with luck. Hoping the community can help me out here. Thanks!




##Assembled by TheBewb using existing Mobius Squeeze Momentum coding and "squeeze" concept made popular by John Carter.

declare lower;

input price = close;
input length = 20;
input Num_Dev_Dn = -2.0;
input Num_Dev_up = 2.0;
input averageType = AverageType.SIMPLE;
input displace = 0;
def sDev = StDev(data = price[-displace], length = length);
def MidLineBB = MovingAverage(averageType, data = price[-displace], length = length);
def LowerBandBB = MidLineBB + Num_Dev_Dn * sDev;
def UpperBandBB = MidLineBB + Num_Dev_up * sDev;
input factorhigh = 1.0;
input factormid = 1.5;
input factorlow = 2.0;
input trueRangeAverageType = AverageType.SIMPLE;
def shifthigh = factorhigh * MovingAverage(trueRangeAverageType, TrueRange(high, close, low), length);
def shiftMid = factormid * MovingAverage(trueRangeAverageType, TrueRange(high, close, low), length);
def shiftlow = factorlow * MovingAverage(trueRangeAverageType, TrueRange(high, close, low), length);
def average = MovingAverage(averageType, price, length);

def Avg = average[-displace];


def UpperBandKCLow = average[-displace] + shiftlow[-displace];
def LowerBandKCLow = average[-displace] - shiftlow[-displace];

def UpperBandKCMid = average[-displace] + shiftMid[-displace];
def LowerBandKCMid = average[-displace] - shiftMid[-displace];

def UpperBandKCHigh = average[-displace] + shifthigh[-displace];
def LowerBandKCHigh = average[-displace] - shifthigh[-displace];

def K = (Highest(high, length) + Lowest(low, length)) /
2 + ExpAverage(close, length);
def momo = Inertia(price - K / 2, length);

def pos = momo >= 0;
def neg = momo < 0;
def up = momo >= momo[1];
def dn = momo < momo[1];


def presqueeze = LowerBandBB > LowerBandKCLow and UpperBandBB < UpperBandKCLow;
def presqueezein = LowerBandBB > LowerBandKCLow and UpperBandBB < UpperBandKCLow and lowerBandBB > lowerBandBB[1];
def presqueezeout = LowerBandBB > LowerBandKCLow and UpperBandBB < UpperBandKCLow and lowerbandbb < lowerbandbb[1];

def originalSqueeze = LowerBandBB > LowerBandKCMid and UpperBandBB < UpperBandKCMid;
def originalSqueezein = LowerBandBB > LowerBandKCMid and UpperBandBB < UpperBandKCMid and lowerbandBB > lowerbandbb[1];
def originalSqueezeout = LowerBandBB > LowerBandKCMid and UpperBandBB < UpperBandKCMid and lowerbandbb < lowerbandbb[1];


def ExtrSqueeze = LowerBandBB > LowerBandKCHigh and UpperBandBB < UpperBandKCHigh;
def ExtrSqueezein = LowerBandBB > LowerBandKCHigh and UpperBandBB < UpperBandKCHigh and lowerbandbb > lowerbandbb[1];
def ExtrSqueezeout = LowerBandBB > LowerBandKCHigh and UpperBandBB < UpperBandKCHigh and lowerbandbb < lowerbandbb[1];



def PosUp = pos and up;
def PosDn = pos and dn;
def NegDn = neg and dn;
def NegUp = neg and up;



plot extrsqueeze is true;
 
@Trader Raider i am sorry that you were disappointed with the TTM SQUEEZE Pro performance. Based on my continuous observation of the combination of BB/KC in relation with Price Action, there is lag that can be costly. What i did is i modified the parameters to help give a better signal on lower time frames
BB(2.0,8,exponential)
KC(1.0,8, exponential)
If BB is inside KC THEN THAT IS A SQZ I WOULD WATCH AND I WILL FOLLOW THE PRICE DIRECTION.
To confirm the accuracy of such set up, the squeeze on chart that is posted on this forum by mobius can go hand in hand with the setting above.
any questions, feel free to ask
What is the displace length and deviation for bb what is that for kc Both are for tos
 

Volatility Trading Range

VTR is a momentum indicator that shows if a stock is overbought or oversold based on its Weekly and Monthly average volatility trading range.

Download the indicator

Similar threads

Not the exact question you're looking for?

Start a new thread and receive assistance from our community.

87k+ Posts
184 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