Announcement

Collapse
No announcement yet.

Partner 728x90

Collapse

Range Bars do not display according to standard

Collapse
X
 
  • Filter
  • Time
  • Show
Clear All
new posts

    Range Bars do not display according to standard

    Hello everyone,

    I am setting up my NT8 platform to use with Range Bars and noticed the bars do not display correctly:
    - the open of a bar does not open at the same price as the previous closed candle;
    - some bars open somewhere inside the body of the previous candle;
    - some bars have a gap up or down from the previous close candle.

    At first I thought something must be wrong with my parameters. After having checked everything, I could, I searched the NT sites and forums. And also the article from the support. ninjatrader show the same strange looking bars (image below):



    And also, for your perusal, I stumbled upon the same issue raised on the forum in the year 2014. Apparently, the issue is still the same ?


    Actually, the rules for constructing range bars are quite simple:

    Three rules of range bars:
    • Each range bar must have a high/low range that equals the specified range.
    • Each range bar must open outside the high/low range of the previous bar.
    • Each range bar must close at either its high or its low.
    And the same definition is used by TradeStation:

    Range Bars look like standard bars, but are different in several ways:
    • Range Bars are all equal in height, based on the Range specified by the user.
    • Range Bar closes are always at the top or bottom of the bar.
    • Range Bars charts have no gaps.
    • The open of each Range Bar is always equal to the close of the previous Range Bar.
    I am aware that there can be a gap whenever the tick data transmitted by the data provider (Rithmic in my case) has some ticks missing, but this would not cause the type of issue I described above, where the display of the range bars are systematically different from what one would expect.
    Please let me know if there is anything to be changed in the setup of my platform or if this is the method use by NT for constructingg range bars (in this case they should not be called "Range Bars", but some other definition).
    Thank you for your assistance.

    #2
    Hello bobby34,


    Thank you for posting on the NinjaTrader forums.


    I think the idea here is the expectation of NinjaTrader range bars to look the same as other range bars since you've quote a couple of different places.


    It's important to understand how these range bars are built in the first place, using tick data. A Range bar is based on a specified tick price range. The bar will continue to develop until the price range is broken, at which point a new bar will be created.



    You can also see more information on NinjaTrader's range bars here.



    Thank you!
    Luis H.NinjaTrader Customer Service

    Comment


      #3
      Hello Luis,
      Thanks for your fast reply.
      But the link you provided is the same I included in my message and does not explain at all how a range bar is constructed. It simply states: Range Bars

      A Range bar is based on a specified tick price range. The bar will continue to develop until the price range is broken, at which point a new bar will be created.

      Well, this does not clarify anything at all.
      Is it possible to obtain from NT a clear and logical explanation of the method used to construct Range Bars ?

      You wrote:
      " I think the idea here is the expectation of NinjaTrader range bars to look the same as other range bars since you've quote a couple of different places."

      I disagree, a Range Bar is a Range Bar, period. I have quoted two well-known places ( I could give you some other dozens if you like), but the definition of a range bar is the same all over the world.
      So, what is the problem here ?
      Best regards,

      Comment


        #4
        [QUOTE=bobby34;n1333895] Hello everyone,


        Range Bars look like standard bars, but are different in several ways:
        • Range Bars are all equal in height, based on the Range specified by the user.
        • Range Bar closes are always at the top or bottom of the bar.
        • Range Bars charts have no gaps.
        [LIST][*]The open of each Range Bar is always equal to the close of the previous Range Bar.
        Perhaps you want renko bars?

        Comment


          #5
          Hello bobby34,


          Hope you had a great weekend - the thought process essentially comes down to a 1-tick gap.


          Range bars in NinjaTrader are designed to have high and low wicks that exactly match the range you set. However, because of how markets execute trades, the closing price of one bar and the opening price of the next bar can be different by 1 tick.


          This happens because of:
          1. Bid/Ask Spread – If the last price of the current bar closes at the bid, the next bar may open at the ask (or vice versa), causing a 1-tick gap.
          2. Fast Market Movement – If price moves quickly between trades, the next trade may occur slightly above or below the previous bar’s close.
          3. No Trade at Exact Close Price – The market might skip over the exact close price of the previous bar, meaning the next bar starts at the nearest available price, which can be 1 tick away.

          As MiCe1999, you might be interested in Renko bars instead.



          Thanks!
          Luis H.NinjaTrader Customer Service

          Comment


            #6
            Hello Luis,
            Thank you for the reply.
            I understand your comments about: bid/ask spread, fast market mouvements, gaps, etc.
            BUT: these issues are valid for all non-time related types of bars: range bars, renko bars, etc.
            On the other hand, how come that NT has managed to display e.g. Renko bars with no gaps ?

            And other platforms also display Range bars without the issues I mentioned.
            Regarding using Renko bars instead: well, Renko bars do not use the same logic, as you certainly know.
            Namely, Renko bars display a new candle only when the new candle has moved a range in the same direction or in the opposite direction.
            Range bars display a new candle when the new candle has reached the range, whatever the direction. T
            his helps in keeping track the volatility.

            The disdvantage of Renko bars is that the displayed candles are obscuring some details, so one has e.g. to wait that a candle has developed entirely in the opposite direction of the previous candle to realize that the trend has changed. So, e.g. if you use a 8-tick range, the next candle might close 16 ticks in the opposite direction ! Not so for range bars: with the same 8-tick range, the next candle will always be displayed after a range of 8 ticks has developed, regardless of the direction.
            The following image shows the same period (this night) as above, this time with the NT range bars. It is obvious that the issues I mentioned are recurring:
            - ranges of the bars are correct, they display the correct range of the parameters, but:
            - some candles open in the middle of the prevous candle,
            - some candles open at the same level as the previous candle,
            - some candles open with a gap up/down,

            There is no continuity in the display, just candles jumping around,,,,

            Well, let's drop the issue, as I see that NT is not willing, at the moment, to correct this issue.
            In my opinion, you should inform the development team of this request.
            Thanks and best regards,

            Comment


              #7
              "Well, let's drop the issue, as I see that NT is not willing, at the moment, to correct this issue.
              In my opinion, you should inform the development team of this request.​"


              There is no issue to correct. If you want Renko bars with wicks, they are available from third parties. If you want Range bars with no gap, look around again. If you want a no gap Range bar, should a 4 Range (no gap) bar open at the previous bar close price even though price isn't there, but is one tick away? Would you like five ticks from high to low if it is a 4 tick range bar with no gaps? See, the most accurate display of Range bars is the way NT has done them.

              "The following image shows the same period (this night) as above, this time with the NT range bars. It is obvious that the issues I mentioned are recurring:
              - ranges of the bars are correct, they display the correct range of the parameters, but:
              - some candles open in the middle of the prevous candle,
              - some candles open at the same level as the previous candle,
              - some candles open with a gap up/down,​"


              The image does not show any inconsistencies. Every open is 1 tick from the previous close. Look closer.
              eDanny
              NinjaTrader Ecosystem Vendor - Integrity Traders

              Comment


                #8
                MiCe1999 : thank you for your AI code for range bars. Impressive what AI can do nowadays.

                I have compiled the code, corrected a couple of minor glitches, and could get the candles displayed (image attached).
                Each new candle has its open identical to the close price of the previous candle. This is correct.

                But the bodies of the candles all have the same body range, namely the range specified in the parameters.
                Well, a new candle should be formed when the high/low range reaches the specified range. This allows to display candles with varied body lengths, each candle having the same high/low range, therefore the bodies will have different lengths.

                Here is a simple definition:
                "A range bar with the same price span (i.e. range) measured from high to low and each bar closes either at the high or the low, regardless of where it has opened."

                Could I ask you to see if your friend ChatGPT could amend the code ?

                Thanks again for your kind help.
                Best,


                Click image for larger version

Name:	MiCe1999 Range Bars.png
Views:	68
Size:	32.7 KB
ID:	1334363

                Comment


                  #9
                  Yeah I noticed that it's not exactly TS style, but I actually like it as it forms visible levels at certain range values 'naturally'.

                  I have not tested this, here's OnDataPoint method with strict candle height:

                  PHP Code:
                  protected override void OnDataPoint(
                  Bars bars,
                  double open,
                  double high,
                  double low,
                  double close,
                  DateTime time,
                  long volume,
                  bool isBar,
                  double bid,
                  double ask)
                  {
                  // Set up session logic
                  if (SessionIterator == null)
                  SessionIterator = new SessionIterator(bars);
                  
                  bool isNewSession = SessionIterator.IsNewSession(time, isBar);
                  if (isNewSession)
                  SessionIterator.GetNextSession(time, isBar);
                  
                  double tickSize = bars.Instrument.MasterInstrument.TickSize;
                  double rangeValue = bars.BarsPeriod.Value * tickSize;
                  
                  // If we have no bars yet OR we reset on new trading day => start a brand new bar at this price
                  if (bars.Count == 0 || (bars.IsResetOnNewTradingDay && isNewSession))
                  {
                  AddBar(bars, close, close, close, close, time, volume);
                  bars.LastPrice = close;
                  return;
                  }
                  
                  // Retrieve the last (most recent) bar’s info
                  int lastBarIndex = bars.Count - 1;
                  double barOpen = bars.GetOpen(lastBarIndex);
                  double barHigh = bars.GetHigh(lastBarIndex);
                  double barLow = bars.GetLow(lastBarIndex);
                  double barClose = bars.GetClose(lastBarIndex);
                  
                  //---------------------------------------------------------------------------------------------
                  // 1) Check if price is STILL WITHIN the current bar’s permissible range
                  // i.e. barOpen ± range has NOT been exceeded, so we simply update the current bar
                  //---------------------------------------------------------------------------------------------
                  if (close <= barOpen + rangeValue && close >= barOpen - rangeValue)
                  {
                  // Price has not exceeded the ±range, so just update the existing bar’s high, low, and close
                  double updatedHigh = Math.Max(barHigh, close);
                  double updatedLow = Math.Min(barLow, close);
                  UpdateBar(bars, updatedHigh, updatedLow, close, time, volume);
                  }
                  
                  //---------------------------------------------------------------------------------------------
                  // 2) Price EXCEEDED the bar’s upper boundary (barOpen + rangeValue) or lower boundary (barOpen - rangeValue)
                  // => We finalize the current bar exactly at barOpen ± range, then add more bars if needed.
                  //---------------------------------------------------------------------------------------------
                  else
                  {
                  double priceToProcess = close; // The *entire* new price we must account for
                  double sign = (close >= barOpen ? +1 : -1); // +1 if we broke the top, -1 if we broke the bottom
                  double finalBoundary = barOpen + sign * rangeValue; // Where we finalize the *existing* bar
                  
                  // Finalize the CURRENT bar exactly at the boundary
                  // Example: if we broke above barOpen + rangeValue => close that bar at barOpen + rangeValue
                  double finalizedClose = finalBoundary;
                  double updatedHigh = Math.Max(barHigh, finalizedClose);
                  double updatedLow = Math.Min(barLow, finalizedClose);
                  
                  // Update the existing bar with a close at the boundary
                  UpdateBar(bars, updatedHigh, updatedLow, finalizedClose, time, volume);
                  
                  // "priceToProcess" is still the full close. We may have leftover if price jumped more than 1 range.
                  // Next bar’s open is the old bar’s close.
                  double nextBarOpen = finalizedClose;
                  long remainingVolume = volume;
                  
                  // While price is STILL more than 1 range away from the "nextBarOpen",
                  // keep creating "phantom" bars to fill the gap with no bar "gaps."
                  while (
                  (sign > 0 && priceToProcess >= nextBarOpen + rangeValue) // If we still exceed nextBarOpen + range
                  ||
                  (sign < 0 && priceToProcess <= nextBarOpen - rangeValue) // Or we still exceed nextBarOpen - range
                  )
                  {
                  double nextBarClose = nextBarOpen + sign * rangeValue; // finalize it exactly 1 range from the open
                  double hi = Math.Max(nextBarOpen, nextBarClose);
                  double lo = Math.Min(nextBarOpen, nextBarClose);
                  
                  // Add a full bar that’s exactly "range" in height
                  AddBar(bars, nextBarOpen, hi, lo, nextBarClose, time, 0);
                  
                  // Next bar’s open is the newly‐finalized bar’s close
                  nextBarOpen = nextBarClose;
                  }
                  
                  // Finally, if "priceToProcess" is NOT exactly one more full range bar away,
                  // we need a partial bar. For example, if price jumped 1.5 ranges above the open,
                  // we created 1 bar to fill the first range, and we have a partial leftover .5 range
                  // that starts a new bar’s open but has not yet reached ±range from that open.
                  if ((sign > 0 && priceToProcess > nextBarOpen) || (sign < 0 && priceToProcess < nextBarOpen))
                  {
                  // Start a new bar. For now, this bar is "in progress" until we see if future ticks
                  // exceed nextBarOpen ± range. We track the leftover volume in it.
                  double hi = Math.Max(nextBarOpen, priceToProcess);
                  double lo = Math.Min(nextBarOpen, priceToProcess);
                  
                  AddBar(bars, nextBarOpen, hi, lo, priceToProcess, time, remainingVolume);
                  }
                  }
                  
                  // Keep track of the last price
                  bars.LastPrice = close;
                  } 
                  

                  Comment


                    #10
                    @MiCe1999

                    Good job !
                    From the commented lines inside the code, the described logic and steps are quite correct.
                    I have changed the initial file by inserting your new OnDataPoint method.
                    There are a few errors, .zip file attached
                    As I am not a coder, it would be nice if you would take a look at it ? We are close to have a correct Range Bars type.
                    Thanks again,
                    Best
                    Attached Files

                    Comment

                    Latest Posts

                    Collapse

                    Topics Statistics Last Post
                    Started by celtey, 03-21-2025, 09:46 AM
                    1 response
                    45 views
                    0 likes
                    Last Post celtey
                    by celtey
                     
                    Started by clarocque1, Today, 08:17 AM
                    0 responses
                    5 views
                    0 likes
                    Last Post clarocque1  
                    Started by MatthewLesko, Today, 07:38 AM
                    1 response
                    10 views
                    0 likes
                    Last Post rayko
                    by rayko
                     
                    Started by renosdim01, Today, 07:45 AM
                    0 responses
                    7 views
                    0 likes
                    Last Post renosdim01  
                    Started by several, 03-18-2025, 03:53 AM
                    13 responses
                    200 views
                    1 like
                    Last Post timko
                    by timko
                     
                    Working...
                    X