Author: Copyright � 2005 Bob O'Brien / Barcode
Profit factor:
1.05

This script is an automated trading system designed to manage market entries, order types, and risk management based on two primary technical indicators: the MACD (Moving Average Convergence Divergence) and the Williams %R.

Core Trading Logic

The system operates by looking for specific alignments between different timeframes to determine the trend and potential entry points:

  • Trend Identification: The script checks the MACD indicator on a Weekly timeframe to establish the overall market direction. If the MACD is moving upward, it looks for buying opportunities; if it is moving downward, it seeks selling opportunities.
  • Entry Confirmation: While the MACD sets the broad direction, the Williams %R indicator (on a Daily timeframe) acts as the specific trigger. The script monitors whether the price is in "oversold" or "overbought" territories to decide when to place an order.

Order Execution Strategy

Unlike systems that enter trades immediately at current prices, this script utilizes Pending Orders (Buy Stops and Sell Stops). This means it places orders at specific price levels that must be reached before a trade is executed:

  • Buy Orders: These are placed above recent price highs once the trend and Williams %R conditions align.
  • Sell Orders: These are placed below recent price lows once the trend and Williams %R conditions align.
  • Dynamic Adjustments: The script continuously monitors these pending orders. If the market trend shifts unexpectedly, it will automatically delete the pending orders to prevent entering a trade against the new momentum. It also modifies the entry prices of these orders based on moving high/low price points.

Risk and Trade Management

The script includes several automated features to protect the account and optimize profit:

  • Automated Money Management: The system calculates the appropriate "Lot Size" (trade volume) based on your account balance, leverage, and available margin. It ensures that you do not over-leverage your account based on preset risk levels.
  • Dynamic Profit Targets & Stop Losses: Every trade is automatically assigned a Stop Loss and a Take Profit price upon entry. The Take Profit levels are calculated dynamically, ensuring they are placed at a logical distance relative to the risk taken.
  • Trailing Stop: For active trades that move into profitability, the script employs a "Trailing Stop" mechanism. This automatically moves the stop loss behind the price as it moves in your favor, aiming to lock in profits while giving the trade room to continue running.
  • Trade Limits: The logic ensures that only one trade is open per symbol at any given time, preventing the accumulation of multiple risky positions on the same asset.
Price Data Components
Series array that contains the highest prices of each barSeries array that contains the lowest prices of each bar
Orders Execution
Checks for the total of open orders
Indicators Used
Larry William percent range indicator
12 Views
0 Downloads
0 Favorites
TSD
/*-----------------------------+
|			       |
| Shared by www.Aptrafx.com    |
|			       |
+------------------------------*/

//+------------------------------------------------------------------+
//|                                                          TSD.mq4 |
//|                           Copyright ® 2005 Bob O'Brien / Barcode |
//|                          TSD v1.2 rewritten to MQL4 by Mindaugas |
//+------------------------------------------------------------------+
#property copyright "Copyright ® 2005 Bob O'Brien / Barcode"

//---- input parameters
extern int WilliamsP =  24;
extern int WilliamsL = -75;
extern int WilliamsH = -25;

#include <stdlib.mqh>

int Slippage = 5, LotsMax = 50;
int MM = 0, Leverage = 1, MarginChoke = 500;
int TakeProfit = 100, TrailingStop = 60;

double Spread, Lots = 0.1;

int PeriodMacd = PERIOD_W1, PeriodWilliams = PERIOD_D1, PeriodTrailing = PERIOD_H4, CandlesTrailing = 3;

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

int init()   { return(0); }
int deinit() { return(0); }

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

int start() {
   int TradesThisSymbol, Direction;
   int i, ticket;
   
   bool WilliamsSell, WilliamsBuy;
   
   double PriceOpen, Buy_Sl, Buy_Tp, LotMM;
   double WilliamsValue;
   
   datetime NewBar = 0;
   
   Spread = Ask - Bid;
   TradesThisSymbol = TotalTradesThisSymbol ();
   Direction = MacdDirection (PeriodMacd);
   WilliamsValue = iWPR(NULL, PeriodWilliams, WilliamsP, 1);
   
   Comment ("\nMACD Direction: ", Direction, "\niWPR: ", NormalizeDouble(WilliamsValue, 1));
   
   /////////////////////////////////////////////////
   //  Process the next bar details
   /////////////////////////////////////////////////
   if ( NewBar != iTime (NULL, PeriodWilliams, 0) ) {
      NewBar = iTime (NULL, PeriodWilliams, 0);
      
      if ( TradesThisSymbol < 1 ) {

         LotMM = CalcMM(MM);
         if ( LotMM < 0 )  return(0);

  	   	WilliamsSell = WilliamsValue > WilliamsL;
		   WilliamsBuy  = WilliamsValue < WilliamsH;

         /////////////////////////////////////////////////
         //  New Orders Management
         /////////////////////////////////////////////////
		
         ticket = 0;

         if ( Direction == 1 && WilliamsBuy )
		      ticket = OrderSend (Symbol(), OP_BUYSTOP, LotMM, CalcOpenBuy(), Slippage, CalcSlBuy(), CalcTpBuy(),
		                          "TSD BuyStop", 0, 0, Blue);
		   
         if ( Direction == -1 && WilliamsSell )
		      ticket = OrderSend (Symbol(), OP_SELLSTOP, LotMM, CalcOpenSell(), Slippage, CalcSlSell(), CalcTpSell(),
		                          "TSD SellStop", 0, 0, Red);
 
		   if ( ticket == -1 )  ReportError ();
		   if ( ticket != 0 )   return(0);
		} // End of TradesThisSymbol < 1
		
      /////////////////////////////////////////////////
      //  Pending Order Management
      /////////////////////////////////////////////////
      for (i = 0; i < OrdersTotal(); i++) {
         if ( OrderSelect (i, SELECT_BY_POS) == false )  continue;
         if ( OrderSymbol() != Symbol () )  continue;

         if ( OrderType () == OP_BUYSTOP ) {
            if ( Direction != 1 ) {
               OrderDelete ( OrderTicket() );
               return(0);
            }
            if ( iHigh(NULL, PeriodWilliams, 1) < iHigh(NULL, PeriodWilliams, 2) ) {
        		   OrderModify (OrderTicket(), CalcOpenBuy(), CalcSlBuy(), CalcTpBuy(), 0, White);
               return(0);
            }
         }

         if ( OrderType () == OP_SELLSTOP ) {
            if ( Direction != -1 ) {
               OrderDelete ( OrderTicket() );
               return(0);
            }
            if ( iLow(NULL, PeriodWilliams, 1) > iLow(NULL, PeriodWilliams, 2) ) {
        		   OrderModify (OrderTicket(), CalcOpenSell(), CalcSlSell(), CalcTpSell(), 0, Gold);
               return(0);
            }
         }
      } // End of Pending Order Management
   } // End of Process Next Bar Details
   
   /////////////////////////////////////////////////
   //  Stop Loss Management
   /////////////////////////////////////////////////
   if ( TradesThisSymbol > 0 && TrailingStop > 0 ) {
      for (i = 0; i < OrdersTotal(); i++) {
         if ( OrderSelect (i, SELECT_BY_POS) == false )  continue;
         if ( OrderSymbol() != Symbol () )  continue;
         TrailStop (i, TrailingStop);
      }
   }

   return(0);
}

//+------------------------------------------------------------------+
double CalcOpenBuy  () { return (dMax (iHigh(NULL, PeriodWilliams, 1) + 1*Point + Spread, Ask + 16*Point)); }
double CalcOpenSell () { return (dMin (iLow(NULL, PeriodWilliams, 1) - 1*Point,  Bid - 16*Point)); }
double CalcSlBuy  () { return (iLow (NULL, PeriodWilliams, 1) - 1*Point); }
double CalcSlSell () { return (iHigh(NULL, PeriodWilliams, 1) + 1*Point + Spread); }
double CalcTpBuy  () {
   double PriceOpen = CalcOpenBuy(), SL = CalcSlBuy();
   return (PriceOpen + dMax(TakeProfit, (PriceOpen - SL)*2));
}
double CalcTpSell  () {
   double PriceOpen = CalcOpenSell(), SL = CalcSlSell();
   return (PriceOpen - dMax(TakeProfit, (SL - PriceOpen)*2));
}
//+------------------------------------------------------------------+
void TrailStop (int i, int TrailingStop) {
   double StopLoss;

   if ( OrderType() == OP_BUY ) {
      if ( Bid < OrderOpenPrice () )  return;
      StopLoss = iLow(NULL, PeriodTrailing, Lowest (NULL, PeriodTrailing, MODE_LOW, CandlesTrailing+1, 0)) - 1*Point;
      if ( StopLoss > OrderStopLoss() )
         OrderModify (OrderTicket(), OrderOpenPrice(), StopLoss, OrderTakeProfit(), 0, White);
   }
   
   if ( OrderType() == OP_SELL ) {
      if ( Ask < OrderOpenPrice () )  return;
      StopLoss = iHigh(NULL, PeriodTrailing, Highest (NULL, PeriodTrailing, MODE_HIGH, CandlesTrailing+1, 0)) + 1*Point
                 + Spread;
      if ( StopLoss < OrderStopLoss() )
         OrderModify (OrderTicket(), OrderOpenPrice(), StopLoss, OrderTakeProfit(), 0, Gold);
   }
}
//+------------------------------------------------------------------+
int MacdDirection (int PeriodMacd) {
   int Direction = 0;
   double MacdPrevious, MacdPrevious2;

	MacdPrevious  = iMACD (NULL, PeriodMacd, 5, 34, 5, PRICE_MEDIAN, MODE_MAIN, 1);
	MacdPrevious2 = iMACD (NULL, PeriodMacd, 5, 34, 5, PRICE_MEDIAN, MODE_MAIN, 2);

   if ( MacdPrevious > MacdPrevious2 )
      Direction = 1;
   if ( MacdPrevious < MacdPrevious2 )
      Direction = -1;
   return (Direction);
}
//+------------------------------------------------------------------+
double CalcMM (int MM) {
   double LotMM;

   if ( MM < -1) {
      if ( AccountFreeMargin () < 5 )  return(-1);
		LotMM = MathFloor (AccountBalance()*Leverage/1000);
		if ( LotMM < 1 )  LotMM = 1;
		LotMM = LotMM/100;
   }
	if ( MM == -1 ) {
		if ( AccountFreeMargin() < 50 )  return(-1);
		LotMM = MathFloor(AccountBalance()*Leverage/10000);
		if ( LotMM < 1 )  LotMM = 1;
		LotMM = LotMM/10;
   }
	if ( MM == 0 ) {
		if ( AccountFreeMargin() < MarginChoke ) return(-1); 
		LotMM = Lots;
	}
	if ( MM > 0 ) {
      if ( AccountFreeMargin() < 500 )  return(-1);
		LotMM = MathFloor(AccountBalance()*Leverage/100000);
 		if ( LotMM < 1 )  LotMM = 1;
	}
	if ( LotMM > LotsMax )  LotMM = LotsMax;
	return(LotMM);
}
//+------------------------------------------------------------------+
int TotalTradesThisSymbol () {
   int i, TradesThisSymbol = 0;
   
   for (i = 0; i < OrdersTotal(); i++)
      if ( OrderSelect (i, SELECT_BY_POS) )
         if ( OrderSymbol() == Symbol () )
            TradesThisSymbol++;

   return (TradesThisSymbol);
}
//+------------------------------------------------------------------+
void ReportError () {
   int err = GetLastError();
   Print("Error(",err,"): ", ErrorDescription(err));
}
//+------------------------------------------------------------------+
double dMax (double val1, double val2) {
  if (val1 > val2)  return(val1);
  return(val2);
}
//+------------------------------------------------------------------+
double dMin (double val1, double val2) {
  if (val1 < val2)  return(val1);
  return(val2);
}

Profitability Reports

PERFORMANCE BY SYMBOL

Expected payoff

Average expected payoff across the available backtests for each symbol.

Positive Negative
15 reports
AUD/USD Jul 2025 - Sep 2025
8.43
Total Trades 3
Won Trades 2
Lost trades 1
Win Rate 66.67 %
Expected payoff 23.77
Gross Profit 80.90
Gross Loss -9.60
Total Net Profit 71.30
-100%
-50%
0%
50%
100%
USD/CAD Jul 2025 - Sep 2025
1.72
Total Trades 13
Won Trades 6
Lost trades 7
Win Rate 46.15 %
Expected payoff 6.43
Gross Profit 199.15
Gross Loss -115.56
Total Net Profit 83.59
-100%
-50%
0%
50%
100%
GBP/CAD Oct 2025 - Feb 2026
1.33
Total Trades 9
Won Trades 4
Lost trades 5
Win Rate 44.44 %
Expected payoff 6.69
Gross Profit 243.14
Gross Loss -182.93
Total Net Profit 60.21
-100%
-50%
0%
50%
100%
EUR/USD Oct 2025 - Feb 2026
1.29
Total Trades 4
Won Trades 2
Lost trades 2
Win Rate 50.00 %
Expected payoff 4.05
Gross Profit 72.00
Gross Loss -55.80
Total Net Profit 16.20
-100%
-50%
0%
50%
100%
GBP/CAD Jul 2025 - Sep 2025
0.96
Total Trades 4
Won Trades 2
Lost trades 2
Win Rate 50.00 %
Expected payoff -0.68
Gross Profit 60.49
Gross Loss -63.21
Total Net Profit -2.72
-100%
-50%
0%
50%
100%
USD/CAD Oct 2024 - Jan 2025
0.83
Total Trades 10
Won Trades 4
Lost trades 6
Win Rate 40.00 %
Expected payoff -1.41
Gross Profit 67.75
Gross Loss -81.86
Total Net Profit -14.11
-100%
-50%
0%
50%
100%
USD/JPY Jul 2025 - Sep 2025
0.75
Total Trades 15
Won Trades 5
Lost trades 10
Win Rate 33.33 %
Expected payoff -3.44
Gross Profit 158.34
Gross Loss -209.89
Total Net Profit -51.55
-100%
-50%
0%
50%
100%
EUR/USD Jul 2025 - Sep 2025
0.43
Total Trades 2
Won Trades 1
Lost trades 1
Win Rate 50.00 %
Expected payoff -18.70
Gross Profit 27.80
Gross Loss -65.20
Total Net Profit -37.40
-100%
-50%
0%
50%
100%
AUD/USD Oct 2024 - Jan 2025
0.00
Total Trades 0
Won Trades 0
Lost trades 0
Win Rate 0.0 %
Expected payoff 0.00
Gross Profit 0.00
Gross Loss 0.00
Total Net Profit 0.00
-100%
-50%
0%
50%
100%
GBP/USD Oct 2024 - Jan 2025
0.00
Total Trades 0
Won Trades 0
Lost trades 0
Win Rate 0.0 %
Expected payoff 0.00
Gross Profit 0.00
Gross Loss 0.00
Total Net Profit 0.00
-100%
-50%
0%
50%
100%
NZD/USD Oct 2024 - Jan 2025
0.00
Total Trades 1
Won Trades 0
Lost trades 1
Win Rate 0.00 %
Expected payoff -17.80
Gross Profit 0.00
Gross Loss -17.80
Total Net Profit -17.80
-100%
-50%
0%
50%
100%
GBP/AUD Jul 2025 - Sep 2025
0.00
Total Trades 1
Won Trades 1
Lost trades 0
Win Rate 100.00 %
Expected payoff 60.02
Gross Profit 60.02
Gross Loss 0.00
Total Net Profit 60.02
-100%
-50%
0%
50%
100%
GBP/USD Jul 2025 - Sep 2025
0.00
Total Trades 1
Won Trades 1
Lost trades 0
Win Rate 100.00 %
Expected payoff 5.20
Gross Profit 5.20
Gross Loss 0.00
Total Net Profit 5.20
-100%
-50%
0%
50%
100%
NZD/USD Jul 2025 - Sep 2025
0.00
Total Trades 1
Won Trades 0
Lost trades 1
Win Rate 0.00 %
Expected payoff -12.90
Gross Profit 0.00
Gross Loss -12.90
Total Net Profit -12.90
-100%
-50%
0%
50%
100%
GBP/AUD Oct 2025 - Feb 2026
0.00
Total Trades 4
Won Trades 0
Lost trades 4
Win Rate 0.00 %
Expected payoff -31.59
Gross Profit 0.00
Gross Loss -126.34
Total Net Profit -126.34
-100%
-50%
0%
50%
100%

Comments