Closing order at current 4h closing

Created at 08 Sep 2021, 19:42
How’s your experience with the cTrader Platform?
Your feedback is crucial to cTrader's development. Please take a few seconds to share your opinion and help us improve your trading experience. Thanks!
V.

v.fiodorov83

Joined 24.07.2019

Closing order at current 4h closing
08 Sep 2021, 19:42


Hello everybody!

I open a trade in the current 4H candle. How can I write a code that will close my position exactly in the same 4H candle at its closing?


@v.fiodorov83
Replies

amusleh
09 Sep 2021, 11:42

Hi,

You can use timer and check if the position entry bar is closed or not, if a new bar is opened then you can close your position, here is an example:

using cAlgo.API;

namespace cAlgo.Robots
{
    [Robot(TimeZone = TimeZones.UTC, AccessRights = AccessRights.None)]
    public class Test : Robot
    {
        protected override void OnStart()
        {
            Timer.Start(1);
        }

        protected override void OnTimer()
        {
            Timer.Stop();

            var index = Bars.Count - 1;

            foreach (var position in Positions)
            {
                var positionEntryBarIndex = Bars.OpenTimes.GetIndexByTime(position.EntryTime);

                if (positionEntryBarIndex < index)
                {
                    ClosePosition(position);
                }
            }

            Timer.Start(1);
        }
    }
}

It iterates over all of your open positions every second.


@amusleh

v.fiodorov83
09 Sep 2021, 13:38

RE:

amusleh said:

Hi,

You can use timer and check if the position entry bar is closed or not, if a new bar is opened then you can close your position, here is an example:

using cAlgo.API;

namespace cAlgo.Robots
{
    [Robot(TimeZone = TimeZones.UTC, AccessRights = AccessRights.None)]
    public class Test : Robot
    {
        protected override void OnStart()
        {
            Timer.Start(1);
        }

        protected override void OnTimer()
        {
            Timer.Stop();

            var index = Bars.Count - 1;

            foreach (var position in Positions)
            {
                var positionEntryBarIndex = Bars.OpenTimes.GetIndexByTime(position.EntryTime);

                if (positionEntryBarIndex < index)
                {
                    ClosePosition(position);
                }
            }

            Timer.Start(1);
        }
    }
}

It iterates over all of your open positions every second.

Great thanks!

Almost everything works, but Can I add a conditions?

1. I have the logic of closing positions at a specific price also inside the current H4 candlestick, in the OnTick () method. And now they are ignored and only closed by timer

2. How to make the position close exactly at the end of the candle at 03:59:59, and not at the beginning of the next one. The problem is that the next one can open with a gap.


@v.fiodorov83

... Deleted by UFO ...

amusleh
13 Sep 2021, 11:07

Hi,

You have to give the amount of time of that time frame and then you can check the amount of time passed since the bar opened:

using cAlgo.API;
using System;
using System.Globalization;

namespace cAlgo.Robots
{
    [Robot(TimeZone = TimeZones.UTC, AccessRights = AccessRights.None)]
    public class Test : Robot
    {
        private TimeSpan _barsTimeDiff;

        [Parameter("Bars Time Diff", DefaultValue = "04:00:00")]
        public string BarsTimeDiff { get; set; }

        protected override void OnStart()
        {
            if (!TimeSpan.TryParse(BarsTimeDiff, CultureInfo.InvariantCulture, out _barsTimeDiff))
            {
                Print("Invalid Bars Time Diff");
            }
            else
            {
                // Subtract 1 minute from your provided time amount
                _barsTimeDiff -= TimeSpan.FromMinutes(-1);

                Timer.Start(1);
            }
        }

        protected override void OnTimer()
        {
            Timer.Stop();

            foreach (var position in Positions)
            {
                var positionEntryBarIndex = Bars.OpenTimes.GetIndexByTime(position.EntryTime);

                // You can add more close conditions on this if statment if you want to by using && and ||
                if (Server.Time >= Bars.OpenTimes[positionEntryBarIndex].Add(_barsTimeDiff))
                {
                    ClosePosition(position);
                }
            }

            Timer.Start(1);
        }
    }
}

@amusleh

v.fiodorov83
13 Sep 2021, 13:15

RE:

amusleh said:

Hi,

You have to give the amount of time of that time frame and then you can check the amount of time passed since the bar opened:

using cAlgo.API;
using System;
using System.Globalization;

namespace cAlgo.Robots
{
    [Robot(TimeZone = TimeZones.UTC, AccessRights = AccessRights.None)]
    public class Test : Robot
    {
        private TimeSpan _barsTimeDiff;

        [Parameter("Bars Time Diff", DefaultValue = "04:00:00")]
        public string BarsTimeDiff { get; set; }

        protected override void OnStart()
        {
            if (!TimeSpan.TryParse(BarsTimeDiff, CultureInfo.InvariantCulture, out _barsTimeDiff))
            {
                Print("Invalid Bars Time Diff");
            }
            else
            {
                // Subtract 1 minute from your provided time amount
                _barsTimeDiff -= TimeSpan.FromMinutes(-1);

                Timer.Start(1);
            }
        }

        protected override void OnTimer()
        {
            Timer.Stop();

            foreach (var position in Positions)
            {
                var positionEntryBarIndex = Bars.OpenTimes.GetIndexByTime(position.EntryTime);

                // You can add more close conditions on this if statment if you want to by using && and ||
                if (Server.Time >= Bars.OpenTimes[positionEntryBarIndex].Add(_barsTimeDiff))
                {
                    ClosePosition(position);
                }
            }

            Timer.Start(1);
        }
    }
}

Ohh, cool!) Thank you. It woks!

Can I use a hardcoded parameter like (GetCurrentTimeFrime) instead of the user input 04:00:00? So that this timer is taken based on the currently selected timeframe on the chart.

[Parameter("Bars Time Diff", DefaultValue = "04:00:00")]
        public string BarsTimeDiff { get; set; }

@v.fiodorov83

amusleh
17 Sep 2021, 07:57

Hi,

There is no API function for getting time interval of a time frame, because time frames are all not time based, we have Renko, Range, and Tick time frames.

You can use an extension method for TimeFrame:

        /// <summary>
        /// Returns the approximate amount of time each time frame represent
        /// This method only works for time based time frames
        /// </summary>
        /// <param name="timeFrame"></param>
        /// <returns>TimeSpan</returns>
        public static TimeSpan GetSpan(this TimeFrame timeFrame)
        {
            if (timeFrame == TimeFrame.Minute)
            {
                return TimeSpan.FromMinutes(1);
            }
            else if (timeFrame == TimeFrame.Minute2)
            {
                return TimeSpan.FromMinutes(2);
            }
            else if (timeFrame == TimeFrame.Minute3)
            {
                return TimeSpan.FromMinutes(3);
            }
            else if (timeFrame == TimeFrame.Minute4)
            {
                return TimeSpan.FromMinutes(4);
            }
            else if (timeFrame == TimeFrame.Minute5)
            {
                return TimeSpan.FromMinutes(5);
            }
            else if (timeFrame == TimeFrame.Minute6)
            {
                return TimeSpan.FromMinutes(6);
            }
            else if (timeFrame == TimeFrame.Minute7)
            {
                return TimeSpan.FromMinutes(7);
            }
            else if (timeFrame == TimeFrame.Minute8)
            {
                return TimeSpan.FromMinutes(8);
            }
            else if (timeFrame == TimeFrame.Minute9)
            {
                return TimeSpan.FromMinutes(9);
            }
            else if (timeFrame == TimeFrame.Minute10)
            {
                return TimeSpan.FromMinutes(10);
            }
            else if (timeFrame == TimeFrame.Minute15)
            {
                return TimeSpan.FromMinutes(15);
            }
            else if (timeFrame == TimeFrame.Minute20)
            {
                return TimeSpan.FromMinutes(20);
            }
            else if (timeFrame == TimeFrame.Minute30)
            {
                return TimeSpan.FromMinutes(30);
            }
            else if (timeFrame == TimeFrame.Minute45)
            {
                return TimeSpan.FromMinutes(45);
            }
            else if (timeFrame == TimeFrame.Hour)
            {
                return TimeSpan.FromHours(1);
            }
            else if (timeFrame == TimeFrame.Hour2)
            {
                return TimeSpan.FromHours(2);
            }
            else if (timeFrame == TimeFrame.Hour3)
            {
                return TimeSpan.FromHours(3);
            }
            else if (timeFrame == TimeFrame.Hour4)
            {
                return TimeSpan.FromHours(4);
            }
            else if (timeFrame == TimeFrame.Hour6)
            {
                return TimeSpan.FromHours(6);
            }
            else if (timeFrame == TimeFrame.Hour8)
            {
                return TimeSpan.FromHours(8);
            }
            else if (timeFrame == TimeFrame.Hour12)
            {
                return TimeSpan.FromHours(12);
            }
            else if (timeFrame == TimeFrame.Daily)
            {
                return TimeSpan.FromDays(1);
            }
            else if (timeFrame == TimeFrame.Day2)
            {
                return TimeSpan.FromDays(2);
            }
            else if (timeFrame == TimeFrame.Day3)
            {
                return TimeSpan.FromDays(3);
            }
            else if (timeFrame == TimeFrame.Weekly)
            {
                return TimeSpan.FromDays(7);
            }
            else if (timeFrame == TimeFrame.Monthly)
            {
                return TimeSpan.FromDays(30);
            }
            else
            {
                throw new NotSupportedException("The provided time frame type isn't supported");
            }
        }

 


@amusleh