Opening Range with Breakouts & Targets [LuxAlgo] for ThinkOrSwim

samer800

Moderator - Expert
VIP
Lifetime
TiCS8iC.png

Author Message:

Opening Range with Breakouts & Targets is based on the long-standing Opening Range Breakout strategy popularized by traders such as Toby Crabel and Mark Fisher.

This indicator measures and displays the price range created from the first period within a new trading session, along with price breakouts from that range and targets associated with the range width.

CODE:

CSS:
# Indicator for TOS
#// © LuxAlgo
#indicator("Opening Range with Breakouts & Targets [LuxAlgo]",shorttitle = "LuxAlgo - ORB & Targets"
#Hint OpeningRangePeriod: Sets the Length of Time used for determining Opening Range.
#Hint SignalBias: OR Fill Color is directional based on if the current Day/Session ORM is Above or Below the Previous ORM.\nExamples:\nNo Bias: Signals Occur Regardless of OR Color.\nDaily Bias: Signals do not fire until Target 1 when Breakout is in opposite direction of OR Color.\nDon't Show Signals : No signals will be displayed.
#Hint TargetPercentageOfRange: Uses this % of OR Width to use as the distance for targets.
#Hint TargetCrossSource: Uses this Source to tell the script when a target is hit in order to draw the next target.
# Converted by Sam4Cok@Samer800    - 09/2024

input ShowHistoricalData = yes;     # "Show Historical Data"
input OpeningRangeResetOptions = {Default "Session", "Daily", "Custom"};
input OpeningRangePeriod = AggregationPeriod.THIRTY_MIN; # "Time Period", group = "Opening Range",
input customStartTime = 0930;
input customEndTime = 0945;
input SignalBias = {default "No Bias", "Daily Bias", "Don't Show Signals"}; # "Signal Bias"
input ShowTargets = yes;     #  "Show Targets"
input TargetPercentageOfRange = 50.0; # "Target % of Range"
input TargetCrossSource = {default "Close", "Highs/Lows"}; # "Target Cross Source"
input showSessionMovAvg = no; # "Session Moving Average Enable"
input SessionMovAvgLength = 20; # "Session Moving Average Length"
input SessionMovAvgType = {"SMA",Default "EMA", "RMA", "WMA", "VWMA"}; # "Session Moving Average Type"

def na = Double.NaN;
def bar_index = BarNumber();
def current = GetAggregationPeriod();
def tf = Max(current, OpeningRangePeriod);
def orCustom = OpeningRangeResetOptions==OpeningRangeResetOptions."Custom";
def orSession = OpeningRangeResetOptions==OpeningRangeResetOptions."Session";
def day = GetYYYYMMDD();
def time = GetTime();
def today = GetDay() == GetLastDay();
def dayChange = GetYYYYMMDD()!=GetYYYYMMDD()[1];
def last = if isNaN(close) then yes else if ShowHistoricalData then no else if !today then yes else no;
def RTH = time >= RegularTradingStart(day) and time <= RegularTradingEND(day);
def ETH = if !RTH then yes else ETH[1];
def Session = if ETH then RTH!=RTH[1] else dayChange;
def tfClose = if !isNaN(close) then close(Period = tf) else tfClose[1];
def tfChange = tfClose!=tfClose[1];
def tPer = TargetPercentageOfRange * 0.01;
def crSesh = SecondsTillTime(customEndTime) > 0 and SecondsFromTime(customStartTime) >= 0;
def h_src;
def l_src;
Switch (TargetCrossSource) {
Case "Highs/Lows" :
    h_src = high;
    l_src = low;
Default :
    h_src = close;
    l_src = close;
}
#// Function to calculate WMA
Script f_wma {
input source = close;
input length = 20;
    def norm = fold i = 0 to length with p do
               p + (length - i) * length;
    def sum = fold j = 0 to length with q do
              q + GetValue(source, j) * (length - j) * length;
    def f_wma = sum / norm;
    plot out = f_wma;
}
Script day_ma {
input _start = no;
input _type = "EMA";
input l = 20;
    def fz = if _start then 0 else fz[1] + 1;
    def bs_nd = if fz==0 then 1 else fz;
    def v_len = if bs_nd < l then bs_nd else l;
    def k = 2 / (v_len + 1);
    def a = 1 / v_len;
    def sumS = fold i = 0 to v_len with p do
               p + GetValue(close, i);
    def sumVol = fold v = 0 to v_len with q do
                 q + GetValue(Volume, v);
    def sumSrcVol = fold v1 = 0 to v_len with q1 do
                 q1 + GetValue(Volume * close, v1);
    def nom = sumSrcVol / v_len;
    def den = sumVol / v_len;
    def ma = if _start then close else
    if _type == "EMA" then  (close * k ) + (ma[1]*(1-k)) else
    if _type == "RMA" then a * close + (1 - a) * ma[1] else
    if _type == "SMA" then sumS / v_len else
    if _type == "WMA" then f_wma(close, v_len) else
    if _type == "VWMA" then nom / den else Double.NaN;
    plot out = if _start then Double.NaN else ma;
}
Script get_1up {
    input _val = close;
    def floorVal = Floor(_val);
    def ceilVal = Ceil(_val);
    def intVal = if _val > 0 then floorVal else ceilVal;
    def intVal1 = if (floorVal + 1) > 0 then Floor(floorVal + 1) else Ceil(floorVal + 1);
    def up = if (_val - floorVal) > 0 then intVal1 else intVal;
    plot out = if isNaN(up) then 0 else up;
}

#//Calculations
def or_sesh;
Switch (OpeningRangeResetOptions) {
Case "Custom" :
    or_sesh = crSesh;
Case "Daily" :
    or_sesh = if dayChange then yes else if !dayChange and tfChange then no else or_sesh[1];
Default :
    or_sesh = if Session then yes else if !Session and tfChange then no else or_sesh[1];
}

def or_start = or_sesh and !or_sesh[1];
def or_end   = or_sesh[1] and !or_sesh;

def orh; def orl;def hh; def ll; def prev_orm;
def up_check; def up_check1; def down_check; def down_check1;
def orm = (orh[1] + orl[1]) / 2;
def orw = AbsValue(orh[1] - orl[1]);

if or_start {
    orh = high;
    orl = low;
    prev_orm = orm[1];
    hh = if (orCustom or ETH) then high else high(Period = tf);
    ll = if (orCustom or ETH) then low else low(Period = tf);
    up_check1 = yes;
    down_check1 = yes;
} else if or_sesh {
    orh = Max(orh[1], high);
    orl = Min(orl[1], low);
    prev_orm = prev_orm[1];
    hh = if (orCustom or ETH) then orh else high(Period = tf);
    ll = if (orCustom or ETH) then orl else low(Period = tf);
    up_check1 = up_check[1];
    down_check1 = down_check[1];
    } else {
    orh = orh[1];
    orl = orl[1];
    prev_orm = prev_orm[1];
    hh = na;
    ll = na;
    up_check1 = up_check[1];
    down_check1 = down_check[1];
    }

def day_dir; def hst1; def lst1;
def hst; def lst;
if or_end {
    day_dir = if orm > prev_orm then 1 else if orm < prev_orm then -1 else 0;
    hst1 = orh + (orw * tPer);
    lst1 = orl - (orw * tPer);
    } else {
    day_dir = day_dir[1];
    hst1 = hst[1];
    lst1 = lst[1];
}
def dirUp = day_dir>0;
def dirDn = day_dir<0;
def inOrbHi = if !last and or_sesh and hh then hh else na;
def inOrbLo = if !last and or_sesh and ll then ll else na;
def dayMa = if last then na else day_ma(or_start, SessionMovAvgType, SessionMovAvgLength);

#-- MOV
plot movAvg = if showSessionMovAvg then dayMa else na;
movAvg.SetDefaultColor(Color.WHITE);
#-- ORB
plot OrbHi = if !last and !or_sesh and orh then orh else na;
plot OrbLo = if !last and !or_sesh and orl then orl else na;
plot midOrb = (OrbHi + OrbLo) / 2;
midOrb.SetStyle(Curve.SHORT_DASH);
OrbHi.SetDefaultColor(Color.GRAY);
OrbLo.SetDefaultColor(Color.GRAY);
midOrb.SetDefaultColor(Color.GRAY);

AddCloud(inOrbHi, inOrbLo, Color.GRAY);
AddCloud(if dirUp then OrbHi else na, OrbLo, Color.DARK_GREEN);
AddCloud(if dirDn then OrbHi else na, OrbLo, Color.DARK_RED);

#//Target Calculations
if h_src > hst1 {
    hst = h_src;
    lst = lst1;
} else if l_src < lst1 {
    lst = l_src;
    hst = hst1;
    } else {
    hst = hst1;
    lst = lst1;
}
#def up_max   = get_1up((hst - orh)/(orw * tPer));
#def down_max = get_1up((orl - lst)/(orw * tPer));
def tgt1U = orh + orw * tPer * 1;
def tgt1D = orl - orw * tPer * 1;
def up_cur   = max(0, get_1up((h_src - orh)/(orw * tPer)));
def down_cur = max(0, get_1up((orl - l_src)/(orw * tPer)));
def crossUp1 = (close Crosses Above orh);
def crossUp2 = (close Crosses Above tgt1U);
def crossDn1 = (close Crosses Below orl);
def crossDn2 = (close Crosses Below tgt1D);

#/Signal Calcs
def biasUp; def biasDn;
Switch (SignalBias) {
Case "Don't Show Signals" :
    biasUp = no;
    biasDn = no;
Case "Daily Bias" :
    biasUp = (day_dir !=-1 and crossUp1) or (day_dir ==-1 and crossUp2);
    biasDn = (day_dir != 1 and crossDn1) or (day_dir == 1 and crossDn2);
Default :
    biasUp = crossUp1;
    biasDn = crossDn1;
}
def down_signal;
if  (close > orm and down_check1 == no) {
    down_signal = no;
    down_check = yes;
} else if biasDn and down_check1 {
    down_signal = yes;
    down_check = no;
    } else {
    down_signal = no;
    down_check = down_check1;
}
def up_signal;
if (close < orm and up_check1 == no) {
    up_signal = no;
    up_check = yes;
} else if biasUp and up_check1 {
    up_signal = yes;
    up_check = no;
    } else {
    up_signal = no;
    up_check = up_check1;
}

plot sigUp = if !last and up_signal then orl else na;
plot sigDn = if !last and down_signal then orh else na;
sigUp.SetPaintingStrategy(PaintingStrategy.ARROW_UP);
sigDn.SetPaintingStrategy(PaintingStrategy.ARROW_DOWN);
sigUp.SetDefaultColor(Color.GREEN);
sigDn.SetDefaultColor(Color.RED);

#-- Targets

def tgtPup = if !ShowTargets then na else orh + (orw * tPer * up_cur);
def tgtNup = if !ShowTargets then na else orh + (orw * tPer * (up_cur-2));
def tgtPdn = if !ShowTargets then na else orl - (orw * tPer * (down_cur-2));
def tgtNdn = if !ShowTargets then na else orl - (orw * tPer * down_cur);

def tgt2U = orh + orw * tPer * 2;
def tgt3U = orh + orw * tPer * 3;
def tgt4U = orh + orw * tPer * 4;
def tgt5U = orh + orw * tPer * 5;
def tgt6U = orh + orw * tPer * 6;
def tgt7U = orh + orw * tPer * 7;
def tgt8U = orh + orw * tPer * 8;
def tgt9U = orh + orw * tPer * 9;
def tgt10U = orh + orw * tPer * 10;
def tgt11U = orh + orw * tPer * 11;
def tgt12U = orh + orw * tPer * 12;
def tgt13U = orh + orw * tPer * 13;
def tgt14U = orh + orw * tPer * 14;
def tgt15U = orh + orw * tPer * 15;
def tgt2D = orl - orw * tPer * 2;
def tgt3D = orl - orw * tPer * 3;
def tgt4D = orl - orw * tPer * 4;
def tgt5D = orl - orw * tPer * 5;
def tgt6D = orl - orw * tPer * 6;
def tgt7D = orl - orw * tPer * 7;
def tgt8D = orl - orw * tPer * 8;
def tgt9D = orl - orw * tPer * 9;
def tgt10D = orl - orw * tPer * 10;
def tgt11D = orl - orw * tPer * 11;
def tgt12D = orl - orw * tPer * 12;
def tgt13D = orl - orw * tPer * 13;
def tgt14D = orl - orw * tPer * 14;
def tgt15D = orl - orw * tPer * 15;
def tgtU1 = if or_start then na else if or_end then tgt1U else
            if (tgtPup >= tgt1U) and (tgtNup <= tgt1U) then tgtU1[1] else tgtU1[1];
def tgtU2 = if or_start then na else if (tgtPup >= tgt2U) and (tgtNup <= tgt2U) then tgt2U else tgtU2[1];
def tgtU3 = if or_start then na else if (tgtPup >= tgt3U) and (tgtNup <= tgt3U) then tgt3U else tgtU3[1];
def tgtU4 = if or_start then na else if (tgtPup >= tgt4U) and (tgtNup <= tgt4U) then tgt4U else tgtU4[1];
def tgtU5 = if or_start then na else if (tgtPup >= tgt5U) and (tgtNup <= tgt5U) then tgt5U else tgtU5[1];
def tgtU6 = if or_start then na else if (tgtPup >= tgt6U) and (tgtNup <= tgt6U) then tgt6U else tgtU6[1];
def tgtU7 = if or_start then na else if (tgtPup >= tgt7U) and (tgtNup <= tgt7U) then tgt7U else tgtU7[1];
def tgtU8 = if or_start then na else if (tgtPup >= tgt8U) and (tgtNup <= tgt8U) then tgt8U else tgtU8[1];
def tgtU9 = if or_start then na else if (tgtPup >= tgt9U) and (tgtNup <= tgt9U) then tgt9U else tgtU9[1];
def tgtU10 = if or_start then na else if (tgtPup >= tgt10U) and (tgtNup <= tgt10U) then tgt10U else tgtU10[1];
def tgtU11 = if or_start then na else if (tgtPup >= tgt11U) and (tgtNup <= tgt11U) then tgt11U else tgtU11[1];
def tgtU12 = if or_start then na else if (tgtPup >= tgt12U) and (tgtNup <= tgt12U) then tgt12U else tgtU12[1];
def tgtU13 = if or_start then na else if (tgtPup >= tgt13U) and (tgtNup <= tgt13U) then tgt13U else tgtU13[1];
def tgtU14 = if or_start then na else if (tgtPup >= tgt14U) and (tgtNup <= tgt14U) then tgt14U else tgtU14[1];
def tgtU15 = if or_start then na else if (tgtPup >= tgt15U) and (tgtNup <= tgt15U) then tgt15U else tgtU15[1];

def tgtD1 = if or_start then na else if or_end then tgt1D else
            if (tgtPdn >= tgt1D) and (tgtNdn <= tgt1D) then tgt1D else tgtD1[1];
def tgtD2 = if or_start then na else if (tgtPdn >= tgt2D) and (tgtNdn <= tgt2D) then tgt2D else tgtD2[1];
def tgtD3 = if or_start then na else if (tgtPdn >= tgt3D) and (tgtNdn <= tgt3D) then tgt3D else tgtD3[1];
def tgtD4 = if or_start then na else if (tgtPdn >= tgt4D) and (tgtNdn <= tgt4D) then tgt4D else tgtD4[1];
def tgtD5 = if or_start then na else if (tgtPdn >= tgt5D) and (tgtNdn <= tgt5D) then tgt5D else tgtD5[1];
def tgtD6 = if or_start then na else if (tgtPdn >= tgt6D) and (tgtNdn <= tgt6D) then tgt6D else tgtD6[1];
def tgtD7 = if or_start then na else if (tgtPdn >= tgt7D) and (tgtNdn <= tgt7D) then tgt7D else tgtD7[1];
def tgtD8 = if or_start then na else if (tgtPdn >= tgt8D) and (tgtNdn <= tgt8D) then tgt8D else tgtD8[1];
def tgtD9 = if or_start then na else if (tgtPdn >= tgt9D) and (tgtNdn <= tgt9D) then tgt9D else tgtD9[1];
def tgtD10 = if or_start then na else if (tgtPdn >= tgt10D) and (tgtNdn <= tgt10D) then tgt10D else tgtD10[1];
def tgtD11 = if or_start then na else if (tgtPdn >= tgt11D) and (tgtNdn <= tgt11D) then tgt11D else tgtD11[1];
def tgtD12 = if or_start then na else if (tgtPdn >= tgt12D) and (tgtNdn <= tgt12D) then tgt12D else tgtD12[1];
def tgtD13 = if or_start then na else if (tgtPdn >= tgt13D) and (tgtNdn <= tgt13D) then tgt13D else tgtD13[1];
def tgtD14 = if or_start then na else if (tgtPdn >= tgt14D) and (tgtNdn <= tgt14D) then tgt14D else tgtD14[1];
def tgtD15 = if or_start then na else if (tgtPdn >= tgt15D) and (tgtNdn <= tgt15D) then tgt15D else tgtD15[1];

plot target1U = if !last and !or_sesh and tgtU1 then tgtU1 else na;
plot target2U = if !last and !or_sesh and tgtU2 then tgtU2 else na;
plot target3U = if !last and !or_sesh and tgtU3 then tgtU3 else na;
plot target4U = if !last and !or_sesh and tgtU4 then tgtU4 else na;
plot target5U = if !last and !or_sesh and tgtU5 then tgtU5 else na;
plot target6U = if !last and !or_sesh and tgtU6 then tgtU6 else na;
plot target7U = if !last and !or_sesh and tgtU7 then tgtU7 else na;
plot target8U = if !last and !or_sesh and tgtU8 then tgtU8 else na;
plot target9U = if !last and !or_sesh and tgtU9 then tgtU9 else na;
plot target10U = if !last and !or_sesh and tgtU10 then tgtU10 else na;
plot target11U = if !last and !or_sesh and tgtU11 then tgtU11 else na;
plot target12U = if !last and !or_sesh and tgtU12 then tgtU12 else na;
plot target13U = if !last and !or_sesh and tgtU13 then tgtU13 else na;
plot target14U = if !last and !or_sesh and tgtU14 then tgtU14 else na;
plot target15U = if !last and !or_sesh and tgtU15 then tgtU15 else na;

plot target1D = if !last and !or_sesh and tgtD1 then tgtD1 else na;
plot target2D = if !last and !or_sesh and tgtD2 then tgtD2 else na;
plot target3D = if !last and !or_sesh and tgtD3 then tgtD3 else na;
plot target4D = if !last and !or_sesh and tgtD4 then tgtD4 else na;
plot target5D = if !last and !or_sesh and tgtD5 then tgtD5 else na;
plot target6D = if !last and !or_sesh and tgtD6 then tgtD6 else na;
plot target7D = if !last and !or_sesh and tgtD7 then tgtD7 else na;
plot target8D = if !last and !or_sesh and tgtD8 then tgtD8 else na;
plot target9D = if !last and !or_sesh and tgtD9 then tgtD9 else na;
plot target10D = if !last and !or_sesh and tgtD10 then tgtD10 else na;
plot target11D = if !last and !or_sesh and tgtD11 then tgtD11 else na;
plot target12D = if !last and !or_sesh and tgtD12 then tgtD12 else na;
plot target13D = if !last and !or_sesh and tgtD13 then tgtD13 else na;
plot target14D = if !last and !or_sesh and tgtD14 then tgtD14 else na;
plot target15D = if !last and !or_sesh and tgtD15 then tgtD15 else na;

target1U.SetDefaultColor(Color.DARK_GREEN);
target2U.SetDefaultColor(Color.DARK_GREEN);
target3U.SetDefaultColor(Color.DARK_GREEN);
target4U.SetDefaultColor(Color.DARK_GREEN);
target5U.SetDefaultColor(Color.DARK_GREEN);
target6U.SetDefaultColor(Color.DARK_GREEN);
target7U.SetDefaultColor(Color.DARK_GREEN);
target8U.SetDefaultColor(Color.DARK_GREEN);
target9U.SetDefaultColor(Color.DARK_GREEN);
target10U.SetDefaultColor(Color.DARK_GREEN);
target11U.SetDefaultColor(Color.DARK_GREEN);
target12U.SetDefaultColor(Color.DARK_GREEN);
target13U.SetDefaultColor(Color.DARK_GREEN);
target14U.SetDefaultColor(Color.DARK_GREEN);
target15U.SetDefaultColor(Color.DARK_GREEN);

target1D.SetDefaultColor(Color.DARK_RED);
target2D.SetDefaultColor(Color.DARK_RED);
target3D.SetDefaultColor(Color.DARK_RED);
target4D.SetDefaultColor(Color.DARK_RED);
target5D.SetDefaultColor(Color.DARK_RED);
target6D.SetDefaultColor(Color.DARK_RED);
target7D.SetDefaultColor(Color.DARK_RED);
target8D.SetDefaultColor(Color.DARK_RED);
target9D.SetDefaultColor(Color.DARK_RED);
target10D.SetDefaultColor(Color.DARK_RED);
target11D.SetDefaultColor(Color.DARK_RED);
target12D.SetDefaultColor(Color.DARK_RED);
target13D.SetDefaultColor(Color.DARK_RED);
target14D.SetDefaultColor(Color.DARK_RED);
target15D.SetDefaultColor(Color.DARK_RED);

#-- END of CODE
 

Join useThinkScript to post your question to a community of 21,000+ developers and traders.

Similar threads

Not the exact question you're looking for?

Start a new thread and receive assistance from our community.

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