Announcement

Collapse
No announcement yet.

Partner 728x90

Collapse

Strategy with ATM and cancelling non-filled order at bar close

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

    Strategy with ATM and cancelling non-filled order at bar close

    I would like the entry limit order to be cancelled once the bar closes if the order is not yet filled.
    When the order is not cancelled, it is possible to have a long limit order and a short limit order at the same time, thus making for some funky ATM orders.

    How do I cancel the ATM order at the close of the bar to prevent multiple limit orders going out at the same time? I have looked at all of the ATM sample strategies and I can not seem to get this to work correctly in real time.

    Thanks

    Code is below:




    #region Using declarations
    using System;
    using System.ComponentModel;
    using System.Diagnostics;
    using System.Drawing;
    using System.Drawing.Drawing2D;
    using System.Xml.Serialization;
    using NinjaTrader.Cbi;
    using NinjaTrader.Data;
    using NinjaTrader.Indicator;
    using NinjaTrader.Strategy;
    #endregion


    // This namespace holds all strategies and is required. Do not change it.
    namespace NinjaTrader.Strategy
    {
    /// <summary>
    ///
    /// </summary>
    [Description("")]
    public class ATMTEST1: Strategy
    {
    #region Variables
    private string atmStrategyId = string.Empty;
    private string orderId = string.Empty;
    private string atmStrategyName = "atmtest";
    private int slipTicks = 1; // Default setting for SlipTicks





    #endregion

    /// <summary>
    /// This method is used to configure the strategy and is called once before any strategy method is called.
    /// </summary>



    protected override void Initialize()
    {

    MaximumBarsLookBack = MaximumBarsLookBack.Infinite;
    CalculateOnBarClose = true;
    BarsRequired = 10;




    }

    /// <summary>
    /// Called on each bar update event (incoming tick)
    /// </summary>
    protected override void OnBarUpdate()
    {

    if (Historical)
    return;



    // Condition set LONG
    if (//orderId.Length == 0 && atmStrategyId.Length == 0

    GetAtmStrategyMarketPosition(atmStrategyId) == MarketPosition.Flat

    && Low[0] < Low[1]


    )

    {
    atmStrategyId = GetAtmStrategyUniqueId();
    orderId = GetAtmStrategyUniqueId();
    AtmStrategyCreate(Cbi.OrderAction.Buy, OrderType.Limit, (Close[0] + SlipTicks * TickSize), 0, TimeInForce.Day, orderId, AtmStrategyName, atmStrategyId);
    DrawText("Long1"+CurrentBar, "LL " + (Close[0] + SlipTicks * TickSize).ToString(), 0, Low[0] - 8*TickSize, Color.Cyan);
    DrawArrowUp(CurrentBar.ToString(),0,Low[0] - 1*TickSize, Color.Cyan);


    }

    // Condition set SELL
    if (//orderId.Length == 0 && atmStrategyId.Length == 0

    GetAtmStrategyMarketPosition(atmStrategyId) == MarketPosition.Flat

    && High[0] > High[1]


    )

    {
    atmStrategyId = GetAtmStrategyUniqueId();
    orderId = GetAtmStrategyUniqueId();
    AtmStrategyCreate(Cbi.OrderAction.Sell, OrderType.Limit, (Close[0] - SlipTicks * TickSize), 0, TimeInForce.Day, orderId, AtmStrategyName, atmStrategyId);
    DrawText("Short1"+CurrentBar,"SL " + (Close[0] - SlipTicks * TickSize).ToString(), 0, High[0] + 8*TickSize, Color.Cyan);
    DrawArrowDown(CurrentBar.ToString(),0,High[0] + 1*TickSize, Color.Cyan);


    }

    // Check for a pending entry order
    if (orderId.Length > 0)
    {
    string[] status = GetAtmStrategyEntryOrderStatus(orderId);

    // If the status call can't find the order specified, the return array length will be zero otherwise it will hold elements
    if (status.GetLength(0) > 0)
    {
    // If the order state is terminal, reset the order id value
    if (status[2] == "Filled" || status[2] == "Cancelled" || status[2] == "Rejected")
    orderId = string.Empty;
    }
    }

    else if (atmStrategyId.Length > 0 && GetAtmStrategyMarketPosition(atmStrategyId) == Cbi.MarketPosition.Flat)
    atmStrategyId = string.Empty;


    }



    #region Properties

    [Description("Slippage Ticks for Entry")]
    [GridCategory("Parameters")]
    public int SlipTicks
    {
    get { return slipTicks; }
    set { slipTicks = Math.Max(1, value); }
    }





    [Description("Name for the ATM Strategy")]
    [GridCategory("Parameters")]

    public string AtmStrategyName
    {
    get { return atmStrategyName; }
    set { atmStrategyName = value; }
    }


    #endregion
    }
    }

    #2
    Baseheadz, I don't see any calls to cancel the ATM entry order in your script? If you run this on CalculateOnBarClose = true you could simply cancel it on the next bar update seen. Or you save the barnumber of order placement for reference and then cancel when desired comparing to the currently proccessed bar.

    Comment


      #3
      Are there any examples of how to use the bar number of order with an ATM strategy?

      Comment


        #4
        Baseheadz, I would not be aware of one unfortunately, you can access the current bar count with CurrentBar. and then compare to the saved value for example on your order entry so you have a reference.

        Comment


          #5
          Code to Cancel Strategy Submitted ATM orders

          This is an old post but I found it when I was trying to sort out this problem. I am adding some code which will cancel an atm order if it hasn't been filled after X bars, (the X being a variable you can set).

          Here's the relevant code that can be used to execute the test and pull the ATM limit order entry
          if not filled within "bars_past_OE" bars.

          Before implementing this code I had to watch the strategies while they executed (which is still a very good idea) and cancel or move a limit order if price moved away from it without filling. Without this code the limit entry that is entered stays live for the entire trading session, or until it is filled, which by itself isn't necessarily a bad thing, but since I test to see if there is a live order already out there before entering another trade, the strategy is prevented from executing any more trades. This code fixes that problem. The simpler solution is to just enter with a market order, but I don't like the slippage you get when the market is moving a little faster. This method is much more predictable, but it does trade less often than using a market order, (which again is a good thing I think).
          DaveN

          Code Below

          Code:
          # region Variables
          private int bars_past_OE = 1;  //bars to count before pulling an unfilled limit entry order
          private DataSeries barcount; // holds the count after order entry to enable a bar count comparison
          
          // ATM order management variables
          private string  atmStrategyId  =  string.Empty;
          private string  order Id = string.Empty;  
          #endregion
          
          #region Long Entry
          
          // put your long entry conditions here
          if (long entry conditions)
             {
             atmStrategyId = GetAtmStrategyUniqeId();
             orderId = GetAtmStrategy();
             AtmStrategyCreate(OrderAction.Buy, OrderType.Limit, limitpricehere, 0, TimeInForce.Day, orderId, "AtmStrategyName", atmStrategyId);
             barcount.Set(CurrentBars[0]);
             }
          #endregion
          
          #region Order Filll Status and Adjustment
             if (orderId.Length > 0)
                {
                string[] status = GetAtmStrategyEntryOrderStatus(orderId);
                   if (status[2] == "Working" && (CurrentBars[0] + BarsPast_OE)  > barcount[0])
                   {
                   AtmStrategyCancelEntryOrder(orderId);
                   }
                 }
          #endregion

          Comment

          Latest Posts

          Collapse

          Topics Statistics Last Post
          Started by Geovanny Suaza, 02-11-2026, 06:32 PM
          0 responses
          672 views
          0 likes
          Last Post Geovanny Suaza  
          Started by Geovanny Suaza, 02-11-2026, 05:51 PM
          0 responses
          379 views
          1 like
          Last Post Geovanny Suaza  
          Started by Mindset, 02-09-2026, 11:44 AM
          0 responses
          111 views
          0 likes
          Last Post Mindset
          by Mindset
           
          Started by Geovanny Suaza, 02-02-2026, 12:30 PM
          0 responses
          575 views
          1 like
          Last Post Geovanny Suaza  
          Started by RFrosty, 01-28-2026, 06:49 PM
          0 responses
          582 views
          1 like
          Last Post RFrosty
          by RFrosty
           
          Working...
          X