//+------------------------------------------------------------------+ //| TF_DemoEA.mq5 - a deliberately simple demo Expert for Tick Forge. | //| It exists only to show what the audit set exposes. MIT licence. | //| | //| Rule (both modes): on weekdays, at InpHour server time, buy if | //| yesterday closed up, sell if it closed down; hold InpHoldHours. | //| InpMode 0 = LOGIC trades every weekday by that rule. | //| InpMode 1 = DATE LIST same rule, but ONLY on the dates listed | //| in InpDates (a stand-in for a fitted, memorised | //| schedule). | //+------------------------------------------------------------------+ #property strict #property version "1.00" input int InpMode = 0; // 0 = logic, 1 = only on the dates in InpDates input int InpHour = 10; // entry hour (server time) input int InpHoldHours = 3; // hours to hold input double InpLots = 0.10; // volume input string InpDates = ""; // YYYY.MM.DD,YYYY.MM.DD,... (mode 1) ulong g_ticket = 0; datetime g_opened = 0; string g_dates = ""; int g_last_day = -1; int OnInit() { g_dates = "," + InpDates + ","; PrintFormat("TF_DemoEA v1.00 | mode=%d hour=%d hold=%d", InpMode, InpHour, InpHoldHours); return INIT_SUCCEEDED; } ENUM_ORDER_TYPE_FILLING Filling() { const long m = SymbolInfoInteger(_Symbol, SYMBOL_FILLING_MODE); if((m & SYMBOL_FILLING_FOK) != 0) return ORDER_FILLING_FOK; if((m & SYMBOL_FILLING_IOC) != 0) return ORDER_FILLING_IOC; return ORDER_FILLING_RETURN; } bool AllowedToday(const datetime t) { if(InpMode == 0) return true; return StringFind(g_dates, "," + TimeToString(t, TIME_DATE) + ",") >= 0; } void OnTick() { const datetime now = TimeCurrent(); MqlDateTime dt; TimeToStruct(now, dt); if(PositionSelect(_Symbol)) { if(now - g_opened >= InpHoldHours * 3600) { MqlTradeRequest r; MqlTradeResult s; ZeroMemory(r); ZeroMemory(s); r.action = TRADE_ACTION_DEAL; r.symbol = _Symbol; r.volume = PositionGetDouble(POSITION_VOLUME); const bool buy = (PositionGetInteger(POSITION_TYPE) == POSITION_TYPE_BUY); r.type = buy ? ORDER_TYPE_SELL : ORDER_TYPE_BUY; r.price = SymbolInfoDouble(_Symbol, buy ? SYMBOL_BID : SYMBOL_ASK); r.position = PositionGetInteger(POSITION_TICKET); r.type_filling = Filling(); r.deviation = 50; if(!OrderSend(r, s)) Print("TF_DemoEA close failed: ", s.retcode); } return; } if(dt.day_of_week == 0 || dt.day_of_week == 6) return; if(dt.hour != InpHour || dt.day_of_year == g_last_day) return; if(!AllowedToday(now)) return; MqlRates d[]; if(CopyRates(_Symbol, PERIOD_D1, 1, 1, d) != 1) return; MqlTradeRequest r; MqlTradeResult s; ZeroMemory(r); ZeroMemory(s); const bool buy = (d[0].close >= d[0].open); r.action = TRADE_ACTION_DEAL; r.symbol = _Symbol; r.volume = InpLots; r.type = buy ? ORDER_TYPE_BUY : ORDER_TYPE_SELL; r.price = SymbolInfoDouble(_Symbol, buy ? SYMBOL_ASK : SYMBOL_BID); r.type_filling = Filling(); r.deviation = 50; if(OrderSend(r, s) && (s.retcode == TRADE_RETCODE_DONE || s.retcode == TRADE_RETCODE_PLACED)) { g_opened = now; g_last_day = dt.day_of_year; } } //+------------------------------------------------------------------+