Publisher





//+------------------------------------------------------------------+
//|                                                    Publisher.mq4 |
//|                                                       Greatshore |
//|                                               greatshore@live.cn |
//+------------------------------------------------------------------+
#property copyright "Greatshore"
#property link      "greatshore@live.cn"

#define GVARUP        "Publisher_UpdateTime"        // ¸üÐÂʱ¼äÈ«¾Ö±äÁ¿Ãû
#define GVARHASH      "Publisher_LastOrdersHash"    // ÉÏÒ»´Î³Ö²ÖµÄHash
#define DATAPATH      "Publisher\\"                 // Êý¾ÝÎļþĿ¼
#define VARPREFIX     "<!!-"                        // Ìæ»»±äÁ¿Ç°×º
#define VARSUFFIX     "--->"                        // Ìæ»»±äÁ¿ºó׺
#define REALSTR       "$"                           // ÏÔʾÕæʵֵ±ê¼Ç
#define DAYSECOND     86400                         // ÿÌì¶àÉÙÃë
#define ORDERPART     7                             // ÿ¸ö³Ö²ÖÏîÄ¿Êý

//---- input parameters
extern int     UpdatePeriod   = 15;                          // ¸üÐÂÖÜÆÚ£¬·ÖÖÓ£¬×îÉÙ5·ÖÖÓ£¬0±íʾ³Ö²ÖÓб仯¼´¸üÐÂ
extern bool    ShowPending    = true;                        // ÊÇ·ñÏÔʾ¹Òµ¥ÐÅÏ¢
extern int     HistoryNum     = 1;                           // ÀúÊ·½»Ò×µ¥ÖÜÆÚÊýÄ¿
extern int     HistoryPeriod  = 2;                           // ÀúÊ·½»Ò×µ¥ÖÜÆÚµ¥Î»£¬0-¸ö£¬1-Ìì, 2-ÖÜ£¬3-ÔÂ
extern int     TZOffset       = 6;                           // ·þÎñÆ÷ʱÇø»»Ëã
extern string  TZComment      = "Beijing Time:";             // ʱ¼ä±ê×¢
extern string  FTPPath        = "/forexbot";                 // ÉÏ´«µ½·þÎñÆ÷µÄĿ¼
extern string  WebFileName    = "state.htm";                 // ÉÏ´«µ½·þÎñÆ÷µÄÎļþÃû
extern string  TemplateName   = "Publisher.template.htm";    // ·¢²¼Ò³ÃæʹÓõÄÄ£°æÎļþÃû
extern string  ShowAccount    = "$";                         // ÏÔʾµÄÕË»§ºÅ£¬$±íʾʵ¼ÊÕË»§
extern string  ShowName       = "$";                         // ÏÔʾµÄÕË»§Ãû£¬$±íʾʵ¼ÊÕË»§Ãû
extern string  ShowBroker     = "$";                         // ÏÔʾµÄ¹«Ë¾Ãû£¬$±íʾʵ¼Ê¹«Ë¾Ãû
extern bool    ShowTicket     = true;                        // ÊÇ·ñÏÔʾ¶©µ¥ºÅ
extern bool    ShowOpenTime   = true;                        // ÊÇ·ñÏÔʾ¿ª²Öʱ¼ä
extern bool    ShowSize       = true;                        // ÊÇ·ñÏÔʾÊÖÊý
extern bool    ShowTPSL       = true;                        // ÊÇ·ñÏÔʾ»ñÀûÖ¹Ëð¼Û
extern bool    ShowSwap       = true;                        // ÊÇ·ñÏÔʾ¹ýÒ¹ÀûÏ¢
extern int     ShowProfitType = 2;                           // ÏÔʾ»ñÀû·½Ê½£º0-²»ÏÔʾ£¬1-µãÊý£¬2-¼ÛÖµ
extern bool    ShowComment    = false;                       // ÊÇ·ñÏÔʾעÊÍÏî
extern bool    ShowEquity     = true;                        // ÊÇ·ñÏÔʾÕË»§¾»Öµ
extern bool    ShowFreeMargin = true;                        // ÊÇ·ñÏÔʾ×ÔÓɱ£Ö¤½ðÊý
extern string  HiddenText     = "---";                       // Òþ²ØÖµÏÔʾ×Ö·û

string OpStr[] = {"buy", "sell", "buy limit", "sell limit", "buy stop", "sell stop"};

//+------------------------------------------------------------------+
//| expert initialization function                                   |
//+------------------------------------------------------------------+
int init()
{
  if (!ShowSize) // Èç¹û²»ÏÔʾ³Ö²ÖÊÖÊý£¬Ôò¸ôÒ¹ÀûÏ¢ºÍ»ñÀû¶¼²»ÄÜÏÔʾ
  {
    ShowSwap = false;
    if (ShowProfitType == 2)
      ShowProfitType = 1;
  }
  
  if ((UpdatePeriod < 5) && (UpdatePeriod > 0))
    UpdatePeriod = 5;

  return(0);
}

//+------------------------------------------------------------------+
//| expert deinitialization function                                 |
//+------------------------------------------------------------------+
int deinit()
{
  GlobalVariableDel(GVARUP);
  GlobalVariableDel(GVARHASH);

  return(0);
}

//+------------------------------------------------------------------+
//| expert start function                                            |
//+------------------------------------------------------------------+
int start()
{
  datetime LastUpdate, CurrentTime;
  bool NeedUpdate;
  
  CurrentTime = TimeCurrent();
  LastUpdate  = GlobalVariableGet(GVARUP);
  if (UpdatePeriod == 0)
    NeedUpdate = CheckOrderChange();
  else
    NeedUpdate = (CurrentTime - LastUpdate) / 60 >= UpdatePeriod;
  if (NeedUpdate)
  {
    GlobalVariableSet(GVARUP, CurrentTime);
    GeneratePage(DATAPATH + WebFileName);
    SendFTP(DATAPATH + WebFileName, FTPPath);
    FileDelete(DATAPATH + WebFileName);
  }
  
  return(0);
}

//+------------------------------------------------------------------+

// ===== Éú³É³Ö²Ö±¨¸æÒ³Ãæ =====
void GeneratePage(string FileName)
{
  int fin, fout, i, j;
  string linestr;
  
  fin  = FileOpen(DATAPATH + TemplateName, FILE_READ  | FILE_BIN);
  if (fin < 0)
    Print("Error in reading template file.");
  else
  {
    fout = FileOpen(DATAPATH + WebFileName,  FILE_WRITE | FILE_CSV, ' ');
    while (!FileIsEnding(fin))
    {
      linestr = GetOneLine(fin);
      if (StringLen(linestr) > 0)
      {
        i = StringFind(linestr, VARPREFIX);
        if (i >= 0)
          ReplaceVarStr(fout, linestr, i);
        else
          FileWrite(fout, linestr);
      }
    }
    FileClose(fin);
    FileClose(fout);
  }  
}

// ===== ´ÓÎļþÖжÁÈ¡Ò»ÐÐ =====
string GetOneLine(int InFile)
{
  int i, j;
  string ret, char;
  
  ret = "";
  while (!FileIsEnding(InFile))
  {
    char = FileReadString(InFile, 1);
    if ((char == "\r") || (char == "\n"))
      break;
    else
      ret = ret + char;
  }
  return(ret);
}

// ===== Ìæ»»±äÁ¿×Ö·û´®µÄÄÚÈÝ =====
void ReplaceVarStr(int OutFile, string linestr, int start)
{
  string VarName, LeftStr, RightStr, MidStr;
  int end, i;
  
  end = StringFind(linestr, VARSUFFIX, start);
  i = start + StringLen(VARPREFIX);
  if (start > 0)
    LeftStr  = StringSubstr(linestr, 0, start);
  RightStr = StringSubstr(linestr, end + StringLen(VARSUFFIX));
  MidStr   = "";
  VarName  = StringSubstr(linestr, i, end - i);
  if (VarName == "ACCOUNTNUM")         // ÕË»§ºÅÂë
  {    
    if (ShowAccount == REALSTR)
      MidStr = AccountNumber();
    else
      MidStr = ShowAccount;
  }
  else if (VarName == "ACCOUNTNAME")   // ÕË»§Ãû³Æ
  {
    if (ShowName == REALSTR)
      MidStr = AccountName();
    else
      MidStr = ShowName;
  }
  else if (VarName == "BROKER")        // ¹«Ë¾Ãû
  {
    if (ShowBroker == REALSTR)
      MidStr = AccountCompany();
    else
      MidStr = ShowBroker;
  }
  else if (VarName == "CURRENCY")      // ÕË»§»õ±Ò
    MidStr = AccountCurrency();
  else if (VarName == "EQUITY")        // ÕË»§¾»Öµ
  {
    if (ShowEquity)
      MidStr = DoubleToStr(AccountEquity(), 2);
    else
      MidStr = HiddenText;
  }
  else if (VarName == "FREEMARGIN")    // ¿ÉÓñ£Ö¤½ð
  {
    if (ShowFreeMargin)
      MidStr = DoubleToStr(AccountFreeMargin(), 2);
    else
      MidStr = HiddenText;
  }
  else if (VarName == "UPDATETIME")    // ¸üÐÂʱ¼ä
  {
    MidStr = TimeToStr(TimeCurrent());
    if ((TZOffset != 0) && (StringLen(TZComment) > 0))
    MidStr = MidStr + " [" + TZComment +  TimeToStr(TimeCurrent() + TZOffset * 3600) + "]";
  }
  else if (VarName == "HISTORYPERIOD")  // ÀúÊ·µ¥ÖÜÆÚ
  {
    if (HistoryNum > 0)
    {
      MidStr = "    last " + HistoryNum;
      switch (HistoryPeriod)
      {
        case 0 : MidStr = MidStr + " order"; break;
        case 1 : MidStr = MidStr + " day"; break;
        case 2 : MidStr = MidStr + " week"; break;
        case 3 : MidStr = MidStr + " month";
      }
      if (HistoryNum > 1) 
        MidStr = MidStr + "s";
    }
    else
      MidStr = "";    
  }
  else if (VarName == "HOLDINGORDERS")    // ³Ö²ÖÁбí
    WriteHoldingOrders(OutFile);
  else if ((VarName == "PENDINGORDERS") && ShowPending)    // ¹Òµ¥Áбí
    WritePendingOrders(OutFile);
  else if ((VarName == "CLOSEDORDERS") && (HistoryNum > 0))    // ÀúÊ·½»Ò×µ¥Áбí
    WriteClosedOrders(OutFile);
  else
    MidStr = HiddenText;
  
  FileWrite(OutFile, LeftStr+ MidStr + RightStr);
}

// ===== дÈë³Ö²ÖÁбí =====
void WriteHoldingOrders(int OutFile)
{
  int i, c, op;
  string symb;
  
  for (i = 0, c = 0; i < OrdersTotal(); i++)
  {
    OrderSelect(i, SELECT_BY_POS);
    op = OrderType();
    if (op < 2)
    {
      symb = OrderSymbol();
      c++;
      WriteLeftColums(OutFile, c, op, symb, MarketInfo(symb, MODE_DIGITS));
      WriteSwapProfit(OutFile, op, symb);
      WriteComment(OutFile);
      FileWrite(OutFile, "</tr>");
    }
  }
}

// ===== дÈë¹Òµ¥Áбí =====
void WritePendingOrders(int OutFile)
{
  int i, c, op;
  string symb, str = "";
  datetime exp;
  
  for (i = 0, c = 0; i < OrdersTotal(); i++)
  {
    OrderSelect(i, SELECT_BY_POS);
    op = OrderType();
    if (op > 1)
    {
      symb = OrderSymbol();
      c++;
      WriteLeftColums(OutFile, c, op, symb, MarketInfo(symb, MODE_DIGITS));
      exp = OrderExpiration();  // ¹ýÆÚʱ¼ä
      if (exp > 0)
        str = TimeToStr(exp);
      FileWrite(OutFile, "<td class=msdate nowrap>" + str + "</td>");
      WriteComment(OutFile);
      FileWrite(OutFile, "</tr>");
    }
  }
}

// ===== дÈëÀúÊ·½»Ò×µ¥ =====
void WriteClosedOrders(int OutFile)
{
  int i, c, end, op, d;
  string symb, str = "";
  datetime StartTime, OpenTime;

  // ¼ÆËãÊä³ö¶àÉÙÌõÀúÊ·¼Ç¼  
  if (HistoryPeriod == 0)
    end = OrdersHistoryTotal() - HistoryNum;
  else
  {
    end = 0;
    StartTime = GetStartTime(TimeCurrent());
  }
    
  for (i = OrdersHistoryTotal() - 1, c = 0; i >= 0; i--)
  {
    OrderSelect(i, SELECT_BY_POS, MODE_HISTORY);
    OpenTime = OrderOpenTime();
    if ((HistoryPeriod != 0) && (OpenTime < StartTime))
      break;
      
    op = OrderType();
    if (op < 2)
    {
      c++;
      symb = OrderSymbol();
      d = MarketInfo(symb, MODE_DIGITS);
      WriteLeftColums(OutFile, c, op, symb, d);
      // ƽ²Öʱ¼ä¼°Æ½²Ö¼Û
      FileWrite(OutFile, "<td class=msdate nowrap>" + TimeToStr(OrderCloseTime()) + "</td>");
      FileWrite(OutFile, "<td>" + DoubleToStr(OrderClosePrice(), d) + "</td>");

      WriteSwapProfit(OutFile, op, symb);
      WriteComment(OutFile);
      FileWrite(OutFile, "</tr>");
    }
  }
}

// ===== дÈëÇ°°ë²¿·Ö =====
void WriteLeftColums(int OutFile, int c, int op, string symb, int d)
{
  string str, str2;
  int i, p, cl;
  double SL, TP;

  // µÚÒ»ÐУ¬Ðб³¾°É«
  if (c % 2 == 1)
    str = ">";
  else
    str = " bgcolor=#E0E0E0>";
  FileWrite(OutFile, "<tr align=right" + str);
      
  // Ticket
  if (ShowTicket)
    str = OrderTicket();
  else
    str = HiddenText;
  FileWrite(OutFile, "<td>" + str + "</td>");
     
  // ½»Ò×»õ±Ò¶ÔºÍ¿ª²Ö·½Ïò
  FileWrite(OutFile, "<td>" + symb + "</td>");
  FileWrite(OutFile, "<td>" + OpStr[op] + "</td>");

  // ¿ª²ÖÊÖÊý
  if (ShowSize)
    str = DoubleToStr(OrderLots(), 2);
  else
    str = HiddenText;
  FileWrite(OutFile, "<td class=mspt>" + str + "</td>");

  // ¿ª²Öʱ¼ä
  if (ShowOpenTime)
    str = TimeToStr(OrderOpenTime());
  else
    str = HiddenText;
  FileWrite(OutFile, "<td class=msdate nowrap>" + str + "</td>");

  // ¿ª²Ö¼Û
  FileWrite(OutFile, "<td>" + DoubleToStr(OrderOpenPrice(), d) + "</td>");

  // »ñÀûÖ¹Ëð¼Û
  if (ShowTPSL)
  {
    SL = OrderStopLoss();
    TP = OrderTakeProfit();
    if (OrderCloseTime() > 0)  // ÒѾ­Æ½²ÖµÄµ¥×Ó
    {
      p  = MathPow(10, d);
      cl = OrderClosePrice() * p;
      if (cl == SL * p) // Ö¹Ëðµ¥
        str = " bgcolor=\"#FFA0A0\">";
      else
        str = ">";
      if (cl == TP * p) // Ö¹Ó®µ¥
        str2 = " bgcolor=\"#60F060\">";
      else
        str2 = ">";
    }
    else
    {
      str  = ">";
      str2 = ">";
    }  
    str  = str  + DoubleToStr(SL, d);
    str2 = str2 + DoubleToStr(TP, d);
  }
  else
  {
    str  = ">" + HiddenText;
    str2 = ">" + HiddenText;
  }
  FileWrite(OutFile, "<td" + str  + "</td>");
  FileWrite(OutFile, "<td" + str2 + "</td>");
}

// ===== дÈëÀûÏ¢ºÍ»ñÀû =====
void WriteSwapProfit(int OutFile, int op, string symb)
{
  double cp;
  string str;
  
  // ¸ôÒ¹ÀûÏ¢
  if (ShowSwap)
    str = DoubleToStr(OrderSwap(), 2);
  else
    str = HiddenText;
  FileWrite(OutFile, "<td class=mspt>" + str + "</td>");
  
  // Ȗ˞
  switch (ShowProfitType)
  {
    case 0 :
         str =  ">" + HiddenText;
         break;
    case 1 :
         if (op == OP_BUY)
           cp = MarketInfo(symb, MODE_BID);
         else
           cp = MarketInfo(symb, MODE_ASK);
         str = ">" + DoubleToStr((cp - OrderOpenPrice()) / MarketInfo(symb, MODE_POINT), 0) + "p";
         break;
    case 2 :
         str = " class=mspt>" + DoubleToStr(OrderProfit(), 2);
  }
  FileWrite(OutFile, "<td" + str + "</td>");
}

// ===== дÈë×¢ÊÍ =====
void WriteComment(int OutFile)
{
  string str;

  str = OrderComment();
  if (!ShowComment && (StringLen(str) > 0))
    str = HiddenText;
  FileWrite(OutFile, "<td>" + str  + "</td>");
}

// ===== ¼ì²é³Ö²ÖÓÐûÓб仯 =====
bool CheckOrderChange()
{
  int LastOrdersHash, CurrnetOrdersHash;
  
  LastOrdersHash    = GlobalVariableGet(GVARHASH);
  CurrnetOrdersHash = GetOrdersHash(OrdersTotal());
  if (CurrnetOrdersHash != LastOrdersHash)
  {
    GlobalVariableSet(GVARHASH, CurrnetOrdersHash);
    return(true);
  }
  else
    return(false);
}

// ===== ¼ÆË㵱ǰ³Ö²ÖµÄHash =====
int GetOrdersHash(int OrdersCount)
{
  int Orders[][ORDERPART], i, j, k, Hash = 0;
  string OrderSymb, str;

  ArrayResize(Orders, OrdersCount);
  
  // ½«³Ö²Öת»¯³ÉÕûÊý
  for (i = 0; i < OrdersCount; i++)
  {
    OrderSelect(i, SELECT_BY_POS);
    OrderSymb = OrderSymbol();
    k = MarketInfo(OrderSymb, MODE_POINT);
    
    Orders[i][0] = OrderTicket();
    Orders[i][1] = SymbolToInt(OrderSymb);
    Orders[i][2] = OrderType() << 24 + OrderLots() * 100;
    Orders[i][3] = OrderOpenPrice() / k;
    Orders[i][4] = OrderTakeProfit() / k;
    Orders[i][5] = OrderStopLoss() / k;
    Orders[i][6] = OrderSwap() * 100;
  }
  if (OrdersCount > 0)
  {
    ArraySort(Orders);
    // ¼ÆËãHashÖµ
    for (i = 0; i < OrdersCount; i++)
      for (j = 0; j < ORDERPART; j++)
        for (k = 3; k >= 0; k--)
          Hash += (Hash << 5) + ((Orders[i][j] >> (k * 8)) & 0xFF);
  }
  
  return(Hash);
}

// ==== ¼ÆËãÀúÊ·³Ö²ÖÆðʼʱ¼ä ====
datetime GetStartTime(datetime EndTime)
{
  datetime StartTime;
  int y, m, d;
  
  switch (HistoryPeriod)
  {
    case 1 :
        StartTime = EndTime - (HistoryNum - 1) * DAYSECOND;
        break;
    case 2 :
        StartTime = EndTime - HistoryNum * 7 * DAYSECOND;
        while (TimeDayOfWeek(StartTime) > 0)
          StartTime += DAYSECOND;
        break;
    case 3 :
        StartTime = EndTime - (HistoryNum - 1) * 30 * DAYSECOND;
  }
  y = TimeYear(StartTime);
  m = TimeMonth(StartTime);
  if (HistoryPeriod == 3)
    d = 1;
  else
    d = TimeDay(StartTime);
  StartTime = StrToTime(y + "." + m + "." + d);

  return(StartTime);
}

// ===== °Ñ»õ±Ò¶Ôת»»³ÉÕûÐÎ =====
int SymbolToInt(string Symb)
{
  int i, r;
  
  for (r = 0, i = 0; i < StringLen(Symb); i++)
    r += r << 5 + StringGetChar(Symb, i);
  return(r);
}





Sample





Analysis



Market Information Used:



Indicator Curves created:


Indicators Used:



Custom Indicators Used:

Order Management characteristics:
Checks for the total of open orders
Checks for the total of closed orders

Other Features:


Uses files from the file system
It writes information to file
It reads information from a file