//////////////////////////////////////////////////////////// // // SaherElm IT Center MQL5 XTEST Signal Provider Library // -------------------------------------------------------- // Name: XTESTSignalProvider // Description: XTEST based signal provider ... // // // Maintainer: // ------------ // Hadi Khazaee Asl (hadi_khazaee_asl@yahoo.com) // ////////////////////////////////////////////////////// // // Global Properties ... #property library #property copyright "Copyright 2023, SaherElm IT Center" #property link "https://www.saherelm.ir" #property version "1.00" #property strict #define XTESTProviderName "XTEST" // // START Inputs ... // #include "x-saherelm.xtest.provider.inputs.lib.mq5"; // // END Inputs ... // // // Include Common Library ... #include "x-saherelm.common.lib.mq5" // // Include Logger Library ... #include "x-saherelm.log.lib.mq5" // // Include Alert Library ... #include "x-saherelm.alert.lib.mq5" // // Include Draw Library ... #include "x-saherelm.draw.lib.mq5" // // Include Class Libraries ... #include "x-saherelm.class.lib.mq5" // // START Global Definitions: Variables, Properties and etc ... // // XCTrade *xTESTTrader; XCAccountInfo xTESTAccountInfo; // #include "x-saherelm.xtest.provider.indicators.lib.mq5" // double xTESTDeposit = 0; double xTESTBalance = 0; double xTESTFreeMargin = 0; double xTESTMinRewardPerTrade = 0; double xTESTFreeMarginForOpenTrades = 0; double xTESTBalanceForOpenTrades = 0; // // END Global Definitions: Variables, Properties and etc ... // // // START Provided Functions ... // // // Initial Library if required ... bool XTESTInitSignalProviderLibrary() { // bool result = false; // // Validate Inputs ... result = XTESTValidateInputs(); if (!result) { return result; } // // Init Indicators ... result = XTESTInitIndicators(); if (!result) { return result; } // // Calculate Account Deposit ... xTESTDeposit = xTESTAccountInfo.GetInitialBalance(); // // Calculate xTESTMinRewardPerTrade ... if (xTESTMinRewardPerTradeInPips > 0) { xTESTMinRewardPerTrade = PipsToPrice(xTESTMinRewardPerTradeInPips); } // // Calculate Min Balance for Trades ... if (xTESTBalanceFactorForOpenTrades > 0) { xTESTBalanceForOpenTrades = xTESTBalanceFactorForOpenTrades * xTESTDeposit; } // // Claculate Min Free Marging for Trades ... if (xTESTFreeMarginFactorForOpenTrades > 0) { xTESTFreeMarginForOpenTrades = xTESTFreeMarginFactorForOpenTrades * xTESTDeposit; } // // Make XCTrader instance ... xTESTTrader = new XCTrade( XTESTProviderName, _Symbol, xTESTSlippage, xTESTMagicNumber, xTESTMaxAllowedTrades, xTESTMaxAllowedSupportTrades, xTESTMinRewardPerTradeInPips, xTESTSupportTradesPriceDistanceInPips, xTESTFreeMarginForOpenTrades, xTESTBalanceForOpenTrades); // result = true; // // Logging State ... XTESTIssueInitializationSucceedAlert(); // return result; } // // DeInitial Library if required ... void XTESTDeinitSignalProviderLibrary( const int reason) { // // Release Handlers ... XTESTReleaseIndicators(); // // Logging State ... XTESTIssueDeinitializationSucceedAlert(); } // // this is a Globally Function which do all of // checkings and positions handling ... void XTESTSignalProviderHandleTick() { // // Update account Balance ... xTESTBalance = xTESTAccountInfo.GetBalance(); xTESTFreeMargin = xTESTAccountInfo.GetFreeMargin(); // // Check Provider is Enable or Not ... if (!xTESTEnableProvider) { return; } // // Reading Indicator Buffers ... XTESTHandleReadingBuffers(); if (xTESTCalculatedBars < xTESTMaxLengthOfInputs) { return; } // // Handle Open Trades ... XTESTHandleOpenTrades(); // // Handle Close Trades ... XTESTHandleCloseTrades(); // // Handle Support Trades ... XTESTHandleSupportTrades(); } // // Handle Open Trades ... void XTESTHandleOpenTrades() { // // Check Can Trade ... bool canTrade = xTESTAllowLongTrades || xTESTAllowShortTrades; if (!canTrade) { return; } // // Check Signals Exists ... bool hasLongSignal = XTESTCanOpenLongTrade(); bool hasShortSignal = XTESTCanOpenShortTrade(); if (!hasLongSignal && !hasShortSignal) { return; } // // Open Long Trades ... if ( // hasLongSignal && xTESTAllowLongTrades) { // bool isOpened = XTESTOpenLongPosition(); } // // Open Short Trades ... if ( // hasShortSignal && xTESTAllowShortTrades) { // bool isOpened = XTESTOpenShortPosition(); } } // // Handle Close Trades ... void XTESTHandleCloseTrades() { // // All Close Mechanism Handles Here ... // - Force Close; // - Partial Close; // - Risk Free Close; // - Virtual TP/SL Close; // // Force Close Long Trades ... bool canCloseLongTrades = XTESTCanCloseLongTrade(); if (xTESTAllowLongTrades && canCloseLongTrades) { // ENUM_X_SIGNAL_TYPE type = X_SIGNAL_LONG; // XSignal closed[]; xTESTTrader.ClosePositionsByType( type, closed); // bool isClosed = ArraySize(closed) > 0; if (isClosed) { XTESTIssueForceCloseTradesAlert(type); } } // // Force Close Short Trades ... bool canCloseShortTrades = XTESTCanCloseShortTrade(); if (xTESTAllowShortTrades && canCloseShortTrades) { // ENUM_X_SIGNAL_TYPE type = X_SIGNAL_SHORT; // XSignal closed[]; xTESTTrader.ClosePositionsByType( type, closed); // bool isClosed = ArraySize(closed) > 0; if (isClosed) { XTESTIssueForceCloseTradesAlert(type); } } // // Close Risk Free Trades ... // XSignal riskFrees[]; // xTESTTrader.RiskFreeSignals(riskFrees); // bool isRiskFree = ArraySize(riskFrees) > 0; // if (isRiskFree) // { // XTESTIssueRiskFreeTradesAlert(); // } // // Close Virtual TP / SL Trades ... // if (xTESTUseVirtualTPSL) // { // XSignal takeProfits[]; XSignal stopLosses[]; // xTESTTrader.HandleVirtualTPSL( takeProfits, stopLosses); // // Take Profits ... int takeProfitsCount = ArraySize(takeProfits); if (takeProfitsCount > 0) { // // Do What we Want in Profits Trades ... } // // Stop Losses ... int stopLossesCount = ArraySize(stopLosses); if (stopLossesCount > 0) { // // Do What we Want in Stop Losses Trades ... } // } // // Close Max DrawDown Trades ... // // Close Long Time Trades ... } // // Handle Support Trades ... void XTESTHandleSupportTrades() { } // // Open Long Position ... bool XTESTOpenLongPosition() { // bool result = false; // double riskFreeRate = 0; // 0.75; double volume = XTESTCalculateVolume(); double tp = PipsToPrice(xTESTMinRewardPerTradeInPips); double sl = PipsToPrice(xTESTMinRewardPerTradeInPips); double riskFree = 0; // PipsToPrice(xTESTMinRewardPerTradeInPips); // bool useVirtalTPSL = true; // xTESTUseVirtualTPSL; // XSignal signal = {}; signal = xTESTTrader.GenerateTradeSignal( X_SIGNAL_LONG, tp, sl, volume, riskFree, riskFreeRate, useVirtalTPSL); bool isValidSignal = IsValid( signal, xTESTMagicNumber); if (!isValidSignal) { return result; } // int error = -1; result = xTESTTrader.ExecuteSignal(signal, error); if (result) { XTESTIssueSignalExecutionAlert(signal); } // return result; } // // Open Short Position ... bool XTESTOpenShortPosition() { // bool result = false; // // // double riskFreeRate = 0; // 0.75; // double volume = XTESTCalculateVolume(); // double tp = PipsToPrice(xTESTMinRewardPerTradeInPips * 3); // double riskFree = 0; // PipsToPrice(xTESTMinRewardPerTradeInPips); // // // XSignal signal = {}; // signal = xTESTTrader.GenerateTradeSignal( // X_SIGNAL_SHORT, // tp, // 0, // volume, // riskFree, // riskFreeRate, // false); // bool isValidSignal = IsValid( // signal, // xTESTMagicNumber); // if (!isValidSignal) // { // return result; // } // // // int error = -1; // result = xTESTTrader.ExecuteSignal(signal, error); // if (result) // { // XTESTIssueSignalExecutionAlert(signal); // } // return result; } // // Open a Support Signal ... bool XTESTOpenSupportTrade( XSignal &signal // Parent Signal ) { // bool result = false; // return result; } // // END Provided Functions ... // // // START Private Functions ... // // // Calculating Volume for Tradings ... double XTESTCalculateVolume() { // // Assign default Value ... double result = xTESTStaticVolume; // // we can count open trades and in draw down trades // then do check volume based on it for gridding ... int openTrades = xTESTTrader.Count(); if (openTrades == 0) { openTrades = 1; } // // Calculate Normalized Multiplier ... double multiplier = xTESTVolumeMultiplier <= 0 ? 1 : xTESTVolumeMultiplier; // result = multiplier * openTrades * xTESTStaticVolume; // // Normalize Volume ... result = NormalizeVolume(result); // return result; } // // Calculate Signal TP and SL ... XTPSL XTESTCalculateTPSL( ENUM_X_SIGNAL_TYPE type // Position Type ) { // XTPSL result = {}; // // Validate Args ... if ( type != X_SIGNAL_LONG && type != X_SIGNAL_SHORT) { return result; } // bool isLong = type == X_SIGNAL_LONG; // double ask = GetAsk(); double bid = GetBid(); double spread = GetSpread(); double entry = isLong ? ask : bid; // // TODO: Find Risk .. double risk = 0; // // Calculate Reward ... double reward = PipsToPrice(xTESTMinRewardPerTradeInPips) + spread; // // Calculate TP and SL ... double tp = isLong ? entry + reward : entry - reward; double sl = 0; // result.type = type; result.tp = tp; result.sl = sl; result.entry = entry; // // TODO: Calculate R2R ... result.r2r = 0; // return result; } void XTESTIssueInitializationSucceedAlert() { // string message = "Initializion of (" + XTESTProviderName + " Provider" + " _ " + _Symbol + " _ " + EnumToString(_Period) + ") Succeeded ..."; XTESTIssueAlert(message); } void XTESTIssueDeinitializationSucceedAlert() { // string message = "De Initializion of (" + XTESTProviderName + " Provider" + ") Succeeded ..."; XTESTIssueAlert(message); } void XTESTIssueForceCloseTradesAlert(ENUM_X_SIGNAL_TYPE type) { // string typeStr = GetSignalType(type); if (StringLen(typeStr) == 0) { return; } // string message = "Force Close " + typeStr + " Trades ..."; XTESTIssueAlert(message); } void XTESTIssueMaxAllowedTradesReachedAlert() { // string message = "reached Max Allowed Same Time Trades ..."; XTESTIssueAlert(message); } void XTESTIssueMaxAllowedFreeMarginReachedAlert() { // string message = "reached FreeMarigin For Open Trades ..."; XTESTIssueAlert(message); } void XTESTIssueMinAllowedBalanceReachedAlert() { // string message = "doesn't have Minimum Balance For Open Trades ..."; XTESTIssueAlert(message); } void XTESTIssueSignalExecutionAlert( XSignal &signal // Executed Signal ) { // XTESTIssueAlert(signal); } void XTESTIssueSignalExecutionError(int error) { // string message = GetSignalExecutionError(error); if (StringLen(message) == 0) { return; } // XTESTIssueAlert(message); } void XTESTIssueRiskFreeTradesAlert() { // string message = "Make Some Trades Risk Free ..."; XTESTIssueAlert(message); } void XTESTIssueLongInProfitTradeClosed() { // string message = "Closed Long Time in Profit Trades ..."; XTESTIssueAlert(message); } void XTESTIssueLongInDrawdownTradeClosed() { // string message = "Closed Long Time in Profit Trades ..."; XTESTIssueAlert(message); } void XTESTIssueAlert(string message) { // if (xTESTEnableAlerts) { SendAlert(message); } else { LogMessage(message); } } void XTESTIssueAlert(XSignal &signal) { // string signalStr = xTESTTrader.ToString(signal); XTESTIssueAlert(signalStr); // // // if (xTESTEnableAlerts) // { // SendAlert(signal); // } // else // { // LogSignal(signal); // } } // // END Private Functions ... //