Topics

Forum Topics not found

Replies

amusleh
16 May 2022, 09:13

Hi,

Please post a job request or contact one of our consultant partners.


@amusleh

amusleh
16 May 2022, 09:12

RE:

bogdan.titomir said:

seems i know how to doing it, in method onStart just  run server if port hasn't listen

You can use TCP or Named pipe in case of communication in between internal processes.


@amusleh

amusleh
13 May 2022, 11:38

Hi,

I didn't understand exactly what you are looking for, but you can develop a cBot/indicator that will run upon cTrader desktop launch.

There is an option on cTrader automate that will auto restart your cBot when cTrader launched.


@amusleh

amusleh
13 May 2022, 11:18

RE: RE: still unable to connect to my live accounts

mcm187 said:

amusleh said:

Hi,

We are aware of this issue, it will be fixed as soon as possible.

Hi Amusleh do you have an estimated time for when this will be resolved? 

Three days have passed and I am still unable to connect to my live accounts?
it is very frustrating when I am managing several accounts and my investment portfolios doing nothing every day that I am unable to connect to them is  a major problem and costly

Hi,

We are still trying to resolve this issue on our Europe proxies, for the time being please try other proxies and flushing your system DNS cache.


@amusleh

amusleh
13 May 2022, 10:32

Hi,

Try this:

using System;
using cAlgo.API;
using cAlgo.API.Indicators;

namespace cAlgo.Indicators

{
    [Indicator(IsOverlay = true, AccessRights = AccessRights.None)]
    public class IchimokuKinkoHyo : Indicator
    {
        private int _lastAlertBar;

        [Parameter(DefaultValue = 9)]
        public int periodFast { get; set; }

        [Parameter(DefaultValue = 26)]
        public int periodMedium { get; set; }

        [Parameter(DefaultValue = 52)]
        public int periodSlow { get; set; }

        [Parameter(DefaultValue = 26)]
        public int DisplacementChikou { get; set; }

        [Parameter(DefaultValue = 26)]
        public int DisplacementCloud { get; set; }

        [Parameter("Enable", DefaultValue = true, Group = "Alert")]
        public bool IsAlertEnabled { get; set; }

        [Parameter("Sound File Path", Group = "Alert")]
        public string SoundFilePath { get; set; }

        [Parameter("From Email", Group = "Alert")]
        public string FromEmail { get; set; }

        [Parameter("To Email", Group = "Alert")]
        public string ToEmail { get; set; }

        [Output("TenkanSen", Color = Colors.Red)]
        public IndicatorDataSeries TenkanSen { get; set; }

        [Output("Kijunsen", Color = Colors.Blue)]
        public IndicatorDataSeries KijunSen { get; set; }

        [Output("ChikouSpan", Color = Colors.DarkViolet)]
        public IndicatorDataSeries ChikouSpan { get; set; }

        [Output("SenkouSpanB", Color = Colors.Red, LineStyle = LineStyle.Lines)]
        public IndicatorDataSeries SenkouSpanB { get; set; }

        [Output("SenkouSpanA", Color = Colors.Green, LineStyle = LineStyle.Lines)]
        public IndicatorDataSeries SenkouSpanA { get; set; }

        private double maxfast, minfast, maxmedium, minmedium, maxslow, minslow;

        public override void Calculate(int index)

        {
            if ((index < periodFast) || (index < periodSlow)) { return; }

            maxfast = MarketSeries.High[index];

            minfast = MarketSeries.Low[index];

            maxmedium = MarketSeries.High[index];

            minmedium = MarketSeries.Low[index];

            maxslow = MarketSeries.High[index];

            minslow = MarketSeries.Low[index];

            for (int i = 0; i < periodFast; i++)

            {
                if (maxfast < MarketSeries.High[index - i]) { maxfast = MarketSeries.High[index - i]; }

                if (minfast > MarketSeries.Low[index - i]) { minfast = MarketSeries.Low[index - i]; }
            }

            for (int i = 0; i < periodMedium; i++)

            {
                if (maxmedium < MarketSeries.High[index - i]) { maxmedium = MarketSeries.High[index - i]; }

                if (minmedium > MarketSeries.Low[index - i]) { minmedium = MarketSeries.Low[index - i]; }
            }

            for (int i = 0; i < periodSlow; i++)

            {
                if (maxslow < MarketSeries.High[index - i]) { maxslow = MarketSeries.High[index - i]; }

                if (minslow > MarketSeries.Low[index - i]) { minslow = MarketSeries.Low[index - i]; }
            }

            TenkanSen[index] = (maxfast + minfast) / 2;

            KijunSen[index] = (maxmedium + minmedium) / 2;

            ChikouSpan[index - DisplacementChikou] = MarketSeries.Close[index];

            SenkouSpanA[index + DisplacementCloud] = (TenkanSen[index] + KijunSen[index]) / 2;

            SenkouSpanB[index + DisplacementCloud] = (maxslow + minslow) / 2;

            if (IsLastBar && IsAlertEnabled && _lastAlertBar != index)
            {
                _lastAlertBar = index;

                if (TenkanSen.HasCrossedAbove(KijunSen, 0))
                {
                    Notifications.PlaySound(SoundFilePath);
                    Notifications.SendEmail(FromEmail, ToEmail, "Ichimoku kinku hyo Alert | Bullish", "TenkanSen crossed above KijunSen");
                }
                else if (TenkanSen.HasCrossedBelow(KijunSen, 0))
                {
                    Notifications.PlaySound(SoundFilePath);
                    Notifications.SendEmail(FromEmail, ToEmail, "Ichimoku kinku hyo Alert | Bearish", "TenkanSen crossed below KijunSen");
                }
            }
        }
    }
}

For email notification to work you have to first configure your cTrader email notification settings.


@amusleh

amusleh
13 May 2022, 10:21

Hi,

We can only help you if you post a code sample that can reproduce this issue.

Please post the code for your cBot and the custom indicator you are using.


@amusleh

amusleh
13 May 2022, 10:19

Hi,

GetIndexByTime method returns the nearest bar index based on the date time you passed to it, if there is no bar for your passed date time then it will return -1.

Please post a indicator/cBot code sample that can reproduce the issue, then we will be able to help you.

 


@amusleh

amusleh
12 May 2022, 12:24

RE:

noob7 said:

@amusleh

Because of this change Ive lost over 100 euro.

Why you didnt notify me about this breaking changes?

Hi,

The change was not a breaking change, our old proxies are still working and they resolve to new nearest proxies.

We are still investigating the connection issue.


@amusleh

amusleh
12 May 2022, 10:38

Hi,

We updated API proxies: Proxies / Endpoints - cTrader Open API (spotware.github.io)

Please use the new proxies based on your region, and if you faced any connection issue try individual proxies of a region and then report the issue by providing the proxy you used.


@amusleh

amusleh
12 May 2022, 09:06 ( Updated at: 12 May 2022, 09:07 )

Hi,

A closed position is a deal/trade, you have to use either Positions.Closed event or History collection, the deal has both entry time and close time.


@amusleh

amusleh
12 May 2022, 09:05

Hi,

There is no way to do this via API or programmatically.

You can open a thread on suggestions section for such a feature.


@amusleh

amusleh
11 May 2022, 14:50

RE: RE:

ctid2032775 said:

amusleh said:

Hi,

Thanks for providing the details, we are investigating the issue now and if we were able to replicate it we will fix it.

Hi,

any news regarding this issue?

Thx & BR
Christian

Hi,

We tried everything to reproduce the issue you are facing but we couldn't.


@amusleh

amusleh
11 May 2022, 14:16

Hi,

We are aware of this issue, it will be fixed as soon as possible.


@amusleh

amusleh
11 May 2022, 10:43 ( Updated at: 21 Dec 2023, 09:22 )

Hi,

Open API returns Symbol min/max/step volumes in cents, you have to divide it by 100 to get the volume in symbol quote asset unit.

The US 30 minimum volume is 0.01 contracts on my TopFX demo account:

Not 1 contract, maybe you are using two different accounts for Open API and cTrader desktop.

 


@amusleh

amusleh
11 May 2022, 10:04

Hi,

No, you can't, you can create a proxy class for communication between your DLL services and indicator/cBot.

You can also reference automate API assembly and use the base Indicator or Robot interfaces on your own assemblies (DLLs).


@amusleh

amusleh
10 May 2022, 10:59 ( Updated at: 10 May 2022, 11:06 )

RE:

darcome said:

Ok, as I wrote, this is what I am already doing.

I was hoping BeginInvokeOnMainThread could become an async function, so that it could be awaited.

 

Thank you anyway for the answer!

Hi,

Awaiting doesn't solve the issue, the code that calls BeginInvokeOnMainThread is executed on one thread and the action delegate you pass to BeginInvokeOnMainThread will run on cBot/Indicator main thread.

Even if you await, the cBot/Indicator thread has to either execute the continuation code by itself or dispatch it to the calling thread, during this time the calling thread will be free to do other stuff which is the benefit of asynchronous programming as you can do some other task while your passed action delegate to BeginInvokeOnMainThread is waiting to be executed.

To solve this issue you can create a pub/sub messaging agent, with a post method that will take your action delegate to BeginInvokeOnMainThread, and once the action delegate is executed by cBot/indicator main thread the agent will notify you, you can use .NET channels to avoid thread synchronization.

You can use such a wrapper over BeginInvokeOnMainThread to even get retuned values from your code that will be executed on cBot/Indicator main thread.

 


@amusleh

amusleh
10 May 2022, 09:41

Hi,

Try this:

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

namespace cAlgo.Robots
{
    [Robot(TimeZone = TimeZones.UTC, AccessRights = AccessRights.None)]
    public class SampleBreakoutRobot : Robot
    {
        [Parameter("Source")]
        public DataSeries Source { get; set; }

        [Parameter("Band Height (pips)", DefaultValue = 40.0, MinValue = 0)]
        public double BandHeightPips { get; set; }

        [Parameter("Stop Loss (pips)", DefaultValue = 20, MinValue = 1)]
        public int StopLossInPips { get; set; }

        [Parameter("Take Profit (pips)", DefaultValue = 40, MinValue = 1)]
        public int TakeProfitInPips { get; set; }

        [Parameter("Volume", DefaultValue = 10000, MinValue = 1000)]
        public int Volume { get; set; }

        [Parameter("Bollinger Bands Deviations", DefaultValue = 2)]
        public int Deviations { get; set; }

        [Parameter("Bollinger Bands Periods", DefaultValue = 20)]
        public int Periods { get; set; }

        [Parameter("Bollinger Bands MA Type")]
        public MovingAverageType MAType { get; set; }

        [Parameter("Consolidation Periods", DefaultValue = 2)]
        public int ConsolidationPeriods { get; set; }

        [Parameter("Enabled", DefaultValue = false, Group = "Single Direction")]
        public bool IsSingleDirection { get; set; }

        [Parameter("Trade Type", Group = "Single Direction")]
        public TradeType SingleDirectionTradeType { get; set; }

        private BollingerBands bollingerBands;
        private string label = "SampleBreakoutRobot";
        private int consolidation;

        protected override void OnStart()
        {
            bollingerBands = Indicators.BollingerBands(Source, Periods, Deviations, MAType);
        }

        protected override void OnBar()
        {
            var top = bollingerBands.Top.Last(1);
            var bottom = bollingerBands.Bottom.Last(1);

            if (top - bottom <= BandHeightPips * Symbol.PipSize)
            {
                consolidation = consolidation + 1;
            }
            else
            {
                consolidation = 0;
            }

            if (consolidation >= ConsolidationPeriods)
            {
                if (Symbol.Ask > top && (IsSingleDirection == false || SingleDirectionTradeType == TradeType.Buy))
                {
                    ExecuteMarketOrder(TradeType.Buy, Symbol, Volume, label, StopLossInPips, TakeProfitInPips);

                    consolidation = 0;
                }
                else if (Symbol.Bid < bottom && (IsSingleDirection == false || SingleDirectionTradeType == TradeType.Sell))
                {
                    ExecuteMarketOrder(TradeType.Sell, Symbol, Volume, label, StopLossInPips, TakeProfitInPips);

                    consolidation = 0;
                }
            }
        }
    }
}

 


@amusleh

amusleh
10 May 2022, 09:38

Hi,

Please post a job request or contact one of our consultants.


@amusleh

amusleh
10 May 2022, 09:37 ( Updated at: 10 May 2022, 09:42 )

Hi,

BeginInvokeOnMainThread executes your code as a promise in future without blocking, asynchronously on cBot/Indicator main thread.

It passes your action delegate to the cBot/Indicator main thread event loop.

What do you mean by waiting? do you mean blocking the calling thread until the execution of your passed code to BeginInvokeOnMainThread finish? 

There is only one way to wait, block your current thread by using a thread synchronization context like ManualResetEventSlim until cBot/Indicator thread execute your code.

You can avoid some of this issues, but the solutions are dependent on your circumstance and there is no general solution.


@amusleh

amusleh
09 May 2022, 09:03

Hi,

The screenshot from your logs tab is not readable, if there is any error please post it instead.

Or if possible post a sample cBot that can reproduce the issue.


@amusleh