文章 "创建一个人工交易助手"

 

新文章 创建一个人工交易助手已发布:

近来,货币市场上的交易机器人已经大幅增加,它们执行着各种各样的策略和概念,然而,它们还都没有能够成功创造人工智能双赢、多赢的实例,所以,很多交易者还是进行人工交易。但是,即使对于这样的专家,还是可以为他们创建被称为机器人助手的交易面板。本文就是从头开始创建交易面板的一个实例。

让我们使用一个新的页面,并在其中绘制我们未来的面板,把所有所需软件放置其中。

当进行交易面板的设计开发时,应该考虑实现的可行性。首先,交易面板应该包含足够的信息,容易阅读并不包括多余的元件,我们应该永远记住它不只是屏幕上一幅好看的图片,而是交易者的基本工具,

这是我的版本。

设计

作者:Dmitriy Gizlyk

 

类似的面板在本网站上发布已久。与标准面板相比,没有任何用处。

至于想法

1) 止损后的反向挂单按钮。

2) 单按钮仓位反转 按钮。

3) 仓位 Trall 按钮

4) 马丁格尔反向订单按钮

5) 获利按钮 3 对 1 或可定制。

最低标准设置。

 
Ilya Vasenin:

类似的面板在本网站上发布已久。与标准面板相比,没有任何用处。

至于想法

1) 止损后的挂单反转按钮。

2) 单按钮仓位反转 按钮。

3) 仓位 Trall 按钮

4) 马丁格尔反向订单按钮

5) 获利按钮 3 对 1 或可定制。

最低标准设置。

是的,市场上有很多交易面板。自由职业者中也有很多创建交易面板的工作。你和其他人一样,可以免费使用这个现成的面板。但这是一篇文章,不是市场上的产品。这篇文章的目的不是提供现成的产品,而是向大家展示并教那些想学习的人如何根据自己的要求创建自己的个人交易面板。
 
账户余额和资产净值显示在面板底部,与终端的 "工具 "标签重复。我建议在这里显示当天进行了多少笔交易,交易 的结果如何,并在将来当达到指定的交易笔数 或当天指定的损失时关闭终端。
 
Dmitriy Gizlyk:
这篇文章的目的不是提供现成的产品供大家使用,而是向大家展示和传授如何根据自己的要求创建自己的个性化交易面板。

德米特里,今天我开始按照您的教程在 µl 4 上制作一个面板。几乎一切正常,但当我点击面板或任何按钮时,打开的只有买入。原因是什么?

//+------------------------------------------------------------------+
//|TradePanel.mq4
///2015年,MetaQuotes Software Corp.版权所有。
//|https://www.mql5.com ||
//+------------------------------------------------------------------+
#property copyright "Copyright 2015, MetaQuotes Software Corp."
#property link      "https://www.mql5.com"
#property version   "1.00"
#property strict

#include <Controls\Dialog.mqh>
#include <Controls\Label.mqh>
#include <Controls\Button.mqh>

//--- 输入
extern double Lot        = 0.1;      // lot
extern int StopLoss      = 500;      // 驼鹿
extern int TakeProfit    = 500;      // yazi
extern int Slip          = 30;       // 重新报价
extern int Magic         = 0;        // 魔法
//+------------------------------------------------------------------+
//||
//+------------------------------------------------------------------+
enum label_align
  {
   left=-1,
   right=1,
   center=0
  };
//+------------------------------------------------------------------+
//||
//+------------------------------------------------------------------+
class CTradePanel : public CAppDialog
  {
private:

   CLabel            Lots_label;                      // 显示标签 " 乐ots
   CEdit             Lots;                            // 显示下一个订单的数量
   CButton           SELL,BUY;                        // 出售和购买按钮
   CButton           CloseAll;                        // 关闭按钮

   //--- 创建标签对象
   bool              CreateLabel(const long chart,const int subwindow,CLabel &object,const string text,const uint x,const uint y,label_align align);
   //--- 创建按钮
   bool              CreateButton(const long chart,const int subwindow,CButton &object,const string text,const uint x,const uint y,const uint x_size,const uint y_size);
   //--- 创建编辑对象
   bool              CreateEdit(const long chart,const int subwindow,CEdit &object,const string text,const uint x,const uint y,const uint x_size,const uint y_size);

   //--- 事件功能
   void              LotsEndEdit(void);               // 编辑地块大小

   //--- 当前值的变量
   double            cur_lot;                         // 下一个订单的批量

   void              BuyClick();                      // 点击购买按钮
   void              SellClick();                     // 点击销售按钮
   void              CloseClick();                    // 点击关闭按钮 

public:
                     CTradePanel(void){};
                    ~CTradePanel(void){};
   virtual bool      Create(const long chart,const string name,const int subwin=0,const int x1=20,const int y1=20,const int x2=320,const int y2=420);
   virtual bool      OnEvent(const int id,const long &lparam,const double &dparam,const string &sparam);
   virtual void      Destroy(const int reason);
  };

CTradePanel TradePanel;
//+------------------------------------------------------------------+
//| 专家初始化函数|
//+------------------------------------------------------------------+
int OnInit()
  {
//---
// 创建贸易面板
   TradePanel.Create(ChartID(),"Panelka",0,20,20,150,200);
//---
   return(INIT_SUCCEEDED);
  }
//+------------------------------------------------------------------+
//| 专家去初始化函数|
//+------------------------------------------------------------------+
void OnDeinit(const int reason)
  {
   TradePanel.Destroy(reason);
  }
//+------------------------------------------------------------------+
//||
//+------------------------------------------------------------------+
bool CTradePanel::CreateLabel(const long chart,const int subwindow,CLabel &object,const string text,const uint x,const uint y,label_align align)
  {
// 所有对象都必须有单独的名称
   string name=m_name+"Label"+(string)ObjectsTotal(chart,-1,OBJ_LABEL);
//--- 调用创建函数
   if(!object.Create(chart,name,subwindow,x,y,0,0))
     {
      return false;
     }
//--- 调整文本
   if(!object.Text(text))
     {
      return false;
     }
//--- 将文本对齐对话框的网格
   ObjectSetInteger(chart,object.Name(),OBJPROP_ANCHOR,(align==left ? ANCHOR_LEFT_UPPER :(align==right ? ANCHOR_RIGHT_UPPER : ANCHOR_UPPER)));
//--- 为控件添加对象
   if(!Add(object))
     {
      return false;
     }
   return true;
  }
//+------------------------------------------------------------------+
//||
//+------------------------------------------------------------------+
bool CTradePanel::CreateButton(const long chart,const int subwindow,CButton &object,const string text,const uint x,const uint y,const uint x_size,const uint y_size)
  {
// 所有对象都必须有单独的名称
   string name=m_name+"Button"+(string)ObjectsTotal(chart,-1,OBJ_BUTTON);
//--- 调用创建函数
   if(!object.Create(chart,name,subwindow,x,y,x+x_size,y+y_size))
     {
      return false;
     }
//--- 调整文本
   if(!object.Text(text))
     {
      return false;
     }
//--- 设置按钮标志为解锁
   object.Locking(false);
//--- 将按钮标志设置为未按下
   if(!object.Pressed(false))
     {
      return false;
     }
//--- 为控件添加对象
   if(!Add(object))
     {
      return false;
     }
   return true;
  }
//+------------------------------------------------------------------+
//||
//+------------------------------------------------------------------+
bool CTradePanel::CreateEdit(const long chart,const int subwindow,CEdit &object,const string text,const uint x,const uint y,const uint x_size,const uint y_size)
  {
// 所有对象都必须有单独的名称
   string name=m_name+"Edit"+(string)ObjectsTotal(chart,-1,OBJ_EDIT);
//--- 调用创建函数
   if(!object.Create(chart,name,subwindow,x,y,x+x_size,y+y_size))
     {
      return false;
     }
//--- 调整文本
   if(!object.Text(text))
     {
      return false;
     }
//--- 对齐编辑框中的文本
   if(!object.TextAlign(ALIGN_CENTER))
     {
      return false;
     }
//--- 将只读标记设为 false
   if(!object.ReadOnly(false))
     {
      return false;
     }
//--- 为控件添加对象
   if(!Add(object))
     {
      return false;
     }
   return true;
  }
//+------------------------------------------------------------------+
//||
//+------------------------------------------------------------------+
bool CTradePanel::Create(const long chart,const string name,const int subwin=0,const int x1=20,const int y1=20,const int x2=320,const int y2=420)
  {
// 首次调用父类的创建函数
   CAppDialog::Create(chart,name,subwin,x1,y1,x2,y2);

// 计算 BID 对象的坐标和大小

// 创建对象
   CreateLabel(chart,subwin,Lots_label,"LOT",55,5,0);
   CreateEdit(chart,subwin,Lots,"0.1",33,35,60,20);
   CreateButton(chart,subwin,BUY,"BUY",33,65,60,20);
   CreateButton(chart,subwin,SELL,"SELL",33,95,60,20);
   CreateButton(chart,subwin,CloseAll,"CLOSE",33,125,60,20);

   return(true);
  }
//+------------------------------------------------------------------+
//| 事件处理|
//+------------------------------------------------------------------+
EVENT_MAP_BEGIN(CTradePanel)
ON_EVENT(ON_END_EDIT,Lots,LotsEndEdit)
ON_EVENT(ON_CLICK,BUY,BuyClick)
ON_EVENT(ON_CLICK,SELL,SellClick)
ON_EVENT(ON_CLICK,CloseAll,CloseClick)
EVENT_MAP_END(CAppDialog)
//+------------------------------------------------------------------+
//| 点击购买按钮|
//+------------------------------------------------------------------+
void CTradePanel::BuyClick(void)
  {
   PutOrder(0,Ask);
  }
//+------------------------------------------------------------------+
//| 点击购买按钮|
//+------------------------------------------------------------------+
void CTradePanel::SellClick(void)
  {
   PutOrder(1,Bid);
  }
//+------------------------------------------------------------------+
//| 点击购买按钮|
//+------------------------------------------------------------------+
void CTradePanel::CloseClick(void)
  {
   CloseAll();
  }
//+------------------------------------------------------------------+
//| 编辑后读取地段值|
//+------------------------------------------------------------------+
void CTradePanel::LotsEndEdit(void)
  {
//--- 读取地段值并将其标准化
   cur_lot=NormalizeDouble(StringToDouble(Lots.Text()),2);
  }
//+------------------------------------------------------------------+
//| 应用程序去初始化功能
//+------------------------------------------------------------------+
void CTradePanel::Destroy(const int reason)
  {
   CAppDialog::Destroy(reason);
   return;
  }
//+------------------------------------------------------------------+
//| 设置订单|
//+------------------------------------------------------------------+
void PutOrder(int type,double price)
  {
   int r=0;
   color clr=Green;
   double sl=0,tp=0;

   if(type==1 || type==3 || type==5)
     {
      clr=Red;
      if(StopLoss>0)   sl=NormalizeDouble(price+StopLoss*Point,Digits);
      if(TakeProfit>0) tp=NormalizeDouble(price-TakeProfit*Point,Digits);
     }

   if(type==0 || type==2 || type==4)
     {
      clr=Blue;
      if(StopLoss>0)   sl=NormalizeDouble(price-StopLoss*Point,Digits);
      if(TakeProfit>0) tp=NormalizeDouble(price+TakeProfit*Point,Digits);
     }

   r=OrderSend(NULL,type,Lot,NormalizeDouble(price,Digits),Slip,sl,tp,"",Magic,0,clr);
   return;
  }
//+------------------------------------------------------------------+
//| 按订单类型关闭仓位|
//+------------------------------------------------------------------+
void CloseAll(int ot=-1)
  {
   bool cl;
   for(int i=OrdersTotal()-1;i>=0;i--)
     {
      if(OrderSelect(i,SELECT_BY_POS,MODE_TRADES))
        {
         if(OrderSymbol()==Symbol() && OrderMagicNumber()==Magic)
           {
            if(OrderType()==0 && (ot==0 || ot==-1))
              {
               RefreshRates();
               cl=OrderClose(OrderTicket(),OrderLots(),NormalizeDouble(Bid,Digits),Slip,White);
              }
            if(OrderType()==1 && (ot==1 || ot==-1))
              {
               RefreshRates();
               cl=OrderClose(OrderTicket(),OrderLots(),NormalizeDouble(Ask,Digits),Slip,White);
              }
           }
        }
     }
  }
//+------------------------------------------------------------------+
//| 专家勾选功能|
//+------------------------------------------------------------------+
void OnTick()
  {
//---

  }
//+------------------------------------------------------------------+
//| 图表事件函数|
//+------------------------------------------------------------------+
void OnChartEvent(const int id,
                  const long &lparam,
                  const double &dparam,
                  const string &sparam)
  {
//---
   TradePanel.OnEvent(id,lparam,dparam,sparam);
  }
//+------------------------------------------------------------------+
 
Andrew Kornishkin:

德米特里,今天我开始按照你的教程在 µl 4 上制作一个面板。几乎一切正常,但当点击面板或任何按钮时,却只能打开 "购买"。这是什么原因呢?

晚安,安德鲁。
你在课程描述中做的一切都很正确。你唯一的错误是在创建 交易面板类后 的 OnInit 函数中没有使用 Run 函数开始执行。

int OnInit()
  {
//---
// 创建贸易面板
   TradePanel.Create(ChartID(),"Panelka",0,20,20,150,200);
   TradePanel.Run();
//---
   return(INIT_SUCCEEDED);
  }

谢谢、

德米特里

 
Dmitriy Gizlyk:

晚安,安德烈。
你在类描述中做的一切都很正确。您唯一的错误是,在创建 交易面板类后 的 OnInit 函数中,您没有使用 Run 函数开始执行。

再见、

德米特里

谢谢你,德米特里!
成功了!
 
我下载了您的交易面板到 metatrader,但它不能用。这太糟糕了。
 
19681:
我将您的交易面板下载到了 metatrader 上,但它不起作用。真遗憾。
它是如何表现出来的?
为了使面板和其他交易程序一样正常工作,必须在终端中激活自动交易功能。
 
Dmitriy Gizlyk:
它的表现形式是什么? 要使面板发挥作用,就像其他交易程序一样,必须在终端中激活自动交易功能。
自动交易当然已启用。它表现为按钮不起作用(当您点击卖出或买入时,会出现 "未结买入订单错误")。
 
19681:
自动交易当然已启用。它表现为按钮不起作用(点击卖出或买入时显示 "未结买入订单错误")。
检查是否允许在符号上进行交易?由于近期发生的事件(英国脱欧),一些经纪商暂时限制了交易操作