Built a custom ThinkScript study that combines a standard Opening Range Breakout (5m / 15m / 30m) with automatic directional Fibonacci level
Script below for you to use too!
The script:
* plots the ORB high/low as a defined range box
* automatically builds fib retracement + extension levels from the ORB
* determines bullish/bearish bias based on where the opening range closes
* keeps the original ORB bias locked for the day (doesn’t repaint)
* shows left-side fib % labels
* includes breakout arrows + alerts
Still testing it, but the structure interaction has been surprisingly clean so far. Best tip I got so far is that If one time frame looks sloppy and isn’t respecting levels, try a different one out.
Script provided below that you can copy/paste into ThinkScript and run your own.
\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_
\# ORB + Directional Fibonacci Levels
\# Native-style ORB box + left % labels + right price labels
input OR\_Length = {default FiveMin, FifteenMin, ThirtyMin};
input showOnlyRTH = yes;
input showSignals = yes;
input showORBCloud = yes;
input showFibLevels = yes;
input showLeftPercentLabels = yes;
input showRightPriceLabels = yes;
input showExtensions = yes;
input show236 = yes;
input show382 = yes;
input show500 = yes;
input show618 = yes;
input show786 = yes;
def RTHopen = 0930;
def RTHclose = 1600;
def ORend =
if OR\_Length == OR\_Length.FiveMin then 0935
else if OR\_Length == OR\_Length.FifteenMin then 0945
else 1000;
def isRTH = SecondsFromTime(RTHopen) >= 0 and SecondsTillTime(RTHclose) > 0;
def inOR = SecondsFromTime(RTHopen) >= 0 and SecondsTillTime(ORend) > 0;
def afterOR = SecondsFromTime(ORend) >= 0 and SecondsTillTime(RTHclose) > 0;
def newDay = GetDay() <> GetDay()\[1\];
def ORHigh = CompoundValue(1,
if newDay then Double.NaN
else if inOR and IsNaN(ORHigh\[1\]) then high
else if inOR then Max(ORHigh\[1\], high)
else ORHigh\[1\],
Double.NaN);
def ORLow = CompoundValue(1,
if newDay then Double.NaN
else if inOR and IsNaN(ORLow\[1\]) then low
else if inOR then Min(ORLow\[1\], low)
else ORLow\[1\],
Double.NaN);
def ORClose = CompoundValue(1,
if newDay then Double.NaN
else if inOR then close
else ORClose\[1\],
Double.NaN);
def ORMid = (ORHigh + ORLow) / 2;
def ORRange = ORHigh - ORLow;
def bullishORB = ORClose >= ORMid;
def bearishORB = ORClose < ORMid;
def plotOk = if showOnlyRTH then isRTH else yes;
def orbOk = plotOk and afterOR and !IsNaN(ORHigh) and ORRange > 0;
def fibOk = orbOk and showFibLevels;
\# --- Directional fib logic ---
def F0 =
if bullishORB then ORLow else ORHigh;
def F236 =
if bullishORB then ORLow + ORRange \* 0.236
else ORHigh - ORRange \* 0.236;
def F382 =
if bullishORB then ORLow + ORRange \* 0.382
else ORHigh - ORRange \* 0.382;
def F500 =
if bullishORB then ORLow + ORRange \* 0.500
else ORHigh - ORRange \* 0.500;
def F618 =
if bullishORB then ORLow + ORRange \* 0.618
else ORHigh - ORRange \* 0.618;
def F786 =
if bullishORB then ORLow + ORRange \* 0.786
else ORHigh - ORRange \* 0.786;
def F100 =
if bullishORB then ORHigh else ORLow;
def F1618 =
if bullishORB then ORHigh + ORRange \* 0.618
else ORLow - ORRange \* 0.618;
def F2618 =
if bullishORB then ORHigh + ORRange \* 1.618
else ORLow - ORRange \* 1.618;
\# --- ORB range structure ---
plot pORHigh = if orbOk then ORHigh else Double.NaN;
plot pORLow = if orbOk then ORLow else Double.NaN;
pORHigh.SetDefaultColor(Color.CYAN);
pORLow.SetDefaultColor(Color.CYAN);
pORHigh.SetLineWeight(4);
pORLow.SetLineWeight(4);
pORHigh.HideBubble();
pORLow.HideBubble();
plot ORCloudHigh = if showORBCloud and orbOk then ORHigh else Double.NaN;
plot ORCloudLow = if showORBCloud and orbOk then ORLow else Double.NaN;
ORCloudHigh.Hide();
ORCloudLow.Hide();
AddCloud(ORCloudHigh, ORCloudLow, Color.DARK\_GRAY, Color.DARK\_GRAY);
\# --- Fib plots ---
plot p0 = if fibOk then F0 else Double.NaN;
plot p236 = if fibOk and show236 then F236 else Double.NaN;
plot p382 = if fibOk and show382 then F382 else Double.NaN;
plot p500 = if fibOk and show500 then F500 else Double.NaN;
plot p618 = if fibOk and show618 then F618 else Double.NaN;
plot p786 = if fibOk and show786 then F786 else Double.NaN;
plot p100 = if fibOk then F100 else Double.NaN;
plot p1618 = if fibOk and showExtensions then F1618 else Double.NaN;
plot p2618 = if fibOk and showExtensions then F2618 else Double.NaN;
p0.SetDefaultColor(Color.CYAN);
p236.SetDefaultColor(Color.CYAN);
p382.SetDefaultColor(Color.CYAN);
p500.SetDefaultColor(Color.CYAN);
p618.SetDefaultColor(Color.CYAN);
p786.SetDefaultColor(Color.CYAN);
p100.SetDefaultColor(Color.CYAN);
p1618.SetDefaultColor(Color.CYAN);
p2618.SetDefaultColor(Color.CYAN);
p0.SetLineWeight(2);
p100.SetLineWeight(2);
p236.SetStyle(Curve.SHORT\_DASH);
p382.SetStyle(Curve.SHORT\_DASH);
p500.SetStyle(Curve.SHORT\_DASH);
p618.SetStyle(Curve.SHORT\_DASH);
p786.SetStyle(Curve.SHORT\_DASH);
p1618.SetStyle(Curve.LONG\_DASH);
p2618.SetStyle(Curve.LONG\_DASH);
p0.HideBubble();
p236.HideBubble();
p382.HideBubble();
p500.HideBubble();
p618.HideBubble();
p786.HideBubble();
p100.HideBubble();
p1618.HideBubble();
p2618.HideBubble();
\# --- Label positioning ---
def firstFibBar = afterOR and !afterOR\[1\];
def lastBar = BarNumber() == HighestAll(BarNumber());
\# Left-side percent labels
AddChartBubble(showLeftPercentLabels and fibOk and firstFibBar, F0, "0.0%", Color.CYAN, yes);
AddChartBubble(showLeftPercentLabels and fibOk and show236 and firstFibBar, F236, "23.6%", Color.CYAN, yes);
AddChartBubble(showLeftPercentLabels and fibOk and show382 and firstFibBar, F382, "38.2%", Color.CYAN, yes);
AddChartBubble(showLeftPercentLabels and fibOk and show500 and firstFibBar, F500, "50.0%", Color.CYAN, yes);
AddChartBubble(showLeftPercentLabels and fibOk and show618 and firstFibBar, F618, "61.8%", Color.CYAN, yes);
AddChartBubble(showLeftPercentLabels and fibOk and show786 and firstFibBar, F786, "78.6%", Color.CYAN, yes);
AddChartBubble(showLeftPercentLabels and fibOk and firstFibBar, F100, "100.0%", Color.CYAN, yes);
AddChartBubble(showLeftPercentLabels and fibOk and showExtensions and firstFibBar, F1618, "161.8%", Color.CYAN, yes);
AddChartBubble(showLeftPercentLabels and fibOk and showExtensions and firstFibBar, F2618, "261.8%", Color.CYAN, yes);
\# Right-side price labels
AddChartBubble(showRightPriceLabels and fibOk and lastBar, F0, "$" + AsText(Round(F0, 2)), Color.CYAN, no);
AddChartBubble(showRightPriceLabels and fibOk and show236 and lastBar, F236, "$" + AsText(Round(F236, 2)), Color.CYAN, no);
AddChartBubble(showRightPriceLabels and fibOk and show382 and lastBar, F382, "$" + AsText(Round(F382, 2)), Color.CYAN, no);
AddChartBubble(showRightPriceLabels and fibOk and show500 and lastBar, F500, "$" + AsText(Round(F500, 2)), Color.CYAN, no);
AddChartBubble(showRightPriceLabels and fibOk and show618 and lastBar, F618, "$" + AsText(Round(F618, 2)), Color.CYAN, no);
AddChartBubble(showRightPriceLabels and fibOk and show786 and lastBar, F786, "$" + AsText(Round(F786, 2)), Color.CYAN, no);
AddChartBubble(showRightPriceLabels and fibOk and lastBar, F100, "$" + AsText(Round(F100, 2)), Color.CYAN, no);
AddChartBubble(showRightPriceLabels and fibOk and showExtensions and lastBar, F1618, "$" + AsText(Round(F1618, 2)), Color.CYAN, no);
AddChartBubble(showRightPriceLabels and fibOk and showExtensions and lastBar, F2618, "$" + AsText(Round(F2618, 2)), Color.CYAN, no);
\# --- Bias / failure state ---
def bullishFailed = bullishORB and afterOR and close < ORLow;
def bearishFailed = bearishORB and afterOR and close > ORHigh;
AddLabel(afterOR,
if bullishFailed then "ORB FIB BIAS: BULLISH FAILED"
else if bearishFailed then "ORB FIB BIAS: BEARISH FAILED"
else if bullishORB then "ORB FIB BIAS: BULLISH"
else "ORB FIB BIAS: BEARISH",
if bullishFailed or bearishFailed then Color.YELLOW
else if bullishORB then [Color.GREEN](http://Color.GREEN)
else [Color.RED](http://Color.RED)
);
AddLabel(afterOR,
"ORB Range: $" + AsText(Round(ORLow, 2)) + " - $" + AsText(Round(ORHigh, 2)),
Color.CYAN
);
\# --- Breakout signals ---
def breakUp = showSignals and afterOR and close crosses above ORHigh;
def breakDn = showSignals and afterOR and close crosses below ORLow;
plot UpSignal = if breakUp then low else Double.NaN;
plot DnSignal = if breakDn then high else Double.NaN;
UpSignal.SetPaintingStrategy(PaintingStrategy.ARROW\_UP);
DnSignal.SetPaintingStrategy(PaintingStrategy.ARROW\_DOWN);
UpSignal.SetDefaultColor(Color.GREEN);
DnSignal.SetDefaultColor(Color.RED);
Alert(breakUp, "Opening Range Breakout UP", [Alert.BAR](http://Alert.BAR), Sound.Ring);
Alert(breakDn, "Opening Range Breakout DOWN", [Alert.BAR](http://Alert.BAR), Sound.Ring);