انتقل إلى المحتوى

عينات كود cBot

توفر هذه الصفحة العديد من أمثلة الكود بلغتي Python وC# لإنشاء روبوتات التداول وتطوير الخوارزميات. لاحظ أن أيًا من خوارزميات cBot المدرجة أدناه لا تضمن أي عوائد مالية. تأكد من إجراء اختبار عكسي وتخصيص خوارزميات cBot الخاصة بك قبل نشر أي نسخ على حساب حقيقي.

مستودعات عينات cBot

تتوفر عينات كود cBot الشاملة، بما في ذلك القوالب الجاهزة للتشغيل لمختلف الاستراتيجيات الآلية وأساليب التداول، في مستودعات منفصلة لـ Python وC# على GitHub.

العمليات المتزامنة

تنفذ جميع خوارزميات cBot في هذا القسم عملياتها بشكل متزامن.

تنفيذ أوامر السوق

  • خوارزمية cBot بسيطة تنفذ عمليات ناجحة

    تنشئ خوارزمية التداول التالية أمر سوق عند بدء التشغيل وتحفظ النتيجة في المتغير result.

    إذا نجح تنفيذ الأمر، يتم طباعة سعر الدخول في السجل.

     1
     2
     3
     4
     5
     6
     7
     8
     9
    10
    11
    12
    13
    14
    [Robot()]
    public class Sample_cBot : Robot
    {
        protected override void OnStart()
        {
            var result = ExecuteMarketOrder(TradeType.Buy, SymbolName, 10000);
    
            if (result.IsSuccessful)
            {
                var position = result.Position;
                Print("Position entry price is {0}", position.EntryPrice);
            }
        }
    }
    
    1
    2
    3
    4
    5
    6
    7
    class Sample_cBot():
        def on_start(self):
            result = api.ExecuteMarketOrder(TradeType.Buy, api.SymbolName, 10000)
    
            if result.IsSuccessful:
                position = result.Position
                api.Print(f"Position entry price is {position.EntryPrice}")
    

    مخرجات السجل

    • تم بدء تشغيل خوارزمية cBot "خوارزمية cBot جديدة" بنجاح لـ EURUSD، h1.
    • تنفيذ أمر السوق لشراء 10000 EURUSD
    • نجح تنفيذ أمر السوق لشراء 10000 EURUSD، المركز PID14576001
    • سعر دخول المركز هو 1.19067
  • خوارزمية cBot بسيطة بمعلمات قابلة للتخصيص

    عند الإعلان عن خصائص مختلفة لخوارزمية cBot، يمكنك تحويلها إلى معلمات قابلة للتخصيص باستخدام الإعلان [Parameter()]. عند إطلاق نسخة جديدة من خوارزمية cBot الخاصة بك، ستتمكن أنت (أو المستخدمون الآخرون) من تعيين قيم مخصصة لهذه.

    انظر إلى المثال التالي.

    1
    2
    [Parameter("SMA Period", DefaultValue = 14)]
    public int SmaPeriod { get; set; }
    

    ملاحظة

    تستخدم خوارزميات cBot بلغة Python معلمات قابلة للتخصيص معلنة في ملفاتها .cs.

    1
    2
    [Parameter("SMA Period", DefaultValue = 14)]
    public int SmaPeriod { get; set; }
    

    في المثال أعلاه، نحدد الخصائص التالية:

    • اسم المعلمة. سيظهر لاحقًا في واجهة مستخدم cTrader ("SMA Period").
    • القيمة الافتراضية للمعلمة التي ستنطبق على جميع النسخ الجديدة ما لم يتم تغييرها من قبل المستخدمين (DefaultValue = 14).

    في الكود أدناه، نوضح كيف يمكن استخدام خاصية SmaPeriod في روبوت تداول فعلي.

     1
     2
     3
     4
     5
     6
     7
     8
     9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    [Robot(TimeZone = TimeZones.UTC, AccessRights = AccessRights.None)]
    public class SamplecBotReferenceSMA : Robot
    {
        [Parameter("Source")]
        public DataSeries Source { get; set; }
    
        [Parameter("SMA Period", DefaultValue = 14)]
        public int SmaPeriod { get; set; }
    
        private SampleSMA sma;
    
        protected override void OnStart()
        {
            sma = Indicators.GetIndicator<SampleSMA>(Source, SmaPeriod);
        }
    
        protected override void OnTick()
        {
            Print("{0}", sma.Result.LastValue);
        }
    }
    

    ملاحظة

    تستخدم خوارزميات cBot بلغة Python معلمات قابلة للتخصيص معلنة في ملفاتها .cs.

    1
    2
    3
    4
    5
    6
    class Sample_cBot():
        def on_start(self):
            self.sma = api.Indicators.GetIndicator<SampleSMA>(api.Source, api.SmaPeriod)
    
        def on_tick(self):
            api.Print(f"{self.sma.Result.LastValue}")
    

    يأخذ الروبوت الخاص بنا خاصية SmaPeriod القابلة للتخصيص وعند البدء، يمرر قيمتها إلى طريقة Indicators.GetIndicator<SampleSMA>(). تعيد هذه الطريقة قيمة المتوسط المتحرك البسيط للفترة المحددة.

    عند إنشاء نسخة من خوارزمية cBot، يمكن إعداد جميع المعلمات القابلة للتعديل في نافذة إضافة نسخة.

    عند التشغيل، تخبرنا خوارزمية cBot بآخر قيمة للمتوسط المتحرك البسيط في كل نقرة.

    مخرجات السجل

    • تم بدء تشغيل نسخة CBot [Sample cBot Reference SMA, EURUSD, h1].
    • 0.975685714285714
    • 0.975681428571429
    • 0.97568
    • تم إيقاف نسخة CBot [Sample cBot Reference SMA, EURUSD, h1] من قبل المستخدم.
  • تنفيذ أمر سوق بمزيد من الوسائط

    في المثال السابق، قمنا بتمرير الحد الأدنى الممكن من الوسائط إلى طريقة ExecuteMarketOrder(). كانت هذه الوسائط هي نوع التداول (TradeType.Buy)، والرمز (Symbol) والحجم (-1).

    يمكن استدعاء طريقة ExecuteMarketOrder() بوسائط إضافية مثل Label، وStopLoss، وTakeProfit وComment. يحدد المثال أدناه التسمية ("order 1")، وآلية حماية وقف الخسارة (10) ومستوى جني الأرباح (10).

     1
     2
     3
     4
     5
     6
     7
     8
     9
    10
    11
    12
    13
    14
    15
    [Robot(TimeZone = TimeZones.UTC)]
    public class Sample_cBot : Robot
    {
        protected override void OnStart()
        {
            var result = ExecuteMarketOrder(TradeType.Buy, SymbolName, 10000, "order 1", 10, 10);
    
            if (result.IsSuccessful)
            {
                var position = result.Position;
                Print("Position entry price is {0}", position.EntryPrice);
                Print("Position SL price is {0}", position.StopLoss);
            }
        }
    }
    
    1
    2
    3
    4
    5
    6
    7
    8
    class Sample_cBot():
        def on_start(self):
            result = api.ExecuteMarketOrder(TradeType.Buy, api.SymbolName, 10000, "order 1", 10, 10)
    
            if result.IsSuccessful:
                position = result.Position
                api.Print(f"Position entry price is {position.EntryPrice}")
                api.Print(f"Position SL price is {position.StopLoss}")
    

    مخرجات السجل

    • تم بدء تشغيل خوارزمية cBot "خوارزمية cBot جديدة" بنجاح لـ EURUSD، h1.
    • تنفيذ أمر السوق لشراء 10000 EURUSD (وقف الخسارة: 10، جني الأرباح: 10)
    • نجح تنفيذ أمر السوق لشراء 10000 EURUSD (وقف الخسارة: 10، جني الأرباح: 10)، المركز PID14576098
    • سعر دخول المركز هو 1.1896
    • سعر وقف الخسارة للمركز هو 1.1886

تعديل مركز

في المثال أدناه، نضيف فقط قيمة جني الأرباح (10) عند تنفيذ الأمر. بعد ذلك، نقوم بتعديل المركز لإضافة وقف الخسارة.

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
[Robot()]
public class SamplecBbot : Robot
{
    protected override void OnStart()
    {
        var result = ExecuteMarketOrder(TradeType.Buy, SymbolName, 10000,
                                "order 1", null, 10);
        if (result.IsSuccessful)
        {
            var position = result.Position;
            Print("Position SL price is {0}", position.StopLoss);

            var stopLoss = position.EntryPrice - 10*Symbol.PipSize;
            ModifyPosition(position, stopLoss, position.TakeProfit);

            Print("New Position SL price is {0}", position.StopLoss);

        }
    }
}
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
class Sample_cBot():
    def on_start(self):
        result = api.ExecuteMarketOrder(TradeType.Buy, api.SymbolName, 10000, "order 1", None, 10)

        if result.IsSuccessful:
            position = result.Position
            api.Print(f"Position SL price is {position.StopLoss}")
            stopLoss = position.EntryPrice - 10 * api.Symbol.PipSize
            api.ModifyPosition(position, stopLoss, position.TakeProfit)
            api.Print(f"New Position SL price is {position.StopLoss}")

مخرجات السجل

إغلاق مركز

  • تنفيذ إغلاق كامل

    يضع نموذج الكود أدناه أمر سوق. إذا تجاوز الربح الإجمالي للمركز الناتج قيمة معينة (null && position.GrossProfit > 10)، يتم إغلاقه.

     1
     2
     3
     4
     5
     6
     7
     8
     9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    [Robot()]
    public class Sample_cBot : Robot
    {
        protected override void OnStart()
        {
            ExecuteMarketOrder(TradeType.Buy, SymbolName, 10000, "myLabel");
        }
    
        protected override void OnTick()
        {
            var position = Positions.Find("myLabel");
            if (position != null && position.GrossProfit > 10)
            {
                ClosePosition(position);
                Stop();
            }
        }
    }
    
    1
    2
    3
    4
    5
    6
    7
    8
    9
    class Sample_cBot():
        def on_start(self):
            api.ExecuteMarketOrder(TradeType.Buy, api.SymbolName, 10000, "myLabel")
    
        def on_tick(self):
            position = api.Positions.Find("myLabel")
            if position is not None and position.GrossProfit > 10:
                api.ClosePosition(position)
                api.Stop()
    

    مخرجات السجل

    • تم بدء تشغيل خوارزمية cBot "خوارزمية cBot جديدة" بنجاح لـ EURUSD، h1.
    • تنفيذ أمر السوق لشراء 10000 EURUSD
    • نجح تنفيذ أمر السوق لشراء 10000 EURUSD، المركز PID14576180
  • تنفيذ إغلاق جزئي

    سنقوم بتعديل المثال السابق لإنشاء أمري سوق بنفس التسميات ("myLabel"). في كل شريط جديد، سيقوم روبوت التداول الخاص بنا بإغلاق نصف واحد بالضبط من أحد هذه الأوامر ولكن فقط إذا كان حجمه يساوي أو يزيد عن 20,000.

    نستخدم أيضًا طريقة Positions.FindAll(). تعيد هذه الطريقة قائمة بالمراكز التي يمكننا التكرار خلالها.

     1
     2
     3
     4
     5
     6
     7
     8
     9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    [Robot()]
    public class Sample_cBot : Robot
    {
        protected override void OnStart()
        {
            ExecuteMarketOrder(TradeType.Buy, SymbolName, 20000, "myLabel");
            ExecuteMarketOrder(TradeType.Buy, SymbolName, 30000, "myLabel");
        }
    
        protected override void OnBar()
        {
            var positions = Positions.FindAll("myLabel", SymbolName, TradeType.Buy);
    
            foreach (var position in positions)
            {
                if (position.VolumeInUnits >= 20000)
                {
                    ClosePosition(position, 15000);
                }
            }
        }
    }
    
     1
     2
     3
     4
     5
     6
     7
     8
     9
    10
    class Sample_cBot():
        def on_start(self):
            api.ExecuteMarketOrder(TradeType.Buy, api.SymbolName, 20000, "myLabel")
            api.ExecuteMarketOrder(TradeType.Buy, api.SymbolName, 30000, "myLabel")
    
        def on_tick(self):
            positions = api.Positions.FindAll("myLabel", api.SymbolName, TradeType.Buy)
            for position in positions:
                if position.VolumeInUnits >= 20000:
                    api.ClosePosition(position, 15000)
    

    مخرجات السجل

    • تم بدء تشغيل خوارزمية cBot "خوارزمية cBot جديدة" بنجاح لـ EURUSD، h1.
    • تنفيذ أمر السوق لشراء 20000 EURUSD
    • نجح تنفيذ أمر السوق لشراء 20000 EURUSD، المركز PID14579299
    • تنفيذ أمر السوق لشراء 30000 EURUSD
    • نجح تنفيذ أمر السوق لشراء 30000 EURUSD، المركز PID14579300

إنشاء الأوامر المعلقة

  • إنشاء أوامر الحد والإيقاف

    أوامر الحد والإيقاف هي أوامر معلقة؛ على الرغم من ذلك، يتم إنشاؤها بطريقة مماثلة لأوامر السوق. ومع ذلك، عند إنشاء أوامر الحد والإيقاف، يجب عليك أيضًا تحديد سعرها المستهدف ولا يوجد نطاق للسوق.

    ينشئ هذا الـ cBot أمرين للحد وأمر إيقاف واحد. ثم يقوم بالتكرار خلال الأوامر ويطبع تسمياتها ومعرفاتها في السجل.

     1
     2
     3
     4
     5
     6
     7
     8
     9
    10
    11
    12
    13
    14
    15
    16
    [Robot()]
    public class Sample_cBot : Robot
    {
        protected override void OnStart()
        {
            PlaceLimitOrder(TradeType.Buy, SymbolName, 10000, Symbol.Bid, "myLimitOrder");
            PlaceLimitOrder(TradeType.Buy, SymbolName, 20000, Symbol.Bid-2*Symbol.PipSize,
                    "myLimitOrder");
            PlaceStopOrder(TradeType.Buy, SymbolName, 10000, Symbol.Ask, "myStopOrder");
    
            foreach (var pendingOrder in PendingOrders)
            {
                Print("Order placed with label {0}, id {1}", pendingOrder.Label, pendingOrder.Id);
            }
        }
    }
    
    1
    2
    3
    4
    5
    6
    7
    8
    class Sample_cBot():
        def on_start(self):
            api.PlaceLimitOrder(TradeType.Buy, api.SymbolName, 10000, api.Symbol.Bid, "myLimitOrder")
            api.PlaceLimitOrder(TradeType.Buy, api.SymbolName, 20000, api.Symbol.Bid - 2 * api.Symbol.PipSize, "myLimitOrder")
            api.PlaceStopOrder(TradeType.Buy, api.SymbolName, 10000, api.Symbol.Ask, "myStopOrder")
    
            for pendingOrder in api.PendingOrders:
                Print(f"Order placed with label {pendingOrder.Label}, id {pendingOrder.Id}")
    

    مخرجات السجل

    • تم بدء تشغيل خوارزمية cBot "خوارزمية cBot جديدة" بنجاح لـ EURUSD، h1.
    • وضع أمر حد لشراء 10000 EURUSD (السعر: 1.19036)
    • وضع أمر حد لشراء 10000 EURUSD (السعر: 1.19036) تم بنجاح، أمر معلق OID25220794
    • وضع أمر حد لشراء 20000 EURUSD (السعر: 1.19017)
    • وضع أمر حد لشراء 20000 EURUSD (السعر: 1.19017) تم بنجاح، أمر معلق OID25220795
    • وضع أمر إيقاف لشراء 10000 EURUSD (السعر: 1.19040)
    • وضع أمر إيقاف لشراء 10000 EURUSD (السعر: 1.19040) تم بنجاح، أمر معلق OID25220796
    • تم وضع الأمر بتسمية myLimitOrder، المعرف 25220794
    • تم وضع الأمر بتسمية myLimitOrder، المعرف 25220795
    • تم وضع الأمر بتسمية myStopOrder، المعرف 25220796
  • إنشاء أوامر معلقة بمعلمات إضافية

    كما هو الحال مع أوامر السوق، يمكنك أيضًا تحديد تسمية الأمر، وآليات الحماية المختلفة، وتاريخ انتهاء صلاحية الأمر وتقديم تعليق.

     1
     2
     3
     4
     5
     6
     7
     8
     9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    [Robot()]
    public class Sample_cBot : Robot
    {
        protected override void OnStart()
        {
            var midnight = Server.Time.AddDays(1).Date;
    
            PlaceLimitOrder(TradeType.Buy, SymbolName, 10000, Symbol.Bid, "mySample_cBot", 10, null, midnight, "First");
    
            PlaceStopOrder(TradeType.Buy, SymbolName, 10000, Symbol.Ask, "mySample_cBot", 10, 10, null, "Second");
    
            foreach (var order in PendingOrders)
            {
                var sl = order.StopLoss == null ? "" : "SL: " + order.StopLoss;
                var tp = order.TakeProfit == null ? "" : " TP: " + order.TakeProfit;
    
                var text = string.Format("{0} {1}", sl, tp);
    
                if (order.OrderType == PendingOrderType.Limit)
                    Print(order.Comment + " Limit Order " + text);
                else
                    Print(order.Comment + " Stop Order " + text);
            }
        }
    }
    
     1
     2
     3
     4
     5
     6
     7
     8
     9
    10
    11
    12
    class Sample_cBot():
        def on_start(self):
            midnight = api.Server.Time.AddDays(1).Date
    
            api.PlaceLimitOrder(TradeType.Buy, api.SymbolName, 10000, api.Symbol.Bid, "mySample_cBot", 10, None, midnight, "First")
            api.PlaceStopOrder(TradeType.Buy, api.SymbolName, 10000, api.Symbol.Ask, "mySample_cBot", 10, 10, None, "Second")
    
            for order in api.PendingOrders:
                sl = "" if order.StopLoss is None else f"SL: {order.StopLoss}"
                tp = "" if order.TakeProfit is None else f"TP: {order.TakeProfit}"
    
                api.Print(f"{order.Comment} {order.OrderType} Order {sl} {tp}")
    

    مخرجات السجل

    • تم بدء تشغيل خوارزمية cBot "خوارزمية cBot جديدة" بنجاح لـ EURUSD، h1.
    • وضع أمر حد لشراء 10000 EURUSD (السعر: 1.19049، إيقاف الخسارة: 10، وقت الانتهاء: 12/05/2018 00:00:00)
    • وضع أمر حد لشراء 10000 EURUSD (السعر: 1.19049، إيقاف الخسارة: 10، وقت الانتهاء: 12/05/2018 00:00:00) تم بنجاح، أمر معلق OID25220807
    • وضع أمر إيقاف لشراء 10000 EURUSD (السعر: 1.19053، إيقاف الخسارة: 10، جني الأرباح: 10)
    • وضع أمر إيقاف لشراء 10000 EURUSD (السعر: 1.19053، إيقاف الخسارة: 10، جني الأرباح: 10) تم بنجاح، أمر معلق OID25220808
    • أمر الحد
    • أمر الحد الأول إيقاف الخسارة: 1.18949
    • أمر الإيقاف الثاني إيقاف الخسارة: 1.18953 جني الأرباح: 1.19153

تعديل الأوامر المعلقة

من الممكن تعديل العديد من خصائص الأوامر المعلقة.

يوضح المثال أدناه كيفية تعديل السعر المستهدف، ومستويات الحماية أو تاريخ ووقت انتهاء صلاحية الأمر المعلق.

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
[Robot()]
public class Sample_cBot : Robot
{
    protected override void OnStart()
    {
        var price = Symbol.Ask + 10 * Symbol.PipSize;
        var expiry = Server.Time.AddHours(12);
        PlaceStopOrder(TradeType.Buy, SymbolName, 10000, price, "myLabel", 10, 10, expiry);
    }

    protected override void OnBar()
    {
        foreach (var order in PendingOrders)
        {
            if (order.Label == "myLabel")
            {
                double newPrice = Symbol.Ask + 5 * Symbol.PipSize;
                ModifyPendingOrder(order, newPrice, order.StopLossPips,
                                                            order.TakeProfitPips, order.ExpirationTime);
            }
        }
    }
}
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
class Sample_cBot():
    def on_start(self):
        price = api.Symbol.Ask + 10 * api.Symbol.PipSize
        expiry = Server.Time.AddHours(12)

        api.PlaceStopOrder(TradeType.Buy, api.SymbolName, 10000, price, "myLabel", 10, 10, expiry)

    def on_bar(self):
        for order in api.PendingOrders:
            if order.Label == "myLabel":
                newPrice = api.Symbol.Ask + 5 * api.Symbol.PipSize
                api.ModifyPendingOrder(order, newPrice, order.StopLossPips, order.TakeProfitPips, order.ExpirationTime)

مخرجات السجل

إلغاء الأوامر المعلقة

صيغة إلغاء الأمر هي CancelPendingOrder(order)، حيث order هو من نوع PendingOrder.

يوضح المثال أدناه إلغاء جميع الأوامر التي تحمل التسمية "myLabel".

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
[Robot()]
public class Sample_cBot : Robot
{
    protected override void OnTick()
    {
        foreach (var order in PendingOrders)
        {
            if (order.Label == "myLabel")
            {
                CancelPendingOrder(order);
            }
        }
    }
}
1
2
3
4
5
class Sample_cBot():
    def on_tick(self):
        for order in api.PendingOrders:
            if order.Label == "myLabel":
                api.CancelPendingOrder(order)

أحداث المركز

من الممكن الاشتراك في الأحداث المتعلقة بعمليات التداول المختلفة. على سبيل المثال، لاختبار ما إذا تم فتح مركز، نشترك في حدث يتم رفعه لجميع كائنات Position عند الفتح.

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
[Robot()]
public class Sample_cBot : Robot
{
    protected override void OnStart()
    {
        Positions.Opened += PositionsOnOpened;
        ExecuteMarketOrder(TradeType.Buy, Symbol, 10000, "myLabel", 10, 10);
    }

    private void PositionsOnOpened(PositionOpenedEventArgs args)
    {
        var pos = args.Position;
        Print("Position opened at {0}", pos.EntryPrice);
    }
}
1
2
3
4
5
6
7
8
class Sample_cBot():
    def on_start(self):
        api.Positions.Opened += self.on_position_opened
        api.ExecuteMarketOrder(TradeType.Buy, api.Symbol, 10000, "myLabel", 10, 10)

    def on_position_opened(self, args):
        pos = args.Position
        api.Print(f"Position opened at {pos.EntryPrice}")

مخرجات السجل

وبالمثل، من الممكن الاشتراك في الأحداث التي يتم رفعها في كل مرة يتم فيها إغلاق مركز.

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
[Robot()]
public class Sample_cBot : Robot
{
    protected override void OnStart()
    {
        Positions.Closed += PositionsOnClosed;
        ExecuteMarketOrder(TradeType.Buy, Symbol, 10000, "myLabel", 10, 10);
    }

    protected override void OnBar()
    {
        var position = Positions.Find("myLabel");
        if (position != null)
            ClosePosition(position);
    }

    private void PositionsOnClosed(PositionClosedEventArgs args)
    {
        var pos = args.Position;
        Print("Position closed with {0} profit", pos.GrossProfit);
    }
}
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
class Sample_cBot():
    def on_start(self):
        api.Positions.Closed += self.on_position_closed
        api.ExecuteMarketOrder(TradeType.Buy, api.Symbol, 10000, "myLabel", 10, 10)

    def on_bar(self):
        position = api.Positions.Find("myLabel")

        if position is not None:
            api.ClosePosition(position);            

    def on_position_closed(self, args):
        pos = args.Position
        api.Print(f"Position closed with {pos.GrossProfit} profit")

مخرجات السجل

تحويل الإحداثيات

يسمح الـ cBot أدناه للمستخدمين بوضع أوامر حد في اتجاه مناسب ببساطة عن طريق النقر بزر الماوس الأيمن على الرسم البياني. يحقق ذلك من خلال تحويل إحداثيات Y للماوس إلى إحداثيات Y للرسم البياني (والتي، بالنسبة للرموز، تتوافق مع أسعار الرمز).

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
[Robot(AccessRights = AccessRights.None)]
public class CoordinatesConverter : Robot
{
    protected override void OnStart()
    {
        Chart.MouseUp += Chart_MouseUp;
    }

    private void Chart_MouseUp(ChartMouseEventArgs obj)
    {
        var desiredPrice = Chart.YToYValue(obj.MouseY);
        var desiredTradeType = desiredPrice > Symbol.Bid ? TradeType.Sell : TradeType.Buy;
        PlaceLimitOrder(desiredTradeType, SymbolName, 10000, desiredPrice);
    }
}
1
2
3
4
5
6
7
8
class Sample_cBot():
    def on_start(self):
        api.Chart.MouseUp += self.on_chart_mouse_up        

    def on_chart_mouse_up(self, args):
        desiredPrice = api.Chart.YToYValue(args.MouseY)
        desiredTradeType = TradeType.Sell if desiredPrice > api.Symbol.Bid else TradeType.Buy
        api.PlaceLimitOrder(desiredTradeType, api.SymbolName, 10000, desiredPrice)

التنفيذ غير المتزامن

تم تصميم عينات الكود أعلاه لتنفيذ روبوتات التداول باستخدام التنفيذ المتزامن. تدعم كل من C# و Python العمليات غير المتزامنة، مما يسمح لـ cBot الخاص بك بتنفيذ عدة إجراءات في نفس الإطار الزمني.

تنفيذ أوامر السوق بشكل غير متزامن

صيغة الأساليب غير المتزامنة مشابهة لتلك الخاصة بالأساليب المتزامنة. بينما تقبل نفس أنواع الوسائط، فإن نوع الإرجاع الخاص بها هو TradeOperation بدلاً من TradeResult.

  • العمليات غير المتزامنة الأساسية

    يوضح الـ cBot التالي كيفية عمل العمليات غير المتزامنة. يتم إنشاء أمر سوق؛ في الشرط التالي، يتحقق الـ cBot مما إذا كانت العملية قيد التنفيذ.

     1
     2
     3
     4
     5
     6
     7
     8
     9
    10
    11
    12
    13
    [Robot()]
    public class Sample_cBot : Robot
    {
        protected override void OnStart()
        {
            var operation = ExecuteMarketOrderAsync(TradeType.Buy, SymbolName, 10000);
    
            if (operation.IsExecuting)
            {
                Print("Operation Is Executing");
            }
        }
    }
    
    1
    2
    3
    4
    5
    6
    class Sample_cBot():
        def on_start(self):
            operation = api.ExecuteMarketOrderAsync(TradeType.Buy, api.SymbolName, 10000)
    
            if operation.IsExecuting:
                api.Print("Operation Is Executing")
    

    مخرجات السجل

    • تم بدء تشغيل خوارزمية cBot "خوارزمية cBot جديدة" بنجاح لـ EURUSD، h1.
    • تنفيذ أمر سوق لشراء 10000 EURUSD
    • العملية قيد التنفيذ
    • تنفيذ أمر سوق لشراء 10000 EURUSD تم بنجاح، مركز PID14579532
  • تنفيذ أمر

    يسلط المثال التالي الضوء على الفرق بين الأساليب المتزامنة وغير المتزامنة.

    يتحقق الـ cBot مما إذا كانت العملية قيد التنفيذ مباشرة بعد استدعاء أسلوب غير متزامن. يقوم بذلك مرة أخرى بعد استدعاء أسلوب متزامن. يختلف إخراج السجل لهذين الإجراءين.

     1
     2
     3
     4
     5
     6
     7
     8
     9
    10
    11
    [Robot()]
    public class Sample_cBot : Robot
    {
        protected override void OnStart()
        {
            var operation = ExecuteMarketOrderAsync(TradeType.Buy, SymbolName, 10000);
            Print(operation.IsExecuting ? "Operation Is Executing" : "Operation executed");
            ExecuteMarketOrder(TradeType.Buy, SymbolName, 20000);
            Print(operation.IsExecuting ? "Operation Is Executing" : "Operation executed");
        }
    }
    
    1
    2
    3
    4
    5
    6
    class Sample_cBot():
        def on_start(self):
            operation = api.ExecuteMarketOrderAsync(TradeType.Buy, api.SymbolName, 10000)
            api.Print("Operation Is Executing" if operation.IsExecuting else "Operation executed")
            api.ExecuteMarketOrder(TradeType.Buy, api.SymbolName, 20000)
            api.Print("Operation Is Executing" if operation.IsExecuting else "Operation executed")
    

    مخرجات السجل

    • تم بدء تشغيل خوارزمية cBot "خوارزمية cBot جديدة" بنجاح لـ EURUSD، h1.
    • تنفيذ أمر سوق لشراء 10000 EURUSD
    • العملية قيد التنفيذ
    • تنفيذ أمر سوق لشراء 20000 EURUSD
    • تنفيذ أمر سوق لشراء 10000 EURUSD تم بنجاح، مركز PID14579541
    • تنفيذ أمر سوق لشراء 20000 EURUSD تم بنجاح، مركز PID14579542
    • تم تنفيذ العملية
  • تنفيذ أمر بمعلمات إضافية

    يضع الـ cBot التالي أمرًا محددًا تسميته ("myLabel")، ومستويات الحماية (10, 10)، والرمز (SymbolName) والحجم (10000).

    يحتوي المثال أيضًا على مجموعة Positions وطريقة FindAll(). يمكن استخدام Find() و FindAll() للعثور على المراكز ذات نفس التسمية والرمز ونوع التداول.

     1
     2
     3
     4
     5
     6
     7
     8
     9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    [Robot()]
    public class Sample_cBot : Robot
    {
        protected override void OnStart()
        {
            ExecuteMarketOrderAsync(TradeType.Buy, SymbolName, 10000, "myLabel", 10, 10);
        }
        protected override void OnTick()
        {
            var positions = Positions.FindAll("myLabel", SymbolName, TradeType.Buy);
    
            if (positions.Length == 0)
                return;
    
            foreach (var position in positions)
                Print("Buy at {0} SL {1}", position.EntryPrice, position.StopLoss);
    
            Stop();
        }
    }
    
     1
     2
     3
     4
     5
     6
     7
     8
     9
    10
    11
    12
    13
    14
    class Sample_cBot():
        def on_start(self):
            api.ExecuteMarketOrderAsync(TradeType.Buy, api.SymbolName, 10000, "myLabel", 10, 10)
    
        def on_tick(self):
            positions = api.Positions.FindAll("myLabel", api.SymbolName, TradeType.Buy)
    
            if positions.Length == 0:
                return
    
            for position in positions:
                api.Print(f"Buy at {position.EntryPrice} SL {position.StopLoss}")
    
            api.Stop()            
    

    مخرجات السجل

    • تم بدء تشغيل خوارزمية cBot "خوارزمية cBot جديدة" بنجاح لـ EURUSD، h1.
    • تنفيذ أمر سوق لشراء 10000 EURUSD (إيقاف الخسارة: 10، جني الأرباح: 10)
    • تنفيذ أمر سوق لشراء 10000 EURUSD (إيقاف الخسارة: 10، جني الأرباح: 10) تم بنجاح، مركز PID14579719
    • شراء عند 1.19087 إيقاف الخسارة null
    • شراء عند 1.19357 إيقاف الخسارة 1.19257
    • تم إيقاف cBot New cBot" لـ EURUSD، h1."

تعديل المركز بشكل غير متزامن

يضع الـ cBot أدناه أمر سوق ثم يعدل المركز المفتوح حديثًا.

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
[Robot()]
public class Sample_cBot : Robot
{
    protected override void OnStart()
    {
        ExecuteMarketOrderAsync(TradeType.Buy, SymbolName, 10000, "myLabel", null, 10);
    }

    protected override void OnTick()
    {
        Position myPosition = Positions.Find("myLabel");
        if (myPosition != null && myPosition.StopLoss == null)
        {
            double stopLoss = Symbol.Bid - 10 * Symbol.PipSize;
            ModifyPositionAsync(myPosition, stopLoss, myPosition.TakeProfit);
        }
    }
}
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
class Sample_cBot():
    def on_start(self):
        api.ExecuteMarketOrderAsync(TradeType.Buy, api.SymbolName, 10000, "myLabel", None, 10)

    def on_tick(self):
        myPosition = Positions.Find("myLabel")

        if myPosition is None or myPosition.StopLoss is not None:
            return

        stopLoss = api.Symbol.Bid - 10 * api.Symbol.PipSize

        api.ModifyPositionAsync(myPosition, stopLoss, myPosition.TakeProfit)        

مخرجات السجل

إغلاق مركز بشكل غير متزامن

يوضح المثال التالي إغلاق مركز بشكل غير متزامن إذا كان موجودًا.

يتم استخدام طريقة Find() للبحث في مجموعة Positions عن المركز ذي التسمية المحددة.

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
[Robot()]
public class Sample_cBot : Robot
{
    protected override void OnStart()
    {
        ExecuteMarketOrderAsync(TradeType.Buy, Symbol, 10000, "myLabel", null, 10);
    }

    protected override void OnTick()
    {
        Position myPosition = Positions.Find("myLabel");
        if (myPosition != null && myPosition.GrossProfit > 10)
        {
            ClosePositionAsync(myPosition);
            Stop();
        }
    }
}
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
class Sample_cBot():
    def on_start(self):
        api.ExecuteMarketOrderAsync(TradeType.Buy, api.SymbolName, 10000, "myLabel", None, 10)

    def on_tick(self):
        myPosition = Positions.Find("myLabel")

        if myPosition is None or myPosition.GrossProfit <= 10:
            return

        api.ClosePositionAsync(myPosition)
        api.Stop()        

مخرجات السجل

إدراج أوامر الحد والإيقاف بشكل غير متزامن

كما ذُكر أعلاه، فإن إدراج الأوامر المعلقة مشابه لإنشاء أوامر السوق.

ومع ذلك، هناك بعض الاختلافات الطفيفة في الوسائط بين هاتين الطريقتين. نطاق السوق غائب من قائمة الوسائط. علاوة على ذلك، يجب عليك تحديد السعر المستهدف، ويمكنك تمرير وسيطة اختيارية تحدد تاريخ انتهاء صلاحية الأمر.

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
[Robot()]
public class Sample_cBot : Robot
{
    protected override void OnStart()
    {
        var expiry = Server.Time.AddHours(12);
        PlaceLimitOrderAsync(TradeType.Buy, SymbolName, 10000, Symbol.Bid, "myLabel", null, null, expiry);
        PlaceStopOrderAsync(TradeType.Buy, SymbolName, 10000, Symbol.Ask + 10 * Symbol.PipSize, "myLabel", null, null, expiry);
    }
}
1
2
3
4
5
class Sample_cBot():
    def on_start(self):
        expiry = api.Server.Time.AddHours(12)
        api.PlaceLimitOrderAsync(TradeType.Buy, api.SymbolName, 10000, api.Symbol.Bid, "myLabel", None, None, expiry)
        api.PlaceStopOrderAsync(TradeType.Buy, api.SymbolName, 10000, api.Symbol.Ask + 10 * api.Symbol.PipSize, "myLabel", None, None, expiry)    

مخرجات السجل

تعديل الأوامر المعلقة بشكل غير متزامن

يقوم cBot التالي بتعديل أوامر الحد بشكل غير متزامن.

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
[Robot()]
public class Sample_cBot : Robot
{
    protected override void OnStart()
    {
        var expiry = Server.Time.AddHours(12);
        PlaceLimitOrderAsync(TradeType.Buy, SymbolName, 10000, Symbol.Bid, "myLabel", null, 10, expiry);

    }
    protected override void OnTick()
    {
        foreach (var order in PendingOrders)
        {
            if (order.Label == "myLabel" && order.StopLoss == null)
                ModifyPendingOrderAsync(order, order.TargetPrice, 10, 10, null);
        }
    }
}
1
2
3
4
5
6
7
8
9
class Sample_cBot():
    def on_start(self):
        expiry = api.Server.Time.AddHours(12)
        api.PlaceLimitOrderAsync(TradeType.Buy, api.SymbolName, 10000, api.Symbol.Bid, "myLabel", None, 10, expiry)

    def on_tick(self):
        for order in api.PendingOrders:
            if order.Label == "myLabel" and order.StopLoss is None:
                api.ModifyPendingOrderAsync(order, order.TargetPrice, 10, 10, None)

مخرجات السجل

إلغاء الأوامر المعلقة بشكل غير متزامن

  • إلغاء جميع الأوامر المعلقة

    يقوم cBot أدناه بإلغاء جميع الأوامر المعلقة حاليًا بشكل غير متزامن.

     1
     2
     3
     4
     5
     6
     7
     8
     9
    10
    11
    [Robot()]
    public class Sample_cBot : Robot
    {
        protected override void OnBar()
        {
            foreach (var pendingOrder in PendingOrders)
            {
                CancelPendingOrderAsync(pendingOrder);
            }
        }
    }
    
    1
    2
    3
    4
    class Sample_cBot():
        def on_bar(self):
            for order in api.PendingOrders:
                api.CancelPendingOrderAsync(order)
    

    مخرجات السجل

    • تم بدء تشغيل cBot "cancel pending order" بنجاح لـ EURUSD، h1.
    • إلغاء الأمر المعلق OID274705
    • إلغاء الأمر المعلق OID274706
    • إلغاء الأمر المعلق OID274707
    • إلغاء الأمر المعلق OID274708
    • إلغاء الأمر المعلق OID274709
    • إلغاء الأمر المعلق OID274705 تم بنجاح، الأمر المعلق OID274705
    • إلغاء الأمر المعلق OID274706 تم بنجاح، الأمر المعلق OID274706
    • إلغاء الأمر المعلق OID274707 تم بنجاح، الأمر المعلق OID274707
    • إلغاء الأمر المعلق OID274708 تم بنجاح، الأمر المعلق OID274708
    • إلغاء الأمر المعلق OID274709 تم بنجاح، الأمر المعلق OID274709
  • إلغاء الأوامر المعلقة ذات تسمية معينة

    يقوم cBot هذا بإلغاء الأوامر المعلقة ذات تسمية معينة فقط.

     1
     2
     3
     4
     5
     6
     7
     8
     9
    10
    11
    12
    [Robot()]
    public class Sample_cBot : Robot
    {
        protected override void OnBar()
        {
            foreach (var pendingOrder in PendingOrders)
            {
                if (pendingOrder.Label == "myLabel")
                    CancelPendingOrderAsync(pendingOrder);
            }
        }
    }
    
    1
    2
    3
    4
    5
    class Sample_cBot():
        def on_bar(self):
            for order in api.PendingOrders:
                if order.Label == "myLabel":
                    api.CancelPendingOrderAsync(order)
    

دوال رد الاتصال للطرق غير المتزامنة

بمجرد إرجاع نتيجة، غالبًا ما تتطلب العمليات غير المتزامنة التحكم في التنفيذ. للتعامل مع هذا، يمكنك إضافة دالة رد اتصال في نهاية قائمة المعلمات لجميع الطرق غير المتزامنة.

سيتم استدعاء هذه الدالة بمجرد تلقي استجابة من الخادم. على سبيل المثال، يمكن استدعاؤها عند فتح مركز أو تعديله أو إغلاقه.

  • أمر السوق غير المتزامن مع رد اتصال

     1
     2
     3
     4
     5
     6
     7
     8
     9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    [Robot()]
    public class Sample_cBot : Robot
    {
        protected override void OnStart()
        {
            var operation = ExecuteMarketOrderAsync(TradeType.Buy, SymbolName, 10000, PositionOpened);
            if (operation.IsExecuting)
                Print(operation.ToString());
            else
                Print(operation.TradeResult.ToString());
    
        }
    
        private void PositionOpened(TradeResult tradeResult)
        {
            var position = tradeResult.Position;
            Print(tradeResult.ToString());
            if (tradeResult.IsSuccessful)
                Print("Position {0} opened at {1}", position.Id, position.EntryPrice);
        }
    }
    
     1
     2
     3
     4
     5
     6
     7
     8
     9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    from System import Action
    
    class Sample_cBot():
        def on_start(self):
            operation = api.ExecuteMarketOrderAsync(TradeType.Buy, api.SymbolName, 10000, Action[TradeResult](self.on_position_opened))
    
            if (operation.IsExecuting)
                api.Print(operation.ToString())
            else
                api.Print(operation.TradeResult.ToString())
    
        def on_position_opened(self, tradeResult):
            position = tradeResult.Position
    
            api.Print(tradeResult.ToString())
    
            if tradeResult.IsSuccessful:
                api.Print(f"Position {position.Id} opened at {position.EntryPrice}")
    

    مخرجات السجل

    • تم بدء تشغيل خوارزمية cBot "خوارزمية cBot جديدة" بنجاح لـ EURUSD، h1.
    • تنفيذ أمر السوق لشراء 10000 EURUSD
    • عملية التداول (تنفيذ أمر السوق لشراء 10000 EURUSD قيد التنفيذ)
    • تنفيذ أمر السوق لشراء 10000 EURUSD تم بنجاح، المركز PID14579835
    • نتيجة التداول (نجاح، المركز: PID14579835)
    • تم فتح المركز 14579835 عند 1.19414
  • استخدام تعبيرات لامدا

    بدلاً من تعريف طريقة رد اتصال مسماة، يمكنك استخدام تعبيرات لامدا.

    في المثال التالي، عند إدراج أمر، سيتم طباعة وصف النتيجة في السجل.

    1
    2
    3
    4
    5
    6
    7
    8
    9
    [Robot()]
    public class Sample_cBot : Robot
    {
        protected override void OnStart()
        {
            PlaceLimitOrderAsync(TradeType.Buy, SymbolName, 10000,
                    Symbol.Ask - 20 * Symbol.PipSize, "myLabel", result => Print(result.ToString()));
        }
    }
    
    1
    2
    3
    4
    5
    from System import Action
    
    class Samples():
        def on_start(self):
            operation = api.PlaceLimitOrderAsync(TradeType.Buy, api.SymbolName, 10000, api.Symbol.Ask - 20 * api.Symbol.PipSize, "myLabel", Action[TradeResult](lambda result: api.Print(result.ToString())))
    

    مخرجات السجل

    • تم بدء تشغيل "cBot "New cBot بنجاح لـ EURUSD، h1.
    • إدراج أمر حد الشراء 10000 EURUSD (السعر: 1.19320)
    • إدراج أمر حد الشراء 10000 EURUSD (السعر: 1.19320) تم بنجاح، الأمر المعلق OID25222083
    • نتيجة التداول (نجاح، الأمر المعلق: OID25222083)

Image title