Weekly Range Compression Tracker

by @gerald_on_cable

G

Gerald Fitch-Morrow

@gerald_on_cable
Open sourceformulaMIT

Tracks consecutive weeks where price has stayed inside a progressively shrinking ATR band relative to the prior month's average range. Measures range compression depth and duration, colour-coding the band to signal tightening regimes without generating explicit trade signals — pure structural context.

0 likes💬 0 comments👁 1 views🔖 0 saves0 forks5 in use
Sign in to interact.

Try it live

Run the preview to see this indicator plotted on a real chart.

Inputs

ATR Periodint · default 14
Monthly Lookback (bars)int · default 20
Compression Ratio Thresholdfloat · default 0.85
Min Consecutive Bars in Squeezeint · default 3
Deep Squeeze Z-Score Thresholdfloat · default -1
Band Width Multiplierfloat · default 1.5

Outputs / plots

ATR Upper Band (series)ATR Lower Band (series)Compressed Upper Band (series)Compressed Lower Band (series)Compression Ratio (series)Monthly Avg ATR (series)Consecutive Compression Bars (series)Squeeze Strength (0–3) (series)Compression Ratio Z-Score (series)Squeeze Active (event)Deep Squeeze (event)Squeeze Threshold Reached (event)Squeeze Broken (event)

Latest changelog

Initial release.

Version history

v17/22/2026, 7:41:59 PM

Source code

formula
let atr_len = atr_period
let weekly_atr = atr(atr_len)
let monthly_avg_range = sma(weekly_atr, monthly_lookback)
let compression_ratio = weekly_atr / monthly_avg_range
let is_compressing = compression_ratio < compression_threshold
let compress_count = barssince(not(is_compressing))
let in_squeeze = compress_count >= min_weeks
let band_half = weekly_atr * band_mult
let upper_band = hl2 + band_half
let lower_band = hl2 - band_half
let tight_upper = hl2 + band_half * compression_ratio
let tight_lower = hl2 - band_half * compression_ratio
let squeeze_strength = clamp(compress_count / min_weeks, 0, 3)
let ratio_z = zscore(compression_ratio, monthly_lookback)
let deep_squeeze = and(in_squeeze, ratio_z < squeeze_z_thresh)
plot("compression_ratio", compression_ratio)
plot("monthly_avg", monthly_avg_range)
plot("upper_band", upper_band)
plot("lower_band", lower_band)
plot("tight_upper", tight_upper)
plot("tight_lower", tight_lower)
plot("compress_count", compress_count)
plot("squeeze_strength", squeeze_strength)
plot("ratio_zscore", ratio_z)
event("squeeze_active", in_squeeze)
event("deep_squeeze", deep_squeeze)
event("squeeze_start", and(in_squeeze, compress_count == min_weeks))
event("squeeze_end", and(not(is_compressing), shift(is_compressing, 1)))

Comments (0)

Sign in to leave a comment.

No comments yet.

Want to use this?

Sign in to preview it live on a chart, fork it into your own Indicators Lab, or use it in a strategy.