//+------------------------------------------------------------------+ //| MAProfit.mq4 | //| Copyright © 2010, Thomas Quester. | //| tquester@gmx.de | //+------------------------------------------------------------------+ /* I do custom mql4/mql5 programming at low prices. If you wish to thank the autor, you might do the following - Send money to PayPal: tquester@gmx.de - Send money to Moneybrokers: tquester@gmx.de - Open an account at avafx and drop me a line with your user name (both will receive a rebate) - Open an account at instaforex and refer to my account number: 3003318 */ #property copyright "Copyright © 2010, Thomas Quester 'tflores'." #property link "tquester@gmx.de" #property indicator_chart_window #property indicator_buffers 2 #property indicator_color1 Aqua #property indicator_color2 Yellow // if you want speach, get gspeak from "http://www.forex-tsd.com" // you can download also here: http://codebase.mql4.com/5036 // Remove comment in LoudAlert below #import "speak.dll" void gRate(int rate); void gVolume(int rate); void gPitch(int rate); void gSpeak(string text); #import // if you do not have (or want) the speach.dll uncomment this /* void gSpeak(string x) { } */ /* You may change this if you want different audio files for long/short signals. */ string AlertShort = "alert.wav"; string AlertLong = "alert.wav"; extern bool bOptimize=true; // True: Find the best single MA by optimizing (switch time frame to re-optimize) extern bool bOptimizeIntersect=true; // True: optimize for minimum intersections, otherwise optimize for max profit extern int PeriodMA=400; // If you do not want to optimize, you can define a period extern int Method=0; // Method for MA 0 = Simple, 1 = Expotential, 2 = Smoothed, 3 = Linear weighted extern bool DrawTringles=true; // Draws triangles for the simulated trading extern int MinMA=5; // Minimum test for optimizing extern int MaxMA=500; // Maximum test for optimizing extern int StepMA=1; // Step during optimizion, 1 tests every MA, 10 tests every 10th etc. extern int CountOptimize=300; // Number of candles for optimizing extern int RepaintBars=3000; // Number of candles on which we draw triangles and calculate the win/loss extern bool Alarm=true; // Make a visible alert on new signal extern bool bSpeak=true; // Speak the alert with gspeak bool bNeedOptimize; int ColorLongTrade = MediumSpringGreen; int ColorShortTrade = Red; int ColorBadTrade = Violet; bool bAlertViaAlert = true; datetime lastSignalTime=0; datetime firstTradeCandle; // we trade 300 candles but at all calls it should be the same candle int Method1 = MODE_SMA; int Method2 = MODE_SMA; int Price1 = PRICE_MEDIAN; int Price2 = PRICE_HIGH; int Price3 = PRICE_LOW; //---- buffers double ExtMapBuffer[]; // Fast MA curve double ExtMapBuffer2[]; // Fast MA curve int OldPeriod; // The period, we check for changes and re-init ourself int spread; int cBars; // Saved number of bars in order to see if new bar string OldSymbol; // If symbol canges, we re-initialize string rsiMessage; // Last Message RSI Oversold/Overbought #define SIGNAL_NONE 0 #define SIGNAL_SHORT 1 #define SIGNAL_LONG 2 int MaxObj = 0; int yesterday,today; // index of yesterday and today double gTradeOpen[], gTradeMin[], gTradeMax[]; int gTradeCmd[], gTradeStart[], gTradeEnd[], gTradeID; int gStartShort,gEndShort, gStartLong,gEndLong; void LoudAlert(string s) { if (bAlertViaAlert) Alert(s); Print(s); if (bSpeak) gSpeak(s); // uncomment this for speak } string FormatNumber(string s) { int c; while (true) { c = StringGetChar(s,StringLen(s)-1); if (c != '.' && c != '0') break; s = StringSubstr(s,0,StringLen(s)-1); } return (s); } string LongName(string s) { if (s == "EUR") s = "Euro "; if (s == "USD") s = "US Dollar "; if (s == "JPY") s = "Japanese Yen"; if (s == "CAD") s = "Canadian Dollar"; if (s == "AUD") s = "Australian Dollar"; if (s == "NZD") s = "New Zeeland Dollar"; if (s == "CHF") s = "Swiss Francs"; return (s); } string PairName(string s) { string a,b; a = StringSubstr(s,0,3); b = StringSubstr(s,3,3); a = LongName(a); if (StringLen(a) > 3) a = a + " to "; b = LongName(b); return (a+b); } string SpeakTime() { int p; string s; p = Period(); switch(p) { case 30: s = "half hour"; break; case 60: s = "One hour"; break; case 120: s = "Two horus"; break; case 240: s = "Four hours"; break; case 1440: s = "One day"; break; case 10080: s = "One week"; break; case 43200: s = "One month"; break; default: s = p+" Minutes"; } return (s); } //+------------------------------------------------------------------+ //| Custom indicator initialization function | //+------------------------------------------------------------------+ bool bInit; int init() { //---- indicators OldPeriod = -1; OldSymbol = ""; bNeedOptimize = true; lastSignalTime = 0 ; SetIndexStyle(0,DRAW_LINE); SetIndexStyle(1,DRAW_LINE); SetIndexBuffer(0,ExtMapBuffer); SetIndexBuffer(1,ExtMapBuffer2); IndicatorShortName("Cross Moving Average"); SetIndexLabel(0,"Fast Moving Average"); makelabel("profit", 0,20,"Profit Total",White); makelabel("profityesterday", 300,20,"Profit Total",White); makelabel("signal", 500,20,"Signal",White); makelabel("message", 600,20,"Message",White); makelabel("message2", 600,40,"Message",White); makelabel("hint", 400,0,"MAProfit (C) Thomas Quester",White); makelabel("hint2", 600,0,"look at source code for description",White); cBars = 0; ArrayResize(gTradeOpen,500); ArrayResize(gTradeMin,500); ArrayResize(gTradeMax,500); ArrayResize(gTradeCmd,500); ArrayResize(gTradeStart,500); ArrayResize(gTradeEnd,500); SendVars(); firstTradeCandle = 0; bInit = true; //---- return(0); } void SendVars() { string sym = Symbol()+Period(); GlobalVariableSet(sym+"PeriodMA",PeriodMA); GlobalVariableSet(sym+"Method",Method); } void GetVars() { string sym = Symbol()+Period(); PeriodMA = GlobalVariableGet(sym+"PeriodMA"); Method = GlobalVariableGet(sym+"Method"); } void DelVars() { string sym = Symbol()+Period(); GlobalVariableDel(sym+"PeriodMA"); GlobalVariableDel(sym+"Method"); } //+------------------------------------------------------------------+ //| Custom indicator deinitialization function | //+------------------------------------------------------------------+ int deinit() { //---- DeleteObjects(); DelVars(); //---- return(0); } //+------------------------------------------------------------------+ //| Custom indicator iteration function | //+------------------------------------------------------------------+ int start() { int counted_bars=IndicatorCounted(); spread = MarketInfo(Symbol(),MODE_SPREAD); //---- //---- int i; // some running integer int start; int objid; // the number of triangles string name; // name of triangle double d; // some double double maPeriod; // moving average Period double profit = 0; // profit of "trade" as difference between open and close double open; // the open price int day; // the day datetime opentime; // the time of open trade int openid; // the index of open trade int signal,s; // active and new singal double totalProfit; // total profit double totalProfitYesterday; // total profit yesterday bool newBar; string speak; string alert; double ma,price,maHigh; if (bNeedOptimize) Optimize(); bNeedOptimize=false; speak = "*"; alert = "*"; //SpeakRSI(); signal = SIGNAL_NONE; if (Bars != cBars) newBar = true; else newBar = false; cBars = Bars; //if (Period() != OldPeriod || Symbol() != OldSymbol) if (bInit) { OldPeriod = Period(); OldSymbol = Symbol(); Print("Symbol Changed, last Speak time set to ",TimeToStr(lastSignalTime)); } objid = 0; if (newBar) DeleteObjects(); // delete old objects // when starts today? CalcDays(); totalProfit = 0; totalProfitYesterday = 0; if (lastSignalTime == 0) lastSignalTime = Time[0]; ObjectCreate("today",OBJ_VLINE,0,Time[today],0); ObjectCreate("yesterday",OBJ_VLINE,0,Time[yesterday],0); start = Bars; if (start > RepaintBars) start = RepaintBars; if (RepaintBars != 0) if (start > RepaintBars) start = RepaintBars; ma = iMA(NULL,NULL,PeriodMA,0,Method,PRICE_MEDIAN,start); // find first bar to start trading int tradeStart=RepaintBars; if (firstTradeCandle == 0) { if (Bars > RepaintBars) { firstTradeCandle = Time[RepaintBars]; tradeStart = RepaintBars; } else { firstTradeCandle = Time[Bars]; tradeStart = Bars; } } else { for (i=0;i lastSignalTime && bSpeak) { Print("Speak time ",TimeToStr(Time[i])); lastSignalTime = Time[i]; alert = AlertLong; speak = "New signal at "+PairName(Symbol()) + " " + SpeakTime()+". Signal is long. "; SetText("signal","Long"); } } profit = 0; if (signal == SIGNAL_SHORT) { profit = open-Close[i]; profit /= Point; profit -= spread; } if (signal == SIGNAL_LONG) { profit = Close[i]-open; profit /= Point; profit -= spread; } totalWin+=profit; if (profit < 0) fails++; if (profit > 0) good++; if (signal != SIGNAL_NONE) { objid++; DrawTriangle(objid,signal,opentime,Open[openid],Time[i],Close[i],profit); } //ExtMapBuffer2[i] = profit; if (i <= today) totalProfit+=profit; if (i <= yesterday && i > today) totalProfitYesterday+=profit; opentime = Time[i]; openid = i; signal = s; open = Open[i]; } profit = 0; } } // terminate open "trade" if (signal != SIGNAL_NONE) { i = 0; if (signal == SIGNAL_SHORT) { profit = open-Close[i]; profit /= Point; profit -= spread; SetText("signal","Short"); } if (signal == SIGNAL_LONG) { profit = Close[i]-open; profit /= Point; profit -= spread; SetText("signal","Long"); } //ExtMapBuffer2[i] = profit; totalProfit+=profit; totalWin+=profit; if (profit < 0) fails++; if (profit > 0) good++; objid++; DrawTriangle(objid,signal,opentime,Open[openid],Time[i],Close[i],profit); } i = totalProfit; SetText("profit","Profit totay with MA "+PeriodMA+" is "+i+" Pips"); SetText("message2","Total Profit="+totalWin+" Fails="+fails+" Wins="+good); if (totalWin < 0) ObjectSet("message2",OBJPROP_COLOR,Red); else ObjectSet("message2",OBJPROP_COLOR,GreenYellow); i = totalProfitYesterday; SetText("profityesterday","Profit yesterday is "+i+" Pips"); MaxObj=objid+1; //---- bInit = false; if (alert != "*") Alert(alert); if (speak != "*") LoudAlert(speak); return(0); } //+------------------------------------------------------------------+ int trades; double wins, losses; double CalcProfit(int bars, int mode1, int price1, int mode2, int price2, int price3, int periodMA) { double ma; // moving average small and long value double profit = 0; // profit of "trade" as difference between open and close double totalProfit; int i,gOpenTime,openid; double d,open,price,min,max; int s,signal; signal = SIGNAL_NONE; totalProfit = 0; open = 0; gTradeID=-1; for (i=bars;i>=0;i--) { ma = iMA(NULL,NULL,periodMA,0,mode1,price1,i); s = signal; price = (High[i]+Low[i])/2; if (ma < price) s = SIGNAL_SHORT; if (ma > price) s = SIGNAL_LONG; // calc min/max if (signal != SIGNAL_NONE) { if (price< min) min = price; if (price > max) max = price; } if (s != signal) { if (gTradeID >= 0) { gTradeMin[gTradeID] = min; gTradeMax[gTradeID] = max; gTradeEnd[gTradeID] = i; gTradeCmd[gTradeID] = s; } gTradeID++; gTradeOpen[gTradeID] = price; gTradeStart[gTradeID] = i; gTradeEnd[gTradeID] = 0; min = 99999; max = -9999; profit = 0; if (signal == SIGNAL_SHORT) { profit = open-price; profit /= Point; profit -= spread; totalProfit += profit; } if (signal == SIGNAL_LONG) { profit = price-open; profit /= Point; profit -= spread; totalProfit += profit; } gOpenTime = Time[i]; openid = i; signal = s; open = price; } } if (signal != SIGNAL_NONE) { profit = 0; i = 0; if (signal == SIGNAL_SHORT) { profit = open-Open[i]; profit /= Point; profit -= spread; totalProfit += profit; } if (signal == SIGNAL_LONG) { profit = Open[i]-open; profit /= Point; profit -= spread; totalProfit += profit; } } return (totalProfit); } void Optimize() { if (bOptimize) { if (bOptimizeIntersect) OptimizeIntersects(); else OptimizeAll(); } else SetText("message","Optimizing is disabled"); } void OptimizeIntersects() { int i,s,intersects,minInterSects; double ma; minInterSects = 9999; for (s = MinMA; s<=MaxMA;s+=StepMA) { intersects=0; for (i=CountOptimize;i>=0;i--) { ma = iMA(NULL,NULL,s,0,Method,PRICE_MEDIAN,i); if (ma >= Low[i] && ma <= High[i]) intersects++; } if (intersects < minInterSects) { minInterSects = intersects; PeriodMA = s; } } SetText("message","BestMA="+PeriodMA+" Intersects="+minInterSects); } void OptimizeAll() { double profit, maxProfit; int s,l,a; int bestMA; bestMA = 0; maxProfit=-9999; for (s = MinMA; s<=MaxMA;s+=StepMA) { //a = s*130; //a /= 100; profit = CalcProfit(CountOptimize,Method,PRICE_MEDIAN,Method,PRICE_HIGH,PRICE_LOW,s); if (profit > maxProfit && profit != 0) { bestMA = s; maxProfit = profit; } } Method1 = Method; Method2 = Method; Price1 = PRICE_MEDIAN; Price2 = PRICE_HIGH; Price3 = PRICE_LOW; PeriodMA = bestMA; SetText("message","BestMA="+PeriodMA+" Profit="+maxProfit); SendVars(); } void CalcDays() { int day; int i; day = TimeDay(Time[0]); for (i=0;i