TrailingFiftyFifty

Download script
Author: I_D
TrailingFiftyFifty

This script is designed to automate the management of open trades by dynamically adjusting your "Stop Loss" (the price at which a trade automatically closes to prevent further loss). It uses a logic called "Half-and-Half" trailing, which calculates and moves the stop loss based on a specific percentage of the distance between your entry price and the current market price.

Core Logic Overview

Instead of moving the stop loss by a fixed amount (like 10 pips), this script looks at the progress of the trade. It evaluates the distance between where you entered the trade and where the price is currently moving, then calculates a new stop loss position based on a "coefficient" (a percentage) provided by the user.

How it Works

  • Time-Based Execution: The script does not move the stop loss every second. It waits for a specific time frame to complete (e.g., every hour or every 15 minutes). This ensures that the movement is based on "confirmed" price action rather than temporary market fluctuations.
  • The Calculation: When a new candle opens, the script calculates the distance from the current price to either your entry price or your existing stop loss (depending on your settings). It then takes a fraction of that distance—determined by your coefficient—and moves the stop loss accordingly.
    • Example: If your trade is in profit and you set a 0.5 coefficient, the script will move your stop loss to the halfway point between the current price and your starting point. As the price moves further into profit, the "halfway point" also moves forward, effectively locking in gains.
  • Smart Protection: The script is programmed to be cautious. It will only move the stop loss if the new position actually improves your situation (i.e., it moves the stop closer to the profit). It will not move the stop loss in a way that increases your risk.
  • Loss Zone Handling: There is an optional setting that allows the script to begin moving the stop loss even while the trade is still in a losing position (between the entry price and the initial stop loss). If turned off, the script primarily focuses on trailing profits.

Key Parameters Explained

  • Ticket Number: Allows you to target one specific open trade for this logic to apply to.
  • Time Frame: Sets how often the calculation happens (e.g., every 60 minutes).
  • Coefficient: Determines the "aggressiveness" of the trail. A higher number moves the stop loss closer to the current price more quickly; a lower number keeps it further back.
  • Loss Trailing: A simple toggle to decide if you want the script to manage the stop loss while the trade is underwater or only when it moves into profit.

In summary, this tool acts as an automated safety net that "follows" the market price, moving your exit point forward as the trade succeeds, ensuring that a winning trade doesn't turn into a losing one due to a sudden market reversal.

Orders Execution
It can change open orders parameters, due to possible stepping strategy
13 Views
0 Downloads
0 Favorites
TrailingFiftyFifty
//+------------------------------------------------------------------+
//|                                           TrailingFiftyFifty.mq4 |
//|                                                              I_D |
//|                                            http://www.mymmk.com/ |
//+------------------------------------------------------------------+
#property copyright "I_D"
#property link      "http://www.mymmk.com/ Ñîôò äëÿ óïðàâëåíèÿ êàïèòàëîì"

extern   int      iTicket;             // óíèêàëüíûé íîìåð (òèêåò) îòêðûòîé ïîçèöèè
extern   int      iTmFrme = 60;        // ïåðèîä ÷àðòà, ïî áàðàì êîòîðîãî ïðîèñõîäèò ïîäæàòèå
extern   double   dCoeff = 0.5;        // "êîýôôèöèåíò ïîäæàòèÿ", â % îò 0.01 äî 1 
extern   bool     bTrlinloss = false;  // ñëåäóåò ëè òðàëèòü íà ó÷àñòêå ëîññîâ (ìåæäó êóðñîì ñòîïëîññà è îòêðûòèÿ)

static datetime sdtPrevtime = 0;
 
//+------------------------------------------------------------------+
//| ÒÐÅÉËÈÍÃ "ÏÎËÎÂÈÍßÙÈÉ"                                           |
//| Ïî çàêðûòèè î÷åðåäíîãî ïåðèîäà (áàðà) ïîäòÿãèâàåì ñòîïëîññ íà    |
//| ïîëîâèíó (íî ìîæíî è ëþáîé èíîé êîýôôèöèåíò) äèñòàíöèè, ïðîé-    |
//| äåííîé êóðñîì (ò.å., íàïðèìåð, ïî çàêðûòèè ñóòîê ïðîôèò +55 ï. - |
//| ñòîïëîññ ïåðåíîñèì â 55/2=27 ï. Åñëè ïî çàêðûòèè ñëåä.           |
//| ñóòîê ïðîôèò äîñòèã, äîïóñòèì, +80 ï., òî ñòîïëîññ ïåðåíîñèì íà  |
//| ïîëîâèíó (íàïð.) ðàññòîÿíèÿ ìåæäó òåê. ñòîïëîññîì è êóðñîì íà    |
//| çàêðûòèè áàðà - 27 + (80-27)/2 = 27 + 53/2 = 27 + 26 = 53 ï.     |
//| Ïðè çàïóñêå ýêñïåðòà åìó íåîáõîäèìî óêàçàòü óíèêàëüíûé íîìåð     |
//| (òèêåò) îòêðûòîé ïîçèöèè (iTicket); iTmFrme - òàéìôðåéì (â       |
//| ìèíóòàõ, öèôðàìè dCoeff - "êîýôôèöèåíò ïîäæàòèÿ", â % îò 0.01 äî |
//| 1 (â ïîñëåäíåì ñëó÷àå ñòîïëîññ áóäåò ïåðåíåñåí (åñëè ïîëó÷èòñÿ)  |
//| âïëîòíóþ ê òåê. êóðñó è ïîçèöèÿ, ñêîðåå âñåãî, ñðàçó æå          |
//| çàêðîåòñÿ) bTrlinloss - ñòîèò ëè òðàëèòü íà ëîññîâîì ó÷àñòêå -   |
//| åñëè äà, òî ïî çàêðûòèþ î÷åðåäíîãî áàðà ðàññòîÿíèå ìåæäó         |
//| ñòîïëîññîì (â ò.÷. "äî" áåçóáûòêà) è òåêóùèì êóðñîì áóäåò        |
//| ñîêðàùàòüñÿ â dCoeff ðàç ÷òîáû ïîñë. âàðèàíò ðàáîòàë, îáÿçàòåëüíî| 
//| äîëæåí áûòü îïðåäåë¸í  còîïëîññ (íå ðàâåí 0)                     |
//+------------------------------------------------------------------+

//+------------------------------------------------------------------+
//| expert initialization function                                   |
//+------------------------------------------------------------------+
int init()
  {    
   return(0);
  }
  
//+------------------------------------------------------------------+
//| expert deinitialization function                                 |
//+------------------------------------------------------------------+
int deinit()
  {
   return(0);
  }
  
//+------------------------------------------------------------------+
//| expert start function                                            |
//+------------------------------------------------------------------+
int start()
  {
   TrailingFiftyFifty(iTicket,iTmFrme,dCoeff,bTrlinloss);
   return(0);
  }
//+------------------------------------------------------------------+

void TrailingFiftyFifty(int iTicket,int iTmFrme,double dCoeff,bool bTrlinloss)
   { 
   // àêòèâèðóåì òðåéëèíã òîëüêî ïî çàêðûòèè áàðà
   if (sdtPrevtime == iTime(Symbol(),iTmFrme,0)) return(0);
   else
      {
      sdtPrevtime = iTime(Symbol(),iTmFrme,0);             
      
      // ïðîâåðÿåì ïåðåäàííûå çíà÷åíèÿ
      if ((iTicket==0) || (!OrderSelect(iTicket,SELECT_BY_TICKET)) || 
      ((iTmFrme!=1) && (iTmFrme!=5) && (iTmFrme!=15) && (iTmFrme!=30) && (iTmFrme!=60) && (iTmFrme!=240) && 
      (iTmFrme!=1440) && (iTmFrme!=10080) && (iTmFrme!=43200)) || (dCoeff<0.01) || (dCoeff>1.0))
         {
         Print("Òðåéëèíã ôóíêöèåé TrailingFiftyFifty() íåâîçìîæåí èç-çà íåêîððåêòíîñòè çíà÷åíèé ïåðåäàííûõ åé àðãóìåíòîâ.");
         return(0);
         }
         
      // íà÷èíàåì òðàëèòü - ñ ïåðâîãî áàðà ïîñëå îòêðûâàþùåãî (èíà÷å ïðè bTrlinloss ñðàçó æå ïîñëå îòêðûòèÿ 
      // ïîçèöèè ñòîïëîññ áóäåò ïåðåíåñåí íà ïîëîâèíó ðàññòîÿíèÿ ìåæäó ñòîïëîññîì è êóðñîì îòêðûòèÿ)
      // ò.å. ðàáîòàåì òîëüêî ïðè óñëîâèè, ÷òî ñ ìîìåíòà OrderOpenTime() ïðîøëî íå ìåíåå iTmFrme ìèíóò
      if (iTime(Symbol(),iTmFrme,0)>OrderOpenTime())
      {         
      
      double dBid = MarketInfo(Symbol(),MODE_BID);
      double dAsk = MarketInfo(Symbol(),MODE_ASK);
      double dNewSl;
      double dNexMove;     
      
      // äëÿ äëèííîé ïîçèöèè ïåðåíîñèì ñòîïëîññ íà dCoeff äèñòàíöèè îò êóðñà îòêðûòèÿ äî Bid íà ìîìåíò îòêðûòèÿ áàðà
      // (åñëè òàêîé ñòîïëîññ ëó÷øå èìåþùåãîñÿ è èçìåíÿåò ñòîïëîññ â ñòîðîíó ïðîôèòà)
      if (OrderType()==OP_BUY)
         {
         if ((bTrlinloss) && (OrderStopLoss()!=0))
            {
            dNexMove = NormalizeDouble(dCoeff*(dBid-OrderStopLoss()),Digits);
            dNewSl = NormalizeDouble(OrderStopLoss()+dNexMove,Digits);            
            }
         else
            {
            // åñëè ñòîïëîññ íèæå êóðñà îòêðûòèÿ, òî òðàëèì "îò êóðñà îòêðûòèÿ"
            if (OrderOpenPrice()>OrderStopLoss())
               {
               dNexMove = NormalizeDouble(dCoeff*(dBid-OrderOpenPrice()),Digits);                 
               //Print("dNexMove = ",dCoeff,"*(",dBid,"-",OrderOpenPrice(),")");
               dNewSl = NormalizeDouble(OrderOpenPrice()+dNexMove,Digits);
               //Print("dNewSl = ",OrderOpenPrice(),"+",dNexMove);
               }
         
            // åñëè ñòîïëîññ âûøå êóðñà îòêðûòèÿ, òðàëèì îò ñòîïëîññà
            if (OrderStopLoss()>=OrderOpenPrice())
               {
               dNexMove = NormalizeDouble(dCoeff*(dBid-OrderStopLoss()),Digits);
               dNewSl = NormalizeDouble(OrderStopLoss()+dNexMove,Digits);
               }                                      
            }
            
         // ñòîïëîññ ïåðåìåùàåì òîëüêî â ñëó÷àå, åñëè íîâûé ñòîïëîññ ëó÷øå òåêóùåãî è åñëè ñìåùåíèå - â ñòîðîíó ïðîôèòà
         // (ïðè ïåðâîì ïîäæàòèè, îò êóðñà îòêðûòèÿ, íîâûé ñòîïëîññ ìîæåò áûòü ëó÷øå èìåþùåãîñÿ, è â òî æå âðåìÿ íèæå 
         // êóðñà îòêðûòèÿ (åñëè dBid íèæå ïîñëåäíåãî) 
         if ((dNewSl>OrderStopLoss()) && (dNexMove>0) && ((dNewSl<Bid- MarketInfo(Symbol(),MODE_STOPLEVEL)*Point)))
            {
            if (!OrderModify(OrderTicket(),OrderOpenPrice(),dNewSl,OrderTakeProfit(),OrderExpiration(),Red))
            Print("Íå óäàëîñü ìîäèôèöèðîâàòü ñòîïëîññ îðäåðà ¹",OrderTicket(),". Îøèáêà: ",GetLastError());
            }
         }       
      
      // äåéñòâèÿ äëÿ êîðîòêîé ïîçèöèè   
      if (OrderType()==OP_SELL)
         {
         if ((bTrlinloss) && (OrderStopLoss()!=0))
            {
            dNexMove = NormalizeDouble(dCoeff*(OrderStopLoss()-(dAsk+MarketInfo(Symbol(),MODE_SPREAD)*Point)),Digits);
            dNewSl = NormalizeDouble(OrderStopLoss()-dNexMove,Digits);            
            }
         else
            {         
            // åñëè ñòîïëîññ âûøå êóðñà îòêðûòèÿ, òî òðàëèì "îò êóðñà îòêðûòèÿ"
            if (OrderOpenPrice()<OrderStopLoss())
               {
               dNexMove = NormalizeDouble(dCoeff*(OrderOpenPrice()-(dAsk+MarketInfo(Symbol(),MODE_SPREAD)*Point)),Digits);                 
               dNewSl = NormalizeDouble(OrderOpenPrice()-dNexMove,Digits);
               }
         
            // åñëè ñòîïëîññ íèæó êóðñà îòêðûòèÿ, òðàëèì îò ñòîïëîññà
            if (OrderStopLoss()<=OrderOpenPrice())
               {
               dNexMove = NormalizeDouble(dCoeff*(OrderStopLoss()-(dAsk+MarketInfo(Symbol(),MODE_SPREAD)*Point)),Digits);
               dNewSl = NormalizeDouble(OrderStopLoss()-dNexMove,Digits);
               }                  
            }
         
         // ñòîïëîññ ïåðåìåùàåì òîëüêî â ñëó÷àå, åñëè íîâûé ñòîïëîññ ëó÷øå òåêóùåãî è åñëè ñìåùåíèå - â ñòîðîíó ïðîôèòà
         if ((dNewSl<OrderStopLoss()) && (dNexMove>0) && (dNewSl>Ask+MarketInfo(Symbol(),MODE_STOPLEVEL)*Point))
            {
            if (!OrderModify(OrderTicket(),OrderOpenPrice(),dNewSl,OrderTakeProfit(),OrderExpiration(),Blue))
            Print("Íå óäàëîñü ìîäèôèöèðîâàòü ñòîïëîññ îðäåðà ¹",OrderTicket(),". Îøèáêà: ",GetLastError());
            }
         }               
      }
      }   
   }
//+------------------------------------------------------------------+

Comments