diff --git a/.github/workflows/backtest.yml b/.github/workflows/backtest.yml index 273f2d9..8e0fba4 100644 --- a/.github/workflows/backtest.yml +++ b/.github/workflows/backtest.yml @@ -41,14 +41,14 @@ jobs: include: . init-platform: true mt-version: 5.0.0.2361 - path: Stg_Meta_Trend.mq4 + path: Stg_Meta_RSI.mq4 verbose: true - name: Compile for MQL5 uses: fx31337/mql-compile-action@master with: include: . mt-version: 5.0.0.2515 - path: Stg_Meta_Trend.mq5 + path: Stg_Meta_RSI.mq5 verbose: true - name: List compiled files run: '(Get-ChildItem -Recurse -Path . -Include *.ex[45]).fullname' @@ -79,7 +79,7 @@ jobs: OptFormatBrief: true OptFormatJson: true OptVerbose: true - TestExpert: "Stg_Meta_Trend" + TestExpert: "Stg_Meta_RSI" TestPeriod: M1 TestReportName: Report-${{ matrix.year }}-${{ matrix.month }} - name: Upload results diff --git a/.github/workflows/compile.yml b/.github/workflows/compile.yml index ae0bd66..ba72e0c 100644 --- a/.github/workflows/compile.yml +++ b/.github/workflows/compile.yml @@ -43,14 +43,14 @@ jobs: include: . init-platform: true mt-version: 5.0.0.2361 - path: Stg_Meta_Trend.mq4 + path: Stg_Meta_RSI.mq4 verbose: true - name: Compile for MQL5 uses: fx31337/mql-compile-action@master with: include: . mt-version: 5.0.0.2515 - path: Stg_Meta_Trend.mq5 + path: Stg_Meta_RSI.mq5 verbose: true - name: List compiled files run: '(Get-ChildItem -Recurse -Path . -Include *.ex[45]).fullname' diff --git a/README.md b/README.md index b44d9c0..b1d2454 100644 --- a/README.md +++ b/README.md @@ -1,4 +1,4 @@ -# Strategy Meta Trend +# Strategy Meta RSI [![Status][gha-image-check-master]][gha-link-check-master] [![Status][gha-image-compile-master]][gha-link-compile-master] @@ -7,8 +7,8 @@ [![License][license-image]][license-link] [![Edit][gh-edit-badge]][gh-edit-link] -Trend meta strategy to filter out -signals of other strategies based on the current trend. +RSI meta strategy to trade with different strategies +based on the current daily RSI value. ## Dependencies @@ -22,12 +22,12 @@ signals of other strategies based on the current trend. [gh-discuss-link]: https://github.com/EA31337/EA31337-Strategies/discussions [gh-edit-badge]: https://img.shields.io/badge/GitHub-edit-purple.svg?logo=github -[gh-edit-link]: https://github.dev/EA31337/Strategy-Meta_Trend +[gh-edit-link]: https://github.dev/EA31337/Strategy-Meta_RSI -[gha-link-check-master]: https://github.com/EA31337/Strategy-Meta_Trend/actions?query=workflow:Check+branch%3Amaster -[gha-image-check-master]: https://github.com/EA31337/Strategy-Meta_Trend/workflows/Check/badge.svg?branch=master -[gha-link-compile-master]: https://github.com/EA31337/Strategy-Meta_Trend/actions?query=workflow:Compile+branch%3Amaster -[gha-image-compile-master]: https://github.com/EA31337/Strategy-Meta_Trend/workflows/Compile/badge.svg?branch=master +[gha-link-check-master]: https://github.com/EA31337/Strategy-Meta_RSI/actions?query=workflow:Check+branch%3Amaster +[gha-image-check-master]: https://github.com/EA31337/Strategy-Meta_RSI/workflows/Check/badge.svg?branch=master +[gha-link-compile-master]: https://github.com/EA31337/Strategy-Meta_RSI/actions?query=workflow:Compile+branch%3Amaster +[gha-image-compile-master]: https://github.com/EA31337/Strategy-Meta_RSI/workflows/Compile/badge.svg?branch=master [tg-channel-image]: https://img.shields.io/badge/Telegram-join-0088CC.svg?logo=telegram [tg-channel-link]: https://t.me/EA31337 diff --git a/Stg_Meta_Trend.mq4 b/Stg_Meta_RSI.mq4 similarity index 86% rename from Stg_Meta_Trend.mq4 rename to Stg_Meta_RSI.mq4 index e709df9..baf2214 100644 --- a/Stg_Meta_Trend.mq4 +++ b/Stg_Meta_RSI.mq4 @@ -6,8 +6,8 @@ /** * @file - * Implements Trend meta strategy. + * Implements RSI meta strategy. */ // Includes the main code. -#include "Stg_Meta_Trend.mq5" +#include "Stg_Meta_RSI.mq5" diff --git a/Stg_Meta_Trend.mq5 b/Stg_Meta_RSI.mq5 similarity index 85% rename from Stg_Meta_Trend.mq5 rename to Stg_Meta_RSI.mq5 index e7ca22a..847e19d 100644 --- a/Stg_Meta_Trend.mq5 +++ b/Stg_Meta_RSI.mq5 @@ -1,6 +1,6 @@ /** * @file - * Implements Trend meta strategy. + * Implements RSI meta strategy. */ // Includes conditional compilation directives. @@ -32,13 +32,13 @@ input ENUM_LOG_LEVEL Log_Level = V_INFO; // Log level. input bool Info_On_Chart = true; // Display info on chart. // Includes strategy class. -#include "Stg_Meta_Trend.mqh" +#include "Stg_Meta_RSI.mqh" // Defines. -#define ea_name "Strategy Meta Trend" +#define ea_name "Strategy Meta RSI" #define ea_version "2.000" -#define ea_desc "Trend meta strategy to filter out signals of other strategies based on the current trend." -#define ea_link "https://github.com/EA31337/Strategy-Meta_Trend" +#define ea_desc "RSI meta strategy to trade with different strategies based on the current daily RSI value." +#define ea_link "https://github.com/EA31337/Strategy-Meta_RSI" #define ea_author "EA31337 Ltd" // Properties. @@ -64,7 +64,7 @@ int OnInit() { bool _result = true; EAParams ea_params(__FILE__, Log_Level); ea = new EA(ea_params); - _result &= ea.StrategyAdd(Active_Tfs); + _result &= ea.StrategyAdd(Active_Tfs); return (_result ? INIT_SUCCEEDED : INIT_FAILED); } diff --git a/Stg_Meta_RSI.mqh b/Stg_Meta_RSI.mqh new file mode 100644 index 0000000..c29e563 --- /dev/null +++ b/Stg_Meta_RSI.mqh @@ -0,0 +1,334 @@ +/** + * @file + * Implements RSI meta strategy. + */ + +// Prevents processing this includes file multiple times. +#ifndef STG_META_RSI_MQH +#define STG_META_RSI_MQH + +// User input params. +INPUT2_GROUP("Meta RSI strategy: main params"); +INPUT2 ENUM_STRATEGY Meta_RSI_Strategy_RSI_Neutral = STRAT_BANDS; // Strategy for RSI at neutral range (40-60) +INPUT2 ENUM_STRATEGY Meta_RSI_Strategy_RSI_Peak = STRAT_FORCE; // Strategy for RSI at peak range (0-20,80-100) +INPUT2 ENUM_STRATEGY Meta_RSI_Strategy_RSI_Trend = STRAT_AC; // Strategy for RSI at trend range (20-40,60-80) +INPUT2_GROUP("Meta RSI strategy: common params"); +INPUT2 float Meta_RSI_LotSize = 0; // Lot size +INPUT2 int Meta_RSI_SignalOpenMethod = 0; // Signal open method +INPUT2 float Meta_RSI_SignalOpenLevel = 0; // Signal open level +INPUT2 int Meta_RSI_SignalOpenFilterMethod = 32; // Signal open filter method +INPUT2 int Meta_RSI_SignalOpenFilterTime = 3; // Signal open filter time (0-31) +INPUT2 int Meta_RSI_SignalOpenBoostMethod = 0; // Signal open boost method +INPUT2 int Meta_RSI_SignalCloseMethod = 0; // Signal close method +INPUT2 int Meta_RSI_SignalCloseFilter = 32; // Signal close filter (-127-127) +INPUT2 float Meta_RSI_SignalCloseLevel = 0; // Signal close level +INPUT2 int Meta_RSI_PriceStopMethod = 0; // Price limit method +INPUT2 float Meta_RSI_PriceStopLevel = 2; // Price limit level +INPUT2 int Meta_RSI_TickFilterMethod = 32; // Tick filter method (0-255) +INPUT2 float Meta_RSI_MaxSpread = 4.0; // Max spread to trade (in pips) +INPUT2 short Meta_RSI_Shift = 0; // Shift +INPUT2 float Meta_RSI_OrderCloseLoss = 200; // Order close loss +INPUT2 float Meta_RSI_OrderCloseProfit = 200; // Order close profit +INPUT2 int Meta_RSI_OrderCloseTime = 2880; // Order close time in mins (>0) or bars (<0) +INPUT_GROUP("Meta RSI strategy: RSI oscillator params"); +INPUT int Meta_RSI_RSI_Period = 14; // Period +INPUT ENUM_APPLIED_PRICE Meta_RSI_RSI_Applied_Price = PRICE_TYPICAL; // Applied Price +INPUT int Meta_RSI_RSI_Shift = 0; // Shift +INPUT ENUM_IDATA_SOURCE_TYPE Meta_RSI_RSI_SourceType = IDATA_BUILTIN; // Source type + +// Structs. +// Defines struct with default user strategy values. +struct Stg_Meta_RSI_Params_Defaults : StgParams { + Stg_Meta_RSI_Params_Defaults() + : StgParams(::Meta_RSI_SignalOpenMethod, ::Meta_RSI_SignalOpenFilterMethod, ::Meta_RSI_SignalOpenLevel, + ::Meta_RSI_SignalOpenBoostMethod, ::Meta_RSI_SignalCloseMethod, ::Meta_RSI_SignalCloseFilter, + ::Meta_RSI_SignalCloseLevel, ::Meta_RSI_PriceStopMethod, ::Meta_RSI_PriceStopLevel, + ::Meta_RSI_TickFilterMethod, ::Meta_RSI_MaxSpread, ::Meta_RSI_Shift) { + Set(STRAT_PARAM_LS, ::Meta_RSI_LotSize); + Set(STRAT_PARAM_OCL, ::Meta_RSI_OrderCloseLoss); + Set(STRAT_PARAM_OCP, ::Meta_RSI_OrderCloseProfit); + Set(STRAT_PARAM_OCT, ::Meta_RSI_OrderCloseTime); + Set(STRAT_PARAM_SOFT, ::Meta_RSI_SignalOpenFilterTime); + } +}; + +class Stg_Meta_RSI : public Strategy { + protected: + DictStruct> strats; + + public: + Stg_Meta_RSI(StgParams &_sparams, TradeParams &_tparams, ChartParams &_cparams, string _name = "") + : Strategy(_sparams, _tparams, _cparams, _name) {} + + static Stg_Meta_RSI *Init(ENUM_TIMEFRAMES _tf = NULL, EA *_ea = NULL) { + // Initialize strategy initial values. + Stg_Meta_RSI_Params_Defaults stg_rsi_defaults; + StgParams _stg_params(stg_rsi_defaults); + // Initialize Strategy instance. + ChartParams _cparams(_tf, _Symbol); + TradeParams _tparams; + Strategy *_strat = new Stg_Meta_RSI(_stg_params, _tparams, _cparams, "(Meta) RSI"); + return _strat; + } + + /** + * Event on strategy's init. + */ + void OnInit() { + StrategyAdd(Meta_RSI_Strategy_RSI_Neutral, 0); + StrategyAdd(Meta_RSI_Strategy_RSI_Peak, 1); + StrategyAdd(Meta_RSI_Strategy_RSI_Trend, 2); + // Initialize indicators. + { + IndiRSIParams _indi_params(::Meta_RSI_RSI_Period, ::Meta_RSI_RSI_Applied_Price, ::Meta_RSI_RSI_Shift); + _indi_params.SetDataSourceType(::Meta_RSI_RSI_SourceType); + _indi_params.SetTf(PERIOD_D1); + SetIndicator(new Indi_RSI(_indi_params)); + } + } + + /** + * Sets strategy. + */ + bool StrategyAdd(ENUM_STRATEGY _sid, long _index) { + bool _result = true; + long _magic_no = Get(STRAT_PARAM_ID); + ENUM_TIMEFRAMES _tf = Get(STRAT_PARAM_TF); + + switch (_sid) { + case STRAT_NONE: + break; + case STRAT_AC: + _result &= StrategyAdd(_tf, _magic_no, _sid, _index); + break; + case STRAT_AD: + _result &= StrategyAdd(_tf, _magic_no, _sid, _index); + break; + case STRAT_ADX: + _result &= StrategyAdd(_tf, _magic_no, _sid, _index); + break; + case STRAT_AMA: + _result &= StrategyAdd(_tf, _magic_no, _sid, _index); + break; + case STRAT_ARROWS: + _result &= StrategyAdd(_tf, _magic_no, _sid, _index); + break; + case STRAT_ASI: + _result &= StrategyAdd(_tf, _magic_no, _sid, _index); + break; + case STRAT_ATR: + _result &= StrategyAdd(_tf, _magic_no, _sid, _index); + break; + case STRAT_ALLIGATOR: + _result &= StrategyAdd(_tf, _magic_no, _sid, _index); + break; + case STRAT_AWESOME: + _result &= StrategyAdd(_tf, _magic_no, _sid, _index); + break; + case STRAT_BWMFI: + _result &= StrategyAdd(_tf, _magic_no, _sid, _index); + break; + case STRAT_BANDS: + _result &= StrategyAdd(_tf, _magic_no, _sid, _index); + break; + case STRAT_BEARS_POWER: + _result &= StrategyAdd(_tf, _magic_no, _sid, _index); + break; + case STRAT_BULLS_POWER: + _result &= StrategyAdd(_tf, _magic_no, _sid, _index); + break; + case STRAT_CCI: + _result &= StrategyAdd(_tf, _magic_no, _sid, _index); + break; + case STRAT_CHAIKIN: + _result &= StrategyAdd(_tf, _magic_no, _sid, _index); + break; + case STRAT_DEMA: + _result &= StrategyAdd(_tf, _magic_no, _sid, _index); + break; + case STRAT_DPO: + _result &= StrategyAdd(_tf, _magic_no, _sid, _index); + break; + case STRAT_DEMARKER: + _result &= StrategyAdd(_tf, _magic_no, _sid, _index); + break; + case STRAT_ENVELOPES: + _result &= StrategyAdd(_tf, _magic_no, _sid, _index); + break; + case STRAT_FORCE: + _result &= StrategyAdd(_tf, _magic_no, _sid, _index); + break; + case STRAT_FRACTALS: + _result &= StrategyAdd(_tf, _magic_no, _sid, _index); + break; + case STRAT_GATOR: + _result &= StrategyAdd(_tf, _magic_no, _sid, _index); + break; + case STRAT_HEIKEN_ASHI: + _result &= StrategyAdd(_tf, _magic_no, _sid, _index); + break; + case STRAT_ICHIMOKU: + _result &= StrategyAdd(_tf, _magic_no, _sid, _index); + break; + case STRAT_INDICATOR: + _result &= StrategyAdd(_tf, _magic_no, _sid, _index); + break; + case STRAT_MA: + _result &= StrategyAdd(_tf, _magic_no, _sid, _index); + break; + case STRAT_MA_BREAKOUT: + _result &= StrategyAdd(_tf, _magic_no, _sid, _index); + break; + case STRAT_MA_CROSS_PIVOT: + _result &= StrategyAdd(_tf, _magic_no, _sid, _index); + break; + case STRAT_MA_CROSS_SHIFT: + _result &= StrategyAdd(_tf, _magic_no, _sid, _index); + break; + case STRAT_MA_CROSS_SUP_RES: + _result &= StrategyAdd(_tf, _magic_no, _sid, _index); + break; + case STRAT_MA_TREND: + _result &= StrategyAdd(_tf, _magic_no, _sid, _index); + break; + case STRAT_MACD: + _result &= StrategyAdd(_tf, _magic_no, _sid, _index); + break; + case STRAT_MFI: + _result &= StrategyAdd(_tf, _magic_no, _sid, _index); + break; + case STRAT_MOMENTUM: + _result &= StrategyAdd(_tf, _magic_no, _sid, _index); + break; + case STRAT_OBV: + _result &= StrategyAdd(_tf, _magic_no, _sid, _index); + break; + case STRAT_OSCILLATOR: + _result &= StrategyAdd(_tf, _magic_no, _sid, _index); + break; + case STRAT_OSCILLATOR_DIVERGENCE: + _result &= StrategyAdd(_tf, _magic_no, _sid, _index); + break; + case STRAT_OSCILLATOR_MULTI: + _result &= StrategyAdd(_tf, _magic_no, _sid, _index); + break; + case STRAT_OSCILLATOR_CROSS: + _result &= StrategyAdd(_tf, _magic_no, _sid, _index); + break; + case STRAT_OSCILLATOR_CROSS_SHIFT: + _result &= StrategyAdd(_tf, _magic_no, _sid, _index); + break; + case STRAT_OSCILLATOR_CROSS_ZERO: + _result &= StrategyAdd(_tf, _magic_no, _sid, _index); + break; + case STRAT_OSCILLATOR_RANGE: + _result &= StrategyAdd(_tf, _magic_no, _sid, _index); + break; + case STRAT_OSCILLATOR_TREND: + _result &= StrategyAdd(_tf, _magic_no, _sid, _index); + break; + case STRAT_OSMA: + _result &= StrategyAdd(_tf, _magic_no, _sid, _index); + break; + case STRAT_PATTERN: + _result &= StrategyAdd(_tf, _magic_no, _sid, _index); + break; + case STRAT_PINBAR: + _result &= StrategyAdd(_tf, _magic_no, _sid, _index); + break; + case STRAT_PIVOT: + _result &= StrategyAdd(_tf, _magic_no, _sid, _index); + break; + case STRAT_RSI: + _result &= StrategyAdd(_tf, _magic_no, _sid, _index); + break; + case STRAT_RVI: + _result &= StrategyAdd(_tf, _magic_no, _sid, _index); + break; + case STRAT_SAR: + _result &= StrategyAdd(_tf, _magic_no, _sid, _index); + break; + case STRAT_STDDEV: + _result &= StrategyAdd(_tf, _magic_no, _sid, _index); + break; + case STRAT_STOCHASTIC: + _result &= StrategyAdd(_tf, _magic_no, _sid, _index); + break; + case STRAT_WPR: + _result &= StrategyAdd(_tf, _magic_no, _sid, _index); + break; + case STRAT_ZIGZAG: + _result &= StrategyAdd(_tf, _magic_no, _sid, _index); + break; + default: + logger.Warning(StringFormat("Unknown strategy: %d", _sid), __FUNCTION_LINE__, GetName()); + break; + } + + return _result; + } + + /** + * Adds strategy to specific timeframe. + * + * @param + * _tf - timeframe to add the strategy. + * _magic_no - unique order identified + * + * @return + * Returns true if the strategy has been initialized correctly, otherwise false. + */ + template + bool StrategyAdd(ENUM_TIMEFRAMES _tf, long _magic_no = 0, int _type = 0, long _index = 0) { + bool _result = true; + _magic_no = _magic_no > 0 ? _magic_no : rand(); + Ref _strat = ((SClass *)NULL).Init(_tf); + _strat.Ptr().Set(STRAT_PARAM_ID, _magic_no); + _strat.Ptr().Set(STRAT_PARAM_TF, _tf); + _strat.Ptr().Set(STRAT_PARAM_TYPE, _type); + _strat.Ptr().OnInit(); + strats.Set(_index, _strat); + return _result; + } + + /** + * Check strategy's opening signal. + */ + bool SignalOpen(ENUM_ORDER_TYPE _cmd, int _method, float _level = 0.0f, int _shift = 0) { + bool _result = true; + // uint _ishift = _indi.GetShift(); + uint _ishift = _shift; + IndicatorBase *_indi = GetIndicator(); + Ref _strat_ref; + if (_indi[_ishift][0] <= 20 || _indi[_ishift][0] >= 80) { + // RSI value is at peak range (0-20 or 80-100). + _strat_ref = strats.GetByKey(1); + } else if (_indi[_ishift][0] < 40 || _indi[_ishift][0] > 60) { + // RSI value is at trend range (20-40 or 60-80). + _strat_ref = strats.GetByKey(2); + } else if (_indi[_ishift][0] > 40 && _indi[_ishift][0] < 60) { + // RSI value is at neutral range (40-60). + _strat_ref = strats.GetByKey(0); + } + if (!_strat_ref.IsSet()) { + // Returns false when strategy is not set. + return false; + } + _level = _level == 0.0f ? _strat_ref.Ptr().Get(STRAT_PARAM_SOL) : _level; + _method = _method == 0 ? _strat_ref.Ptr().Get(STRAT_PARAM_SOM) : _method; + _shift = _shift == 0 ? _strat_ref.Ptr().Get(STRAT_PARAM_SHIFT) : _shift; + _result &= _strat_ref.Ptr().SignalOpen(_cmd, _method, _level, _shift); + return _result; + } + + /** + * Check strategy's closing signal. + */ + bool SignalClose(ENUM_ORDER_TYPE _cmd, int _method, float _level = 0.0f, int _shift = 0) { + bool _result = false; + _result = SignalOpen(Order::NegateOrderType(_cmd), _method, _level, _shift); + return _result; + } +}; + +#endif // STG_META_RSI_MQH diff --git a/Stg_Meta_Trend.mqh b/Stg_Meta_Trend.mqh deleted file mode 100644 index bdf36a1..0000000 --- a/Stg_Meta_Trend.mqh +++ /dev/null @@ -1,339 +0,0 @@ -/** - * @file - * Implements Trend meta strategy. - */ - -// Prevents processing this includes file multiple times. -#ifndef STG_META_TREND_MQH -#define STG_META_TREND_MQH - -// User input params. -INPUT2_GROUP("Meta Trend strategy: main params"); -INPUT2 ENUM_STRATEGY Meta_Trend_Strategy = STRAT_STOCHASTIC; // Strategy to filter by trend -INPUT2_GROUP("Meta Trend strategy: common params"); -INPUT2 float Meta_Trend_LotSize = 0; // Lot size -INPUT2 int Meta_Trend_SignalOpenMethod = 0; // Signal open method -INPUT2 float Meta_Trend_SignalOpenLevel = 0; // Signal open level -INPUT2 int Meta_Trend_SignalOpenFilterMethod = 32; // Signal open filter method -INPUT2 int Meta_Trend_SignalOpenFilterTime = 3; // Signal open filter time (0-31) -INPUT2 int Meta_Trend_SignalOpenBoostMethod = 0; // Signal open boost method -INPUT2 int Meta_Trend_SignalCloseMethod = 0; // Signal close method -INPUT2 int Meta_Trend_SignalCloseFilter = 32; // Signal close filter (-127-127) -INPUT2 float Meta_Trend_SignalCloseLevel = 0; // Signal close level -INPUT2 int Meta_Trend_PriceStopMethod = 0; // Price limit method -INPUT2 float Meta_Trend_PriceStopLevel = 2; // Price limit level -INPUT2 int Meta_Trend_TickFilterMethod = 32; // Tick filter method (0-255) -INPUT2 float Meta_Trend_MaxSpread = 4.0; // Max spread to trade (in pips) -INPUT2 short Meta_Trend_Shift = 0; // Shift -INPUT2 float Meta_Trend_OrderCloseLoss = 200; // Order close loss -INPUT2 float Meta_Trend_OrderCloseProfit = 200; // Order close profit -INPUT2 int Meta_Trend_OrderCloseTime = 2880; // Order close time in mins (>0) or bars (<0) -INPUT_GROUP("Meta Trend strategy: RSI oscillator params"); -INPUT int Meta_Trend_RSI_Period = 16; // Period -INPUT ENUM_APPLIED_PRICE Meta_Trend_RSI_Applied_Price = PRICE_WEIGHTED; // Applied Price -INPUT int Meta_Trend_RSI_Shift = 0; // Shift -INPUT ENUM_IDATA_SOURCE_TYPE Meta_Trend_RSI_SourceType = IDATA_BUILTIN; // Source type - -// Structs. -// Defines struct with default user strategy values. -struct Stg_Meta_Trend_Params_Defaults : StgParams { - Stg_Meta_Trend_Params_Defaults() - : StgParams(::Meta_Trend_SignalOpenMethod, ::Meta_Trend_SignalOpenFilterMethod, ::Meta_Trend_SignalOpenLevel, - ::Meta_Trend_SignalOpenBoostMethod, ::Meta_Trend_SignalCloseMethod, ::Meta_Trend_SignalCloseFilter, - ::Meta_Trend_SignalCloseLevel, ::Meta_Trend_PriceStopMethod, ::Meta_Trend_PriceStopLevel, - ::Meta_Trend_TickFilterMethod, ::Meta_Trend_MaxSpread, ::Meta_Trend_Shift) { - Set(STRAT_PARAM_LS, ::Meta_Trend_LotSize); - Set(STRAT_PARAM_OCL, ::Meta_Trend_OrderCloseLoss); - Set(STRAT_PARAM_OCP, ::Meta_Trend_OrderCloseProfit); - Set(STRAT_PARAM_OCT, ::Meta_Trend_OrderCloseTime); - Set(STRAT_PARAM_SOFT, ::Meta_Trend_SignalOpenFilterTime); - } -}; - -class Stg_Meta_Trend : public Strategy { - protected: - Ref strat; - - public: - Stg_Meta_Trend(StgParams &_sparams, TradeParams &_tparams, ChartParams &_cparams, string _name = "") - : Strategy(_sparams, _tparams, _cparams, _name) {} - - static Stg_Meta_Trend *Init(ENUM_TIMEFRAMES _tf = NULL, EA *_ea = NULL) { - // Initialize strategy initial values. - Stg_Meta_Trend_Params_Defaults stg_trend_defaults; - StgParams _stg_params(stg_trend_defaults); - // Initialize Strategy instance. - ChartParams _cparams(_tf, _Symbol); - TradeParams _tparams; - Strategy *_strat = new Stg_Meta_Trend(_stg_params, _tparams, _cparams, "(Meta) Trend"); - return _strat; - } - - /** - * Event on strategy's init. - */ - void OnInit() { - SetStrategy(Meta_Trend_Strategy); - // Initialize indicators. - { - IndiRSIParams _indi_params(::Meta_Trend_RSI_Period, ::Meta_Trend_RSI_Applied_Price, ::Meta_Trend_RSI_Shift); - _indi_params.SetDataSourceType(::Meta_Trend_RSI_SourceType); - _indi_params.SetTf(PERIOD_D1); - SetIndicator(new Indi_RSI(_indi_params)); - } - } - - /** - * Sets strategy. - */ - bool SetStrategy(ENUM_STRATEGY _sid) { - bool _result = true; - long _magic_no = Get(STRAT_PARAM_ID); - ENUM_TIMEFRAMES _tf = Get(STRAT_PARAM_TF); - - switch (_sid) { - case STRAT_NONE: - break; - case STRAT_AC: - _result &= StrategyAdd(_tf, _magic_no, _sid); - break; - case STRAT_AD: - _result &= StrategyAdd(_tf, _magic_no, _sid); - break; - case STRAT_ADX: - _result &= StrategyAdd(_tf, _magic_no, _sid); - break; - case STRAT_AMA: - _result &= StrategyAdd(_tf, _magic_no, _sid); - break; - case STRAT_ARROWS: - _result &= StrategyAdd(_tf, _magic_no, _sid); - break; - case STRAT_ASI: - _result &= StrategyAdd(_tf, _magic_no, _sid); - break; - case STRAT_ATR: - _result &= StrategyAdd(_tf, _magic_no, _sid); - break; - case STRAT_ALLIGATOR: - _result &= StrategyAdd(_tf, _magic_no, _sid); - break; - case STRAT_AWESOME: - _result &= StrategyAdd(_tf, _magic_no, _sid); - break; - case STRAT_BWMFI: - _result &= StrategyAdd(_tf, _magic_no, _sid); - break; - case STRAT_BANDS: - _result &= StrategyAdd(_tf, _magic_no, _sid); - break; - case STRAT_BEARS_POWER: - _result &= StrategyAdd(_tf, _magic_no, _sid); - break; - case STRAT_BULLS_POWER: - _result &= StrategyAdd(_tf, _magic_no, _sid); - break; - case STRAT_CCI: - _result &= StrategyAdd(_tf, _magic_no, _sid); - break; - case STRAT_CHAIKIN: - _result &= StrategyAdd(_tf, _magic_no, _sid); - break; - case STRAT_DEMA: - _result &= StrategyAdd(_tf, _magic_no, _sid); - break; - case STRAT_DEMARKER: - _result &= StrategyAdd(_tf, _magic_no, _sid); - break; - case STRAT_DPO: - _result &= StrategyAdd(_tf, _magic_no, _sid); - break; - case STRAT_ENVELOPES: - _result &= StrategyAdd(_tf, _magic_no, _sid); - break; - case STRAT_FORCE: - _result &= StrategyAdd(_tf, _magic_no, _sid); - break; - case STRAT_FRACTALS: - _result &= StrategyAdd(_tf, _magic_no, _sid); - break; - case STRAT_GATOR: - _result &= StrategyAdd(_tf, _magic_no, _sid); - break; - case STRAT_HEIKEN_ASHI: - _result &= StrategyAdd(_tf, _magic_no, _sid); - break; - case STRAT_ICHIMOKU: - _result &= StrategyAdd(_tf, _magic_no, _sid); - break; - case STRAT_INDICATOR: - _result &= StrategyAdd(_tf, _magic_no, _sid); - break; - case STRAT_MA: - _result &= StrategyAdd(_tf, _magic_no, _sid); - break; - case STRAT_MA_BREAKOUT: - _result &= StrategyAdd(_tf, _magic_no, _sid); - break; - case STRAT_MA_CROSS_PIVOT: - _result &= StrategyAdd(_tf, _magic_no, _sid); - break; - case STRAT_MA_CROSS_SHIFT: - _result &= StrategyAdd(_tf, _magic_no, _sid); - break; - case STRAT_MA_CROSS_SUP_RES: - _result &= StrategyAdd(_tf, _magic_no, _sid); - break; - case STRAT_MA_TREND: - _result &= StrategyAdd(_tf, _magic_no, _sid); - break; - case STRAT_MACD: - _result &= StrategyAdd(_tf, _magic_no, _sid); - break; - case STRAT_MFI: - _result &= StrategyAdd(_tf, _magic_no, _sid); - break; - case STRAT_MOMENTUM: - _result &= StrategyAdd(_tf, _magic_no, _sid); - break; - case STRAT_OBV: - _result &= StrategyAdd(_tf, _magic_no, _sid); - break; - case STRAT_OSCILLATOR: - _result &= StrategyAdd(_tf, _magic_no, _sid); - break; - case STRAT_OSCILLATOR_DIVERGENCE: - _result &= StrategyAdd(_tf, _magic_no, _sid); - break; - case STRAT_OSCILLATOR_MULTI: - _result &= StrategyAdd(_tf, _magic_no, _sid); - break; - case STRAT_OSCILLATOR_CROSS: - _result &= StrategyAdd(_tf, _magic_no, _sid); - break; - case STRAT_OSCILLATOR_CROSS_SHIFT: - _result &= StrategyAdd(_tf, _magic_no, _sid); - break; - case STRAT_OSCILLATOR_CROSS_ZERO: - _result &= StrategyAdd(_tf, _magic_no, _sid); - break; - case STRAT_OSCILLATOR_RANGE: - _result &= StrategyAdd(_tf, _magic_no, _sid); - break; - case STRAT_OSCILLATOR_TREND: - _result &= StrategyAdd(_tf, _magic_no, _sid); - break; - case STRAT_OSMA: - _result &= StrategyAdd(_tf, _magic_no, _sid); - break; - case STRAT_PATTERN: - _result &= StrategyAdd(_tf, _magic_no, _sid); - break; - case STRAT_PINBAR: - _result &= StrategyAdd(_tf, _magic_no, _sid); - break; - case STRAT_PIVOT: - _result &= StrategyAdd(_tf, _magic_no, _sid); - break; - case STRAT_RSI: - _result &= StrategyAdd(_tf, _magic_no, _sid); - break; - case STRAT_RVI: - _result &= StrategyAdd(_tf, _magic_no, _sid); - break; - case STRAT_SAR: - _result &= StrategyAdd(_tf, _magic_no, _sid); - break; - case STRAT_STDDEV: - _result &= StrategyAdd(_tf, _magic_no, _sid); - break; - case STRAT_STOCHASTIC: - _result &= StrategyAdd(_tf, _magic_no, _sid); - break; - case STRAT_WPR: - _result &= StrategyAdd(_tf, _magic_no, _sid); - break; - case STRAT_ZIGZAG: - _result &= StrategyAdd(_tf, _magic_no, _sid); - break; - default: - logger.Warning(StringFormat("Unknown strategy: %d", _sid), __FUNCTION_LINE__, GetName()); - break; - } - - return _result; - } - - /** - * Adds strategy to specific timeframe. - * - * @param - * _tf - timeframe to add the strategy. - * _magic_no - unique order identified - * - * @return - * Returns true if the strategy has been initialized correctly, otherwise false. - */ - template - bool StrategyAdd(ENUM_TIMEFRAMES _tf, long _magic_no = 0, int _type = 0) { - bool _result = true; - _magic_no = _magic_no > 0 ? _magic_no : rand(); - Ref _strat = ((SClass *)NULL).Init(_tf); - _strat.Ptr().Set(STRAT_PARAM_ID, _magic_no); - _strat.Ptr().Set(STRAT_PARAM_TF, _tf); - _strat.Ptr().Set(STRAT_PARAM_TYPE, _type); - _strat.Ptr().OnInit(); - strat = _strat; - return _result; - } - - /** - * Check strategy's opening signal. - */ - bool SignalOpen(ENUM_ORDER_TYPE _cmd, int _method, float _level = 0.0f, int _shift = 0) { - bool _result = true; - if (!strat.IsSet()) { - // Returns false when strategy is not set. - return false; - } - IndicatorBase *_indi = GetIndicator(); - // uint _ishift = _indi.GetShift(); - uint _ishift = _shift; - switch (_cmd) { - case ORDER_TYPE_BUY: - _result &= _indi[_shift][0] >= 50 - _level && _indi[_shift + 1][0] >= 50 - _level; - break; - case ORDER_TYPE_SELL: - _result &= _indi[_shift][0] <= 50 + _level && _indi[_shift + 1][0] <= 50 + _level; - break; - } - _level = _level == 0.0f ? strat.Ptr().Get(STRAT_PARAM_SOL) : _level; - _method = _method == 0 ? strat.Ptr().Get(STRAT_PARAM_SOM) : _method; - _shift = _shift == 0 ? strat.Ptr().Get(STRAT_PARAM_SHIFT) : _shift; - _result &= strat.Ptr().SignalOpen(_cmd, _method, _level, _shift); - return _result; - } - - /** - * Check strategy's closing signal. - */ - bool SignalClose(ENUM_ORDER_TYPE _cmd, int _method, float _level = 0.0f, int _shift = 0) { - bool _result = true; - if (!strat.IsSet()) { - // Returns false when strategy is not set. - return false; - } - IndicatorBase *_indi = GetIndicator(); - switch (_cmd) { - case ORDER_TYPE_BUY: - _result &= _indi[_shift][0] <= 50 + _level && _indi[_shift + 1][0] <= 50 + _level; - break; - case ORDER_TYPE_SELL: - _result &= _indi[_shift][0] >= 50 - _level && _indi[_shift + 1][0] >= 50 - _level; - break; - } - return _result; - } -}; - -#endif // STG_META_TREND_MQH