Master this unique system of horizontal price levels in TradingView's Pinescript, based on W.D. Gann's theories, used to identify potential support, resistance, and crucial turning points in the market.
Murrey Math Lines are a system of geometric price lines derived from the principles of W.D. Gann's squares. Developed by T. H. Murrey, this indicator simplifies Gann's complex theories into a practical set of equally spaced horizontal lines that divide price action into eight "octaves" or zones. These lines are intended to represent major and minor support and resistance levels where price is likely to find equilibrium, reverse, or accelerate.
The core idea behind Murrey Math is that price tends to move in predictable ranges and will often react strongly at specific, harmonically related levels. Each of the nine lines (from 0/8 to 8/8) has a specific interpretation regarding price behavior:
The calculation of Murrey Math Lines begins by identifying a significant trading range, often called the "Major Square." This range's highest high and lowest low within a defined period (e.g., 64, 128, or 256 bars) forms the basis. The range is then divided into eight equal parts.
//@version=5
indicator("My Murrey Math Lines", overlay=true, max_bars_back=500) // overlay=true to plot on price chart.
// --- User Inputs ---
// Period for identifying the major square (highest high and lowest low)
lookbackPeriod = input.int(256, title="Lookback Period (Bars for Major Square)", minval=64, maxval=500)
lineTransparency = input.int(0, title="Line Transparency (0-100)", minval=0, maxval=100)
showLabels = input.bool(true, title="Show Level Labels")
// --- Calculate Murrey Math Levels ---
// 1. Find Highest High and Lowest Low over the lookback period
highestHigh = ta.highest(high, lookbackPeriod)
lowestLow = ta.lowest(low, lookbackPeriod)
// We only recalculate the base prices if a new significant high or low occurs.
// This makes the lines stable for periods and then shift.
var float mmHighest = na
var float mmLowest = na
var float mmRange = na
// Recalculate MM base levels when a new highest high or lowest low is found within the lookback
// Use `ta.highestbars` and `ta.lowestbars` to find if the current high/low is the period's extreme
if (high[0] == highestHigh and bar_index == bar_index[ta.highestbars(high, lookbackPeriod)]) or
(low[0] == lowestLow and bar_index == bar_index[ta.lowestbars(low, lookbackPeriod)])
// 2. Adjust Price Range to Nearest Power of 2 (for proper scaling)
priceRange = highestHigh - lowestLow
// Handle cases where priceRange might be zero or too small
if priceRange == 0
priceRange := 0.000000001 // Small non-zero value to prevent issues
// Calculate the power of 2 that covers the price range
pow2 = math.ceil(math.log(priceRange) / math.log(2))
scaledRange = math.pow(2, pow2)
// Adjust the lowest price so that the range fits perfectly within the scaledRange
adjustedLowest = lowestLow - (scaledRange - priceRange) / 2
// Store these values to use for plotting all subsequent bars until a new extreme
mmHighest := adjustedLowest + scaledRange
mmLowest := adjustedLowest
mmRange := scaledRange
// Use `nz()` to carry forward the last calculated levels
mmHighest := nz(mmHighest[1], mmHighest)
mmLowest := nz(mmLowest[1], mmLowest)
mmRange := nz(mmRange[1], mmRange)
// 3. Calculate the Octave Step
octaveStep = mmRange / 8.0
// 4. Calculate Each Murrey Math Line
mm_8_8 = mmHighest
mm_7_8 = mmHighest - octaveStep
mm_6_8 = mmHighest - (2 * octaveStep)
mm_5_8 = mmHighest - (3 * octaveStep)
mm_4_8 = mmHighest - (4 * octaveStep) // Median Line
mm_3_8 = mmLowest + (3 * octaveStep)
mm_2_8 = mmLowest + (2 * octaveStep)
mm_1_8 = mmLowest + octaveStep
mm_0_8 = mmLowest
// --- Plotting Murrey Math Levels ---
// Define colors and styles for each line for easier interpretation
color_8_0 = color.new(color.red, lineTransparency)
color_7_1 = color.new(color.orange, lineTransparency)
color_6_2 = color.new(color.maroon, lineTransparency) // Stronger resistance/support
color_5_3 = color.new(color.gray, lineTransparency)
color_4_4 = color.new(color.purple, lineTransparency) // Median line, strongest
color_line = color.new(color.blue, lineTransparency)
plot(mm_0_8, title="0/8", color=color_8_0, linewidth=1, style=plot.style_stepline)
plot(mm_1_8, title="1/8", color=color_7_1, linewidth=1, style=plot.style_stepline)
plot(mm_2_8, title="2/8", color=color_6_2, linewidth=2, style=plot.style_stepline) // Stronger
plot(mm_3_8, title="3/8", color=color_5_3, linewidth=1, style=plot.style_stepline)
plot(mm_4_8, title="4/8", color=color_4_4, linewidth=3, style=plot.style_stepline) // Strongest
plot(mm_5_8, title="5/8", color=color_5_3, linewidth=1, style=plot.style_stepline)
plot(mm_6_8, title="6/8", color=color_6_2, linewidth=2, style=plot.style_stepline) // Stronger
plot(mm_7_8, title="7/8", color=color_7_1, linewidth=1, style=plot.style_stepline)
plot(mm_8_8, title="8/8", color=color_8_0, linewidth=1, style=plot.style_stepline)
// --- Optional: Add Labels to Lines ---
if showLabels and bar_index == last_bar_index
// Only draw labels on the current (last) bar for clarity
label.new(x=bar_index, y=mm_0_8, text="0/8 - Extreme Oversold", style=label.style_label_left, color=color_8_0, textcolor=color.white, size=size.small)
label.new(x=bar_index, y=mm_1_8, text="1/8 - Weak Support", style=label.style_label_left, color=color_7_1, textcolor=color.white, size=size.small)
label.new(x=bar_index, y=mm_2_8, text="2/8 - Strong Support", style=label.style_label_left, color=color_6_2, textcolor=color.white, size=size.small)
label.new(x=bar_index, y=mm_3_8, text="3/8 - Minor Support", style=label.style_label_left, color=color_5_3, textcolor=color.white, size=size.small)
label.new(x=bar_index, y=mm_4_8, text="4/8 - Median Line (Major S/R)", style=label.style_label_left, color=color_4_4, textcolor=color.white, size=size.small)
label.new(x=bar_index, y=mm_5_8, text="5/8 - Minor Resistance", style=label.style_label_left, color=color_5_3, textcolor=color.white, size=size.small)
label.new(x=bar_index, y=mm_6_8, text="6/8 - Strong Resistance", style=label.style_label_left, color=color_6_2, textcolor=color.white, size=size.small)
label.new(x=bar_index, y=mm_7_8, text="7/8 - Weak Resistance", style=label.style_label_left, color=color_7_1, textcolor=color.white, size=size.small)
label.new(x=bar_index, y=mm_8_8, text="8/8 - Extreme Overbought", style=label.style_label_left, color=color_8_0, textcolor=color.white, size=size.small)
// --- Simple Strategy Example (Conceptual) ---
// This strategy demonstrates how you might react to Murrey Math levels.
// It is highly simplified and for educational purposes only.
// Real trading strategies require more complex confirmation.
strategy("Murrey Math Strategy", overlay=true)
// Use the calculated Murrey Math levels for strategy logic
// Re-calculate the levels to ensure they are available to the strategy
// (This is redundant if the above indicator part is run first, but good practice for standalone strategy)
var float strat_mmHighest = na
var float strat_mmLowest = na
var float strat_mmRange = na
highestHigh_strat = ta.highest(high, lookbackPeriod)
lowestLow_strat = ta.lowest(low, lookbackPeriod)
if (high[0] == highestHigh_strat and bar_index == bar_index[ta.highestbars(high, lookbackPeriod)]) or
(low[0] == lowestLow_strat and bar_index == bar_index[ta.lowestbars(low, lookbackPeriod)])
priceRange_strat = highestHigh_strat - lowestLow_strat
if priceRange_strat == 0
priceRange_strat := 0.000000001
pow2_strat = math.ceil(math.log(priceRange_strat) / math.log(2))
scaledRange_strat = math.pow(2, pow2_strat)
adjustedLowest_strat = lowestLow_strat - (scaledRange_strat - priceRange_strat) / 2
strat_mmHighest := adjustedLowest_strat + scaledRange_strat
strat_mmLowest := adjustedLowest_strat
strat_mmRange := scaledRange_strat
strat_mmHighest := nz(strat_mmHighest[1], strat_mmHighest)
strat_mmLowest := nz(strat_mmLowest[1], strat_mmLowest)
strat_mmRange := nz(strat_mmRange[1], strat_mmRange)
strat_octaveStep = strat_mmRange / 8.0
strat_mm_0_8 = strat_mmLowest
strat_mm_1_8 = strat_mmLowest + strat_octaveStep
strat_mm_2_8 = strat_mmLowest + (2 * strat_octaveStep)
strat_mm_3_8 = strat_mmLowest + (3 * strat_octaveStep)
strat_mm_4_8 = strat_mmLowest + (4 * strat_octaveStep)
strat_mm_5_8 = strat_mmLowest + (5 * strat_octaveStep)
strat_mm_6_8 = strat_mmLowest + (6 * strat_octaveStep)
strat_mm_7_8 = strat_mmLowest + (7 * strat_octaveStep)
strat_mm_8_8 = strat_mmHighest
// Strategy Logic: Reversals at 0/8, 8/8, and 4/8 lines (Median Line)
// Buy at 0/8 or 1/8 (extreme oversold/weak support)
longCondition = ta.crossover(close, strat_mm_0_8) or ta.crossover(close, strat_mm_1_8)
// Sell at 8/8 or 7/8 (extreme overbought/weak resistance)
shortCondition = ta.crossunder(close, strat_mm_8_8) or ta.crossunder(close, strat_mm_7_8)
// Additional reversal at 4/8 (Median Line) - can be entry or exit
// If price crosses 4/8 from below, it's bullish. If from above, it's bearish.
long4_8 = ta.crossover(close, strat_mm_4_8)
short4_8 = ta.crossunder(close, strat_mm_4_8)
if (longCondition)
strategy.entry("Long MM", strategy.long)
if (shortCondition)
strategy.entry("Short MM", strategy.short)
// Exit logic: Using 4/8 line as profit target or reversal point
// Or using fixed stop loss and profit target based on levels
profitTargetLong = strat_mm_4_8 // Target 4/8 for long
stopLossLong = strat_mm_0_8 - (strat_octaveStep / 2) // Below 0/8, giving some buffer
profitTargetShort = strat_mm_4_8 // Target 4/8 for short
stopLossShort = strat_mm_8_8 + (strat_octaveStep / 2) // Above 8/8, giving some buffer
strategy.exit("Long MM Exit", from_entry="Long MM", profit=profitTargetLong, stop=stopLossLong)
strategy.exit("Short MM Exit", from_entry="Short MM", profit=profitTargetShort, stop=stopLossShort)
To get the most from Murrey Math Lines in Pinescript:
Murrey Math Lines divide price into harmonically related octaves, based on Gann's theory that markets move in predictable, geometric patterns. This offers a unique perspective on price behavior.
Murrey Math Lines offer a fascinating and structured approach to technical analysis in Pinescript for TradingView. Derived from W.D. Gann's theories, these equally spaced horizontal lines provide a unique framework for identifying potential support, resistance, and crucial turning points within various "octaves" of price action. While their calculation requires a clear definition of the "Major Square" and their interpretation benefits from an understanding of each line's significance, mastering Murrey Math can significantly enhance your Pinescript strategies. By combining these powerful levels with price action confirmation, volume analysis, and other technical tools, you can leverage Murrey Math Lines to improve your decision-making, anticipate market reactions, and gain a deeper understanding of market harmony and equilibrium.
Get a high-performance Pinescript analysis tool for actionable market insights, designed for traders on the move.
This strategy runs in live mode on TradingView, helping you identify potential opportunities.
Get Pinescript Strategy