Two-Stage Modification of Opened Positions
Introduction
The article named "T.DeMark's Approach to Technical Analysis" contains the recommended coefficients of the correction length, particularly 0.382 and 0.618. Using these coefficients during positions opening, you can avoid the unnecessary situations of closing and re-opening of positions in situations close to the trend. The function works well, especially in the situation of divergence occurring.
This approach, provided the profit value is reset, helps to detect the appearance of a "favorable" trend. For example, as it is shown in Fig.1 and compared to Fig.2.
Function Algorithm
The first modification of the order is performed by the specified TrailingStop value, the subsequent ones set the StopLoss smaller than the possible correction level by 1 or 2 points (in this case, the correction coefficient = 0,382 "Coeff_"). Increase the value of TakeProfit on every step by, for example, a half of the TrailingStop value (you can choose another value, too!). The value of TakeProfit can be changed, as well. For this purpose, zero value of the extern double March = 0; operator should be set at the beginning of the program.
It would be wiser for traders who prefer the address analysis-support of program-specific actions to be performed directly while trading, to transfer the MagicNumber variable into the code of the Expert Advisor itself, where the position is opened. You can read more detailed information about the specific address support in the book by S. Kovalyov published on the MQL4.com website.
Let's examine the suggested code of the prospective function in EA and the comments on it in details:
//+------------------------------------------------------------------+ //| Two-stage variant of TrailingStop Modify_2step v5.mq4 | //| Orders modification: re-placing StopLoss and TakeProfit | //+------------------------------------------------------------------+ #property copyright "Copyright © 2008, GenKov" #property link Genkov@bk.ru //+------------------------------------------------------------------+ /* Magic=N
Magic=N - this operator should be inserted while position opening right after the condition compliance controlling operator in the program itself (Expert Advisor), and in the function! I couldn't create a universal modifier, maybe in view of market unpredictability, as it seems to me, so the function of tracking (movement of S/L and T/P) and position closing conditions should be written for every type of position opening condition (by Magic=N).
extern double March = 1; // step of increasing TakeProfit // step 0 doesn't increase T/P.
S/L must be smaller than TrailingStop by 1 point to bring the S/L onto a safe level at the very first triggering. In such a manner, we insure ourselves from possible losses (management of capital).
extern double StopLoss = 15; extern double TrailingStop = 16; extern double TakeProfit = 60; // fitting with the tester //+------------------------------------------------------------------+ //void TrailingStop() int start() { //----------------------------------------------------------------+ int point = MarketInfo(Symbol(),MODE_POINT); // Point size int StopLev= MarketInfo(Symbol(),MODE_STOPLEVEL); double half_Trail = MathRound(TrailingStop/2);//half TrailingStop double Step = March*half_Trail; //value of TakeProfit increase if (TrailingStop<0) return; { for (int i=0; i<OrdersTotal(); i++) { if (OrderSelect(i,SELECT_BY_POS,MODE_TRADES)==false) break; if (OrderSymbol()!=Symbol() || OrderMagicNumber()!=Magic) continue; if (OrderType()==OP_BUY) {
First stage of BUY position modification
if(OrderStopLoss()<OrderOpenPrice())//if S/L is less than the order open price { // and if the difference between the current price and the position opening price is greater than T/S if(Bid-OrderOpenPrice()>TrailingStop*Point) // && { // and if OrderStopLoss() is less than the difference between the current price and T/S if(OrderStopLoss()<Bid-TrailingStop*Point) { // calculate new T/P value double Now_T_P=(OrderTakeProfit()+Step*Point); { OrderModify(OrderTicket(),OrderOpenPrice(), OrderStopLoss()+TrailingStop*Point, OrderTakeProfit()+Step*Point,0,Aqua); // increasing T/P value return; } } } }
However, the following situation may occur: shifting TakeProfit becomes 2-3 points higher than the previously planned profit level, stops and starts to decrease slowly.
To avoid missing profits, let's enter the operator of situation controlling that will close the order on the planned profit level. If the price continues to grow, then the shifting of StopLoss and TakeProfit will continue.
if(Bid-OrderOpenPrice()>=TakeProfit*Point && (Pr_Op_1-Pr_Op_0)>2*Point) { // Print(" Bid= ",Bid," >= ",OrderTakeProfit()," Magic= ",Magic); OrderClose(OrderTicket(),Lots,Bid,2,Red); }
// Second stage of BUY position modification
if(OrderStopLoss()>=OrderOpenPrice()) // StopLoss is on a lossless level { // calculate correction coefficient double Coeff_up = NormalizeDouble((Bid-OrderOpenPrice())*0.382,Digits); // and if the differnece between the current and the open price of the position is greater than corr. coefficient if(Bid-OrderOpenPrice()>Coeff_up) { // calculate the value of new StopLoss with the margin of 2 points double New_S_Loss = Bid-Coeff_up-2*Point; // and if the value of new StopLoss is higer than the current one if(New_S_Loss-OrderStopLoss()>3*Point) { // move S/L and T/P OrderModify(OrderTicket(),OrderOpenPrice(), New_S_Loss,OrderTakeProfit()+Step*Point,0,Yellow); } // Print(" Bid-OrderOpenPrice()= ",Bid-OrderOpenPrice()); // Print(" 2 Coeff_up= ",Coeff_up," Order_S_Los= ",New_S_Loss," Bid= ",Bid); return; } } }
The approach to the short position is the same as described above, so there are less comments.
// ---------------------------- 1 stage of modification -----SELL-------------& else if(OrderType()==OP_SELL) { if(OrderStopLoss()>OrderOpenPrice())//if S/L is greater than order open price { if(OrderOpenPrice()-Ask>TrailingStop*Point && OrderStopLoss()>Ask+TrailingStop*Point) { OrderModify(OrderTicket(),OrderOpenPrice(), Ask+TrailingStop*Point,OrderTakeProfit()-Step*Point,0,SkyBlue); return; } } if(OrderOpenPrice()-Ask>=TakeProfit*Point && (Pr_Op_0-Pr_Op_1)>2*Point) { OrderClose(OrderTicket(),Lots,Bid,2,Red); } // ---------------------------- 2 stage of modification -----SELL-------------& if(OrderStopLoss()<=OrderOpenPrice()) // StopLoss is on a lossless level { // calculate correction coefficient double Coeff_down = NormalizeDouble((OrderOpenPrice()-Ask)*0.382,Digits); // and if the difference between the price of position opening and the current price is greater than corr. coefficient if(OrderOpenPrice()-Ask>Coeff_down) { // calculate the value of new StopLoss with the margin of 2 points New_S_Loss = Ask+Coeff_down+2*Point; // and if the value of new StopLoss is less than the current value if(New_S_Loss-OrderStopLoss()>3*Point) { // move S/L and T/P OrderModify(OrderTicket(),OrderOpenPrice(), New_S_Loss,OrderTakeProfit()-Step*Point,0,Khaki); return; } } } } } // -----------------------------------------------------------------------------------
To turn this EA into a function, it is necessary to comment-out the special int start() function located at the beginning of the program, and replace with uncommented description of the TrailingStop() function located at the beginning of the program. Uncomment the function call:
//TrailingStop();
at the end of the program.
If we add the block represented below, then we can check the function efficiency using it as an EA in the Tester.
// -------------------------------------------------------------------------------- double Macd_m15_0= iMACD(NULL,PERIOD_M15,12,26,9,PRICE_CLOSE,MODE_MAIN,0); double Macd_m15_1= iMACD(NULL,PERIOD_M15,12,26,9,PRICE_CLOSE,MODE_MAIN,1); if(OrdersTotal()<2) { if(Macd_m15_0<Macd_m15_1) { OrderSend(Symbol(),OP_SELL,0.1,Bid,3,Ask+StopLoss*Point,Bid-TakeProfit*Point,"",Magic,0,Red); } if(Macd_m15_0>Macd_m15_1) { OrderSend(Symbol(),OP_BUY,0.1,Ask,3,Bid-StopLoss*Point,Ask+TakeProfit*Point,"",Magic,0,Blue); } return(0); } // -------------------------------------------------------------------------------- // TrailingStop(); } return(0); } // --- end --- &
Now remove the detailed comments from the code text mentioned above and form it as an executing function: we will get the executable file that is recommended to be stored in the terminal_folder\experts\include directory with the .mqh extension or in the terminal_folder\libraries directory with the mq4 extension.
//+------------------------------------------------------------------+ //| Modify_2_Step v5.mq4 | //| Copyright © 2008, GenKov | //| Genkov@bk.ru | //+------------------------------------------------------------------+ #property copyright "Copyright © 2008, GenKov" #property link "Genkov@bk.ru" extern double March = 1; // the step of TakeProfit increase // "0" step doesn't increase T/P. // S/L must be less than TrailingStop by 1 point to bring the S/L // on a safe level in the time of the very first triggering extern double StopLoss = 15; extern double TrailingStop = 16; extern double Lots = 0.1; extern double TakeProfit = 60; // fitting with the tester void TrailingStop() { int Magic=3090; // number of condition that opens position int point = MarketInfo(Symbol(),MODE_POINT); // Point size int StopLev= MarketInfo(Symbol(),MODE_STOPLEVEL); double half_Trail = MathRound(TrailingStop/2);//half TrailingStop double Step = March*half_Trail; //TakeProfit-а increase size if (TrailingStop<0) return; { for (int i=0; i<OrdersTotal(); i++) {//1 +cycle by orders search if (OrderSelect(i,SELECT_BY_POS,MODE_TRADES)==false) break; if (OrderSymbol()!=Symbol() || OrderMagicNumber()!=Magic) continue; if (OrderType()==OP_BUY) { // --------------------------- 1 stage of modification -----BUY-------------& if(OrderStopLoss()<OrderOpenPrice())//if the S/L is less than the order open price { // and if the difference between the current and the open price is greater than T/S if(Bid-OrderOpenPrice()>TrailingStop*Point) // && { // and if OrderStopLoss() is less than the difference between current price andT/S if(OrderStopLoss()<Bid-TrailingStop*Point) { // calculate new T/P value double Now_T_P=(OrderTakeProfit()+Step*Point); { OrderModify(OrderTicket(),OrderOpenPrice(), OrderStopLoss()+TrailingStop*Point, OrderTakeProfit()+Step*Point,0,Aqua); // increase T/P value return; } } } } if(Bid-OrderOpenPrice()>=TakeProfit*Point) { OrderClose(OrderTicket(),Lots,Bid,2,Red); } //------------------------- 2 stage of modification -----BUY---------------& if(OrderStopLoss()>=OrderOpenPrice()) // StopLoss is on the lossless level { // calculate correction coefficient double Coeff_up = NormalizeDouble((Bid-OrderOpenPrice())*0.382,Digits); // and if the difference between the current and the position price is greater than correction coefficient if(Bid-OrderOpenPrice()>Coeff_up) { // clculate new StopLoss value with the margin of 6 points double New_S_Loss = Bid-Coeff_up-6*Point-StopLev*Point; // if the value of new StopLoss is greater than the current value if((New_S_Loss-OrderStopLoss())<2*Point) { // move S/L and T/P OrderModify(OrderTicket(),OrderOpenPrice(), OrderStopLoss(),OrderTakeProfit()+Step*Point/2,0,Yellow); } else { OrderModify(OrderTicket(),OrderOpenPrice(), New_S_Loss+1*Point,OrderTakeProfit()+Step*Point,0,Yellow); } return; } } } // ---------------------------- 1 stage of modification -----SELL-------------& else if(OrderType()==OP_SELL) { if(OrderStopLoss()>OrderOpenPrice())//if S/L is greater than the order open price { if(OrderOpenPrice()-Ask>TrailingStop*Point && OrderStopLoss()>Ask+TrailingStop*Point) { OrderModify(OrderTicket(),OrderOpenPrice(), Ask+TrailingStop*Point,OrderTakeProfit()-Step*Point,0,SkyBlue); return; } } if(OrderOpenPrice()-Ask>=TakeProfit*Point) { OrderClose(OrderTicket(),Lots,Bid,2,Red); } // ---------------------------- 2 stage of modification -----SELL-------------& if(OrderStopLoss()<=OrderOpenPrice()) // StopLoss is on the lossless level if(OrderOpenPrice()-Ask>=OrderTakeProfit()) OrderClose(OrderTicket(),Lots,Ask,2,Red); { // calculate correction coefficient double Coeff_down = NormalizeDouble((OrderOpenPrice()-Ask)*0.382,Digits); // and if the difference between the position open price and the current price is greater than corr. coefficient if(OrderOpenPrice()-Ask>Coeff_down) { // calculate the value of new StopLoss with the margin of 6 points New_S_Loss = Ask+Coeff_down+6*Point; // and if the value of new StopLoss is less than the current value if((OrderStopLoss()-New_S_Loss-StopLev*Point)>=10*Point) { // move S/L and T/P OrderModify(OrderTicket(),OrderOpenPrice(), New_S_Loss-5*Point,OrderTakeProfit()-Step*Point,0,Khaki); return; } } } } } return(0); } } // ---end----- void TrailingStop()--------------------------------& // this block is only for error controlling in the function code // int start() // { // if(25>26) TrailingStop(); // } // --------------------------------
Conclusion
It should be said that, as compared to the "exemplary trailing-stop" described in the "A Pattern Trailing Stop and Exit the Market" article by Sergey Kravchuk, the suggested version is easier to understand and it has worked in my EA (to tell the truth, on a demo account) and, as I think, it fits the aggressive and moderate trailing.
The attached versions:
v4 - with closing by S/L; v5 - with predicted closing by T/P; v6 - with a glance to prediction and address support by Magic number.
Translated from Russian by MetaQuotes Ltd.
Original article: https://www.mql5.com/ru/articles/1529
- Free trading apps
- Over 8,000 signals for copying
- Economic news for exploring financial markets
You agree to website policy and terms of use
So in an EA you would put this here:
Correct?Get warning:
Start function not found and cannot be run.
yeah I think the same thing, nondisclosure.
it send modify function all the time??
and what is
(Pr_Op_0-Pr_Op_1)>2*Point
i don't see they got any value?