How can I code 2 different take profits with different conditions ?

Created at 09 Feb 2025, 09:06
KA

karimemad94

Joined 07.12.2024

How can I code 2 different take profits with different conditions ?
09 Feb 2025, 09:06


I have made a cBot based on an oscillator with a lot volume of 0.1 and i want it to take 2 different take profits with the following conditions:
1- a fixed take profit of 100 pips with a lot volume of 0.08
2- a take profit based on the oscillator's value. I need it to take profit of 0.02 lot (remainder of the initial 0.1 lot volume) whenever the oscillator crosses down the zero line (if it was an open buy position) and whenever it crosses above the zero line (if it was an open sell position)

This idea is similar to the Advanced take profit option, I just don't know how to code it

This is the code I am using:

using System;
using cAlgo.API;
using cAlgo.API.Collections;
using cAlgo.API.Indicators;
using cAlgo.API.Internals;

namespace cAlgo.Robots
{
    [Robot(AccessRights = AccessRights.None)]
    public class Momentumhighopenlow : Robot
    {
        [Parameter(DefaultValue = 0.1)]
        public double Volume { get; set; }

        [Parameter(DefaultValue = 9)]
        public int Periods { get; set; }
        
        [Parameter(DefaultValue = 100)]
        public double TakeProfit { get; set; }

        private MovingAverage Hullopen;
        private MovingAverage HullHigh;
        private MovingAverage HullLow;

        protected override void OnStart()
        {
            // Initialize Hull Moving Averages for Open, High, and Low prices
            Hullopen = Indicators.MovingAverage(Bars.OpenPrices, Periods, MovingAverageType.Hull);
            HullHigh = Indicators.MovingAverage(Bars.HighPrices, Periods, MovingAverageType.Hull);
            HullLow = Indicators.MovingAverage(Bars.LowPrices, Periods, MovingAverageType.Hull);
        }

        protected override void OnTick()
        {
            // Calculate Momentum value
double hullolastvalue = Hullopen.Result.LastValue;
double hullhlastvalue = HullHigh.Result.LastValue;
double hullllastvalue = HullLow.Result.LastValue;
double hullopreviousbar = Hullopen.Result.Last(1);
double hullhpreviousbar = HullHigh.Result.Last(1);
double hulllpreviousbar = HullLow.Result.Last(1);
double momo = hullolastvalue - hullopreviousbar;
double momh = hullhlastvalue - hullhpreviousbar;
double moml = hulllpreviousbar - hullllastvalue;
double mom = momh-(momo+moml);
double hullopreviousbar2 = Hullopen.Result.Last(2);
double hullhpreviousbar2 = HullHigh.Result.Last(2);
double hulllpreviousbar2 = HullLow.Result.Last(2);
double momo2 = hullopreviousbar - hullopreviousbar2;
double momh2 = hullhpreviousbar - hullhpreviousbar2;
double moml2 = hulllpreviousbar2 - hullllastvalue;
double previousmom = momh2-(momo2+moml2);

            // Trading logic
            if (mom > 0 && previousmom <= 0)
            {
                Open(TradeType.Buy);
                Close(TradeType.Sell);
            }
            else if (mom < 0 && previousmom >= 0)
            {
                Close(TradeType.Buy);
                Open(TradeType.Sell);
            }
        }

        private void Open(TradeType tradeType)
        {
            // Open a trade only if there are no open positions
            if(Positions.Count == 0)
            ExecuteMarketOrder(tradeType, SymbolName, Volume);
        }

        private void Close(TradeType tradeType)
        {
            // Close all positions of the specified trade type
            Print($"Attempting to close {tradeType} positions...");
            foreach (var position in Positions)
            {
                if (position.TradeType == tradeType && position.SymbolName == SymbolName)
                {
                    Print($"Closing position {position.Id} ({position.TradeType})");
                    position.Close();
                }
            }
        }

        protected override void OnStop()
        {
            // Handle cBot stop event
        }
    }
}

@karimemad94
Replies

claudiorubbiani
09 Feb 2025, 13:21

Assuming that a volume of 0.02 is above the min volume for the symbol that you are trading → you can check this with Symbol.VolumeInUnitsMin

You can only manage a double take profit programmatically.

You have to do something like this:

        protected override void OnTick()
       {
           double myTakeProfit1 = 100;
           foreach (Position position in Positions)
           {
               if (position.Pips >= myTakeProfit1)
               {
                   if (position.VolumeInUnits > 0.02)
                       position.ModifyVolume(0.02);
               }
           }
 

With position.ModifyVolume you close the first part of the position that reached your TP,

and then check for the second take profit condition at a later stage.

Having the volume coded into your logic is not elegant even if it's working,

you you want to something better then you need to create a list of positions that you manage.

 

I hope this helps.

Claudio

 

 

 


@claudiorubbiani