diff --git a/Documents/BKP/1/1.mq5 b/Documents/BKP/1/1.mq5 new file mode 100644 index 00000000..90e6eeb9 --- /dev/null +++ b/Documents/BKP/1/1.mq5 @@ -0,0 +1,580 @@ +////////////////////////////////////////////////////// +// +// SaherElm IT Center MQL5 Indicator +// --------------------------------------------- +// Name: XSTR +// Description: Super Trend Indicator ... +// +// +// Maintainer: +// ------------ +// Hadi Khazaee Asl (hadi_khazaee_asl@yahoo.com) +// +////////////////////////////////////////////////////// +// +// Global Properties ... +#property copyright "Copyright 2023, SaherElm IT Center" +#property link "https://saherelm.ir" +#property version "1.00" +#property description "SaherElm X121_XAMA Indicator" +#property strict + +// +// START Constants ... +// + +#define ShortName "XSTR" + +// +// END Constants ... +// + +// +// START Inputs ... +// + +// +// Market ... +input group "ATR"; +input int atrLength = 14; // Length +input double atrMultiplier = 3.0; // Multiplier +input ENUM_APPLIED_PRICE atrAppliedTo = PRICE_MEDIAN; // Applied To + +// +// Presentation ... +input group "Presentation"; +input bool showTrends = true; // Show Trends +input bool fillTrends = true; // Fill Trends + +// +// END Inputs ... +// + +// +// Includes Common Library ... +#include "../Libraries/x-saherelm.common.lib.mq5" + +// +// START Buffers ... +// + +// +#property indicator_chart_window + +// +#property indicator_buffers 9 +#property indicator_plots 2 + +// +#define fillUpBufferIndex 0 +double fillUpBuffer[]; + +#define fillDownBufferIndex 1 +double fillDownBuffer[]; + +// +#define fillingPlotBufferIndex 0 + +// +#property indicator_label1 "XSTR Filling" +#property indicator_type1 DRAW_FILLING +#property indicator_color1 clrBisque, clrPaleGreen + +// +#define mainBufferIndex 2 +#define mainPlotBufferIndex 1 +double mainBuffer[]; + +// +#define mainColorBufferIndex 3 +double mainColorBuffer[]; + +// +#property indicator_label2 "XSTR" +#property indicator_type2 DRAW_COLOR_LINE +#property indicator_color2 CLR_NONE, clrGreen, clrDarkRed +#property indicator_style2 STYLE_DOT + +// +// DATA Buffers ... + +// +#define atrBufferIndex 4 +double atrBuffer[]; + +// +#define trendBufferIndex 5 +double trendBuffer[]; + +// +#define upBufferIndex 6 +double upBuffer[]; + +// +#define downBufferIndex 7 +double downBuffer[]; + +// +#define priceBufferIndex 8 +double priceBuffer[]; + +// +// END Buffers ... +// + +// +// START Global Definitions: Variables, Properties and etc ... +// + +// +int maxLength; + +// +int atrHandler = INVALID_HANDLE; + +// +int changeOfTrend; +int startBearishTrend; +int startBullishTrend; + +// +// END Global Definitions: Variables, Properties and etc ... +// + +// +// START Event Handlers ... +// + +// +// Initialization ... +int OnInit() +{ + // + // Validate Inputs ... + if (!ValidateInputs()) + { + return INIT_PARAMETERS_INCORRECT; + } + + // + // because in some cases we may have more than one input for + // calculation and we must prevent any calculation + // untill we pass the biggest input length, here we get max Input length + // and then wait until pass it ... + maxLength = ExtractMaxLengthOfInputs(); + + // + atrHandler = iATR( + _Symbol, + _Period, + atrLength); + if (atrHandler == INVALID_HANDLE) + { + return INIT_FAILED; + } + + // + // Define Index Buffers ... + DefineBuffers(); + + // + // Set Indicator ShortName ... + SetIndicatorName(); + + // + // Init Succeed ... + return INIT_SUCCEEDED; +} + +// +// DeInitialization ... +void OnDeinit(const int reason) +{ + // + // REASON_PROGRAM 0 The EA has stopped working calling the ExpertRemove() function + // REASON_REMOVE 1 Program removed from a chart + // REASON_RECOMPILE 2 Program recompiled + // REASON_CHARTCHANGE 3 A symbol or a chart period is changed + // REASON_CHARTCLOSE 4 Chart closed + // REASON_PARAMETERS 5 Inputs changed by a user + // REASON_ACCOUNT 6 Another account has been activated or reconnection to the trade server has occurred due to changes in the account settings + // REASON_TEMPLATE 7 Another chart template applied + // REASON_INITFAILED 8 The OnInit() handler returned a non-zero value + // REASON_CLOSE 9 Terminal closed + + // + // Here we can handle De Initialization Reasons ... + IndicatorRelease(atrHandler); +} + +// +// Calculating what we want ... +int OnCalculate( + // + // total Candles on chart ... + const int rates_total, + // + // total calculated Candles on charts ... + const int prev_calculated, + // + // history of Candles Open Time ... + const datetime &time[], + // + // history of Candles Open Price ... + const double &open[], + // + // history of Candles High Price ... + const double &high[], + // + // history of Candles Low Price ... + const double &low[], + // + // history of Candles Close Price ... + const double &close[], + // + // history of Tick Volumes on Candle ... + const long &tick_volume[], + // + // history of Trade Volumes ... + const long &volume[], + // + // history of Candles Spread Price ... + const int &spread[]) +{ + // + int numOfRequiredAtrs; + if (prev_calculated > rates_total || prev_calculated < 0) + { + numOfRequiredAtrs = rates_total; + } + else + { + // + numOfRequiredAtrs = rates_total - prev_calculated; + if (prev_calculated > 0) + { + numOfRequiredAtrs++; + } + } + + // + // Checking for stop ... + if (IsStopped()) + { + return 0; + } + + // + // Check Number of items Copy or not ... + int copiedATRs = CopyBuffer(atrHandler, 0, 0, numOfRequiredAtrs, atrBuffer); + if (copiedATRs <= 0) + { + return 0; + } + + // + int limit; + + // + // checking for the limit start of calculation of an indicator ... + if (prev_calculated > rates_total || prev_calculated <= 0) + { + // + // starting index for calculation of all bars ... + limit = maxLength; + } + else + { + // + // starting number for calculation of new bars + limit = prev_calculated - 1; + } + + // + // Main Loop ... + for (int i = limit; i < rates_total && !IsStopped(); i++) + { + // + // Calculated Price ... + double price = getPrice( + atrAppliedTo, + open, + high, + low, + close, + i); + // price = (high[i] + low[i]) / 2; + priceBuffer[i] = price; + + // + double atr = atrBuffer[i]; + + // + // Up ... + upBuffer[i] = price + (atrMultiplier * atr); + + // + // Down ... + downBuffer[i] = price - (atrMultiplier * atr); + + // + if (close[i] > upBuffer[i - 1]) + { + // + trendBuffer[i] = 1; + if (trendBuffer[i - 1] == -1) + { + changeOfTrend = 1; + } + } + else if (close[i] < downBuffer[i - 1]) + { + // + trendBuffer[i] = -1; + if (trendBuffer[i - 1] == 1) + { + changeOfTrend = 1; + } + } + else if (trendBuffer[i - 1] == 1) + { + // + trendBuffer[i] = 1; + changeOfTrend = 0; + } + else if (trendBuffer[i - 1] == -1) + { + // + trendBuffer[i] = -1; + changeOfTrend = 0; + } + + // + // Down Trend Starting ... + if (trendBuffer[i] < 0 && trendBuffer[i - 1] > 0) + { + startBearishTrend = 1; + } + else + { + startBearishTrend = 0; + } + + // + // Up Trend Starting ... + if (trendBuffer[i] > 0 && trendBuffer[i - 1] < 0) + { + startBullishTrend = 1; + } + else + { + startBullishTrend = 0; + } + + // + if (trendBuffer[i] > 0 && downBuffer[i] < downBuffer[i - 1]) + { + downBuffer[i] = downBuffer[i - 1]; + } + + // + if (trendBuffer[i] < 0 && upBuffer[i] > upBuffer[i - 1]) + { + upBuffer[i] = upBuffer[i - 1]; + } + + // + if (startBearishTrend == 1) + { + upBuffer[i] = priceBuffer[i] + (atrMultiplier * atr); + } + + // + if (startBullishTrend == 1) + { + downBuffer[i] = priceBuffer[i] - (atrMultiplier * atr); + } + + // + // Draw the indicator ... + + // + double colorIDX = 0; + mainColorBuffer[i] = colorIDX; + + // + if (trendBuffer[i] == 1) + { + // + mainBuffer[i] = downBuffer[i]; + if (changeOfTrend == 1) + { + mainBuffer[i - 1] = mainBuffer[i - 2]; + changeOfTrend = 0; + } + + // + colorIDX = 1; + } + else if (trendBuffer[i] == -1) + { + // + mainBuffer[i] = upBuffer[i]; + if (changeOfTrend == 1) + { + // + mainBuffer[i - 1] = mainBuffer[i - 2]; + changeOfTrend = 0; + } + + // + colorIDX = 2; + } + + // + if (showTrends) + { + mainColorBuffer[i] = colorIDX; + } + + // + // Filling ... + if (fillTrends) + { + // + fillUpBuffer[i] = mainBuffer[i]; + fillDownBuffer[i] = close[i]; + } + else + { + // + fillUpBuffer[i] = EMPTY_VALUE; + fillDownBuffer[i] = EMPTY_VALUE; + } + } + + // + return rates_total; +} + +// +// END Event Handlers ... +// + +// +// START Functions ... +// + +// +// Validate Input Args for Initialization ... +bool ValidateInputs() +{ + // + bool result = false; + + // + // Validate Args ... + result = + // + atrLength >= 2 + // + ; + + // + return result; +} + +// +// Retrieve all Exists Input Max Length ... +// use for Start Of Drawing ... +int ExtractMaxLengthOfInputs() +{ + // + int result = 0; + + // + result = atrLength; + + // + return result; +} + +// +// Set Indicator Short Name and also we can define Buffers Labels ... +void SetIndicatorName() +{ + IndicatorSetString(INDICATOR_SHORTNAME, ShortName); +} + +// +// Define Indexes and Styles ... +void DefineBuffers() +{ + // + // PLOT Buffers ... + + // + // FILLINGS ... + SetIndexBuffer(fillUpBufferIndex, fillUpBuffer, INDICATOR_DATA); + SetIndexBuffer(fillDownBufferIndex, fillDownBuffer, INDICATOR_DATA); + PlotIndexSetInteger(fillingPlotBufferIndex, PLOT_SHOW_DATA, false); + + // + // MAIN ... + SetIndexBuffer(mainBufferIndex, mainBuffer, INDICATOR_DATA); + PlotIndexSetInteger(mainPlotBufferIndex, PLOT_SHOW_DATA, showTrends); + SetIndexBuffer(mainColorBufferIndex, mainColorBuffer, INDICATOR_COLOR_INDEX); + + // + // DATA Buffers ... + + // + // ATR ... + SetIndexBuffer(atrBufferIndex, atrBuffer, INDICATOR_CALCULATIONS); + + // + // TREND ... + SetIndexBuffer(trendBufferIndex, trendBuffer, INDICATOR_CALCULATIONS); + + // + // UP ... + SetIndexBuffer(upBufferIndex, upBuffer, INDICATOR_CALCULATIONS); + + // + // DOWN ... + SetIndexBuffer(downBufferIndex, downBuffer, INDICATOR_CALCULATIONS); + + // + // PRICE ... + SetIndexBuffer(priceBufferIndex, priceBuffer, INDICATOR_CALCULATIONS); +} + +// +// END Functions ... +// + +// +// TEMPLATE Function ... + +template +double getPrice(ENUM_APPLIED_PRICE tprice, T &open[], T &high[], T &low[], T &close[], int i) +{ + switch (tprice) + { + case PRICE_CLOSE: + return (close[i]); + case PRICE_OPEN: + return (open[i]); + case PRICE_HIGH: + return (high[i]); + case PRICE_LOW: + return (low[i]); + case PRICE_MEDIAN: + return ((high[i] + low[i]) / 2.0); + case PRICE_TYPICAL: + return ((high[i] + low[i] + close[i]) / 3.0); + case PRICE_WEIGHTED: + return ((high[i] + low[i] + close[i] + close[i]) / 4.0); + } + return (0); +} diff --git a/Documents/BKP/1/2.mq5 b/Documents/BKP/1/2.mq5 new file mode 100644 index 00000000..3081db24 --- /dev/null +++ b/Documents/BKP/1/2.mq5 @@ -0,0 +1,195 @@ + +//+------------------------------------------------------------------+ +//| SuperTrend.mq5 | +//| Copyright 2011, FxGeek | +//| http://www.mql5.com | +//+------------------------------------------------------------------+ +#property copyright "Copyright 2011, FxGeek" +#property link " http://www.mql5.com" +#property version "1.00" +#property indicator_chart_window +#property indicator_buffers 9 +#property indicator_plots 2 + +#property indicator_label1 "Filling" +#property indicator_type1 DRAW_FILLING +#property indicator_color1 clrBisque, clrPaleGreen + +#property indicator_label2 "SuperTrend" +#property indicator_type2 DRAW_COLOR_LINE +#property indicator_color2 clrGreen, clrRed + +input int Periode=10; +input double Multiplier=3; +input bool Show_Filling=true; // Show as DRAW_FILLING + +double Filled_a[]; +double Filled_b[]; +double SuperTrend[]; +double ColorBuffer[]; +double Atr[]; +double Up[]; +double Down[]; +double Middle[]; +double trend[]; + +int atrHandle; +int changeOfTrend; +int flag; +int flagh; +//+------------------------------------------------------------------+ +//| Custom indicator initialization function | +//+------------------------------------------------------------------+ +int OnInit() + { +//--- indicator buffers mapping + SetIndexBuffer(0,Filled_a,INDICATOR_DATA); + SetIndexBuffer(1,Filled_b,INDICATOR_DATA); + SetIndexBuffer(2,SuperTrend,INDICATOR_DATA); + SetIndexBuffer(3,ColorBuffer,INDICATOR_COLOR_INDEX); + SetIndexBuffer(4,Atr,INDICATOR_CALCULATIONS); + SetIndexBuffer(5,Up,INDICATOR_CALCULATIONS); + SetIndexBuffer(6,Down,INDICATOR_CALCULATIONS); + SetIndexBuffer(7,Middle,INDICATOR_CALCULATIONS); + SetIndexBuffer(8,trend,INDICATOR_CALCULATIONS); + + atrHandle=iATR(_Symbol,_Period,Periode); +//--- + return(0); + } +//+------------------------------------------------------------------+ +//| Custom indicator iteration function | +//+------------------------------------------------------------------+ +int OnCalculate(const int rates_total, + const int prev_calculated, + const datetime &time[], + const double &open[], + const double &high[], + const double &low[], + const double &close[], + const long &tick_volume[], + const long &volume[], + const int &spread[]) + { +//--- + int to_copy; + if(prev_calculated>rates_total || prev_calculated<0) to_copy=rates_total; + else + { + to_copy=rates_total-prev_calculated; + if(prev_calculated>0) to_copy++; + } + + if(IsStopped()) return(0); //Checking for stop flag + if(CopyBuffer(atrHandle,0,0,to_copy,Atr)<=0) + { + Print("Getting Atr is failed! Error",GetLastError()); + return(0); + } + + int first; + if(prev_calculated>rates_total || prev_calculated<=0) // checking for the first start of calculation of an indicator + { + first=Periode; // starting index for calculation of all bars + } + else + { + first=prev_calculated-1; // starting number for calculation of new bars + } + for(int i=first; iUp[i-1]) + { + trend[i]=1; + if(trend[i-1]==-1) changeOfTrend=1; + + } + else if(close[i]0) + { + flag=1; + } + else + { + flag=0; + } + + if(trend[i]>0 && trend[i-1]<0) + { + flagh=1; + } + else + { + flagh=0; + } + + if(trend[i]>0 && Down[i]Up[i-1]) + Up[i]=Up[i-1]; + + if(flag==1) + Up[i]=Middle[i]+(Multiplier*Atr[i]); + + if(flagh==1) + Down[i]=Middle[i]-(Multiplier*Atr[i]); + + //-- Draw the indicator + if(trend[i]==1) + { + SuperTrend[i]=Down[i]; + if(changeOfTrend==1) + { + SuperTrend[i-1]=SuperTrend[i-2]; + changeOfTrend=0; + } + ColorBuffer[i]=0.0; + } + else if(trend[i]==-1) + { + SuperTrend[i]=Up[i]; + if(changeOfTrend==1) + { + SuperTrend[i-1]= SuperTrend[i-2]; + changeOfTrend = 0; + } + ColorBuffer[i]=1.0; + } + + if(Show_Filling) + { + Filled_a[i]= SuperTrend[i]; + Filled_b[i]= close[i]; + }else{ + Filled_a[i]= EMPTY_VALUE; + Filled_b[i]= EMPTY_VALUE; + } + + } + +//--- return value of prev_calculated for next call + return(rates_total); + } +//+------------------------------------------------------------------+ + + \ No newline at end of file diff --git a/Documents/BKP/1/x-saherelm.x121.helper.mq5 b/Documents/BKP/1/x-saherelm.x121.helper.mq5 new file mode 100644 index 00000000..e2bb0557 --- /dev/null +++ b/Documents/BKP/1/x-saherelm.x121.helper.mq5 @@ -0,0 +1,4636 @@ +/////////////////////////////////////////////////////// +// +// SaherElm IT Center MQL5 Helper Class Library +// ---------------------------------------------- +// Name: XCX121Helper +// Description: provides all Indicator +// Helper requirements ... +// +// +// 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 + +// +// Imports ... +#include "../Classes/x-saherelm.x-helper.class.mq5" + +// +// Definitions ... +enum ENUM_X121_BUFFERS +{ + // + // Main Buffers ... + X121_PEAKS_LINE = 0, + X121_VALES_LINE = 1, + X121_SAR_LINE = 2, + X121_ATR_UPPER_LINE = 3, + X121_ATR_LOWER_LINE = 4, + X121_STR_LOWER_LINE = 5, + X121_VWAP_FAST_LINE = 7, + X121_VWAP_MID_LINE = 9, + X121_VWAP_SLOW_LINE = 11, + X121_DON_OPEN_UPPER_LINE = 13, + X121_DON_OPEN_LOWER_LINE = 14, + X121_DON_HIGH_UPPER_LINE = 15, + X121_DON_HIGH_LOWER_LINE = 16, + X121_DON_LOW_UPPER_LINE = 17, + X121_DON_LOW_LOWER_LINE = 18, + X121_DON_CLOSE_UPPER_LINE = 19, + X121_DON_CLOSE_LOWER_LINE = 20, + // + // Data Buffers ... + // + // XPV Data ... + X121_CURRENT_HH_LINE = 21, + X121_CURRENT_LL_LINE = 22, + X121_SHORT_HH_LINE = 23, + X121_SHORT_LL_LINE = 24, + X121_MEDIUM_HH_LINE = 25, + X121_MEDIUM_LL_LINE = 26, + X121_LONG_HH_LINE = 27, + X121_LONG_LL_LINE = 28, + X121_HIND_HH_LINE = 29, + X121_HIND_LL_LINE = 30, + // + // VWAP Data ... + X121_VWAP_VOLUME_LINE = 31, + X121_VWAP_PRICE_LINE = 32, + X121_VWAP_FAST_STATE_LINE = 33, + X121_VWAP_MID_STATE_LINE = 34, + X121_VWAP_SLOW_STATE_LINE = 35, + // + // ATR ... + X121_ATR_LINE = 36, + X121_ATR_UPPER_RAW_LINE = 37, + X121_ATR_LOWER_RAW_LINE = 38, + // + // RSI ... + X121_RSI_LINE = 39, + // + // STR ... + X121_STR_PRICE_LINE = 40, + X121_STR_UP_LINE = 41, + X121_STR_DOWN_LINE = 42, + X121_STR_STATE_LINE = 43, +}; + +// +enum ENUM_XVWAP_STATES +{ + // + XVWAP_STATE_BULLISH = 1, + XVWAP_STATE_BEARISH = 2, + XVWAP_STATE_NEUTURAL = 3, +}; + +// +// Inputs ... +struct X121Inputs +{ + // + // Props ... + + // + // Cycles ... + + // + // Short ... + ENUM_X_PERIOD_METHOD scMethod; // How to Find Period + ENUM_TIMEFRAMES scPeriod; // Time Period + + // + // Medium ... + ENUM_X_PERIOD_METHOD mcMethod; // How to Find Period + ENUM_TIMEFRAMES mcPeriod; // Time Period + + // + // Long ... + ENUM_X_PERIOD_METHOD lcMethod; // How to Find Period + ENUM_TIMEFRAMES lcPeriod; // Time Period + + // + // Hind ... + ENUM_X_PERIOD_METHOD hcMethod; // How to Find Period + ENUM_TIMEFRAMES hcPeriod; // Time Period + + // + // Boundary Detection ... + ENUM_SERIESMODE hhMode; // Highest High Calculation Method + ENUM_SERIESMODE llMode; // Lowest Low Calculation Method + + // + // Parabolic Sar Detection ... + double sarStep; // Step + double sarMax; // Maximum + + // + // RSI ... + int rsiLength; // Length + double rsiOverSoldLevel; // Over Sold Level + double rsiOverBoughtLevel; // Over Bought Level + ENUM_APPLIED_PRICE rsiAppliedTo; // Applied To + + // + // Atr Detection ... + int atrLength; // Length + double atrMultiplier; // Multiplier + ENUM_APPLIED_PRICE atrUpperAppliedTo; // Upper Zone Applied To + ENUM_APPLIED_PRICE atrLowerAppliedTo; // Lower Zone Applied To + ENUM_X_MA_METHOD atrSmoothingMode; // Smoothing Method + + // + // Str Detection ... + ENUM_APPLIED_PRICE strAppliedTo; // Applied To + + // + // VWap Detection ... + int vwapFastLength; // Fast Length + int vwapMidLength; // Mid Length + int vwapSlowLength; // Slow Length + ENUM_APPLIED_PRICE vwapAppliedTo; // Applied To + + // + // Donchain Detection ... + int donchainLength; // Donchain Length + + // + // Presentation ... + + // + int startCalculationForLastBars; // Calculate Last n Bars + + // + int sarArrowCode; // Parabolic Sar Arrow Code + int peaksArrowCode; // Peaks Arrow Code + int valesArrowCode; // Vales Arrow Code + + // + // Global ... + bool showSar; // Show Parabolic Sar + bool showAtr; // Show Atr + bool showStr; // Show Str + bool showPeaks; // Show Peaks + bool showVales; // Show Vales + bool showVWap; // Show VWap + bool showDonchain; // Show Donchain + + // + // Atr Presentation ... + bool showAtrUpper; // Show Upper Zone + bool showAtrLower; // Show Lower Zone + + // + // VWap Presentation ... + bool showVWapFast; // Show VWap Fast + bool showVWapMedium; // Show VWap Medium + bool showVWapSlow; // Show VWap Slow + + // + // Donchain Presentation ... + + // + bool showUpper; // Show Upper Band + bool showLower; // Show Lower Band + + // + bool showOpen; // Show Open + bool showHigh; // Show High + bool showClose; // Show Close + bool showLow; // Show Low + + // + // Constructor ... + X121Inputs() + { + Clean(); + } + + // + // Tools ... + + /** + * Cleaning Up ... + */ + void Clean() + { + // + // Cycles ... + + // + // Short ... + scMethod = X_PERIOD_NOTHING; + scPeriod = NULL; + + // + // Medium ... + mcMethod = X_PERIOD_NOTHING; + mcPeriod = NULL; + + // + // Long ... + lcMethod = X_PERIOD_NOTHING; + lcPeriod = NULL; + + // + // Hind ... + hcMethod = X_PERIOD_NOTHING; + hcPeriod = NULL; + + // + // Boundary Detection ... + hhMode = MODE_HIGH; + llMode = MODE_LOW; + + // + // RSI ... + rsiLength = 0; + rsiOverSoldLevel = 0; + rsiOverBoughtLevel = 0; + rsiAppliedTo = PRICE_CLOSE; + + // + // Paraboli Sar Detection ... + sarStep = 0; + sarMax = 0; + + // + // Atr Detection ... + atrLength = 0; // Length + atrMultiplier = 0; // Multiplier + atrUpperAppliedTo = PRICE_HIGH; // Upper Zone Applied To + atrLowerAppliedTo = PRICE_LOW; // Lower Zone Applied To + atrSmoothingMode = X_MA_MODE_NONE; // Smoothing Method + + // + // Str Detection ... + strAppliedTo = PRICE_MEDIAN; + + // + // VWap Detection ... + vwapFastLength = 0; + vwapMidLength = 0; + vwapSlowLength = 0; + vwapAppliedTo = PRICE_CLOSE; + + // + // Donchain Detection ... + donchainLength = 0; + + // + // Presentation ... + + // + startCalculationForLastBars = 0; + + // + sarArrowCode = 0; + peaksArrowCode = 0; + valesArrowCode = 0; + + // + // Globals ... + showSar = false; + showAtr = false; + showStr = false; + showPeaks = false; + showVales = false; + showVWap = false; + showDonchain = false; + + // + // Atr Presentation ... + showAtrUpper = false; // Show Upper Zone + showAtrLower = false; // Show Lower Zone + + // + // VWap Presentation ... + showVWapFast = false; + showVWapMedium = false; + showVWapSlow = false; + + // + // Donchain Presentation ... + + // + showUpper = false; + showLower = false; + + // + showOpen = false; + showHigh = false; + showClose = false; + showLow = false; + } + + /** + * Set Default Values ... + */ + void Default() + { + // + // Cycles ... + + // + // Short ... + scMethod = X_PERIOD_AUTO; + scPeriod = NULL; + + // + // Medium ... + mcMethod = X_PERIOD_AUTO; + mcPeriod = NULL; + + // + // Long ... + lcMethod = X_PERIOD_AUTO; + lcPeriod = NULL; + + // + // Hind ... + hcMethod = X_PERIOD_AUTO; + hcPeriod = NULL; + + // + // Boundary Detection ... + hhMode = MODE_HIGH; + llMode = MODE_LOW; + + // + // RSI ... + rsiLength = 14; + rsiOverSoldLevel = 30; + rsiOverBoughtLevel = 70; + rsiAppliedTo = PRICE_CLOSE; + + // + // Paraboli Sar Detection ... + sarStep = 0.02; + sarMax = 0.2; + + // + // Atr Detection ... + atrLength = 14; // Length + atrMultiplier = 1; // Multiplier + atrUpperAppliedTo = PRICE_HIGH; // Upper Zone Applied To + atrLowerAppliedTo = PRICE_LOW; // Lower Zone Applied To + atrSmoothingMode = X_MA_MODE_EMA; // Smoothing Method + + // + // Str Detection ... + strAppliedTo = PRICE_MEDIAN; + + // + // VWap Detection ... + vwapFastLength = 20; + vwapMidLength = 40; + vwapSlowLength = 60; + vwapAppliedTo = PRICE_CLOSE; + + // + // Donchain Detection ... + donchainLength = 40; + + // + // Presentation ... + + // + startCalculationForLastBars = 1500; + + // + sarArrowCode = 159; + peaksArrowCode = 159; + valesArrowCode = 159; + + // + // Globals ... + showSar = true; + showAtr = true; + showStr = true; + showPeaks = true; + showVales = true; + showVWap = false; + showDonchain = false; + + // + // Atr Presentation ... + showAtrUpper = true; // Show Upper Zone + showAtrLower = true; // Show Lower Zone + + // + // VWap Presentation ... + showVWapFast = true; + showVWapMedium = true; + showVWapSlow = true; + + // + // Donchain Presentation ... + + // + showUpper = true; + showLower = true; + + // + showOpen = true; + showHigh = false; + showClose = true; + showLow = false; + } + + /** + * Validate ... + * + * @return ( bool ) + */ + bool IsValid() + { + // + bool result = false; + + // + result = + // + // RSI ... + rsiLength > 0 && + rsiOverSoldLevel > 0 && + rsiOverBoughtLevel > 0 && + rsiOverSoldLevel < rsiOverBoughtLevel && + // PSAR ... + sarMax > 0 && + sarStep > 0 && + sarMax > sarStep && + // + // ATR ... + atrLength > 0 && + atrMultiplier > 0 && + // + // XDON ... + donchainLength > 0 && + // + // VWAP ... + vwapFastLength > 2 && + vwapMidLength > vwapFastLength && + vwapSlowLength > vwapMidLength && + // + // XPV ... + (IsValid(scMethod, scPeriod) && + IsValid(mcMethod, mcPeriod) && + IsValid(lcMethod, lcPeriod) && + IsValid(hcMethod, hcPeriod)) + // + ; + + // + return result; + } + + /** + * Extract Max Input Length ... + * + * @return ( int ) + */ + int Max() + { + // + int result = 0; + + // + // VWAP ... + result = MathMax(result, vwapFastLength); + result = MathMax(result, vwapFastLength); + result = MathMax(result, vwapMidLength); + + // + // ATR ... + result = MathMax(result, atrLength); + result = MathMax(result, rsiLength); + + // + return result; + } +}; + +// +// Conditions ... +struct X121Conditions +{ + // + // Common ... + string symbol; + ENUM_TIMEFRAMES period; + datetime time; + + // + // Buffers ... + double peaksBuffer[]; + double valesBuffer[]; + double sarBuffer[]; + double atrUpperBuffer[]; + double atrLowerBuffer[]; + double vwapFastBuffer[]; + double vwapMidBuffer[]; + double vwapSlowBuffer[]; + double donOpenUpperBuffer[]; + double donOpenLowerBuffer[]; + double donCloseUpperBuffer[]; + double donCloseLowerBuffer[]; + double donHighUpperBuffer[]; + double donHighLowerBuffer[]; + double donLowUpperBuffer[]; + double donLowLowerBuffer[]; + double cHHBuffer[]; + double cLLBuffer[]; + double sHHBuffer[]; + double sLLBuffer[]; + double mHHBuffer[]; + double mLLBuffer[]; + double lHHBuffer[]; + double lLLBuffer[]; + double hHHBuffer[]; + double hLLBuffer[]; + double atrBuffer[]; + double atrUpperRawBuffer[]; + double atrLowerRawBuffer[]; + double vwapVolumeBuffer[]; + double vwapPriceBuffer[]; + double vwapFastStateBuffer[]; + double vwapMidStateBuffer[]; + double vwapSlowStateBuffer[]; + double rsiBuffer[]; + double strBuffer[]; + double strStateBuffer[]; + + // + // Conditions ... + + // + // STR ... + + // + bool isStrBullish; + bool isStrSwitchedToBullish; + + // + bool isStrBearish; + bool isStrSwitchedToBearish; + + // + // XRSI ... + + // + bool isRSIOverBought; + bool isRSICrossedOverOverBought; + bool isRSICrossedUnderOverBought; + + // + bool isRSIOverSold; + bool isRSICrossedUnderOverSold; + bool isRSICrossedOverOverSold; + + // + // XSAR ... + + // + bool isSarBullish; + bool isSarBearish; + + // + bool isSarSwitchedToBullish; + bool isSarSwitchedToBearish; + + // + // XPV ... + + // + bool isNewPeak; + bool isNewPeakOverLast; + bool isNewPeakUnderLast; + + // + bool isNewVale; + bool isNewValeOverLast; + bool isNewValeUnderLast; + + // + // XVWAP ... + + // + bool isVWapFastBullish; + bool isVWapFastBearish; + bool isVWapFastNeutural; + + // + bool isVWapMidBullish; + bool isVWapMidBearish; + bool isVWapMidNeutural; + + // + bool isVWapSlowBullish; + bool isVWapSlowBearish; + bool isVWapSlowNeutural; + + // + bool isVWapFastOverMid; + bool isVWapMidOverSlow; + + // + bool isVWapFastUnderMid; + bool isVWapMidUnderSlow; + + // + bool isVWapBullishState; + bool isVWapBearishState; + bool isVWapNeuturalState; + + // + bool isVWapBullishOrdered; + bool isVWapBearishOrdered; + + // + bool isVWapSwitchedToBullishOrdered; + bool isVWapSwitchedToBearishOrdered; + + // + bool isVWapSwitchedToBullishState; + bool isVWapSwitchedToBearishState; + bool isVWapSwitchedToNeuturalState; + + // + // XDON ... + + // + // bool isCloseLower + + // + // Constructor ... + X121Conditions() + { + Clean(); + } + + // + // Tools ... + + /** + * Cleaning Up ... + */ + void Clean() + { + // + // Commons ... + symbol = NULL; + period = NULL; + time = NULL; + + // + // Buffers ... + + // + Clean(peaksBuffer); + Clean(valesBuffer); + Clean(sarBuffer); + Clean(atrUpperBuffer); + Clean(atrLowerBuffer); + Clean(vwapFastBuffer); + Clean(vwapMidBuffer); + Clean(vwapSlowBuffer); + Clean(donOpenUpperBuffer); + Clean(donOpenLowerBuffer); + Clean(donCloseUpperBuffer); + Clean(donCloseLowerBuffer); + Clean(donHighUpperBuffer); + Clean(donHighLowerBuffer); + Clean(donLowUpperBuffer); + Clean(donLowLowerBuffer); + Clean(cHHBuffer); + Clean(cLLBuffer); + Clean(sHHBuffer); + Clean(sLLBuffer); + Clean(mHHBuffer); + Clean(mLLBuffer); + Clean(lHHBuffer); + Clean(lLLBuffer); + Clean(hHHBuffer); + Clean(hLLBuffer); + Clean(atrBuffer); + Clean(atrUpperRawBuffer); + Clean(atrLowerRawBuffer); + Clean(vwapVolumeBuffer); + Clean(vwapPriceBuffer); + Clean(vwapFastStateBuffer); + Clean(vwapMidStateBuffer); + Clean(vwapSlowStateBuffer); + Clean(rsiBuffer); + Clean(strBuffer); + Clean(strStateBuffer); + + // + ArraySetAsSeries(peaksBuffer, true); + ArraySetAsSeries(valesBuffer, true); + ArraySetAsSeries(sarBuffer, true); + ArraySetAsSeries(atrUpperBuffer, true); + ArraySetAsSeries(atrLowerBuffer, true); + ArraySetAsSeries(vwapFastBuffer, true); + ArraySetAsSeries(vwapMidBuffer, true); + ArraySetAsSeries(vwapSlowBuffer, true); + ArraySetAsSeries(donOpenUpperBuffer, true); + ArraySetAsSeries(donOpenLowerBuffer, true); + ArraySetAsSeries(donCloseUpperBuffer, true); + ArraySetAsSeries(donCloseLowerBuffer, true); + ArraySetAsSeries(donHighUpperBuffer, true); + ArraySetAsSeries(donHighLowerBuffer, true); + ArraySetAsSeries(donLowUpperBuffer, true); + ArraySetAsSeries(donLowLowerBuffer, true); + ArraySetAsSeries(cHHBuffer, true); + ArraySetAsSeries(cLLBuffer, true); + ArraySetAsSeries(sHHBuffer, true); + ArraySetAsSeries(sLLBuffer, true); + ArraySetAsSeries(mHHBuffer, true); + ArraySetAsSeries(mLLBuffer, true); + ArraySetAsSeries(lHHBuffer, true); + ArraySetAsSeries(lLLBuffer, true); + ArraySetAsSeries(hHHBuffer, true); + ArraySetAsSeries(hLLBuffer, true); + ArraySetAsSeries(atrBuffer, true); + ArraySetAsSeries(atrUpperRawBuffer, true); + ArraySetAsSeries(atrLowerRawBuffer, true); + ArraySetAsSeries(vwapVolumeBuffer, true); + ArraySetAsSeries(vwapPriceBuffer, true); + ArraySetAsSeries(vwapFastStateBuffer, true); + ArraySetAsSeries(vwapMidStateBuffer, true); + ArraySetAsSeries(vwapSlowStateBuffer, true); + ArraySetAsSeries(rsiBuffer, true); + ArraySetAsSeries(strBuffer, true); + ArraySetAsSeries(strStateBuffer, true); + + // + // Conditions ... + + // + // STR ... + + // + isStrBullish = false; + isStrSwitchedToBullish = false; + + // + isStrBearish = false; + isStrSwitchedToBearish = false; + + // + // XRSI ... + + // + isRSIOverBought = false; + isRSICrossedUnderOverBought = false; + isRSICrossedOverOverBought = false; + + // + isRSIOverSold = false; + isRSICrossedOverOverSold = false; + isRSICrossedUnderOverSold = false; + + // + // XSAR ... + + // + isSarBullish = false; + isSarBearish = false; + + // + isSarSwitchedToBullish = false; + isSarSwitchedToBearish = false; + + // + // XPV ... + + // + isNewPeak = false; + isNewPeakOverLast = false; + isNewPeakUnderLast = false; + + // + isNewVale = false; + isNewValeOverLast = false; + isNewValeUnderLast = false; + + // + // XVWAP ... + + // + isVWapFastBullish = false; + isVWapFastBearish = false; + isVWapFastNeutural = false; + + // + isVWapMidBullish = false; + isVWapMidBearish = false; + isVWapMidNeutural = false; + + // + isVWapSlowBullish = false; + isVWapSlowBearish = false; + isVWapSlowNeutural = false; + + // + isVWapFastOverMid = false; + isVWapMidOverSlow = false; + + // + isVWapFastUnderMid = false; + isVWapMidUnderSlow = false; + + // + isVWapBullishState = false; + isVWapBearishState = false; + isVWapNeuturalState = false; + + // + isVWapBullishOrdered = false; + isVWapBearishOrdered = false; + + // + isVWapSwitchedToBullishOrdered = false; + isVWapSwitchedToBearishOrdered = false; + + // + isVWapSwitchedToBullishState = false; + isVWapSwitchedToBearishState = false; + isVWapSwitchedToNeuturalState = false; + + // + // XDON ... + } + + /** + * Generate Conditions Scores ... + * + * @param bullishScore: Double, Directional Scores Reference ... + * @param bearishScore: Double, Directional Scores Reference ... + */ + void GenerateScore( + double &bullishScore, + double &bearishScore // + ) + { + // + bullishScore = 0; + bearishScore = 0; + + // + // TODO: Implement if Required ... + } + + /** + * Generate Summary String for Represent Conditions State ... + * + * @param onlyCommons: Boolean, Just Generate Only Commons Conditions ... + * @param onlyConditions: Boolean, Just Generate Only Conditions ... + * @param includeScores: Boolean, Attach Scores Representations on Result ... + * @param ignoreFalseConditions: Boolean, Ignore False Conditions on Result ... + * @param separator: String, Separate Lines ... + * + * @return ( string ) + */ + string GenerateSummary( + bool onlyCommons = false, + bool onlyConditions = false, + bool includeScores = true, + bool ignoreFalseConditions = true, + string separator = "\n" // + ) + { + // + string result = NULL; + + // + double bullishScore = 0; + double bearishScore = 0; + GenerateScore( + bullishScore, + bearishScore // + ); + + // + string scoresStr = + // + "Scores: " + separator + + "---------------" + separator + + "Bullish: " + ToString(bullishScore) + separator + + "Bearish: " + ToString(bearishScore) + separator + + "" + // + ; + + // + string commonStr = GenerateSpecifiedCommonSummary( + this, + separator, + includeScores // + ); + + // + // TODO: Implement this if required ... + string conditionsStr = + // + // STR ... + ToString("isStrBullish", isStrBullish, ignoreFalseConditions, separator) + + ToString("isStrSwitchedToBullish", isStrSwitchedToBullish, ignoreFalseConditions, separator) + + ToString("isStrBearish", isStrBearish, ignoreFalseConditions, separator) + + ToString("isStrSwitchedToBearish", isStrSwitchedToBearish, ignoreFalseConditions, separator) + + // + // XSAR ... + ToString("isSarBullish", isSarBullish, ignoreFalseConditions, separator) + + ToString("isSarBearish", isSarBearish, ignoreFalseConditions, separator) + + ToString("isSarSwitchedToBullish", isSarSwitchedToBullish, ignoreFalseConditions, separator) + + ToString("isSarSwitchedToBearish", isSarSwitchedToBearish, ignoreFalseConditions, separator) + + // + // XPV ... + ToString("isNewPeak", isNewPeak, ignoreFalseConditions, separator) + + ToString("isNewPeakOverLast", isNewPeakOverLast, ignoreFalseConditions, separator) + + ToString("isNewPeakUnderLast", isNewPeakUnderLast, ignoreFalseConditions, separator) + + ToString("isNewVale", isNewVale, ignoreFalseConditions, separator) + + ToString("isNewValeOverLast", isNewValeOverLast, ignoreFalseConditions, separator) + + ToString("isNewValeUnderLast", isNewValeUnderLast, ignoreFalseConditions, separator) + + // + // RSI ... + ToString("isRSIOverBought", isRSIOverBought, ignoreFalseConditions, separator) + + ToString("isRSICrossedOverOverBought", isRSICrossedOverOverBought, ignoreFalseConditions, separator) + + ToString("isRSICrossedUnderOverBought", isRSICrossedUnderOverBought, ignoreFalseConditions, separator) + + ToString("isRSIOverSold", isRSIOverSold, ignoreFalseConditions, separator) + + ToString("isRSICrossedUnderOverSold", isRSICrossedUnderOverSold, ignoreFalseConditions, separator) + + ToString("isRSICrossedOverOverSold", isRSICrossedOverOverSold, ignoreFalseConditions, separator) + + // + // XVWAP ... + ToString("isVWapFastBullish", isVWapFastBullish, ignoreFalseConditions, separator) + + ToString("isVWapFastBearish", isVWapFastBearish, ignoreFalseConditions, separator) + + ToString("isVWapFastNeutural", isVWapFastNeutural, ignoreFalseConditions, separator) + + ToString("isVWapMidBullish", isVWapMidBullish, ignoreFalseConditions, separator) + + ToString("isVWapMidBearish", isVWapMidBearish, ignoreFalseConditions, separator) + + ToString("isVWapMidNeutural", isVWapMidNeutural, ignoreFalseConditions, separator) + + ToString("isVWapSlowBullish", isVWapSlowBullish, ignoreFalseConditions, separator) + + ToString("isVWapSlowBearish", isVWapSlowBearish, ignoreFalseConditions, separator) + + ToString("isVWapSlowNeutural", isVWapSlowNeutural, ignoreFalseConditions, separator) + + ToString("isVWapFastOverMid", isVWapFastOverMid, ignoreFalseConditions, separator) + + ToString("isVWapMidOverSlow", isVWapMidOverSlow, ignoreFalseConditions, separator) + + ToString("isVWapFastUnderMid", isVWapFastUnderMid, ignoreFalseConditions, separator) + + ToString("isVWapMidUnderSlow", isVWapMidUnderSlow, ignoreFalseConditions, separator) + + ToString("isVWapBullishState", isVWapBullishState, ignoreFalseConditions, separator) + + ToString("isVWapBearishState", isVWapBearishState, ignoreFalseConditions, separator) + + ToString("isVWapNeuturalState", isVWapNeuturalState, ignoreFalseConditions, separator) + + ToString("isVWapBullishOrdered", isVWapBullishOrdered, ignoreFalseConditions, separator) + + ToString("isVWapBearishOrdered", isVWapBearishOrdered, ignoreFalseConditions, separator) + + ToString("isVWapSwitchedToBullishOrdered", isVWapSwitchedToBullishOrdered, ignoreFalseConditions, separator) + + ToString("isVWapSwitchedToBearishOrdered", isVWapSwitchedToBearishOrdered, ignoreFalseConditions, separator) + + ToString("isVWapSwitchedToBullishState", isVWapSwitchedToBullishState, ignoreFalseConditions, separator) + + ToString("isVWapSwitchedToBearishState", isVWapSwitchedToBearishState, ignoreFalseConditions, separator) + + ToString("isVWapSwitchedToNeuturalState", isVWapSwitchedToNeuturalState, ignoreFalseConditions, separator) + + // + "" + // + ; + + // + result = + // + "[" + GetTag() + "]" + separator + + (onlyConditions + ? "" + : commonStr) + + (!includeScores + ? "" + : scoresStr) + + " " + separator + + (onlyCommons + ? "" + : conditionsStr) + + "" + // + ; + + // + return result; + } + + /** + * Retrieve nique Tag Identifier ... + * + * @return ( string ) + */ + string GetTag() + { + return GetTypeName(this); + } + + // +}; + +// +// Implementation ... + +class XCX121Helper : public XCBaseHelper +{ + // + public: + // + + // + // Constructors ... + XCX121Helper() + : XCBaseHelper(_Symbol, _Period) + { + } + + // + // Deconstructor ... + ~XCX121Helper() + { + } + + // + // Tools ... + + /** + * Initialize Indicator Helper ... + * + * @param symbol: String, Symbol ... + * @param period: ENUM_TIMEFRAMES member, Period ... + * @param inputs: X121Inputs instance, Indicator Inputs ... + * + * @return ( bool ) + */ + bool Init( + string symbol, // Trading Symbol + ENUM_TIMEFRAMES period, // Trading Period + X121Inputs &inputs // Inputs + ) + { + // + bool result = false; + + // + mSymbol = symbol; + mPeriod = period; + + // + // Validate Inputs ... + result = inputs.IsValid(); + if (!result) + { + return result; + } + + // + mInputs = inputs; + + // + // Setting Arrays As Series ... + ArraySetAsSeries(peaksBuffer, true); + ArraySetAsSeries(valesBuffer, true); + ArraySetAsSeries(sarBuffer, true); + ArraySetAsSeries(atrUpperBuffer, true); + ArraySetAsSeries(atrLowerBuffer, true); + ArraySetAsSeries(vwapFastBuffer, true); + ArraySetAsSeries(vwapMidBuffer, true); + ArraySetAsSeries(vwapSlowBuffer, true); + ArraySetAsSeries(donOpenUpperBuffer, true); + ArraySetAsSeries(donOpenLowerBuffer, true); + ArraySetAsSeries(donCloseUpperBuffer, true); + ArraySetAsSeries(donCloseLowerBuffer, true); + ArraySetAsSeries(donHighUpperBuffer, true); + ArraySetAsSeries(donHighLowerBuffer, true); + ArraySetAsSeries(donLowUpperBuffer, true); + ArraySetAsSeries(donLowLowerBuffer, true); + ArraySetAsSeries(cHHBuffer, true); + ArraySetAsSeries(cLLBuffer, true); + ArraySetAsSeries(sHHBuffer, true); + ArraySetAsSeries(sLLBuffer, true); + ArraySetAsSeries(mHHBuffer, true); + ArraySetAsSeries(mLLBuffer, true); + ArraySetAsSeries(lHHBuffer, true); + ArraySetAsSeries(lLLBuffer, true); + ArraySetAsSeries(hHHBuffer, true); + ArraySetAsSeries(hLLBuffer, true); + ArraySetAsSeries(atrBuffer, true); + ArraySetAsSeries(atrUpperRawBuffer, true); + ArraySetAsSeries(atrLowerRawBuffer, true); + ArraySetAsSeries(vwapVolumeBuffer, true); + ArraySetAsSeries(vwapPriceBuffer, true); + ArraySetAsSeries(vwapFastStateBuffer, true); + ArraySetAsSeries(vwapMidStateBuffer, true); + ArraySetAsSeries(vwapSlowStateBuffer, true); + ArraySetAsSeries(rsiBuffer, true); + + // + mHandler = iCustom( + mSymbol, + mPeriod, + "x-saherelm.x121", + // + // Inputs ... + // + // Cycles ... + "", + // + // Short ... + "", + mInputs.scMethod, + mInputs.scPeriod, + // + // Medium ... + "", + mInputs.mcMethod, + mInputs.mcPeriod, + // + // Long ... + "", + mInputs.lcMethod, + mInputs.lcPeriod, + // + // Hind ... + "", + mInputs.hcMethod, + mInputs.hcPeriod, + // + // Boundary Detection ... + "", + mInputs.hhMode, + mInputs.llMode, + // + // Rsi Detection ... + "", + mInputs.rsiLength, + mInputs.rsiAppliedTo, + // + // Parabolic Sar Detection ... + "", + mInputs.sarStep, + mInputs.sarMax, + // + // Atr Detection ... + "", + mInputs.atrLength, + mInputs.atrMultiplier, + mInputs.atrUpperAppliedTo, + mInputs.atrLowerAppliedTo, + mInputs.atrSmoothingMode, + // + // VWap Detection ... + "", + mInputs.vwapFastLength, + mInputs.vwapMidLength, + mInputs.vwapSlowLength, + mInputs.vwapAppliedTo, + // + // Donchain Detection ... + "", + mInputs.donchainLength, + // + // Presentation ... + "", + mInputs.startCalculationForLastBars, + mInputs.sarArrowCode, + mInputs.peaksArrowCode, + mInputs.valesArrowCode, + // + // Commons ... + mInputs.showSar, + mInputs.showAtr, + mInputs.showPeaks, + mInputs.showVales, + mInputs.showVWap, + mInputs.showDonchain, + // + // Atr Presentation ... + "", + mInputs.showAtrUpper, + mInputs.showAtrLower, + // + // VWap Presentation ... + "", + mInputs.showVWapFast, + mInputs.showVWapMedium, + mInputs.showVWapSlow, + // + // Donchain Presentation ... + "", + mInputs.showUpper, + mInputs.showLower, + mInputs.showOpen, + mInputs.showHigh, + mInputs.showClose, + mInputs.showLow + // + ); + result = mHandler != INVALID_HANDLE; + if (!result) + { + return result; + } + + // + return result; + } + + /** + * Retrieve Current Indicator Configs ... + * + * @return ( Inputs ) + */ + X121Inputs GetInputs() + { + return mInputs; + } + + /** + * Set New Indicator Inputs ... + * + * @param inputs: X121Inputs instance, Indicator Inputs ... + * + * @return ( bool ) + */ + bool SetInputs( + X121Inputs &inputs // Configs + ) + { + // + return Init( + mSymbol, + mPeriod, + inputs + // + ); + } + + // + // Implement Value Getters ... + + // + // XRSI ... + + // + double GetRSI( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(rsiBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return rsiBuffer[barIndex]; + } + + // + int CopyRSI( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + rsiBuffer, + buffer, + forceClean + // + ); + } + + // + // SAR ... + + // + double GetSar( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(sarBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return sarBuffer[barIndex]; + } + + // + int CopySar( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + sarBuffer, + buffer, + forceClean + // + ); + } + + // + // ATR ... + + // + // Common ... + + // + double GetAtr( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(atrBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return atrBuffer[barIndex]; + } + + // + int CopyAtr( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + atrBuffer, + buffer, + forceClean + // + ); + } + + // + double GetAtrUpper( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(atrUpperBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return atrUpperBuffer[barIndex]; + } + + // + int CopyAtrUpper( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + atrUpperBuffer, + buffer, + forceClean + // + ); + } + + // + double GetAtrUpperRaw( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(atrUpperRawBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return atrUpperRawBuffer[barIndex]; + } + + // + int CopyAtrUpperRaw( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + atrUpperRawBuffer, + buffer, + forceClean + // + ); + } + + // + double GetAtrLower( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(atrLowerBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return atrLowerBuffer[barIndex]; + } + + // + int CopyAtrLower( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + atrLowerBuffer, + buffer, + forceClean + // + ); + } + + // + double GetAtrLowerRaw( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(atrLowerRawBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return atrLowerRawBuffer[barIndex]; + } + + // + int CopyAtrLowerRaw( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + atrLowerRawBuffer, + buffer, + forceClean + // + ); + } + + // + // PV ... + + // + // PEAKS ... + + // + double GetPeak( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(peaksBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return peaksBuffer[barIndex]; + } + + // + int CopyPeak( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + peaksBuffer, + buffer, + forceClean + // + ); + } + + // + // VALES ... + + // + double GetVale( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(valesBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return valesBuffer[barIndex]; + } + + // + int CopyVale( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + valesBuffer, + buffer, + forceClean + // + ); + } + + // + // + // + + // + double GetHigherPeak( + double peak, // Peak Source + int barIndex = 0, // Bar Index + int loopback = 576 // Max Allowed Loopback + ) + { + // + double result = 0; + + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + if (loopback < 576) + { + loopback = 576; + } + + // + if (peak <= 0) + { + return result; + } + + // + double iValue = 0; + int index = barIndex; + bool canContinue = true; + while (canContinue) + { + // + iValue = GetPeak(index); + if (iValue > peak) + { + // + result = iValue; + break; + } + + // + canContinue = index < barIndex + loopback; + index++; + } + + // + return result; + } + + // + double GetLowerPeak( + double peak, // Peak Source + int barIndex = 0, // Bar Index + int loopback = 576 // Max Allowed Loopback + ) + { + // + double result = 0; + + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + if (loopback < 576) + { + loopback = 576; + } + + // + if (peak <= 0) + { + return result; + } + + // + double iValue = 0; + int index = barIndex; + bool canContinue = true; + while (canContinue) + { + // + iValue = GetPeak(index); + if (iValue < peak) + { + // + result = iValue; + break; + } + + // + canContinue = index < barIndex + loopback; + index++; + } + + // + return result; + } + + // + double GetHigherVale( + double vale, // Vale Source + int barIndex = 0, // Bar Index + int loopback = 576 // Max Allowed Loopback + ) + { + // + double result = 0; + + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + if (loopback < 576) + { + loopback = 576; + } + + // + if (vale <= 0) + { + return result; + } + + // + double iValue = 0; + int index = barIndex; + bool canContinue = true; + while (canContinue) + { + // + iValue = GetVale(index); + if (iValue > vale) + { + // + result = iValue; + break; + } + + // + canContinue = index < barIndex + loopback; + index++; + } + + // + return result; + } + + // + double GetLowerVale( + double vale, // Vale Source + int barIndex = 0, // Bar Index + int loopback = 576 // Max Allowed Loopback + ) + { + // + double result = 0; + + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + if (loopback < 576) + { + loopback = 576; + } + + // + if (vale <= 0) + { + return result; + } + + // + double iValue = 0; + int index = barIndex; + bool canContinue = true; + while (canContinue) + { + // + iValue = GetVale(index); + if (iValue < vale) + { + // + result = iValue; + break; + } + + // + canContinue = index < barIndex + loopback; + index++; + } + + // + return result; + } + + // + // + // + + // + double GetLowestPeak( + int barIndex, + int &index, + double &vale, + int loopback = 576 // + ) + { + // + double result = 0; + + // + index = -1; + vale = 0; + + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + if (loopback < 576) + { + loopback = 576; + } + + // + Calculate(); + + // + for (int i = 0; i < barIndex + loopback; i++) + { + // + double iPeak = GetPeak(i); + if (iPeak == 0) + { + break; + } + + // + if (iPeak > 0 && (result == 0 || + result >= iPeak)) + { + // + index = i; + result = iPeak; + vale = GetVale(index); + } + } + + // + return result; + } + + // + double GetHighestPeak( + int barIndex, + int &index, + double &vale, + int loopback = 576 // + ) + { + // + double result = 0; + + // + index = -1; + vale = 0; + + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + if (loopback < 576) + { + loopback = 576; + } + + // + Calculate(); + + // + for (int i = 0; i < barIndex + loopback; i++) + { + // + double iPeak = GetPeak(i); + if (iPeak == 0) + { + break; + } + + // + if (iPeak > 0 && (result == 0 || + result <= iPeak)) + { + // + index = i; + result = iPeak; + vale = GetVale(index); + } + } + + // + return result; + } + + // + double GetLowestVale( + int barIndex, + int &index, + double &peak, + int loopback = 576 // + ) + { + // + double result = 0; + + // + index = -1; + peak = 0; + + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + if (loopback < 576) + { + loopback = 576; + } + + // + Calculate(); + + // + for (int i = 0; i < barIndex + loopback; i++) + { + // + double iPeak = GetVale(i); + if (iPeak == 0) + { + break; + } + + // + if (iPeak > 0 && (result == 0 || + result >= iPeak)) + { + // + index = i; + result = iPeak; + peak = GetPeak(index); + } + } + + // + return result; + } + + // + double GetHighestVale( + int barIndex, + int &index, + double &peak, + int loopback = 576 // + ) + { + // + double result = 0; + + // + index = -1; + peak = 0; + + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + if (loopback < 576) + { + loopback = 576; + } + + // + Calculate(); + + // + for (int i = 0; i < barIndex + loopback; i++) + { + // + double iPeak = GetVale(i); + if (iPeak == 0) + { + break; + } + + // + if (iPeak > 0 && (result == 0 || + result <= iPeak)) + { + // + index = i; + result = iPeak; + peak = GetPeak(index); + } + } + + // + return result; + } + + // + // CURRENT ... + + // + // HH ... + + // + double GetCHH( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(cHHBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return cHHBuffer[barIndex]; + } + + // + int CopyCHH( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + cHHBuffer, + buffer, + forceClean + // + ); + } + + // + // LL ... + + // + double GetCLL( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(cLLBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return cLLBuffer[barIndex]; + } + + // + int CopyCLL( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + cLLBuffer, + buffer, + forceClean + // + ); + } + + // + // SHORT ... + + // + // HH ... + + // + double GetSHH( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(sHHBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return sHHBuffer[barIndex]; + } + + // + int CopySHH( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + sHHBuffer, + buffer, + forceClean + // + ); + } + + // + // LL ... + + // + double GetSLL( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(sLLBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return sLLBuffer[barIndex]; + } + + // + int CopySLL( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + sLLBuffer, + buffer, + forceClean + // + ); + } + + // + // MEDIUM ... + + // + // HH ... + + // + double GetMHH( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(mHHBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return mHHBuffer[barIndex]; + } + + // + int CopyMHH( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + mHHBuffer, + buffer, + forceClean + // + ); + } + + // + // LL ... + + // + double GetMLL( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(mLLBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return mLLBuffer[barIndex]; + } + + // + int CopyMLL( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + mLLBuffer, + buffer, + forceClean + // + ); + } + + // + // LONG ... + + // + // HH ... + + // + double GetLHH( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(lHHBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return lHHBuffer[barIndex]; + } + + // + int CopyLHH( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + lHHBuffer, + buffer, + forceClean + // + ); + } + + // + // LL ... + + // + double GetLLL( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(lLLBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return lLLBuffer[barIndex]; + } + + // + int CopyLLL( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + lLLBuffer, + buffer, + forceClean + // + ); + } + + // + // HIND ... + + // + // HH ... + + // + double GetHHH( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(hHHBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return hHHBuffer[barIndex]; + } + + // + int CopyHHH( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + hHHBuffer, + buffer, + forceClean + // + ); + } + + // + // LL ... + + // + double GetHLL( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(hLLBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return hLLBuffer[barIndex]; + } + + // + int CopyHLL( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + hLLBuffer, + buffer, + forceClean + // + ); + } + + // + // VWAP ... + + // + // FAST ... + + // + double GetVWapFast( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(vwapFastBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return vwapFastBuffer[barIndex]; + } + + // + int CopyVWapFast( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + vwapFastBuffer, + buffer, + forceClean + // + ); + } + + // + // STATE FAST ... + + // + double GetVWapFastState( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(vwapFastStateBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return vwapFastStateBuffer[barIndex]; + } + + // + int CopyVWapFastState( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + vwapFastStateBuffer, + buffer, + forceClean + // + ); + } + + // + // MID ... + + // + double GetVWapMid( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(vwapMidBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return vwapMidBuffer[barIndex]; + } + + // + int CopyVWapMid( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + vwapMidBuffer, + buffer, + forceClean + // + ); + } + + // + // STATE MID ... + + // + double GetVWapMidState( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(vwapMidStateBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return vwapMidStateBuffer[barIndex]; + } + + // + int CopyVWapMidState( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + vwapMidStateBuffer, + buffer, + forceClean + // + ); + } + + // + // SLOW ... + + // + double GetVWapSlowBuffer( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(vwapSlowBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return vwapSlowBuffer[barIndex]; + } + + // + int CopyVWapSlow( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + vwapSlowBuffer, + buffer, + forceClean + // + ); + } + + // + // STATE SLOW ... + + // + double GetVWapSlowState( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(vwapSlowStateBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return vwapSlowStateBuffer[barIndex]; + } + + // + int CopyVWapSlowState( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + vwapSlowStateBuffer, + buffer, + forceClean + // + ); + } + + // + // VOLUME ... + + // + double GetVWapVolume( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(vwapVolumeBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return vwapVolumeBuffer[barIndex]; + } + + // + int CopyVWapVolume( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + vwapVolumeBuffer, + buffer, + forceClean + // + ); + } + + // + // PRICE ... + + // + double GetVWapPrice( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(vwapPriceBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return vwapPriceBuffer[barIndex]; + } + + // + int CopyVWapPrice( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + vwapPriceBuffer, + buffer, + forceClean + // + ); + } + + // + // Converts to State ... + ENUM_XVWAP_STATES ToVWAPState(double value) + { + // + ENUM_XVWAP_STATES result = + value == 1 + ? XVWAP_STATE_BULLISH + : value == 2 + ? XVWAP_STATE_BEARISH + : XVWAP_STATE_NEUTURAL; + + // + return result; + } + + // + bool IsVWAPBullish(double value) + { + // + bool result = false; + + // + result = ToVWAPState(value) == XVWAP_STATE_BULLISH; + + // + return result; + } + + // + bool IsVWAPBearish(double value) + { + // + bool result = false; + + // + result = ToVWAPState(value) == XVWAP_STATE_BEARISH; + + // + return result; + } + + // + bool IsVWAPNeutural(double value) + { + // + bool result = false; + + // + result = ToVWAPState(value) == XVWAP_STATE_NEUTURAL; + + // + return result; + } + + // + // XDON ... + + // + // OPEN ... + + // + // UPPER ... + + // + double GetDonOpenUpper( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(donOpenUpperBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return donOpenUpperBuffer[barIndex]; + } + + // + int CopyDonOpenUpper( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + donOpenUpperBuffer, + buffer, + forceClean + // + ); + } + + // + // LOWER ... + + // + double GetDonOpenLower( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(donOpenLowerBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return donOpenLowerBuffer[barIndex]; + } + + // + int CopyDonOpenLower( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + donOpenLowerBuffer, + buffer, + forceClean + // + ); + } + + // + // CLOSE ... + + // + // UPPER ... + + // + double GetDonCloseUpper( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(donCloseUpperBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return donCloseUpperBuffer[barIndex]; + } + + // + int CopyDonCloseUpper( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + donCloseUpperBuffer, + buffer, + forceClean + // + ); + } + + // + // LOWER ... + + // + double GetDonCloseLower( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(donCloseLowerBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return donCloseLowerBuffer[barIndex]; + } + + // + int CopyDonCloseLower( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + donCloseLowerBuffer, + buffer, + forceClean + // + ); + } + + // + // HIGH ... + + // + // UPPER ... + + // + double GetDonHighUpper( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(donHighUpperBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return donHighUpperBuffer[barIndex]; + } + + // + int CopyDonHighUpper( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + donHighUpperBuffer, + buffer, + forceClean + // + ); + } + + // + // LOWER ... + + // + double GetDonHighLower( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(donHighLowerBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return donHighLowerBuffer[barIndex]; + } + + // + int CopyDonHighLower( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + donHighLowerBuffer, + buffer, + forceClean + // + ); + } + + // + // LOW ... + + // + // UPPER ... + + // + double GetDonLowUpper( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(donLowUpperBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return donLowUpperBuffer[barIndex]; + } + + // + int CopyDonLowUpper( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + donLowUpperBuffer, + buffer, + forceClean + // + ); + } + + // + // LOWER ... + + // + double GetDonLoweLower( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(donLowLowerBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return donLowLowerBuffer[barIndex]; + } + + // + int CopyDonLoweLower( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + donLowLowerBuffer, + buffer, + forceClean + // + ); + } + + // + // Conditions Generation ... + + bool GetConditions( + X121Conditions &conditions, // + int barIndex = 0, // + int loopback = 5 // + ) + { + // + bool result = true; + + // + if (loopback < 5) + { + loopback = 5; + } + + // + conditions.Clean(); + + // + conditions.symbol = mSymbol; + conditions.period = mPeriod; + conditions.time = TimeCurrent(); + + // + int zIndex = barIndex; + int cIndex = zIndex + 1; + int pIndex = cIndex + 1; + int ppIndex = pIndex + 1; + + // + XOHCL zBar; + result = zBar.Init( + mSymbol, + mPeriod, + zIndex // + ); + if (!result) + { + return result; + } + + // + XOHCL cBar; + result = cBar.Init( + mSymbol, + mPeriod, + cIndex // + ); + if (!result) + { + return result; + } + + // + XOHCL pBar; + result = pBar.Init( + mSymbol, + mPeriod, + pIndex // + ); + if (!result) + { + return result; + } + + // + // Buffers ... + + // + CopyRSI( + zIndex, + loopback, + conditions.rsiBuffer // + ); + + // + CopySar( + zIndex, + loopback, + conditions.sarBuffer // + ); + + // + CopyAtr( + zIndex, + loopback, + conditions.atrBuffer // + ); + + // + CopyAtrUpper( + zIndex, + loopback, + conditions.atrUpperBuffer // + ); + + // + CopyAtrUpperRaw( + zIndex, + loopback, + conditions.atrUpperRawBuffer // + ); + + // + CopyAtrLower( + zIndex, + loopback, + conditions.atrLowerBuffer // + ); + + // + CopyAtrLowerRaw( + zIndex, + loopback, + conditions.atrLowerRawBuffer // + ); + + // + CopyPeak( + zIndex, + loopback, + conditions.peaksBuffer // + ); + + // + CopyVale( + zIndex, + loopback, + conditions.valesBuffer // + ); + + // + CopyCHH( + zIndex, + loopback, + conditions.cHHBuffer // + ); + + // + CopyCLL( + zIndex, + loopback, + conditions.cLLBuffer // + ); + + // + CopySHH( + zIndex, + loopback, + conditions.sHHBuffer // + ); + + // + CopySLL( + zIndex, + loopback, + conditions.sLLBuffer // + ); + + // + CopyMHH( + zIndex, + loopback, + conditions.mHHBuffer // + ); + + // + CopyMLL( + zIndex, + loopback, + conditions.mLLBuffer // + ); + + // + CopyLHH( + zIndex, + loopback, + conditions.lHHBuffer // + ); + + // + CopyLLL( + zIndex, + loopback, + conditions.lLLBuffer // + ); + + // + CopyHHH( + zIndex, + loopback, + conditions.hHHBuffer // + ); + + // + CopyHLL( + zIndex, + loopback, + conditions.hLLBuffer // + ); + + // + CopyVWapFast( + zIndex, + loopback, + conditions.vwapFastBuffer // + ); + + // + CopyVWapFastState( + zIndex, + loopback, + conditions.vwapFastStateBuffer // + ); + + // + CopyVWapMid( + zIndex, + loopback, + conditions.vwapMidBuffer // + ); + + // + CopyVWapMidState( + zIndex, + loopback, + conditions.vwapMidStateBuffer // + ); + + // + CopyVWapSlow( + zIndex, + loopback, + conditions.vwapSlowBuffer // + ); + + // + CopyVWapSlowState( + zIndex, + loopback, + conditions.vwapSlowStateBuffer // + ); + + // + CopyVWapVolume( + zIndex, + loopback, + conditions.vwapVolumeBuffer // + ); + + // + CopyVWapPrice( + zIndex, + loopback, + conditions.vwapPriceBuffer // + ); + + // + CopyDonOpenUpper( + zIndex, + loopback, + conditions.donOpenUpperBuffer // + ); + + // + CopyDonOpenLower( + zIndex, + loopback, + conditions.donOpenLowerBuffer // + ); + + // + CopyDonCloseUpper( + zIndex, + loopback, + conditions.donCloseUpperBuffer // + ); + + // + CopyDonCloseLower( + zIndex, + loopback, + conditions.donCloseLowerBuffer // + ); + + // + CopyDonHighUpper( + zIndex, + loopback, + conditions.donHighUpperBuffer // + ); + + // + CopyDonHighLower( + zIndex, + loopback, + conditions.donHighLowerBuffer // + ); + + // + CopyDonLowUpper( + zIndex, + loopback, + conditions.donLowUpperBuffer // + ); + + // + CopyDonLoweLower( + zIndex, + loopback, + conditions.donLowLowerBuffer // + ); + + // + // Conditions ... + + // + int cIDX = 1; + int pIDX = cIDX + 1; + + // + // XRSI ... + + // + bool isRSIOverBought = conditions.rsiBuffer[cIDX] > mInputs.rsiOverBoughtLevel; + bool isRSIOverBoughtPrev = conditions.rsiBuffer[pIDX] > mInputs.rsiOverBoughtLevel; + + // + bool isRSICrossedOverOverBought = isRSIOverBought && + !isRSIOverBoughtPrev; + bool isRSICrossedUnderOverBought = !isRSIOverBought && + isRSIOverBoughtPrev; + + // + bool isRSIOverSold = conditions.rsiBuffer[cIDX] < mInputs.rsiOverSoldLevel; + bool isRSIOverSoldPrev = conditions.rsiBuffer[pIDX] < mInputs.rsiOverSoldLevel; + + // + bool isRSICrossedUnderOverSold = isRSIOverSold && + !isRSIOverSoldPrev; + bool isRSICrossedOverOverSold = !isRSIOverSold && + isRSIOverSoldPrev; + + // + // XSAR ... + + // + bool isSarBullish = conditions.sarBuffer[cIDX] < cBar.low; + bool isSarBullishPrev = conditions.sarBuffer[pIDX] < pBar.low; + + // + bool isSarBearish = conditions.sarBuffer[cIDX] > cBar.high; + bool isSarBearishPrev = conditions.sarBuffer[pIDX] > pBar.high; + + // + bool isSarSwitchedToBullish = isSarBullish && + !isSarBullishPrev; + bool isSarSwitchedToBearish = isSarBearish && + !isSarBearishPrev; + + // + // XPV ... + + // + bool isNewPeak = conditions.peaksBuffer[cIDX] != conditions.peaksBuffer[pIDX]; + bool isNewPeakOverLast = isNewPeak && + conditions.peaksBuffer[cIDX] > conditions.peaksBuffer[pIDX]; + bool isNewPeakUnderLast = isNewPeak && + conditions.peaksBuffer[cIDX] < conditions.peaksBuffer[pIDX]; + + // + bool isNewVale = conditions.valesBuffer[cIDX] != conditions.valesBuffer[pIDX]; + bool isNewValeOverLast = isNewVale && + conditions.valesBuffer[cIDX] > conditions.valesBuffer[pIDX]; + bool isNewValeUnderLast = isNewVale && + conditions.valesBuffer[cIDX] < conditions.valesBuffer[pIDX]; + + // + // XVWAP ... + + // + bool isVWapFastBullish = IsVWAPBullish(conditions.vwapFastStateBuffer[cIDX]); + bool isVWapFastBullishPrev = IsVWAPBullish(conditions.vwapFastStateBuffer[pIDX]); + + // + bool isVWapFastBearish = IsVWAPBearish(conditions.vwapFastStateBuffer[cIDX]); + bool isVWapFastBearishPrev = IsVWAPBearish(conditions.vwapFastStateBuffer[pIDX]); + + // + bool isVWapFastNeutural = IsVWAPNeutural(conditions.vwapFastStateBuffer[cIDX]); + bool isVWapFastNeuturalPrev = IsVWAPNeutural(conditions.vwapFastStateBuffer[pIDX]); + + // + bool isVWapMidBullish = IsVWAPBullish(conditions.vwapMidStateBuffer[cIDX]); + bool isVWapMidBullishPrev = IsVWAPBullish(conditions.vwapMidStateBuffer[pIDX]); + + // + bool isVWapMidBearish = IsVWAPBearish(conditions.vwapMidStateBuffer[cIDX]); + bool isVWapMidBearishPrev = IsVWAPBearish(conditions.vwapMidStateBuffer[pIDX]); + + // + bool isVWapMidNeutural = IsVWAPNeutural(conditions.vwapMidStateBuffer[cIDX]); + bool isVWapMidNeuturalPrev = IsVWAPNeutural(conditions.vwapMidStateBuffer[pIDX]); + + // + bool isVWapSlowBullish = IsVWAPBullish(conditions.vwapSlowStateBuffer[cIDX]); + bool isVWapSlowBullishPrev = IsVWAPBullish(conditions.vwapSlowStateBuffer[pIDX]); + + // + bool isVWapSlowBearish = IsVWAPBearish(conditions.vwapSlowStateBuffer[cIDX]); + bool isVWapSlowBearishPrev = IsVWAPBearish(conditions.vwapSlowStateBuffer[pIDX]); + + // + bool isVWapSlowNeutural = IsVWAPNeutural(conditions.vwapSlowStateBuffer[cIDX]); + bool isVWapSlowNeuturalPrev = IsVWAPNeutural(conditions.vwapSlowStateBuffer[pIDX]); + + // + bool isVWapFastOverMid = conditions.vwapFastBuffer[cIDX] > conditions.vwapMidBuffer[cIDX]; + bool isVWapFastOverMidPrev = conditions.vwapFastBuffer[pIDX] > conditions.vwapMidBuffer[pIDX]; + + // + bool isVWapMidOverSlow = conditions.vwapMidBuffer[cIDX] > conditions.vwapSlowBuffer[cIDX]; + bool isVWapMidOverSlowPrev = conditions.vwapMidBuffer[pIDX] > conditions.vwapSlowBuffer[pIDX]; + + // + bool isVWapFastUnderMid = conditions.vwapFastBuffer[cIDX] < conditions.vwapMidBuffer[cIDX]; + bool isVWapFastUnderMidPrev = conditions.vwapFastBuffer[pIDX] < conditions.vwapMidBuffer[pIDX]; + + // + bool isVWapMidUnderSlow = conditions.vwapMidBuffer[cIDX] < conditions.vwapSlowBuffer[cIDX]; + bool isVWapMidUnderSlowPrev = conditions.vwapMidBuffer[pIDX] < conditions.vwapSlowBuffer[pIDX]; + + // + bool isVWapBullishState = isVWapFastBullish && + isVWapMidBullish && + isVWapSlowBullish; + bool isVWapBullishStatePrev = isVWapFastBullishPrev && + isVWapMidBullishPrev && + isVWapSlowBullishPrev; + + // + bool isVWapBearishState = isVWapFastBearish && + isVWapMidBearish && + isVWapSlowBearish; + bool isVWapBearishStatePrev = isVWapFastBearishPrev && + isVWapMidBearishPrev && + isVWapSlowBearishPrev; + + // + bool isVWapNeuturalState = isVWapFastNeutural && + isVWapMidNeutural && + isVWapSlowNeutural; + bool isVWapNeuturalStatePrev = isVWapFastNeuturalPrev && + isVWapMidNeuturalPrev && + isVWapSlowNeuturalPrev; + + // + bool isVWapBullishOrdered = isVWapFastOverMid && + isVWapMidOverSlow; + bool isVWapBullishOrderedPrev = isVWapFastOverMidPrev && + isVWapMidOverSlowPrev; + + // + bool isVWapBearishOrdered = isVWapFastUnderMid && + isVWapMidUnderSlow; + bool isVWapBearishOrderedPrev = isVWapFastUnderMidPrev && + isVWapMidUnderSlowPrev; + + // + bool isVWapSwitchedToBullishOrdered = isVWapBullishOrdered && + !isVWapBullishOrderedPrev; + bool isVWapSwitchedToBearishOrdered = isVWapBearishOrdered && + !isVWapBearishOrderedPrev; + + // + bool isVWapSwitchedToBullishState = isVWapBullishState && + !isVWapBullishStatePrev; + bool isVWapSwitchedToBearishState = isVWapBearishState && + !isVWapBearishStatePrev; + bool isVWapSwitchedToNeuturalState = isVWapNeuturalState && + !isVWapNeuturalStatePrev; + + // + // XDON ... + + // + // Set ... + conditions.isRSIOverBought = isRSIOverBought; + conditions.isRSICrossedOverOverBought = isRSICrossedOverOverBought; + conditions.isRSICrossedUnderOverBought = isRSICrossedUnderOverBought; + conditions.isRSIOverSold = isRSIOverSold; + conditions.isRSICrossedUnderOverSold = isRSICrossedUnderOverSold; + conditions.isRSICrossedOverOverSold = isRSICrossedOverOverSold; + conditions.isSarBullish = isSarBullish; + conditions.isSarBearish = isSarBearish; + conditions.isSarSwitchedToBullish = isSarSwitchedToBullish; + conditions.isSarSwitchedToBearish = isSarSwitchedToBearish; + conditions.isNewPeak = isNewPeak; + conditions.isNewPeakOverLast = isNewPeakOverLast; + conditions.isNewPeakUnderLast = isNewPeakUnderLast; + conditions.isNewVale = isNewVale; + conditions.isNewValeOverLast = isNewValeOverLast; + conditions.isNewValeUnderLast = isNewValeUnderLast; + conditions.isVWapFastBullish = isVWapFastBullish; + conditions.isVWapFastBearish = isVWapFastBearish; + conditions.isVWapFastNeutural = isVWapFastNeutural; + conditions.isVWapMidBullish = isVWapMidBullish; + conditions.isVWapMidBearish = isVWapMidBearish; + conditions.isVWapMidNeutural = isVWapMidNeutural; + conditions.isVWapSlowBullish = isVWapSlowBullish; + conditions.isVWapSlowBearish = isVWapSlowBearish; + conditions.isVWapSlowNeutural = isVWapSlowNeutural; + conditions.isVWapFastOverMid = isVWapFastOverMid; + conditions.isVWapMidOverSlow = isVWapMidOverSlow; + conditions.isVWapFastUnderMid = isVWapFastUnderMid; + conditions.isVWapMidUnderSlow = isVWapMidUnderSlow; + conditions.isVWapBullishState = isVWapBullishState; + conditions.isVWapBearishState = isVWapBearishState; + conditions.isVWapNeuturalState = isVWapNeuturalState; + conditions.isVWapBullishOrdered = isVWapBullishOrdered; + conditions.isVWapBearishOrdered = isVWapBearishOrdered; + conditions.isVWapSwitchedToBullishOrdered = isVWapSwitchedToBullishOrdered; + conditions.isVWapSwitchedToBearishOrdered = isVWapSwitchedToBearishOrdered; + conditions.isVWapSwitchedToBullishState = isVWapSwitchedToBullishState; + conditions.isVWapSwitchedToBearishState = isVWapSwitchedToBearishState; + conditions.isVWapSwitchedToNeuturalState = isVWapSwitchedToNeuturalState; + + // + return result; + } + + // + protected: + // + + // + private: + // + // Props ... + X121Inputs mInputs; // Inputs ... + + // + // Buffers ... + double peaksBuffer[]; + double valesBuffer[]; + double sarBuffer[]; + double atrUpperBuffer[]; + double atrLowerBuffer[]; + double vwapFastBuffer[]; + double vwapMidBuffer[]; + double vwapSlowBuffer[]; + double donOpenUpperBuffer[]; + double donOpenLowerBuffer[]; + double donCloseUpperBuffer[]; + double donCloseLowerBuffer[]; + double donHighUpperBuffer[]; + double donHighLowerBuffer[]; + double donLowUpperBuffer[]; + double donLowLowerBuffer[]; + double cHHBuffer[]; + double cLLBuffer[]; + double sHHBuffer[]; + double sLLBuffer[]; + double mHHBuffer[]; + double mLLBuffer[]; + double lHHBuffer[]; + double lLLBuffer[]; + double hHHBuffer[]; + double hLLBuffer[]; + double atrBuffer[]; + double atrUpperRawBuffer[]; + double atrLowerRawBuffer[]; + double vwapVolumeBuffer[]; + double vwapPriceBuffer[]; + double vwapFastStateBuffer[]; + double vwapMidStateBuffer[]; + double vwapSlowStateBuffer[]; + double rsiBuffer[]; + + // + // Tools ... + + /** + * Calculate Buffers ... + */ + void Calculate() + { + // + int totalBars = CountBars(); + if (totalBars > 1000) + { + totalBars = 1000; + } + + // + // Buffers ... + + // + // RSI ... + CopyBuffer( + mHandler, + X121_RSI_LINE, + 0, + totalBars, + rsiBuffer + // + ); + + // + // XSAR ... + CopyBuffer( + mHandler, + X121_SAR_LINE, + 0, + totalBars, + sarBuffer + // + ); + + // + // ATR ... + + // + CopyBuffer( + mHandler, + X121_ATR_UPPER_LINE, + 0, + totalBars, + atrUpperBuffer + // + ); + + // + CopyBuffer( + mHandler, + X121_ATR_LOWER_LINE, + 0, + totalBars, + atrLowerBuffer + // + ); + + // + CopyBuffer( + mHandler, + X121_ATR_LINE, + 0, + totalBars, + atrBuffer + // + ); + + // + CopyBuffer( + mHandler, + X121_ATR_UPPER_RAW_LINE, + 0, + totalBars, + atrUpperRawBuffer + // + ); + + // + CopyBuffer( + mHandler, + X121_ATR_LOWER_RAW_LINE, + 0, + totalBars, + atrLowerRawBuffer + // + ); + + // + // XPV ... + + // + // PEAKS ... + CopyBuffer( + mHandler, + X121_PEAKS_LINE, + 0, + totalBars, + peaksBuffer + // + ); + + // + // VALES ... + CopyBuffer( + mHandler, + X121_VALES_LINE, + 0, + totalBars, + valesBuffer + // + ); + + // + // CURRENT ... + + // + // HH ... + CopyBuffer( + mHandler, + X121_CURRENT_HH_LINE, + 0, + totalBars, + cHHBuffer + // + ); + + // + // LL ... + CopyBuffer( + mHandler, + X121_CURRENT_LL_LINE, + 0, + totalBars, + cLLBuffer + // + ); + + // + // SHORT ... + + // + // HH ... + CopyBuffer( + mHandler, + X121_SHORT_HH_LINE, + 0, + totalBars, + sHHBuffer + // + ); + + // + // LL ... + CopyBuffer( + mHandler, + X121_SHORT_LL_LINE, + 0, + totalBars, + sLLBuffer + // + ); + + // + // MEDIUM ... + + // + // HH ... + CopyBuffer( + mHandler, + X121_MEDIUM_HH_LINE, + 0, + totalBars, + mHHBuffer + // + ); + + // + // LL ... + CopyBuffer( + mHandler, + X121_MEDIUM_LL_LINE, + 0, + totalBars, + mLLBuffer + // + ); + + // + // LONG ... + + // + // HH ... + CopyBuffer( + mHandler, + X121_LONG_HH_LINE, + 0, + totalBars, + lHHBuffer + // + ); + + // + // LL ... + CopyBuffer( + mHandler, + X121_LONG_LL_LINE, + 0, + totalBars, + lLLBuffer + // + ); + + // + // HIND ... + + // + // HH ... + CopyBuffer( + mHandler, + X121_HIND_HH_LINE, + 0, + totalBars, + hHHBuffer + // + ); + + // + // LL ... + CopyBuffer( + mHandler, + X121_HIND_LL_LINE, + 0, + totalBars, + hLLBuffer + // + ); + + // + // XVWAP ... + + // + // FAST ... + CopyBuffer( + mHandler, + X121_VWAP_FAST_LINE, + 0, + totalBars, + vwapFastBuffer + // + ); + + // + // FAST STATE ... + CopyBuffer( + mHandler, + X121_VWAP_FAST_STATE_LINE, + 0, + totalBars, + vwapFastStateBuffer + // + ); + + // + // MID ... + CopyBuffer( + mHandler, + X121_VWAP_MID_LINE, + 0, + totalBars, + vwapMidBuffer + // + ); + + // + // MID STATE ... + CopyBuffer( + mHandler, + X121_VWAP_MID_STATE_LINE, + 0, + totalBars, + vwapMidStateBuffer + // + ); + + // + // SLOW ... + CopyBuffer( + mHandler, + X121_VWAP_SLOW_LINE, + 0, + totalBars, + vwapSlowBuffer + // + ); + + // + // SLOW STATE ... + CopyBuffer( + mHandler, + X121_VWAP_SLOW_STATE_LINE, + 0, + totalBars, + vwapSlowStateBuffer + // + ); + + // + // VOLUME ... + CopyBuffer( + mHandler, + X121_VWAP_VOLUME_LINE, + 0, + totalBars, + vwapVolumeBuffer + // + ); + + // + // PRICE ... + CopyBuffer( + mHandler, + X121_VWAP_PRICE_LINE, + 0, + totalBars, + vwapPriceBuffer + // + ); + + // + // XDON ... + + // + // OPEN ... + + // + // Upper ... + CopyBuffer( + mHandler, + X121_DON_OPEN_UPPER_LINE, + 0, + totalBars, + donOpenUpperBuffer + // + ); + + // + // Lower ... + CopyBuffer( + mHandler, + X121_DON_OPEN_LOWER_LINE, + 0, + totalBars, + donOpenLowerBuffer + // + ); + + // + // CLOSE ... + + // + // Upper ... + CopyBuffer( + mHandler, + X121_DON_CLOSE_UPPER_LINE, + 0, + totalBars, + donCloseUpperBuffer + // + ); + + // + // Lower ... + CopyBuffer( + mHandler, + X121_DON_CLOSE_LOWER_LINE, + 0, + totalBars, + donCloseLowerBuffer + // + ); + + // + // HIGH ... + + // + // Upper ... + CopyBuffer( + mHandler, + X121_DON_HIGH_UPPER_LINE, + 0, + totalBars, + donHighUpperBuffer + // + ); + + // + // Lower ... + CopyBuffer( + mHandler, + X121_DON_HIGH_LOWER_LINE, + 0, + totalBars, + donHighLowerBuffer + // + ); + + // + // LOW ... + + // + // Upper ... + CopyBuffer( + mHandler, + X121_DON_LOW_UPPER_LINE, + 0, + totalBars, + donLowUpperBuffer + // + ); + + // + // Lower ... + CopyBuffer( + mHandler, + X121_DON_LOW_LOWER_LINE, + 0, + totalBars, + donLowLowerBuffer + // + ); + } +}; + +// \ No newline at end of file diff --git a/Indicators/x-saherelm.x121.mq5 b/Documents/BKP/1/x-saherelm.x121.mq5 similarity index 85% rename from Indicators/x-saherelm.x121.mq5 rename to Documents/BKP/1/x-saherelm.x121.mq5 index 363462b3..4a240372 100644 --- a/Indicators/x-saherelm.x121.mq5 +++ b/Documents/BKP/1/x-saherelm.x121.mq5 @@ -80,6 +80,10 @@ input ENUM_APPLIED_PRICE atrUpperAppliedTo = PRICE_HIGH; // Upper Zone Applied T input ENUM_APPLIED_PRICE atrLowerAppliedTo = PRICE_LOW; // Lower Zone Applied To input ENUM_X_MA_METHOD atrSmoothingMode = X_MA_MODE_EMA; // Smoothing Method +// +input group "Str Detecttion"; +input ENUM_APPLIED_PRICE strAppliedTo = PRICE_MEDIAN; // Applied To + // input group "VWap Detection"; input int vwapFastLength = 20; // Fast Length @@ -105,6 +109,7 @@ input int valesArrowCode = 159; // Vales Arrow Code // input bool showSar = true; // Show Parabolic Sar input bool showAtr = true; // Show Atr +input bool showStr = true; // Show Str input bool showPeaks = true; // Show Peaks input bool showVales = true; // Show Vales input bool showVWap = true; // Show VWap @@ -143,8 +148,8 @@ input bool showLow = false; // Show Low #property indicator_chart_window // -#property indicator_buffers 38 -#property indicator_plots 16 +#property indicator_buffers 44 +#property indicator_plots 17 // // PEAKS ... @@ -215,55 +220,71 @@ double atrLowerBuffer[]; #property indicator_width5 2 // -// VWAP ... +// STR ... +#define strBufferIndex 5 +double strBuffer[]; + +#define strColorBufferIndex 6 +double strColorBuffer[]; // -// FAST ... -#define vwapFastBufferIndex 5 -double vwapFastBuffer[]; - -#define vwapFastColorBufferIndex 6 -double vwapFastColorBuffer[]; - -// -#define vwapFastPlotBufferIndex 5 -#property indicator_label6 "X121 VWF" +#define strPlotBufferIndex 5 +#property indicator_label6 "X121 STR" #property indicator_type6 DRAW_COLOR_LINE -#property indicator_color6 CLR_NONE, clrAqua, clrMagenta, clrGray +#property indicator_color6 CLR_NONE, clrLime, clrRed, clrGray #property indicator_style6 STYLE_SOLID #property indicator_width6 2 // -// MID ... -#define vwapMidBufferIndex 7 -double vwapMidBuffer[]; - -#define vwapMidColorBufferIndex 8 -double vwapMidColorBuffer[]; +// VWAP ... // -#define vwapMidPlotBufferIndex 6 -#property indicator_label7 "X121 VWM" +// FAST ... +#define vwapFastBufferIndex 7 +double vwapFastBuffer[]; + +#define vwapFastColorBufferIndex 8 +double vwapFastColorBuffer[]; + +// +#define vwapFastPlotBufferIndex 6 +#property indicator_label7 "X121 VWF" #property indicator_type7 DRAW_COLOR_LINE -#property indicator_color7 CLR_NONE, clrGreen, clrRed, clrGray +#property indicator_color7 CLR_NONE, clrAqua, clrMagenta, clrGray #property indicator_style7 STYLE_SOLID #property indicator_width7 2 +// +// MID ... +#define vwapMidBufferIndex 9 +double vwapMidBuffer[]; + +#define vwapMidColorBufferIndex 10 +double vwapMidColorBuffer[]; + +// +#define vwapMidPlotBufferIndex 7 +#property indicator_label8 "X121 VWM" +#property indicator_type8 DRAW_COLOR_LINE +#property indicator_color8 CLR_NONE, clrGreen, clrRed, clrGray +#property indicator_style8 STYLE_SOLID +#property indicator_width8 2 + // // SLOW ... -#define vwapSlowBufferIndex 9 +#define vwapSlowBufferIndex 11 double vwapSlowBuffer[]; -#define vwapSlowColorBufferIndex 10 +#define vwapSlowColorBufferIndex 12 double vwapSlowColorBuffer[]; // -#define vwapSlowPlotBufferIndex 7 -#property indicator_label8 "X121 VWS" -#property indicator_type8 DRAW_COLOR_LINE -#property indicator_color8 CLR_NONE, clrSteelBlue, clrDarkRed, clrGray -#property indicator_style8 STYLE_SOLID -#property indicator_width8 2 +#define vwapSlowPlotBufferIndex 8 +#property indicator_label9 "X121 VWS" +#property indicator_type9 DRAW_COLOR_LINE +#property indicator_color9 CLR_NONE, clrSteelBlue, clrDarkRed, clrGray +#property indicator_style9 STYLE_SOLID +#property indicator_width9 2 // // XDON ... @@ -272,107 +293,107 @@ double vwapSlowColorBuffer[]; // Open ... // -#define donOpenUpperBufferIndex 11 +#define donOpenUpperBufferIndex 13 double donOpenUpperBuffer[]; // -#define donOpenUpperPlotBufferIndex 8 -#property indicator_label9 "X121 O U" -#property indicator_type9 DRAW_LINE -#property indicator_color9 clrCornflowerBlue -#property indicator_width9 1 - -// -#define donOpenLowerBufferIndex 12 -double donOpenLowerBuffer[]; - -// -#define donOpenLowerPlotBufferIndex 9 -#property indicator_label10 "X121 O L" +#define donOpenUpperPlotBufferIndex 9 +#property indicator_label10 "X121 O U" #property indicator_type10 DRAW_LINE #property indicator_color10 clrCornflowerBlue #property indicator_width10 1 // -// High ... +#define donOpenLowerBufferIndex 14 +double donOpenLowerBuffer[]; // -#define donHighUpperBufferIndex 13 -double donHighUpperBuffer[]; - -// -#define donHighUpperPlotBufferIndex 10 -#property indicator_label11 "X121 H U" +#define donOpenLowerPlotBufferIndex 10 +#property indicator_label11 "X121 O L" #property indicator_type11 DRAW_LINE -#property indicator_color11 clrAquamarine +#property indicator_color11 clrCornflowerBlue #property indicator_width11 1 // -#define donHighLowerBufferIndex 14 -double donHighLowerBuffer[]; +// High ... // -#define donHighLowerPlotBufferIndex 11 -#property indicator_label12 "X121 H L" +#define donHighUpperBufferIndex 15 +double donHighUpperBuffer[]; + +// +#define donHighUpperPlotBufferIndex 11 +#property indicator_label12 "X121 H U" #property indicator_type12 DRAW_LINE #property indicator_color12 clrAquamarine #property indicator_width12 1 // -// Low ... +#define donHighLowerBufferIndex 16 +double donHighLowerBuffer[]; // -#define donLowUpperBufferIndex 15 -double donLowUpperBuffer[]; - -// -#define donLowUpperPlotBufferIndex 12 -#property indicator_label13 "X121 L U" +#define donHighLowerPlotBufferIndex 12 +#property indicator_label13 "X121 H L" #property indicator_type13 DRAW_LINE -#property indicator_color13 clrDarkOrchid +#property indicator_color13 clrAquamarine #property indicator_width13 1 // -#define donLowLowerBufferIndex 16 -double donLowLowerBuffer[]; +// Low ... // -#define donLowLowerPlotBufferIndex 13 -#property indicator_label14 "X121 L L" +#define donLowUpperBufferIndex 17 +double donLowUpperBuffer[]; + +// +#define donLowUpperPlotBufferIndex 13 +#property indicator_label14 "X121 L U" #property indicator_type14 DRAW_LINE #property indicator_color14 clrDarkOrchid #property indicator_width14 1 // -// Close ... +#define donLowLowerBufferIndex 18 +double donLowLowerBuffer[]; // -#define donCloseUpperBufferIndex 17 -double donCloseUpperBuffer[]; - -// -#define donCloseUpperPlotBufferIndex 14 -#property indicator_label15 "X121 C U" +#define donLowLowerPlotBufferIndex 14 +#property indicator_label15 "X121 L L" #property indicator_type15 DRAW_LINE -#property indicator_color15 clrCoral +#property indicator_color15 clrDarkOrchid #property indicator_width15 1 // -#define donCloseLowerBufferIndex 18 -double donCloseLowerBuffer[]; +// Close ... // -#define donCloseLowerPlotBufferIndex 15 -#property indicator_label16 "X121 C L" +#define donCloseUpperBufferIndex 19 +double donCloseUpperBuffer[]; + +// +#define donCloseUpperPlotBufferIndex 15 +#property indicator_label16 "X121 C U" #property indicator_type16 DRAW_LINE #property indicator_color16 clrCoral #property indicator_width16 1 +// +#define donCloseLowerBufferIndex 20 +double donCloseLowerBuffer[]; + +// +#define donCloseLowerPlotBufferIndex 16 +#property indicator_label17 "X121 C L" +#property indicator_type17 DRAW_LINE +#property indicator_color17 clrCoral +#property indicator_width17 1 + // // Data Buffers ... // -int mLastBufferIndex = 18; +int mLastBufferIndex = 20; // // CURRENT ... @@ -471,12 +492,36 @@ double atrLowerRawBuffer[]; #define rsiBufferIndex mLastBufferIndex + 19 double rsiBuffer[]; +// +// STR ... + +// +// Price ... +#define strPriceBufferIndex mLastBufferIndex + 20 +double strPriceBuffer[]; + +// +// Up ... +#define strUpBufferIndex mLastBufferIndex + 21 +double strUpBuffer[]; + +// +// Down ... +#define strDownBufferIndex mLastBufferIndex + 22 +double strDownBuffer[]; + +// +// Trend ... +#define strStateBufferIndex mLastBufferIndex + 23 +double strStateBuffer[]; + // // Variables, Properties and etc ... // // this counts Available Bars ... int limit; +int rlimit; // int maxLength; @@ -494,7 +539,9 @@ int sarHandler = INVALID_HANDLE; int atrHandler = INVALID_HANDLE; // -double mHideColorIDX = 0; +bool isStrTrendChanged; +bool isStrStartBearishTrend; +bool isStrStartBullishTrend; // // XMarketCycle sc; @@ -712,7 +759,12 @@ int OnCalculate( } // - limit = (prev_calculated > rates_total || prev_calculated <= 0) ? rates_total : (rates_total - prev_calculated) + 1; + limit = (prev_calculated > rates_total || prev_calculated <= 0) + ? rates_total + : (rates_total - prev_calculated) + 1; + rlimit = (prev_calculated > rates_total || prev_calculated <= 0) + ? maxLength + : prev_calculated - 1; // // Buffers Copy ... @@ -932,6 +984,13 @@ void DefineBuffers() PlotIndexSetInteger(atrLowerBufferIndex, PLOT_SHOW_DATA, canShowAtrLower); PlotIndexSetInteger(atrLowerBufferIndex, PLOT_DRAW_TYPE, atrLowerDrawType); + // + // STR ... + ArraySetAsSeries(strBuffer, true); + ArraySetAsSeries(strColorBuffer, true); + SetIndexBuffer(strBufferIndex, strBuffer, INDICATOR_DATA); + SetIndexBuffer(strColorBufferIndex, strColorBuffer, INDICATOR_COLOR_INDEX); + // // XVWAP ... @@ -1158,6 +1217,25 @@ void DefineBuffers() // ArraySetAsSeries(rsiBuffer, true); SetIndexBuffer(rsiBufferIndex, rsiBuffer, INDICATOR_CALCULATIONS); + + // + // STR ... + + // + ArraySetAsSeries(strPriceBuffer, true); + SetIndexBuffer(strPriceBufferIndex, strPriceBuffer, INDICATOR_CALCULATIONS); + + // + ArraySetAsSeries(strUpBuffer, true); + SetIndexBuffer(strUpBufferIndex, strUpBuffer, INDICATOR_CALCULATIONS); + + // + ArraySetAsSeries(strDownBuffer, true); + SetIndexBuffer(strDownBufferIndex, strDownBuffer, INDICATOR_CALCULATIONS); + + // + ArraySetAsSeries(strStateBuffer, true); + SetIndexBuffer(strStateBufferIndex, strStateBuffer, INDICATOR_CALCULATIONS); } /** @@ -1233,6 +1311,17 @@ void CalculateBuffers( low // ); + // + CalculateStr( + bar_index, + prevCalculated, + ratesTotal, + open, + high, + close, + low // + ); + // // Calculate Required VWAP Data Buffers ... if (ratesTotal - bar_index <= maxLength) @@ -1455,6 +1544,15 @@ void FillBuffersZero(int barIndex) atrUpperBuffer[barIndex] = 0; atrLowerRawBuffer[barIndex] = 0; + // + // STR ... + strBuffer[barIndex] = 0; + strUpBuffer[barIndex] = 0; + strDownBuffer[barIndex] = 0; + strPriceBuffer[barIndex] = 0; + strColorBuffer[barIndex] = hideColorIDX; + strStateBuffer[barIndex] = hideColorIDX; + // // VWAP ... @@ -2017,7 +2115,7 @@ void CalculateDonchains( } /** - * Calculate Different VWaps ... + * Calculate ATR Zones ... * * @param bar_index: Integer, Represent Current Bar ... * @param prevCalculated: Integer, Represent Previous Calculated Bars ... @@ -2114,4 +2212,196 @@ void CalculateAtrZones( } } +/** + * Calculate STR ... + * + * @param bar_index: Integer, Represent Current Bar ... + * @param prevCalculated: Integer, Represent Previous Calculated Bars ... + * @param ratesTotal: Integer, Represents All Available Bars ... + * @param open: Double Array, History of Open Prices ... + * @param high: Double Array, History of High Prices ... + * @param close: Double Array, History of Close Prices ... + * @param low: Double Array, History of Low Prices ... + */ +void CalculateStr( + int bar_index, // Selected Bar Index + const int prevCalculated, + const int ratesTotal, + const double &open[], + const double &high[], + const double &close[], + const double &low[] // +) +{ + // + // Calculated Price ... + double price = GetAppliedPrice( + strAppliedTo, + open, + high, + low, + close, + bar_index // + ); + + // + strPriceBuffer[bar_index] = price; + + // + double atr = atrBuffer[bar_index]; + + // + double appliedAtr = (atrMultiplier * atr); + double strUp = price + appliedAtr; + double strDown = price - appliedAtr; + + // + strUpBuffer[bar_index] = strUp; + strDownBuffer[bar_index] = strDown; + + // + int currIDX = bar_index; + int prevIDX = currIDX + 1; + int prevOfPrevIDX = prevIDX + 1; + + // + double prevState = strStateBuffer[prevIDX]; + bool isCloseOverUp = close[currIDX] > strUpBuffer[prevIDX]; + bool isCloseUnderDown = close[currIDX] < strUpBuffer[prevIDX]; + + // + if (isCloseOverUp) + { + // + strStateBuffer[currIDX] = 1; + if (strStateBuffer[prevIDX] == -1) + { + isStrTrendChanged = true; + } + } + else if (isCloseUnderDown) + { + // + strStateBuffer[currIDX] = -1; + if (strStateBuffer[prevIDX] == 1) + { + isStrTrendChanged = true; + } + } + else if (strStateBuffer[prevIDX] == 1) + { + // + isStrTrendChanged = false; + strStateBuffer[currIDX] = 1; + } + else if (strStateBuffer[prevIDX] == -1) + { + // + isStrTrendChanged = false; + strStateBuffer[currIDX] = -1; + } + + // + // Calculate Trend Starting ... + + // + if (strStateBuffer[currIDX] < 0 && + strStateBuffer[prevIDX] > 0) + { + isStrStartBearishTrend = true; + } + else + { + isStrStartBearishTrend = false; + } + + // + if (strStateBuffer[currIDX] > 0 && + strStateBuffer[prevIDX] < 0) + { + isStrStartBullishTrend = true; + } + else + { + isStrStartBullishTrend = false; + } + + // + // Re new Up and Down Buffer ... + + // + if (strStateBuffer[currIDX] > 0 && + strDownBuffer[currIDX] < strDownBuffer[prevIDX]) + { + strDownBuffer[currIDX] = strDownBuffer[prevIDX]; + } + + // + if (strStateBuffer[currIDX] < 0 && + strUpBuffer[currIDX] > strUpBuffer[prevIDX]) + { + strUpBuffer[currIDX] = strUpBuffer[prevIDX]; + } + + // + // Handle Strat Trends ... + + // + if (isStrStartBearishTrend) + { + strUpBuffer[currIDX] = strPriceBuffer[currIDX] + (atrMultiplier * atr); + } + + // + if (isStrStartBullishTrend) + { + strDownBuffer[currIDX] = strPriceBuffer[currIDX] - (atrMultiplier * atr); + } + + // + double clr = hideColorIDX; + double state = hideColorIDX; + + // + if (strStateBuffer[currIDX] == 1) + { + // + strBuffer[currIDX] = strDownBuffer[currIDX]; + if (isStrTrendChanged) + { + // + isStrTrendChanged = false; + strBuffer[prevIDX] = strBuffer[prevOfPrevIDX]; + } + + // + clr = bullishColorIDX; + } + else if (state == -1) + { + // + strBuffer[currIDX] = strUpBuffer[currIDX]; + if (isStrTrendChanged) + { + // + isStrTrendChanged = false; + strBuffer[prevIDX] = strBuffer[prevOfPrevIDX]; + } + + // + clr = bearishColorIDX; + } + + // + if (!showStr) + { + clr = hideColorIDX; + } + + // + strColorBuffer[bar_index] = clr; + + // +} + // \ No newline at end of file diff --git a/Documents/BKP/1/x-saherelm.x121.xempty.mq5 b/Documents/BKP/1/x-saherelm.x121.xempty.mq5 new file mode 100644 index 00000000..bec347c3 --- /dev/null +++ b/Documents/BKP/1/x-saherelm.x121.xempty.mq5 @@ -0,0 +1,325 @@ +/////////////////////////////////////////////////////// +// +// SaherElm IT Center MQL5 Indicator +// ------------------------------------------------- +// Name: X121 ??? +// Description: ??? ... +// +// +// Maintainer: +// ------------ +// Hadi Khazaee Asl (hadi_khazaee_asl@yahoo.com) +// +////////////////////////////////////////////////////// +// +// Global Properties ... +#property copyright "Copyright 2023, SaherElm IT Center" +#property link "https://saherelm.ir" +#property version "1.00" +#property description "SaherElm X121 ??? Indicator" +#property strict + +// +// Definitions ... + +// +#define ShortName "X121 ???" + +// +// Includes Common Library ... +#include "../Libraries/x-saherelm.common.lib.mq5" + +// +// Inputs ... + +// +// Market ... +input group "Market"; + +// +// Presentation ... +input group "Presentation"; + +// +input int startCalculationForLastBars = 1000; // Calculate Last n Bars + +// +// Buffers ... + +// +#define hideColorIDX 0 +#define bullishColorIDX 1 +#define bearishColorIDX 2 +#define neuturalColorIDX 3 + +// +#property indicator_chart_window + +// +#property indicator_buffers 0 +#property indicator_plots 0 + +// +// Plot Buffers ... + +// +// Data Buffers ... + +// +int mLastBufferIndex = 20; + +// +// Variables, Properties and etc ... + +// +// this counts Available Bars ... +int limit; + +// +int maxLength; + +// +// Event Handlers ... + +/** + * Initialize Indicator ... + * + * @return ( int ) + */ +int OnInit() +{ + // + // Validate Inputs ... + if (!ValidateInputs()) + { + return INIT_PARAMETERS_INCORRECT; + } + + // + // Initialize Indicator Handlers ... + + // + // because in some cases we may have more than one input for + // calculation and we must prevent any calculation + // untill we pass the biggest input length, here we get max Input length + // and then wait until pass it ... + maxLength = ExtractMaxLengthOfInputs(); + + // + // Define Index Buffers ... + DefineBuffers(); + + // + // Set Indicator ShortName ... + SetIndicatorName(); + + // + // Init Succeed ... + return INIT_SUCCEEDED; +} + +/** + * De Initialize Indicator ... + * + * @param reason: Integer, De Initialization Reason ... + */ +void OnDeinit(const int reason) +{ + // + // REASON_PROGRAM 0 The EA has stopped working calling the ExpertRemove() function + // REASON_REMOVE 1 Program removed from a chart + // REASON_RECOMPILE 2 Program recompiled + // REASON_CHARTCHANGE 3 A symbol or a chart period is changed + // REASON_CHARTCLOSE 4 Chart closed + // REASON_PARAMETERS 5 Inputs changed by a user + // REASON_ACCOUNT 6 Another account has been activated or reconnection to the trade server has occurred due to changes in the account settings + // REASON_TEMPLATE 7 Another chart template applied + // REASON_INITFAILED 8 The OnInit() handler returned a non-zero value + // REASON_CLOSE 9 Terminal closed +} + +/** + * Calculate Bars ... + * + * @param rates_total: Integer, Total Bars on Chart ... + * @param prev_calculated: Integer, Total Calculated Bars on Charts ... + * @param time: DateTime Array, History of Open Time ... + * @param open: Double Array, History of Open Prices ... + * @param high: Double Array, History of High Prices ... + * @param low: Double Array, History of Low Prices ... + * @param close: Double Array, History of Close Prices ... + * @param tick_volume: Long, History of Tick Volumes on Bar ... + * @param volume: Long, History of Trade Volumes ... + * @param spread: Double, History of Spread Price ... + * + * @return ( int ) + */ +int OnCalculate( + const int rates_total, + const int prev_calculated, + const datetime &time[], + const double &open[], + const double &high[], + const double &low[], + const double &close[], + const long &tick_volume[], + const long &volume[], + const int &spread[] // +) +{ + // + // Prepare Buffers ... + ArraySetAsSeries(time, true); + ArraySetAsSeries(open, true); + ArraySetAsSeries(high, true); + ArraySetAsSeries(low, true); + ArraySetAsSeries(close, true); + ArraySetAsSeries(tick_volume, true); + ArraySetAsSeries(volume, true); + ArraySetAsSeries(spread, true); + + // + // Validate Calculated Bars ... + + // + limit = (prev_calculated > rates_total || prev_calculated <= 0) + ? rates_total + : (rates_total - prev_calculated) + 1; + + // + // Buffers Copy ... + + // + // Main Loop ... + for (int i = limit - 1; i >= 0 && !IsStopped(); i--) + { + // + CalculateBuffers( + i, + prev_calculated, + rates_total, + // + open, + high, + close, + low, + tick_volume // + ); + } + + // + return rates_total; +} + +// +// Functions ... + +/** + * Validate Input Args for Initialization ... + * + * @return ( bool ) + */ +bool ValidateInputs() +{ + // + bool result = false; + + // + result = + // + false + // + ; + + // + return result; +} + +/** + * Extract Max Length of Inputs ... + * + * @return ( int ) + */ +int ExtractMaxLengthOfInputs() +{ + // + int result = 0; + + // + return result; +} + +/** + * Define Required Buffers ... + */ +void DefineBuffers() +{ + // + // Plot Buffers ... + + // + // Data Buffers ... +} + +/** + * Set Indicator Short Name and also we can define Buffers Labels ... + */ +void SetIndicatorName() +{ + IndicatorSetString(INDICATOR_SHORTNAME, ShortName); +} + +/** + * Calculate Custom Buffers ... + * + * @param bar_index: Integer, Represent Current Bar ... + * @param prevCalculated: Integer, Represent Previous Calculated Bars ... + * @param ratesTotal: Integer, Represents All Available Bars ... + * @param open: Double Array, History of Open Prices ... + * @param high: Double Array, History of High Prices ... + * @param close: Double Array, History of Close Prices ... + * @param low: Double Array, History of Low Prices ... + * @param tickVolume: Long, History of Tick Volumes on Bar ... + */ +void CalculateBuffers( + int bar_index, // Selected Bar Index + const int prevCalculated, + const int ratesTotal, + const double &open[], + const double &high[], + const double &close[], + const double &low[], + const long &tickVolume[] // +) +{ + // + int barsLimit = startCalculationForLastBars > 0 + ? startCalculationForLastBars + : 0; + // + // bool canCalculate = true; + bool canCalculate = + barsLimit == 0 || + bar_index <= barsLimit; + if (canCalculate) + { + } + else + { + FillBuffersZero(bar_index); + } +} + +// +// Custom ... + +/** + * Fill All Bufers to Zero Vlue for Specified Bar Index ... + * + * @param barIndex: Integer ... + */ +void FillBuffersZero(int barIndex) +{ +} + +// \ No newline at end of file diff --git a/Helpers/x-saherelm.x121.helper.mq5 b/Helpers/x-saherelm.x121.helper.mq5 index cbaf8074..7989cbec 100644 --- a/Helpers/x-saherelm.x121.helper.mq5 +++ b/Helpers/x-saherelm.x121.helper.mq5 @@ -22,69 +22,11 @@ // // Imports ... -#include "../Classes/x-saherelm.x-helper.class.mq5" - -// -// Definitions ... -enum ENUM_X121_BUFFERS -{ - // - // Main Buffers ... - X121_PEAKS_LINE = 0, - X121_VALES_LINE = 1, - X121_SAR_LINE = 2, - X121_ATR_UPPER_LINE = 3, - X121_ATR_LOWER_LINE = 4, - X121_VWAP_FAST_LINE = 5, - X121_VWAP_MID_LINE = 7, - X121_VWAP_SLOW_LINE = 9, - X121_DON_OPEN_UPPER_LINE = 11, - X121_DON_OPEN_LOWER_LINE = 12, - X121_DON_HIGH_UPPER_LINE = 13, - X121_DON_HIGH_LOWER_LINE = 14, - X121_DON_LOW_UPPER_LINE = 15, - X121_DON_LOW_LOWER_LINE = 16, - X121_DON_CLOSE_UPPER_LINE = 17, - X121_DON_CLOSE_LOWER_LINE = 18, - // - // Data Buffers ... - // - // XPV Data ... - X121_CURRENT_HH_LINE = 19, - X121_CURRENT_LL_LINE = 20, - X121_SHORT_HH_LINE = 21, - X121_SHORT_LL_LINE = 22, - X121_MEDIUM_HH_LINE = 23, - X121_MEDIUM_LL_LINE = 24, - X121_LONG_HH_LINE = 25, - X121_LONG_LL_LINE = 26, - X121_HIND_HH_LINE = 27, - X121_HIND_LL_LINE = 28, - // - // VWAP Data ... - X121_VWAP_VOLUME_LINE = 29, - X121_VWAP_PRICE_LINE = 30, - X121_VWAP_FAST_STATE_LINE = 31, - X121_VWAP_MID_STATE_LINE = 32, - X121_VWAP_SLOW_STATE_LINE = 33, - // - // ATR ... - X121_ATR_LINE = 34, - X121_ATR_UPPER_RAW_LINE = 35, - X121_ATR_LOWER_RAW_LINE = 36, - // - // RSI ... - X121_RSI_LINE = 37 -}; - -// -enum ENUM_XVWAP_STATES -{ - // - XVWAP_STATE_BULLISH = 1, - XVWAP_STATE_BEARISH = 2, - XVWAP_STATE_NEUTURAL = 3, -}; +#include "../Helpers/x-saherelm.x121.xatr.helper.mq5" +#include "../Helpers/x-saherelm.x121.xdon.helper.mq5" +#include "../Helpers/x-saherelm.x121.xpv.helper.mq5" +#include "../Helpers/x-saherelm.x121.xstr.helper.mq5" +#include "../Helpers/x-saherelm.x121.xvwap.helper.mq5" // // Inputs ... @@ -92,109 +34,11 @@ struct X121Inputs { // // Props ... - - // - // Cycles ... - - // - // Short ... - ENUM_X_PERIOD_METHOD scMethod; // How to Find Period - ENUM_TIMEFRAMES scPeriod; // Time Period - - // - // Medium ... - ENUM_X_PERIOD_METHOD mcMethod; // How to Find Period - ENUM_TIMEFRAMES mcPeriod; // Time Period - - // - // Long ... - ENUM_X_PERIOD_METHOD lcMethod; // How to Find Period - ENUM_TIMEFRAMES lcPeriod; // Time Period - - // - // Hind ... - ENUM_X_PERIOD_METHOD hcMethod; // How to Find Period - ENUM_TIMEFRAMES hcPeriod; // Time Period - - // - // Boundary Detection ... - ENUM_SERIESMODE hhMode; // Highest High Calculation Method - ENUM_SERIESMODE llMode; // Lowest Low Calculation Method - - // - // Parabolic Sar Detection ... - double sarStep; // Step - double sarMax; // Maximum - - // - // RSI ... - int rsiLength; // Length - double rsiOverSoldLevel; // Over Sold Level - double rsiOverBoughtLevel; // Over Bought Level - ENUM_APPLIED_PRICE rsiAppliedTo; // Applied To - - // - // Atr Detection ... - int atrLength; // Length - double atrMultiplier; // Multiplier - ENUM_APPLIED_PRICE atrUpperAppliedTo; // Upper Zone Applied To - ENUM_APPLIED_PRICE atrLowerAppliedTo; // Lower Zone Applied To - ENUM_X_MA_METHOD atrSmoothingMode; // Smoothing Method - - // - // VWap Detection ... - int vwapFastLength; // Fast Length - int vwapMidLength; // Mid Length - int vwapSlowLength; // Slow Length - ENUM_APPLIED_PRICE vwapAppliedTo; // Applied To - - // - // Donchain Detection ... - int donchainLength; // Donchain Length - - // - // Presentation ... - - // - int startCalculationForLastBars; // Calculate Last n Bars - - // - int sarArrowCode; // Parabolic Sar Arrow Code - int peaksArrowCode; // Peaks Arrow Code - int valesArrowCode; // Vales Arrow Code - - // - // Global ... - bool showSar; // Show Parabolic Sar - bool showAtr; // Show Atr - bool showPeaks; // Show Peaks - bool showVales; // Show Vales - bool showVWap; // Show VWap - bool showDonchain; // Show Donchain - - // - // Atr Presentation ... - bool showAtrUpper; // Show Upper Zone - bool showAtrLower; // Show Lower Zone - - // - // VWap Presentation ... - bool showVWapFast; // Show VWap Fast - bool showVWapMedium; // Show VWap Medium - bool showVWapSlow; // Show VWap Slow - - // - // Donchain Presentation ... - - // - bool showUpper; // Show Upper Band - bool showLower; // Show Lower Band - - // - bool showOpen; // Show Open - bool showHigh; // Show High - bool showClose; // Show Close - bool showLow; // Show Low + X121XPVInputs xpvInputs; + X121XATRInputs xatrInputs; + X121XSTRInputs xstrInputs; + X121XDONInputs xdonInputs; + X121XVWAPInputs xvwapInputs; // // Constructor ... @@ -212,107 +56,11 @@ struct X121Inputs void Clean() { // - // Cycles ... - - // - // Short ... - scMethod = X_PERIOD_NOTHING; - scPeriod = NULL; - - // - // Medium ... - mcMethod = X_PERIOD_NOTHING; - mcPeriod = NULL; - - // - // Long ... - lcMethod = X_PERIOD_NOTHING; - lcPeriod = NULL; - - // - // Hind ... - hcMethod = X_PERIOD_NOTHING; - hcPeriod = NULL; - - // - // Boundary Detection ... - hhMode = MODE_HIGH; - llMode = MODE_LOW; - - // - // RSI ... - rsiLength = 0; - rsiOverSoldLevel = 0; - rsiOverBoughtLevel = 0; - rsiAppliedTo = PRICE_CLOSE; - - // - // Paraboli Sar Detection ... - sarStep = 0; - sarMax = 0; - - // - // Atr Detection ... - atrLength = 0; // Length - atrMultiplier = 0; // Multiplier - atrUpperAppliedTo = PRICE_HIGH; // Upper Zone Applied To - atrLowerAppliedTo = PRICE_LOW; // Lower Zone Applied To - atrSmoothingMode = X_MA_MODE_NONE; // Smoothing Method - - // - // VWap Detection ... - vwapFastLength = 0; - vwapMidLength = 0; - vwapSlowLength = 0; - vwapAppliedTo = PRICE_CLOSE; - - // - // Donchain Detection ... - donchainLength = 0; - - // - // Presentation ... - - // - startCalculationForLastBars = 0; - - // - sarArrowCode = 0; - peaksArrowCode = 0; - valesArrowCode = 0; - - // - // Globals ... - showSar = false; - showAtr = false; - showPeaks = false; - showVales = false; - showVWap = false; - showDonchain = false; - - // - // Atr Presentation ... - showAtrUpper = false; // Show Upper Zone - showAtrLower = false; // Show Lower Zone - - // - // VWap Presentation ... - showVWapFast = false; - showVWapMedium = false; - showVWapSlow = false; - - // - // Donchain Presentation ... - - // - showUpper = false; - showLower = false; - - // - showOpen = false; - showHigh = false; - showClose = false; - showLow = false; + xpvInputs.Clean(); + xatrInputs.Clean(); + xstrInputs.Clean(); + xdonInputs.Clean(); + xvwapInputs.Clean(); } /** @@ -321,107 +69,11 @@ struct X121Inputs void Default() { // - // Cycles ... - - // - // Short ... - scMethod = X_PERIOD_AUTO; - scPeriod = NULL; - - // - // Medium ... - mcMethod = X_PERIOD_AUTO; - mcPeriod = NULL; - - // - // Long ... - lcMethod = X_PERIOD_AUTO; - lcPeriod = NULL; - - // - // Hind ... - hcMethod = X_PERIOD_AUTO; - hcPeriod = NULL; - - // - // Boundary Detection ... - hhMode = MODE_HIGH; - llMode = MODE_LOW; - - // - // RSI ... - rsiLength = 14; - rsiOverSoldLevel = 30; - rsiOverBoughtLevel = 70; - rsiAppliedTo = PRICE_CLOSE; - - // - // Paraboli Sar Detection ... - sarStep = 0.02; - sarMax = 0.2; - - // - // Atr Detection ... - atrLength = 14; // Length - atrMultiplier = 1; // Multiplier - atrUpperAppliedTo = PRICE_HIGH; // Upper Zone Applied To - atrLowerAppliedTo = PRICE_LOW; // Lower Zone Applied To - atrSmoothingMode = X_MA_MODE_EMA; // Smoothing Method - - // - // VWap Detection ... - vwapFastLength = 20; - vwapMidLength = 40; - vwapSlowLength = 60; - vwapAppliedTo = PRICE_CLOSE; - - // - // Donchain Detection ... - donchainLength = 40; - - // - // Presentation ... - - // - startCalculationForLastBars = 1500; - - // - sarArrowCode = 159; - peaksArrowCode = 159; - valesArrowCode = 159; - - // - // Globals ... - showSar = true; - showAtr = true; - showPeaks = true; - showVales = true; - showVWap = true; - showDonchain = true; - - // - // Atr Presentation ... - showAtrUpper = true; // Show Upper Zone - showAtrLower = true; // Show Lower Zone - - // - // VWap Presentation ... - showVWapFast = true; - showVWapMedium = true; - showVWapSlow = true; - - // - // Donchain Presentation ... - - // - showUpper = true; - showLower = true; - - // - showOpen = true; - showHigh = false; - showClose = true; - showLow = false; + xpvInputs.Default(); + xatrInputs.Default(); + xstrInputs.Default(); + xdonInputs.Default(); + xvwapInputs.Default(); } /** @@ -437,33 +89,11 @@ struct X121Inputs // result = // - // RSI ... - rsiLength > 0 && - rsiOverSoldLevel > 0 && - rsiOverBoughtLevel > 0 && - rsiOverSoldLevel < rsiOverBoughtLevel && - // PSAR ... - sarMax > 0 && - sarStep > 0 && - sarMax > sarStep && - // - // ATR ... - atrLength > 0 && - atrMultiplier > 0 && - // - // XDON ... - donchainLength > 0 && - // - // VWAP ... - vwapFastLength > 2 && - vwapMidLength > vwapFastLength && - vwapSlowLength > vwapMidLength && - // - // XPV ... - (IsValid(scMethod, scPeriod) && - IsValid(mcMethod, mcPeriod) && - IsValid(lcMethod, lcPeriod) && - IsValid(hcMethod, hcPeriod)) + xpvInputs.IsValid() && + xatrInputs.IsValid() && + xstrInputs.IsValid() && + xdonInputs.IsValid() && + xvwapInputs.IsValid() // ; @@ -482,15 +112,17 @@ struct X121Inputs int result = 0; // - // VWAP ... - result = MathMax(result, vwapFastLength); - result = MathMax(result, vwapFastLength); - result = MathMax(result, vwapMidLength); + int xpvMax = xpvInputs.Max(); + int xatrMax = xatrInputs.Max(); + int xstrMax = xstrInputs.Max(); + int xdonMax = xdonInputs.Max(); + int xvwapMax = xvwapInputs.Max(); // - // ATR ... - result = MathMax(result, atrLength); - result = MathMax(result, rsiLength); + result = MathMax(xpvMax, xatrMax); + result = MathMax(result, xstrMax); + result = MathMax(result, xdonMax); + result = MathMax(result, xvwapMax); // return result; @@ -509,22 +141,28 @@ struct X121Conditions // // Buffers ... - double peaksBuffer[]; - double valesBuffer[]; - double sarBuffer[]; double atrUpperBuffer[]; double atrLowerBuffer[]; - double vwapFastBuffer[]; - double vwapMidBuffer[]; - double vwapSlowBuffer[]; + double atrUpperRawBuffer[]; + double atrLowerRawBuffer[]; + double rsiBuffer[]; + double atrBuffer[]; + double strBuffer[]; + double strPriceBuffer[]; + double strUpBuffer[]; + double strDownBuffer[]; + double strStateBuffer[]; double donOpenUpperBuffer[]; double donOpenLowerBuffer[]; - double donCloseUpperBuffer[]; - double donCloseLowerBuffer[]; double donHighUpperBuffer[]; double donHighLowerBuffer[]; double donLowUpperBuffer[]; double donLowLowerBuffer[]; + double donCloseUpperBuffer[]; + double donCloseLowerBuffer[]; + double peaksBuffer[]; + double valesBuffer[]; + double sarBuffer[]; double cHHBuffer[]; double cLLBuffer[]; double sHHBuffer[]; @@ -535,46 +173,77 @@ struct X121Conditions double lLLBuffer[]; double hHHBuffer[]; double hLLBuffer[]; - double atrBuffer[]; - double atrUpperRawBuffer[]; - double atrLowerRawBuffer[]; + double vwapFastBuffer[]; + double vwapMidBuffer[]; + double vwapSlowBuffer[]; double vwapVolumeBuffer[]; double vwapPriceBuffer[]; double vwapFastStateBuffer[]; double vwapMidStateBuffer[]; double vwapSlowStateBuffer[]; - double rsiBuffer[]; // // Conditions ... - // - // XRSI ... - - // bool isRSIOverBought; bool isRSICrossedOverOverBought; bool isRSICrossedUnderOverBought; - - // bool isRSIOverSold; bool isRSICrossedUnderOverSold; bool isRSICrossedOverOverSold; // - // XSAR ... + bool isCloseOverATRUper; + bool isCloseOverATRLower; + bool isCloseUnderATRUpper; + bool isCloseUnderATRLower; + + // + bool isRejectUpATRUpper; + bool isRejectDownATRUpper; + + // + bool isRejectUpATRLower; + bool isRejectDownATRLower; + + // + bool isBreakUpATRUpper; + bool isBreakDownATRUpper; + + // + bool isBreakUpATRLower; + bool isBreakDownATRLower; + + // + bool isRejectDonOpenUpper; + bool isRejectDonHighUpper; + bool isRejectDonLowUpper; + bool isRejectDonCloseUpper; + + // + bool isRejectDonOpenLower; + bool isRejectDonHighLower; + bool isRejectDonLowLower; + bool isRejectDonCloseLower; + + // + bool isBreakDonOpenUpper; + bool isBreakDonHighUpper; + bool isBreakDonLowUpper; + bool isBreakDonCloseUpper; + + // + bool isBreakDonOpenLower; + bool isBreakDonHighLower; + bool isBreakDonLowLower; + bool isBreakDonCloseLower; // bool isSarBullish; bool isSarBearish; - - // bool isSarSwitchedToBullish; bool isSarSwitchedToBearish; - // - // XPV ... - // bool isNewPeak; bool isNewPeakOverLast; @@ -586,55 +255,36 @@ struct X121Conditions bool isNewValeUnderLast; // - // XVWAP ... + bool isStrBullish; + bool isStrBearish; + bool isStrSwitchedToBullish; + bool isStrSwitchedToBearish; // bool isVWapFastBullish; bool isVWapFastBearish; bool isVWapFastNeutural; - - // bool isVWapMidBullish; bool isVWapMidBearish; bool isVWapMidNeutural; - - // bool isVWapSlowBullish; bool isVWapSlowBearish; bool isVWapSlowNeutural; - - // bool isVWapFastOverMid; bool isVWapMidOverSlow; - - // bool isVWapFastUnderMid; bool isVWapMidUnderSlow; - - // bool isVWapBullishState; bool isVWapBearishState; bool isVWapNeuturalState; - - // bool isVWapBullishOrdered; bool isVWapBearishOrdered; - - // bool isVWapSwitchedToBullishOrdered; bool isVWapSwitchedToBearishOrdered; - - // bool isVWapSwitchedToBullishState; bool isVWapSwitchedToBearishState; bool isVWapSwitchedToNeuturalState; - // - // XDON ... - - // - // bool isCloseLower - // // Constructor ... X121Conditions() @@ -660,22 +310,28 @@ struct X121Conditions // Buffers ... // - Clean(peaksBuffer); - Clean(valesBuffer); - Clean(sarBuffer); Clean(atrUpperBuffer); Clean(atrLowerBuffer); - Clean(vwapFastBuffer); - Clean(vwapMidBuffer); - Clean(vwapSlowBuffer); + Clean(atrUpperRawBuffer); + Clean(atrLowerRawBuffer); + Clean(rsiBuffer); + Clean(atrBuffer); + Clean(strBuffer); + Clean(strPriceBuffer); + Clean(strUpBuffer); + Clean(strDownBuffer); + Clean(strStateBuffer); Clean(donOpenUpperBuffer); Clean(donOpenLowerBuffer); - Clean(donCloseUpperBuffer); - Clean(donCloseLowerBuffer); Clean(donHighUpperBuffer); Clean(donHighLowerBuffer); Clean(donLowUpperBuffer); Clean(donLowLowerBuffer); + Clean(donCloseUpperBuffer); + Clean(donCloseLowerBuffer); + Clean(peaksBuffer); + Clean(valesBuffer); + Clean(sarBuffer); Clean(cHHBuffer); Clean(cLLBuffer); Clean(sHHBuffer); @@ -686,33 +342,38 @@ struct X121Conditions Clean(lLLBuffer); Clean(hHHBuffer); Clean(hLLBuffer); - Clean(atrBuffer); - Clean(atrUpperRawBuffer); - Clean(atrLowerRawBuffer); + Clean(vwapFastBuffer); + Clean(vwapMidBuffer); + Clean(vwapSlowBuffer); Clean(vwapVolumeBuffer); Clean(vwapPriceBuffer); Clean(vwapFastStateBuffer); Clean(vwapMidStateBuffer); Clean(vwapSlowStateBuffer); - Clean(rsiBuffer); // - ArraySetAsSeries(peaksBuffer, true); - ArraySetAsSeries(valesBuffer, true); - ArraySetAsSeries(sarBuffer, true); ArraySetAsSeries(atrUpperBuffer, true); ArraySetAsSeries(atrLowerBuffer, true); - ArraySetAsSeries(vwapFastBuffer, true); - ArraySetAsSeries(vwapMidBuffer, true); - ArraySetAsSeries(vwapSlowBuffer, true); + ArraySetAsSeries(atrUpperRawBuffer, true); + ArraySetAsSeries(atrLowerRawBuffer, true); + ArraySetAsSeries(rsiBuffer, true); + ArraySetAsSeries(atrBuffer, true); + ArraySetAsSeries(strBuffer, true); + ArraySetAsSeries(strPriceBuffer, true); + ArraySetAsSeries(strUpBuffer, true); + ArraySetAsSeries(strDownBuffer, true); + ArraySetAsSeries(strStateBuffer, true); ArraySetAsSeries(donOpenUpperBuffer, true); ArraySetAsSeries(donOpenLowerBuffer, true); - ArraySetAsSeries(donCloseUpperBuffer, true); - ArraySetAsSeries(donCloseLowerBuffer, true); ArraySetAsSeries(donHighUpperBuffer, true); ArraySetAsSeries(donHighLowerBuffer, true); ArraySetAsSeries(donLowUpperBuffer, true); ArraySetAsSeries(donLowLowerBuffer, true); + ArraySetAsSeries(donCloseUpperBuffer, true); + ArraySetAsSeries(donCloseLowerBuffer, true); + ArraySetAsSeries(peaksBuffer, true); + ArraySetAsSeries(valesBuffer, true); + ArraySetAsSeries(sarBuffer, true); ArraySetAsSeries(cHHBuffer, true); ArraySetAsSeries(cLLBuffer, true); ArraySetAsSeries(sHHBuffer, true); @@ -723,34 +384,75 @@ struct X121Conditions ArraySetAsSeries(lLLBuffer, true); ArraySetAsSeries(hHHBuffer, true); ArraySetAsSeries(hLLBuffer, true); - ArraySetAsSeries(atrBuffer, true); - ArraySetAsSeries(atrUpperRawBuffer, true); - ArraySetAsSeries(atrLowerRawBuffer, true); + ArraySetAsSeries(vwapFastBuffer, true); + ArraySetAsSeries(vwapMidBuffer, true); + ArraySetAsSeries(vwapSlowBuffer, true); ArraySetAsSeries(vwapVolumeBuffer, true); ArraySetAsSeries(vwapPriceBuffer, true); ArraySetAsSeries(vwapFastStateBuffer, true); ArraySetAsSeries(vwapMidStateBuffer, true); ArraySetAsSeries(vwapSlowStateBuffer, true); - ArraySetAsSeries(rsiBuffer, true); // // Conditions ... - // - // XRSI ... - // isRSIOverBought = false; - isRSICrossedUnderOverBought = false; isRSICrossedOverOverBought = false; + isRSICrossedUnderOverBought = false; // isRSIOverSold = false; - isRSICrossedOverOverSold = false; isRSICrossedUnderOverSold = false; + isRSICrossedOverOverSold = false; // - // XSAR ... + isCloseOverATRUper = false; + isCloseOverATRLower = false; + + // + isCloseUnderATRUpper = false; + isCloseUnderATRLower = false; + + // + isRejectUpATRUpper = false; + isRejectDownATRUpper = false; + + // + isRejectUpATRLower = false; + isRejectDownATRLower = false; + + // + isBreakUpATRUpper = false; + isBreakDownATRUpper = false; + + // + isBreakUpATRLower = false; + isBreakDownATRLower = false; + + // + isRejectDonOpenUpper = false; + isRejectDonHighUpper = false; + isRejectDonLowUpper = false; + isRejectDonCloseUpper = false; + + // + isRejectDonOpenLower = false; + isRejectDonHighLower = false; + isRejectDonLowLower = false; + isRejectDonCloseLower = false; + + // + isBreakDonOpenUpper = false; + isBreakDonHighUpper = false; + isBreakDonLowUpper = false; + isBreakDonCloseUpper = false; + + // + isBreakDonOpenLower = false; + isBreakDonHighLower = false; + isBreakDonLowLower = false; + isBreakDonCloseLower = false; // isSarBullish = false; @@ -760,9 +462,6 @@ struct X121Conditions isSarSwitchedToBullish = false; isSarSwitchedToBearish = false; - // - // XPV ... - // isNewPeak = false; isNewPeakOverLast = false; @@ -774,51 +473,37 @@ struct X121Conditions isNewValeUnderLast = false; // - // XVWAP ... + isStrBullish = false; + isStrBearish = false; + + // + isStrSwitchedToBullish = false; + isStrSwitchedToBearish = false; // isVWapFastBullish = false; isVWapFastBearish = false; isVWapFastNeutural = false; - - // isVWapMidBullish = false; isVWapMidBearish = false; isVWapMidNeutural = false; - - // isVWapSlowBullish = false; isVWapSlowBearish = false; isVWapSlowNeutural = false; - - // isVWapFastOverMid = false; isVWapMidOverSlow = false; - - // isVWapFastUnderMid = false; isVWapMidUnderSlow = false; - - // isVWapBullishState = false; isVWapBearishState = false; isVWapNeuturalState = false; - - // isVWapBullishOrdered = false; isVWapBearishOrdered = false; - - // isVWapSwitchedToBullishOrdered = false; isVWapSwitchedToBearishOrdered = false; - - // isVWapSwitchedToBullishState = false; isVWapSwitchedToBearishState = false; isVWapSwitchedToNeuturalState = false; - - // - // XDON ... } /** @@ -835,9 +520,6 @@ struct X121Conditions // bullishScore = 0; bearishScore = 0; - - // - // TODO: Implement if Required ... } /** @@ -889,32 +571,56 @@ struct X121Conditions ); // - // TODO: Implement this if required ... string conditionsStr = // - // XSAR ... - ToString("isSarBullish", isSarBullish, ignoreFalseConditions, separator) + - ToString("isSarBearish", isSarBearish, ignoreFalseConditions, separator) + - ToString("isSarSwitchedToBullish", isSarSwitchedToBullish, ignoreFalseConditions, separator) + - ToString("isSarSwitchedToBearish", isSarSwitchedToBearish, ignoreFalseConditions, separator) + - // - // XPV ... - ToString("isNewPeak", isNewPeak, ignoreFalseConditions, separator) + - ToString("isNewPeakOverLast", isNewPeakOverLast, ignoreFalseConditions, separator) + - ToString("isNewPeakUnderLast", isNewPeakUnderLast, ignoreFalseConditions, separator) + - ToString("isNewVale", isNewVale, ignoreFalseConditions, separator) + - ToString("isNewValeOverLast", isNewValeOverLast, ignoreFalseConditions, separator) + - ToString("isNewValeUnderLast", isNewValeUnderLast, ignoreFalseConditions, separator) + - // - // RSI ... ToString("isRSIOverBought", isRSIOverBought, ignoreFalseConditions, separator) + ToString("isRSICrossedOverOverBought", isRSICrossedOverOverBought, ignoreFalseConditions, separator) + ToString("isRSICrossedUnderOverBought", isRSICrossedUnderOverBought, ignoreFalseConditions, separator) + ToString("isRSIOverSold", isRSIOverSold, ignoreFalseConditions, separator) + ToString("isRSICrossedUnderOverSold", isRSICrossedUnderOverSold, ignoreFalseConditions, separator) + ToString("isRSICrossedOverOverSold", isRSICrossedOverOverSold, ignoreFalseConditions, separator) + - // - // XVWAP ... + ToString("isCloseOverATRUper", isCloseOverATRUper, ignoreFalseConditions, separator) + + ToString("isCloseOverATRLower", isCloseOverATRLower, ignoreFalseConditions, separator) + + ToString("isCloseUnderATRUpper", isCloseUnderATRUpper, ignoreFalseConditions, separator) + + ToString("isCloseUnderATRLower", isCloseUnderATRLower, ignoreFalseConditions, separator) + + ToString("isRejectUpATRUpper", isRejectUpATRUpper, ignoreFalseConditions, separator) + + ToString("isRejectDownATRUpper", isRejectDownATRUpper, ignoreFalseConditions, separator) + + ToString("isRejectUpATRLower", isRejectUpATRLower, ignoreFalseConditions, separator) + + ToString("isRejectDownATRLower", isRejectDownATRLower, ignoreFalseConditions, separator) + + ToString("isBreakUpATRUpper", isBreakUpATRUpper, ignoreFalseConditions, separator) + + ToString("isBreakDownATRUpper", isBreakDownATRUpper, ignoreFalseConditions, separator) + + ToString("isBreakUpATRLower", isBreakUpATRLower, ignoreFalseConditions, separator) + + ToString("isBreakDownATRLower", isBreakDownATRLower, ignoreFalseConditions, separator) + + ToString("isRejectDonOpenUpper", isRejectDonOpenUpper, ignoreFalseConditions, separator) + + ToString("isRejectDonHighUpper", isRejectDonHighUpper, ignoreFalseConditions, separator) + + ToString("isRejectDonLowUpper", isRejectDonLowUpper, ignoreFalseConditions, separator) + + ToString("isRejectDonCloseUpper", isRejectDonCloseUpper, ignoreFalseConditions, separator) + + ToString("isRejectDonOpenLower", isRejectDonOpenLower, ignoreFalseConditions, separator) + + ToString("isRejectDonHighLower", isRejectDonHighLower, ignoreFalseConditions, separator) + + ToString("isRejectDonLowLower", isRejectDonLowLower, ignoreFalseConditions, separator) + + ToString("isRejectDonCloseLower", isRejectDonCloseLower, ignoreFalseConditions, separator) + + ToString("isBreakDonOpenUpper", isBreakDonOpenUpper, ignoreFalseConditions, separator) + + ToString("isBreakDonHighUpper", isBreakDonHighUpper, ignoreFalseConditions, separator) + + ToString("isBreakDonLowUpper", isBreakDonLowUpper, ignoreFalseConditions, separator) + + ToString("isBreakDonCloseUpper", isBreakDonCloseUpper, ignoreFalseConditions, separator) + + ToString("isBreakDonOpenLower", isBreakDonOpenLower, ignoreFalseConditions, separator) + + ToString("isBreakDonHighLower", isBreakDonHighLower, ignoreFalseConditions, separator) + + ToString("isBreakDonLowLower", isBreakDonLowLower, ignoreFalseConditions, separator) + + ToString("isBreakDonCloseLower", isBreakDonCloseLower, ignoreFalseConditions, separator) + + ToString("isSarBullish", isSarBullish, ignoreFalseConditions, separator) + + ToString("isSarBearish", isSarBearish, ignoreFalseConditions, separator) + + ToString("isSarSwitchedToBullish", isSarSwitchedToBullish, ignoreFalseConditions, separator) + + ToString("isSarSwitchedToBearish", isSarSwitchedToBearish, ignoreFalseConditions, separator) + + ToString("isNewPeak", isNewPeak, ignoreFalseConditions, separator) + + ToString("isNewPeakOverLast", isNewPeakOverLast, ignoreFalseConditions, separator) + + ToString("isNewPeakUnderLast", isNewPeakUnderLast, ignoreFalseConditions, separator) + + ToString("isNewVale", isNewVale, ignoreFalseConditions, separator) + + ToString("isNewValeOverLast", isNewValeOverLast, ignoreFalseConditions, separator) + + ToString("isNewValeUnderLast", isNewValeUnderLast, ignoreFalseConditions, separator) + + ToString("isStrBullish", isStrBullish, ignoreFalseConditions, separator) + + ToString("isStrBearish", isStrBearish, ignoreFalseConditions, separator) + + ToString("isStrSwitchedToBullish", isStrSwitchedToBullish, ignoreFalseConditions, separator) + + ToString("isStrSwitchedToBearish", isStrSwitchedToBearish, ignoreFalseConditions, separator) + ToString("isVWapFastBullish", isVWapFastBullish, ignoreFalseConditions, separator) + ToString("isVWapFastBearish", isVWapFastBearish, ignoreFalseConditions, separator) + ToString("isVWapFastNeutural", isVWapFastNeutural, ignoreFalseConditions, separator) + @@ -980,17 +686,23 @@ struct X121Conditions // // Implementation ... - -class XCX121Helper : public XCBaseHelper +class XCX121Helper : public XCBase { // public: // + // + // Helpers ... + XCX121XPVHelper *xpvHelper; + XCX121XATRHelper *xatrHelper; + XCX121XSTRHelper *xstrHelper; + XCX121XDONHelper *xdonHelper; + XCX121XVWAPHelper *xvwapHelper; + // // Constructors ... XCX121Helper() - : XCBaseHelper(_Symbol, _Period) { } @@ -998,6 +710,24 @@ class XCX121Helper : public XCBaseHelper // Deconstructor ... ~XCX121Helper() { + // + delete xpvHelper; + delete xatrHelper; + delete xstrHelper; + delete xdonHelper; + delete xvwapHelper; + } + + // + string GetSymbol() + { + return mSymbol; + } + + // + ENUM_TIMEFRAMES GetPeriod() + { + return mPeriod; } // @@ -1021,161 +751,94 @@ class XCX121Helper : public XCBaseHelper // bool result = false; + // + result = + IsValid(symbol) && + IsValid(period) && + inputs.IsValid(); + if (!result) + { + return result; + } + // mSymbol = symbol; mPeriod = period; // - // Validate Inputs ... - result = inputs.IsValid(); - if (!result) - { - return result; - } + // Setting Inputs ... // mInputs = inputs; + xpvInputs = inputs.xpvInputs; + xatrInputs = inputs.xatrInputs; + xstrInputs = inputs.xstrInputs; + xdonInputs = inputs.xdonInputs; + xvwapInputs = inputs.xvwapInputs; // - // Setting Arrays As Series ... - ArraySetAsSeries(peaksBuffer, true); - ArraySetAsSeries(valesBuffer, true); - ArraySetAsSeries(sarBuffer, true); - ArraySetAsSeries(atrUpperBuffer, true); - ArraySetAsSeries(atrLowerBuffer, true); - ArraySetAsSeries(vwapFastBuffer, true); - ArraySetAsSeries(vwapMidBuffer, true); - ArraySetAsSeries(vwapSlowBuffer, true); - ArraySetAsSeries(donOpenUpperBuffer, true); - ArraySetAsSeries(donOpenLowerBuffer, true); - ArraySetAsSeries(donCloseUpperBuffer, true); - ArraySetAsSeries(donCloseLowerBuffer, true); - ArraySetAsSeries(donHighUpperBuffer, true); - ArraySetAsSeries(donHighLowerBuffer, true); - ArraySetAsSeries(donLowUpperBuffer, true); - ArraySetAsSeries(donLowLowerBuffer, true); - ArraySetAsSeries(cHHBuffer, true); - ArraySetAsSeries(cLLBuffer, true); - ArraySetAsSeries(sHHBuffer, true); - ArraySetAsSeries(sLLBuffer, true); - ArraySetAsSeries(mHHBuffer, true); - ArraySetAsSeries(mLLBuffer, true); - ArraySetAsSeries(lHHBuffer, true); - ArraySetAsSeries(lLLBuffer, true); - ArraySetAsSeries(hHHBuffer, true); - ArraySetAsSeries(hLLBuffer, true); - ArraySetAsSeries(atrBuffer, true); - ArraySetAsSeries(atrUpperRawBuffer, true); - ArraySetAsSeries(atrLowerRawBuffer, true); - ArraySetAsSeries(vwapVolumeBuffer, true); - ArraySetAsSeries(vwapPriceBuffer, true); - ArraySetAsSeries(vwapFastStateBuffer, true); - ArraySetAsSeries(vwapMidStateBuffer, true); - ArraySetAsSeries(vwapSlowStateBuffer, true); - ArraySetAsSeries(rsiBuffer, true); + // Initial Helpers ... // - mHandler = iCustom( - mSymbol, - mPeriod, - "x-saherelm.x121", - // - // Inputs ... - // - // Cycles ... - "", - // - // Short ... - "", - mInputs.scMethod, - mInputs.scPeriod, - // - // Medium ... - "", - mInputs.mcMethod, - mInputs.mcPeriod, - // - // Long ... - "", - mInputs.lcMethod, - mInputs.lcPeriod, - // - // Hind ... - "", - mInputs.hcMethod, - mInputs.hcPeriod, - // - // Boundary Detection ... - "", - mInputs.hhMode, - mInputs.llMode, - // - // Rsi Detection ... - "", - mInputs.rsiLength, - mInputs.rsiAppliedTo, - // - // Parabolic Sar Detection ... - "", - mInputs.sarStep, - mInputs.sarMax, - // - // Atr Detection ... - "", - mInputs.atrLength, - mInputs.atrMultiplier, - mInputs.atrUpperAppliedTo, - mInputs.atrLowerAppliedTo, - mInputs.atrSmoothingMode, - // - // VWap Detection ... - "", - mInputs.vwapFastLength, - mInputs.vwapMidLength, - mInputs.vwapSlowLength, - mInputs.vwapAppliedTo, - // - // Donchain Detection ... - "", - mInputs.donchainLength, - // - // Presentation ... - "", - mInputs.startCalculationForLastBars, - mInputs.sarArrowCode, - mInputs.peaksArrowCode, - mInputs.valesArrowCode, - // - // Commons ... - mInputs.showSar, - mInputs.showAtr, - mInputs.showPeaks, - mInputs.showVales, - mInputs.showVWap, - mInputs.showDonchain, - // - // Atr Presentation ... - "", - mInputs.showAtrUpper, - mInputs.showAtrLower, - // - // VWap Presentation ... - "", - mInputs.showVWapFast, - mInputs.showVWapMedium, - mInputs.showVWapSlow, - // - // Donchain Presentation ... - "", - mInputs.showUpper, - mInputs.showLower, - mInputs.showOpen, - mInputs.showHigh, - mInputs.showClose, - mInputs.showLow - // + // XPV ... + xpvHelper = new XCX121XPVHelper(); + result = xpvHelper.Init( + symbol, + period, + xpvInputs // + ); + if (!result) + { + return result; + } + + // + // XATR ... + xatrHelper = new XCX121XATRHelper(); + result = xatrHelper.Init( + symbol, + period, + xatrInputs // + ); + if (!result) + { + return result; + } + + // + // XSTR ... + xstrHelper = new XCX121XSTRHelper(); + result = xstrHelper.Init( + symbol, + period, + xstrInputs // + ); + if (!result) + { + return result; + } + + // + // XDON ... + xdonHelper = new XCX121XDONHelper(); + result = xdonHelper.Init( + symbol, + period, + xdonInputs // + ); + if (!result) + { + return result; + } + + // + // XVWAP ... + xvwapHelper = new XCX121XVWAPHelper(); + result = xvwapHelper.Init( + symbol, + period, + xvwapInputs // ); - result = mHandler != INVALID_HANDLE; if (!result) { return result; @@ -1185,1941 +848,70 @@ class XCX121Helper : public XCBaseHelper return result; } - /** - * Retrieve Current Indicator Configs ... - * - * @return ( Inputs ) - */ - X121Inputs GetInputs() - { - return mInputs; - } + // + // Conditions Readers ... - /** - * Set New Indicator Inputs ... - * - * @param inputs: X121Inputs instance, Indicator Inputs ... - * - * @return ( bool ) - */ - bool SetInputs( - X121Inputs &inputs // Configs + // + // XPV ... + bool GetPVConditions( + X121XPVConditions &conditions, // + int barIndex = 0, // + int loopback = 5 // ) - { - // - return Init( - mSymbol, - mPeriod, - inputs - // - ); - } - - // - // Implement Value Getters ... - - // - // XRSI ... - - // - double GetRSI( - int barIndex // Bar Index - ) - { - // - if (barIndex < 0) - { - barIndex = 0; - } - - // - Calculate(); - - // - int count = ArraySize(rsiBuffer); - if (barIndex >= count) - { - barIndex = count - 1; - } - - // - return rsiBuffer[barIndex]; - } - - // - int CopyRSI( - int start, // Start - int count, // Number of Items for read - double &buffer[], // Dest Buffer - bool forceClean = true // Force To Clean buffer - ) - { - // - // Update Calculations ... - Calculate(); - - // - // Copy Items ... - return Copy( - start, - count, - rsiBuffer, - buffer, - forceClean - // - ); - } - - // - // SAR ... - - // - double GetSar( - int barIndex // Bar Index - ) - { - // - if (barIndex < 0) - { - barIndex = 0; - } - - // - Calculate(); - - // - int count = ArraySize(sarBuffer); - if (barIndex >= count) - { - barIndex = count - 1; - } - - // - return sarBuffer[barIndex]; - } - - // - int CopySar( - int start, // Start - int count, // Number of Items for read - double &buffer[], // Dest Buffer - bool forceClean = true // Force To Clean buffer - ) - { - // - // Update Calculations ... - Calculate(); - - // - // Copy Items ... - return Copy( - start, - count, - sarBuffer, - buffer, - forceClean - // - ); - } - - // - // ATR ... - - // - // Common ... - - // - double GetAtr( - int barIndex // Bar Index - ) - { - // - if (barIndex < 0) - { - barIndex = 0; - } - - // - Calculate(); - - // - int count = ArraySize(atrBuffer); - if (barIndex >= count) - { - barIndex = count - 1; - } - - // - return atrBuffer[barIndex]; - } - - // - int CopyAtr( - int start, // Start - int count, // Number of Items for read - double &buffer[], // Dest Buffer - bool forceClean = true // Force To Clean buffer - ) - { - // - // Update Calculations ... - Calculate(); - - // - // Copy Items ... - return Copy( - start, - count, - atrBuffer, - buffer, - forceClean - // - ); - } - - // - double GetAtrUpper( - int barIndex // Bar Index - ) - { - // - if (barIndex < 0) - { - barIndex = 0; - } - - // - Calculate(); - - // - int count = ArraySize(atrUpperBuffer); - if (barIndex >= count) - { - barIndex = count - 1; - } - - // - return atrUpperBuffer[barIndex]; - } - - // - int CopyAtrUpper( - int start, // Start - int count, // Number of Items for read - double &buffer[], // Dest Buffer - bool forceClean = true // Force To Clean buffer - ) - { - // - // Update Calculations ... - Calculate(); - - // - // Copy Items ... - return Copy( - start, - count, - atrUpperBuffer, - buffer, - forceClean - // - ); - } - - // - double GetAtrUpperRaw( - int barIndex // Bar Index - ) - { - // - if (barIndex < 0) - { - barIndex = 0; - } - - // - Calculate(); - - // - int count = ArraySize(atrUpperRawBuffer); - if (barIndex >= count) - { - barIndex = count - 1; - } - - // - return atrUpperRawBuffer[barIndex]; - } - - // - int CopyAtrUpperRaw( - int start, // Start - int count, // Number of Items for read - double &buffer[], // Dest Buffer - bool forceClean = true // Force To Clean buffer - ) - { - // - // Update Calculations ... - Calculate(); - - // - // Copy Items ... - return Copy( - start, - count, - atrUpperRawBuffer, - buffer, - forceClean - // - ); - } - - // - double GetAtrLower( - int barIndex // Bar Index - ) - { - // - if (barIndex < 0) - { - barIndex = 0; - } - - // - Calculate(); - - // - int count = ArraySize(atrLowerBuffer); - if (barIndex >= count) - { - barIndex = count - 1; - } - - // - return atrLowerBuffer[barIndex]; - } - - // - int CopyAtrLower( - int start, // Start - int count, // Number of Items for read - double &buffer[], // Dest Buffer - bool forceClean = true // Force To Clean buffer - ) - { - // - // Update Calculations ... - Calculate(); - - // - // Copy Items ... - return Copy( - start, - count, - atrLowerBuffer, - buffer, - forceClean - // - ); - } - - // - double GetAtrLowerRaw( - int barIndex // Bar Index - ) - { - // - if (barIndex < 0) - { - barIndex = 0; - } - - // - Calculate(); - - // - int count = ArraySize(atrLowerRawBuffer); - if (barIndex >= count) - { - barIndex = count - 1; - } - - // - return atrLowerRawBuffer[barIndex]; - } - - // - int CopyAtrLowerRaw( - int start, // Start - int count, // Number of Items for read - double &buffer[], // Dest Buffer - bool forceClean = true // Force To Clean buffer - ) - { - // - // Update Calculations ... - Calculate(); - - // - // Copy Items ... - return Copy( - start, - count, - atrLowerRawBuffer, - buffer, - forceClean - // - ); - } - - // - // PV ... - - // - // PEAKS ... - - // - double GetPeak( - int barIndex // Bar Index - ) - { - // - if (barIndex < 0) - { - barIndex = 0; - } - - // - Calculate(); - - // - int count = ArraySize(peaksBuffer); - if (barIndex >= count) - { - barIndex = count - 1; - } - - // - return peaksBuffer[barIndex]; - } - - // - int CopyPeak( - int start, // Start - int count, // Number of Items for read - double &buffer[], // Dest Buffer - bool forceClean = true // Force To Clean buffer - ) - { - // - // Update Calculations ... - Calculate(); - - // - // Copy Items ... - return Copy( - start, - count, - peaksBuffer, - buffer, - forceClean - // - ); - } - - // - // VALES ... - - // - double GetVale( - int barIndex // Bar Index - ) - { - // - if (barIndex < 0) - { - barIndex = 0; - } - - // - Calculate(); - - // - int count = ArraySize(valesBuffer); - if (barIndex >= count) - { - barIndex = count - 1; - } - - // - return valesBuffer[barIndex]; - } - - // - int CopyVale( - int start, // Start - int count, // Number of Items for read - double &buffer[], // Dest Buffer - bool forceClean = true // Force To Clean buffer - ) - { - // - // Update Calculations ... - Calculate(); - - // - // Copy Items ... - return Copy( - start, - count, - valesBuffer, - buffer, - forceClean - // - ); - } - - // - // - // - - // - double GetHigherPeak( - double peak, // Peak Source - int barIndex = 0, // Bar Index - int loopback = 576 // Max Allowed Loopback - ) - { - // - double result = 0; - - // - if (barIndex < 0) - { - barIndex = 0; - } - - // - if (loopback < 576) - { - loopback = 576; - } - - // - if (peak <= 0) - { - return result; - } - - // - double iValue = 0; - int index = barIndex; - bool canContinue = true; - while (canContinue) - { - // - iValue = GetPeak(index); - if (iValue > peak) - { - // - result = iValue; - break; - } - - // - canContinue = index < barIndex + loopback; - index++; - } - - // - return result; - } - - // - double GetLowerPeak( - double peak, // Peak Source - int barIndex = 0, // Bar Index - int loopback = 576 // Max Allowed Loopback - ) - { - // - double result = 0; - - // - if (barIndex < 0) - { - barIndex = 0; - } - - // - if (loopback < 576) - { - loopback = 576; - } - - // - if (peak <= 0) - { - return result; - } - - // - double iValue = 0; - int index = barIndex; - bool canContinue = true; - while (canContinue) - { - // - iValue = GetPeak(index); - if (iValue < peak) - { - // - result = iValue; - break; - } - - // - canContinue = index < barIndex + loopback; - index++; - } - - // - return result; - } - - // - double GetHigherVale( - double vale, // Vale Source - int barIndex = 0, // Bar Index - int loopback = 576 // Max Allowed Loopback - ) - { - // - double result = 0; - - // - if (barIndex < 0) - { - barIndex = 0; - } - - // - if (loopback < 576) - { - loopback = 576; - } - - // - if (vale <= 0) - { - return result; - } - - // - double iValue = 0; - int index = barIndex; - bool canContinue = true; - while (canContinue) - { - // - iValue = GetVale(index); - if (iValue > vale) - { - // - result = iValue; - break; - } - - // - canContinue = index < barIndex + loopback; - index++; - } - - // - return result; - } - - // - double GetLowerVale( - double vale, // Vale Source - int barIndex = 0, // Bar Index - int loopback = 576 // Max Allowed Loopback - ) - { - // - double result = 0; - - // - if (barIndex < 0) - { - barIndex = 0; - } - - // - if (loopback < 576) - { - loopback = 576; - } - - // - if (vale <= 0) - { - return result; - } - - // - double iValue = 0; - int index = barIndex; - bool canContinue = true; - while (canContinue) - { - // - iValue = GetVale(index); - if (iValue < vale) - { - // - result = iValue; - break; - } - - // - canContinue = index < barIndex + loopback; - index++; - } - - // - return result; - } - - // - // - // - - // - double GetLowestPeak( - int barIndex, - int &index, - double &vale, - int loopback = 576 // - ) - { - // - double result = 0; - - // - index = -1; - vale = 0; - - // - if (barIndex < 0) - { - barIndex = 0; - } - - // - if (loopback < 576) - { - loopback = 576; - } - - // - Calculate(); - - // - for (int i = 0; i < barIndex + loopback; i++) - { - // - double iPeak = GetPeak(i); - if (iPeak == 0) - { - break; - } - - // - if (iPeak > 0 && (result == 0 || - result >= iPeak)) - { - // - index = i; - result = iPeak; - vale = GetVale(index); - } - } - - // - return result; - } - - // - double GetHighestPeak( - int barIndex, - int &index, - double &vale, - int loopback = 576 // - ) - { - // - double result = 0; - - // - index = -1; - vale = 0; - - // - if (barIndex < 0) - { - barIndex = 0; - } - - // - if (loopback < 576) - { - loopback = 576; - } - - // - Calculate(); - - // - for (int i = 0; i < barIndex + loopback; i++) - { - // - double iPeak = GetPeak(i); - if (iPeak == 0) - { - break; - } - - // - if (iPeak > 0 && (result == 0 || - result <= iPeak)) - { - // - index = i; - result = iPeak; - vale = GetVale(index); - } - } - - // - return result; - } - - // - double GetLowestVale( - int barIndex, - int &index, - double &peak, - int loopback = 576 // - ) - { - // - double result = 0; - - // - index = -1; - peak = 0; - - // - if (barIndex < 0) - { - barIndex = 0; - } - - // - if (loopback < 576) - { - loopback = 576; - } - - // - Calculate(); - - // - for (int i = 0; i < barIndex + loopback; i++) - { - // - double iPeak = GetVale(i); - if (iPeak == 0) - { - break; - } - - // - if (iPeak > 0 && (result == 0 || - result >= iPeak)) - { - // - index = i; - result = iPeak; - peak = GetPeak(index); - } - } - - // - return result; - } - - // - double GetHighestVale( - int barIndex, - int &index, - double &peak, - int loopback = 576 // - ) - { - // - double result = 0; - - // - index = -1; - peak = 0; - - // - if (barIndex < 0) - { - barIndex = 0; - } - - // - if (loopback < 576) - { - loopback = 576; - } - - // - Calculate(); - - // - for (int i = 0; i < barIndex + loopback; i++) - { - // - double iPeak = GetVale(i); - if (iPeak == 0) - { - break; - } - - // - if (iPeak > 0 && (result == 0 || - result <= iPeak)) - { - // - index = i; - result = iPeak; - peak = GetPeak(index); - } - } - - // - return result; - } - - // - // CURRENT ... - - // - // HH ... - - // - double GetCHH( - int barIndex // Bar Index - ) - { - // - if (barIndex < 0) - { - barIndex = 0; - } - - // - Calculate(); - - // - int count = ArraySize(cHHBuffer); - if (barIndex >= count) - { - barIndex = count - 1; - } - - // - return cHHBuffer[barIndex]; - } - - // - int CopyCHH( - int start, // Start - int count, // Number of Items for read - double &buffer[], // Dest Buffer - bool forceClean = true // Force To Clean buffer - ) - { - // - // Update Calculations ... - Calculate(); - - // - // Copy Items ... - return Copy( - start, - count, - cHHBuffer, - buffer, - forceClean - // - ); - } - - // - // LL ... - - // - double GetCLL( - int barIndex // Bar Index - ) - { - // - if (barIndex < 0) - { - barIndex = 0; - } - - // - Calculate(); - - // - int count = ArraySize(cLLBuffer); - if (barIndex >= count) - { - barIndex = count - 1; - } - - // - return cLLBuffer[barIndex]; - } - - // - int CopyCLL( - int start, // Start - int count, // Number of Items for read - double &buffer[], // Dest Buffer - bool forceClean = true // Force To Clean buffer - ) - { - // - // Update Calculations ... - Calculate(); - - // - // Copy Items ... - return Copy( - start, - count, - cLLBuffer, - buffer, - forceClean - // - ); - } - - // - // SHORT ... - - // - // HH ... - - // - double GetSHH( - int barIndex // Bar Index - ) - { - // - if (barIndex < 0) - { - barIndex = 0; - } - - // - Calculate(); - - // - int count = ArraySize(sHHBuffer); - if (barIndex >= count) - { - barIndex = count - 1; - } - - // - return sHHBuffer[barIndex]; - } - - // - int CopySHH( - int start, // Start - int count, // Number of Items for read - double &buffer[], // Dest Buffer - bool forceClean = true // Force To Clean buffer - ) - { - // - // Update Calculations ... - Calculate(); - - // - // Copy Items ... - return Copy( - start, - count, - sHHBuffer, - buffer, - forceClean - // - ); - } - - // - // LL ... - - // - double GetSLL( - int barIndex // Bar Index - ) - { - // - if (barIndex < 0) - { - barIndex = 0; - } - - // - Calculate(); - - // - int count = ArraySize(sLLBuffer); - if (barIndex >= count) - { - barIndex = count - 1; - } - - // - return sLLBuffer[barIndex]; - } - - // - int CopySLL( - int start, // Start - int count, // Number of Items for read - double &buffer[], // Dest Buffer - bool forceClean = true // Force To Clean buffer - ) - { - // - // Update Calculations ... - Calculate(); - - // - // Copy Items ... - return Copy( - start, - count, - sLLBuffer, - buffer, - forceClean - // - ); - } - - // - // MEDIUM ... - - // - // HH ... - - // - double GetMHH( - int barIndex // Bar Index - ) - { - // - if (barIndex < 0) - { - barIndex = 0; - } - - // - Calculate(); - - // - int count = ArraySize(mHHBuffer); - if (barIndex >= count) - { - barIndex = count - 1; - } - - // - return mHHBuffer[barIndex]; - } - - // - int CopyMHH( - int start, // Start - int count, // Number of Items for read - double &buffer[], // Dest Buffer - bool forceClean = true // Force To Clean buffer - ) - { - // - // Update Calculations ... - Calculate(); - - // - // Copy Items ... - return Copy( - start, - count, - mHHBuffer, - buffer, - forceClean - // - ); - } - - // - // LL ... - - // - double GetMLL( - int barIndex // Bar Index - ) - { - // - if (barIndex < 0) - { - barIndex = 0; - } - - // - Calculate(); - - // - int count = ArraySize(mLLBuffer); - if (barIndex >= count) - { - barIndex = count - 1; - } - - // - return mLLBuffer[barIndex]; - } - - // - int CopyMLL( - int start, // Start - int count, // Number of Items for read - double &buffer[], // Dest Buffer - bool forceClean = true // Force To Clean buffer - ) - { - // - // Update Calculations ... - Calculate(); - - // - // Copy Items ... - return Copy( - start, - count, - mLLBuffer, - buffer, - forceClean - // - ); - } - - // - // LONG ... - - // - // HH ... - - // - double GetLHH( - int barIndex // Bar Index - ) - { - // - if (barIndex < 0) - { - barIndex = 0; - } - - // - Calculate(); - - // - int count = ArraySize(lHHBuffer); - if (barIndex >= count) - { - barIndex = count - 1; - } - - // - return lHHBuffer[barIndex]; - } - - // - int CopyLHH( - int start, // Start - int count, // Number of Items for read - double &buffer[], // Dest Buffer - bool forceClean = true // Force To Clean buffer - ) - { - // - // Update Calculations ... - Calculate(); - - // - // Copy Items ... - return Copy( - start, - count, - lHHBuffer, - buffer, - forceClean - // - ); - } - - // - // LL ... - - // - double GetLLL( - int barIndex // Bar Index - ) - { - // - if (barIndex < 0) - { - barIndex = 0; - } - - // - Calculate(); - - // - int count = ArraySize(lLLBuffer); - if (barIndex >= count) - { - barIndex = count - 1; - } - - // - return lLLBuffer[barIndex]; - } - - // - int CopyLLL( - int start, // Start - int count, // Number of Items for read - double &buffer[], // Dest Buffer - bool forceClean = true // Force To Clean buffer - ) - { - // - // Update Calculations ... - Calculate(); - - // - // Copy Items ... - return Copy( - start, - count, - lLLBuffer, - buffer, - forceClean - // - ); - } - - // - // HIND ... - - // - // HH ... - - // - double GetHHH( - int barIndex // Bar Index - ) - { - // - if (barIndex < 0) - { - barIndex = 0; - } - - // - Calculate(); - - // - int count = ArraySize(hHHBuffer); - if (barIndex >= count) - { - barIndex = count - 1; - } - - // - return hHHBuffer[barIndex]; - } - - // - int CopyHHH( - int start, // Start - int count, // Number of Items for read - double &buffer[], // Dest Buffer - bool forceClean = true // Force To Clean buffer - ) - { - // - // Update Calculations ... - Calculate(); - - // - // Copy Items ... - return Copy( - start, - count, - hHHBuffer, - buffer, - forceClean - // - ); - } - - // - // LL ... - - // - double GetHLL( - int barIndex // Bar Index - ) - { - // - if (barIndex < 0) - { - barIndex = 0; - } - - // - Calculate(); - - // - int count = ArraySize(hLLBuffer); - if (barIndex >= count) - { - barIndex = count - 1; - } - - // - return hLLBuffer[barIndex]; - } - - // - int CopyHLL( - int start, // Start - int count, // Number of Items for read - double &buffer[], // Dest Buffer - bool forceClean = true // Force To Clean buffer - ) - { - // - // Update Calculations ... - Calculate(); - - // - // Copy Items ... - return Copy( - start, - count, - hLLBuffer, - buffer, - forceClean - // - ); - } - - // - // VWAP ... - - // - // FAST ... - - // - double GetVWapFast( - int barIndex // Bar Index - ) - { - // - if (barIndex < 0) - { - barIndex = 0; - } - - // - Calculate(); - - // - int count = ArraySize(vwapFastBuffer); - if (barIndex >= count) - { - barIndex = count - 1; - } - - // - return vwapFastBuffer[barIndex]; - } - - // - int CopyVWapFast( - int start, // Start - int count, // Number of Items for read - double &buffer[], // Dest Buffer - bool forceClean = true // Force To Clean buffer - ) - { - // - // Update Calculations ... - Calculate(); - - // - // Copy Items ... - return Copy( - start, - count, - vwapFastBuffer, - buffer, - forceClean - // - ); - } - - // - // STATE FAST ... - - // - double GetVWapFastState( - int barIndex // Bar Index - ) - { - // - if (barIndex < 0) - { - barIndex = 0; - } - - // - Calculate(); - - // - int count = ArraySize(vwapFastStateBuffer); - if (barIndex >= count) - { - barIndex = count - 1; - } - - // - return vwapFastStateBuffer[barIndex]; - } - - // - int CopyVWapFastState( - int start, // Start - int count, // Number of Items for read - double &buffer[], // Dest Buffer - bool forceClean = true // Force To Clean buffer - ) - { - // - // Update Calculations ... - Calculate(); - - // - // Copy Items ... - return Copy( - start, - count, - vwapFastStateBuffer, - buffer, - forceClean - // - ); - } - - // - // MID ... - - // - double GetVWapMid( - int barIndex // Bar Index - ) - { - // - if (barIndex < 0) - { - barIndex = 0; - } - - // - Calculate(); - - // - int count = ArraySize(vwapMidBuffer); - if (barIndex >= count) - { - barIndex = count - 1; - } - - // - return vwapMidBuffer[barIndex]; - } - - // - int CopyVWapMid( - int start, // Start - int count, // Number of Items for read - double &buffer[], // Dest Buffer - bool forceClean = true // Force To Clean buffer - ) - { - // - // Update Calculations ... - Calculate(); - - // - // Copy Items ... - return Copy( - start, - count, - vwapMidBuffer, - buffer, - forceClean - // - ); - } - - // - // STATE MID ... - - // - double GetVWapMidState( - int barIndex // Bar Index - ) - { - // - if (barIndex < 0) - { - barIndex = 0; - } - - // - Calculate(); - - // - int count = ArraySize(vwapMidStateBuffer); - if (barIndex >= count) - { - barIndex = count - 1; - } - - // - return vwapMidStateBuffer[barIndex]; - } - - // - int CopyVWapMidState( - int start, // Start - int count, // Number of Items for read - double &buffer[], // Dest Buffer - bool forceClean = true // Force To Clean buffer - ) - { - // - // Update Calculations ... - Calculate(); - - // - // Copy Items ... - return Copy( - start, - count, - vwapMidStateBuffer, - buffer, - forceClean - // - ); - } - - // - // SLOW ... - - // - double GetVWapSlowBuffer( - int barIndex // Bar Index - ) - { - // - if (barIndex < 0) - { - barIndex = 0; - } - - // - Calculate(); - - // - int count = ArraySize(vwapSlowBuffer); - if (barIndex >= count) - { - barIndex = count - 1; - } - - // - return vwapSlowBuffer[barIndex]; - } - - // - int CopyVWapSlow( - int start, // Start - int count, // Number of Items for read - double &buffer[], // Dest Buffer - bool forceClean = true // Force To Clean buffer - ) - { - // - // Update Calculations ... - Calculate(); - - // - // Copy Items ... - return Copy( - start, - count, - vwapSlowBuffer, - buffer, - forceClean - // - ); - } - - // - // STATE SLOW ... - - // - double GetVWapSlowState( - int barIndex // Bar Index - ) - { - // - if (barIndex < 0) - { - barIndex = 0; - } - - // - Calculate(); - - // - int count = ArraySize(vwapSlowStateBuffer); - if (barIndex >= count) - { - barIndex = count - 1; - } - - // - return vwapSlowStateBuffer[barIndex]; - } - - // - int CopyVWapSlowState( - int start, // Start - int count, // Number of Items for read - double &buffer[], // Dest Buffer - bool forceClean = true // Force To Clean buffer - ) - { - // - // Update Calculations ... - Calculate(); - - // - // Copy Items ... - return Copy( - start, - count, - vwapSlowStateBuffer, - buffer, - forceClean - // - ); - } - - // - // VOLUME ... - - // - double GetVWapVolume( - int barIndex // Bar Index - ) - { - // - if (barIndex < 0) - { - barIndex = 0; - } - - // - Calculate(); - - // - int count = ArraySize(vwapVolumeBuffer); - if (barIndex >= count) - { - barIndex = count - 1; - } - - // - return vwapVolumeBuffer[barIndex]; - } - - // - int CopyVWapVolume( - int start, // Start - int count, // Number of Items for read - double &buffer[], // Dest Buffer - bool forceClean = true // Force To Clean buffer - ) - { - // - // Update Calculations ... - Calculate(); - - // - // Copy Items ... - return Copy( - start, - count, - vwapVolumeBuffer, - buffer, - forceClean - // - ); - } - - // - // PRICE ... - - // - double GetVWapPrice( - int barIndex // Bar Index - ) - { - // - if (barIndex < 0) - { - barIndex = 0; - } - - // - Calculate(); - - // - int count = ArraySize(vwapPriceBuffer); - if (barIndex >= count) - { - barIndex = count - 1; - } - - // - return vwapPriceBuffer[barIndex]; - } - - // - int CopyVWapPrice( - int start, // Start - int count, // Number of Items for read - double &buffer[], // Dest Buffer - bool forceClean = true // Force To Clean buffer - ) - { - // - // Update Calculations ... - Calculate(); - - // - // Copy Items ... - return Copy( - start, - count, - vwapPriceBuffer, - buffer, - forceClean - // - ); - } - - // - // Converts to State ... - ENUM_XVWAP_STATES ToVWAPState(double value) - { - // - ENUM_XVWAP_STATES result = - value == 1 - ? XVWAP_STATE_BULLISH - : value == 2 - ? XVWAP_STATE_BEARISH - : XVWAP_STATE_NEUTURAL; - - // - return result; - } - - // - bool IsVWAPBullish(double value) { // bool result = false; // - result = ToVWAPState(value) == XVWAP_STATE_BULLISH; + result = xpvHelper.GetConditions( + conditions, + barIndex, + loopback // + ); // return result; } // - bool IsVWAPBearish(double value) + // XATR ... + bool GetATRConditions( + X121XATRConditions &conditions, // + int barIndex = 0, // + int loopback = 5 // + ) { // bool result = false; // - result = ToVWAPState(value) == XVWAP_STATE_BEARISH; + result = xatrHelper.GetConditions( + conditions, + barIndex, + loopback // + ); // return result; } // - bool IsVWAPNeutural(double value) + // XSTR ... + bool GetSTRConditions( + X121XSTRConditions &conditions, // + int barIndex = 0, // + int loopback = 5 // + ) { // bool result = false; // - result = ToVWAPState(value) == XVWAP_STATE_NEUTURAL; + result = xstrHelper.GetConditions( + conditions, + barIndex, + loopback // + ); // return result; @@ -3127,438 +919,49 @@ class XCX121Helper : public XCBaseHelper // // XDON ... - - // - // OPEN ... - - // - // UPPER ... - - // - double GetDonOpenUpper( - int barIndex // Bar Index + bool GetDONConditions( + X121XDONConditions &conditions, // + int barIndex = 0, // + int loopback = 5 // ) { // - if (barIndex < 0) - { - barIndex = 0; - } + bool result = false; // - Calculate(); - - // - int count = ArraySize(donOpenUpperBuffer); - if (barIndex >= count) - { - barIndex = count - 1; - } - - // - return donOpenUpperBuffer[barIndex]; - } - - // - int CopyDonOpenUpper( - int start, // Start - int count, // Number of Items for read - double &buffer[], // Dest Buffer - bool forceClean = true // Force To Clean buffer - ) - { - // - // Update Calculations ... - Calculate(); - - // - // Copy Items ... - return Copy( - start, - count, - donOpenUpperBuffer, - buffer, - forceClean - // + result = xdonHelper.GetConditions( + conditions, + barIndex, + loopback // ); + + // + return result; } // - // LOWER ... - - // - double GetDonOpenLower( - int barIndex // Bar Index + // XVWAP ... + bool GetVWAPConditions( + X121XVWAPConditions &conditions, // + int barIndex = 0, // + int loopback = 5 // ) { // - if (barIndex < 0) - { - barIndex = 0; - } + bool result = false; // - Calculate(); - - // - int count = ArraySize(donOpenLowerBuffer); - if (barIndex >= count) - { - barIndex = count - 1; - } - - // - return donOpenLowerBuffer[barIndex]; - } - - // - int CopyDonOpenLower( - int start, // Start - int count, // Number of Items for read - double &buffer[], // Dest Buffer - bool forceClean = true // Force To Clean buffer - ) - { - // - // Update Calculations ... - Calculate(); - - // - // Copy Items ... - return Copy( - start, - count, - donOpenLowerBuffer, - buffer, - forceClean - // + result = xvwapHelper.GetConditions( + conditions, + barIndex, + loopback // ); + + // + return result; } // - // CLOSE ... - - // - // UPPER ... - - // - double GetDonCloseUpper( - int barIndex // Bar Index - ) - { - // - if (barIndex < 0) - { - barIndex = 0; - } - - // - Calculate(); - - // - int count = ArraySize(donCloseUpperBuffer); - if (barIndex >= count) - { - barIndex = count - 1; - } - - // - return donCloseUpperBuffer[barIndex]; - } - - // - int CopyDonCloseUpper( - int start, // Start - int count, // Number of Items for read - double &buffer[], // Dest Buffer - bool forceClean = true // Force To Clean buffer - ) - { - // - // Update Calculations ... - Calculate(); - - // - // Copy Items ... - return Copy( - start, - count, - donCloseUpperBuffer, - buffer, - forceClean - // - ); - } - - // - // LOWER ... - - // - double GetDonCloseLower( - int barIndex // Bar Index - ) - { - // - if (barIndex < 0) - { - barIndex = 0; - } - - // - Calculate(); - - // - int count = ArraySize(donCloseLowerBuffer); - if (barIndex >= count) - { - barIndex = count - 1; - } - - // - return donCloseLowerBuffer[barIndex]; - } - - // - int CopyDonCloseLower( - int start, // Start - int count, // Number of Items for read - double &buffer[], // Dest Buffer - bool forceClean = true // Force To Clean buffer - ) - { - // - // Update Calculations ... - Calculate(); - - // - // Copy Items ... - return Copy( - start, - count, - donCloseLowerBuffer, - buffer, - forceClean - // - ); - } - - // - // HIGH ... - - // - // UPPER ... - - // - double GetDonHighUpper( - int barIndex // Bar Index - ) - { - // - if (barIndex < 0) - { - barIndex = 0; - } - - // - Calculate(); - - // - int count = ArraySize(donHighUpperBuffer); - if (barIndex >= count) - { - barIndex = count - 1; - } - - // - return donHighUpperBuffer[barIndex]; - } - - // - int CopyDonHighUpper( - int start, // Start - int count, // Number of Items for read - double &buffer[], // Dest Buffer - bool forceClean = true // Force To Clean buffer - ) - { - // - // Update Calculations ... - Calculate(); - - // - // Copy Items ... - return Copy( - start, - count, - donHighUpperBuffer, - buffer, - forceClean - // - ); - } - - // - // LOWER ... - - // - double GetDonHighLower( - int barIndex // Bar Index - ) - { - // - if (barIndex < 0) - { - barIndex = 0; - } - - // - Calculate(); - - // - int count = ArraySize(donHighLowerBuffer); - if (barIndex >= count) - { - barIndex = count - 1; - } - - // - return donHighLowerBuffer[barIndex]; - } - - // - int CopyDonHighLower( - int start, // Start - int count, // Number of Items for read - double &buffer[], // Dest Buffer - bool forceClean = true // Force To Clean buffer - ) - { - // - // Update Calculations ... - Calculate(); - - // - // Copy Items ... - return Copy( - start, - count, - donHighLowerBuffer, - buffer, - forceClean - // - ); - } - - // - // LOW ... - - // - // UPPER ... - - // - double GetDonLowUpper( - int barIndex // Bar Index - ) - { - // - if (barIndex < 0) - { - barIndex = 0; - } - - // - Calculate(); - - // - int count = ArraySize(donLowUpperBuffer); - if (barIndex >= count) - { - barIndex = count - 1; - } - - // - return donLowUpperBuffer[barIndex]; - } - - // - int CopyDonLowUpper( - int start, // Start - int count, // Number of Items for read - double &buffer[], // Dest Buffer - bool forceClean = true // Force To Clean buffer - ) - { - // - // Update Calculations ... - Calculate(); - - // - // Copy Items ... - return Copy( - start, - count, - donLowUpperBuffer, - buffer, - forceClean - // - ); - } - - // - // LOWER ... - - // - double GetDonLoweLower( - int barIndex // Bar Index - ) - { - // - if (barIndex < 0) - { - barIndex = 0; - } - - // - Calculate(); - - // - int count = ArraySize(donLowLowerBuffer); - if (barIndex >= count) - { - barIndex = count - 1; - } - - // - return donLowLowerBuffer[barIndex]; - } - - // - int CopyDonLoweLower( - int start, // Start - int count, // Number of Items for read - double &buffer[], // Dest Buffer - bool forceClean = true // Force To Clean buffer - ) - { - // - // Update Calculations ... - Calculate(); - - // - // Copy Items ... - return Copy( - start, - count, - donLowLowerBuffer, - buffer, - forceClean - // - ); - } - - // - // Conditions Generation ... - bool GetConditions( X121Conditions &conditions, // int barIndex = 0, // @@ -3624,467 +1027,440 @@ class XCX121Helper : public XCBaseHelper return result; } + // + // XPV ... + X121XPVConditions xpvConditions; + result = GetPVConditions( + xpvConditions, + barIndex, + loopback // + ); + if (!result) + { + return result; + } + + // + // XATR ... + X121XATRConditions xatrConditions; + result = GetATRConditions( + xatrConditions, + barIndex, + loopback // + ); + if (!result) + { + return result; + } + + // + // XSTR ... + X121XSTRConditions xstrConditions; + result = GetSTRConditions( + xstrConditions, + barIndex, + loopback // + ); + if (!result) + { + return result; + } + + // + // XDON ... + X121XDONConditions xdonConditions; + result = GetDONConditions( + xdonConditions, + barIndex, + loopback // + ); + if (!result) + { + return result; + } + + // + // XVWAP ... + X121XVWAPConditions xvwapConditions; + result = GetVWAPConditions( + xvwapConditions, + barIndex, + loopback // + ); + if (!result) + { + return result; + } + + // + // Fill X121 Conditions Reference by Using + // Retrieved Conditions ... + + // + // XPV ... + // // Buffers ... // - CopyRSI( - zIndex, - loopback, - conditions.rsiBuffer // - ); - - // - CopySar( - zIndex, - loopback, - conditions.sarBuffer // - ); - - // - CopyAtr( - zIndex, - loopback, - conditions.atrBuffer // - ); - - // - CopyAtrUpper( - zIndex, - loopback, - conditions.atrUpperBuffer // - ); - - // - CopyAtrUpperRaw( - zIndex, - loopback, - conditions.atrUpperRawBuffer // - ); - - // - CopyAtrLower( - zIndex, - loopback, - conditions.atrLowerBuffer // - ); - - // - CopyAtrLowerRaw( - zIndex, - loopback, - conditions.atrLowerRawBuffer // - ); - - // - CopyPeak( - zIndex, - loopback, + Copy( + xpvConditions.peaksBuffer, conditions.peaksBuffer // ); // - CopyVale( - zIndex, - loopback, + Copy( + xpvConditions.valesBuffer, conditions.valesBuffer // ); // - CopyCHH( - zIndex, - loopback, + Copy( + xpvConditions.sarBuffer, + conditions.sarBuffer // + ); + + // + Copy( + xpvConditions.cHHBuffer, conditions.cHHBuffer // ); // - CopyCLL( - zIndex, - loopback, + Copy( + xpvConditions.cLLBuffer, conditions.cLLBuffer // ); // - CopySHH( - zIndex, - loopback, + Copy( + xpvConditions.sHHBuffer, conditions.sHHBuffer // ); // - CopySLL( - zIndex, - loopback, + Copy( + xpvConditions.sLLBuffer, conditions.sLLBuffer // ); // - CopyMHH( - zIndex, - loopback, + Copy( + xpvConditions.mHHBuffer, conditions.mHHBuffer // ); // - CopyMLL( - zIndex, - loopback, + Copy( + xpvConditions.mLLBuffer, conditions.mLLBuffer // ); // - CopyLHH( - zIndex, - loopback, + Copy( + xpvConditions.lHHBuffer, conditions.lHHBuffer // ); // - CopyLLL( - zIndex, - loopback, + Copy( + xpvConditions.lLLBuffer, conditions.lLLBuffer // ); // - CopyHHH( - zIndex, - loopback, + Copy( + xpvConditions.hHHBuffer, conditions.hHHBuffer // ); // - CopyHLL( - zIndex, - loopback, + Copy( + xpvConditions.hLLBuffer, conditions.hLLBuffer // ); - // - CopyVWapFast( - zIndex, - loopback, - conditions.vwapFastBuffer // - ); - - // - CopyVWapFastState( - zIndex, - loopback, - conditions.vwapFastStateBuffer // - ); - - // - CopyVWapMid( - zIndex, - loopback, - conditions.vwapMidBuffer // - ); - - // - CopyVWapMidState( - zIndex, - loopback, - conditions.vwapMidStateBuffer // - ); - - // - CopyVWapSlow( - zIndex, - loopback, - conditions.vwapSlowBuffer // - ); - - // - CopyVWapSlowState( - zIndex, - loopback, - conditions.vwapSlowStateBuffer // - ); - - // - CopyVWapVolume( - zIndex, - loopback, - conditions.vwapVolumeBuffer // - ); - - // - CopyVWapPrice( - zIndex, - loopback, - conditions.vwapPriceBuffer // - ); - - // - CopyDonOpenUpper( - zIndex, - loopback, - conditions.donOpenUpperBuffer // - ); - - // - CopyDonOpenLower( - zIndex, - loopback, - conditions.donOpenLowerBuffer // - ); - - // - CopyDonCloseUpper( - zIndex, - loopback, - conditions.donCloseUpperBuffer // - ); - - // - CopyDonCloseLower( - zIndex, - loopback, - conditions.donCloseLowerBuffer // - ); - - // - CopyDonHighUpper( - zIndex, - loopback, - conditions.donHighUpperBuffer // - ); - - // - CopyDonHighLower( - zIndex, - loopback, - conditions.donHighLowerBuffer // - ); - - // - CopyDonLowUpper( - zIndex, - loopback, - conditions.donLowUpperBuffer // - ); - - // - CopyDonLoweLower( - zIndex, - loopback, - conditions.donLowLowerBuffer // - ); - // // Conditions ... // - int cIDX = 1; - int pIDX = cIDX + 1; + conditions.isNewPeak = xpvConditions.isNewPeak; + conditions.isNewVale = xpvConditions.isNewVale; + conditions.isSarBullish = xpvConditions.isSarBullish; + conditions.isSarBearish = xpvConditions.isSarBearish; + conditions.isNewPeakOverLast = xpvConditions.isNewPeakOverLast; + conditions.isNewValeOverLast = xpvConditions.isNewValeOverLast; + conditions.isNewPeakUnderLast = xpvConditions.isNewPeakUnderLast; + conditions.isNewValeUnderLast = xpvConditions.isNewValeUnderLast; + conditions.isSarSwitchedToBullish = xpvConditions.isSarSwitchedToBullish; + conditions.isSarSwitchedToBearish = xpvConditions.isSarSwitchedToBearish; // - // XRSI ... + // XATR ... // - bool isRSIOverBought = conditions.rsiBuffer[cIDX] > mInputs.rsiOverBoughtLevel; - bool isRSIOverBoughtPrev = conditions.rsiBuffer[pIDX] > mInputs.rsiOverBoughtLevel; + // Buffers ... // - bool isRSICrossedOverOverBought = isRSIOverBought && - !isRSIOverBoughtPrev; - bool isRSICrossedUnderOverBought = !isRSIOverBought && - isRSIOverBoughtPrev; + Copy( + xatrConditions.atrUpperBuffer, + conditions.atrUpperBuffer // + ); // - bool isRSIOverSold = conditions.rsiBuffer[cIDX] < mInputs.rsiOverSoldLevel; - bool isRSIOverSoldPrev = conditions.rsiBuffer[pIDX] < mInputs.rsiOverSoldLevel; + Copy( + xatrConditions.atrLowerBuffer, + conditions.atrLowerBuffer // + ); // - bool isRSICrossedUnderOverSold = isRSIOverSold && - !isRSIOverSoldPrev; - bool isRSICrossedOverOverSold = !isRSIOverSold && - isRSIOverSoldPrev; + Copy( + xatrConditions.atrUpperRawBuffer, + conditions.atrUpperRawBuffer // + ); // - // XSAR ... + Copy( + xatrConditions.atrLowerRawBuffer, + conditions.atrLowerRawBuffer // + ); // - bool isSarBullish = conditions.sarBuffer[cIDX] < cBar.low; - bool isSarBullishPrev = conditions.sarBuffer[pIDX] < pBar.low; + Copy( + xatrConditions.atrBuffer, + conditions.atrBuffer // + ); // - bool isSarBearish = conditions.sarBuffer[cIDX] > cBar.high; - bool isSarBearishPrev = conditions.sarBuffer[pIDX] > pBar.high; + Copy( + xatrConditions.rsiBuffer, + conditions.rsiBuffer // + ); // - bool isSarSwitchedToBullish = isSarBullish && - !isSarBullishPrev; - bool isSarSwitchedToBearish = isSarBearish && - !isSarBearishPrev; + // Conditions ... // - // XPV ... + conditions.isRSIOverSold = xatrConditions.isRSIOverSold; + conditions.isRSIOverBought = xatrConditions.isRSIOverBought; + conditions.isBreakUpATRUpper = xatrConditions.isBreakUpATRUpper; + conditions.isBreakUpATRLower = xatrConditions.isBreakUpATRLower; + conditions.isCloseOverATRUper = xatrConditions.isCloseOverATRUper; + conditions.isRejectUpATRUpper = xatrConditions.isRejectUpATRUpper; + conditions.isRejectUpATRLower = xatrConditions.isRejectUpATRLower; + conditions.isCloseOverATRLower = xatrConditions.isCloseOverATRLower; + conditions.isBreakDownATRUpper = xatrConditions.isBreakDownATRUpper; + conditions.isBreakDownATRLower = xatrConditions.isBreakDownATRLower; + conditions.isCloseUnderATRUpper = xatrConditions.isCloseUnderATRUpper; + conditions.isCloseUnderATRLower = xatrConditions.isCloseUnderATRLower; + conditions.isRejectDownATRUpper = xatrConditions.isRejectDownATRUpper; + conditions.isRejectDownATRLower = xatrConditions.isRejectDownATRLower; + conditions.isRSICrossedOverOverSold = xatrConditions.isRSICrossedOverOverSold; + conditions.isRSICrossedUnderOverSold = xatrConditions.isRSICrossedUnderOverSold; + conditions.isRSICrossedOverOverBought = xatrConditions.isRSICrossedOverOverBought; + conditions.isRSICrossedUnderOverBought = xatrConditions.isRSICrossedUnderOverBought; // - bool isNewPeak = conditions.peaksBuffer[cIDX] != conditions.peaksBuffer[pIDX]; - bool isNewPeakOverLast = isNewPeak && - conditions.peaksBuffer[cIDX] > conditions.peaksBuffer[pIDX]; - bool isNewPeakUnderLast = isNewPeak && - conditions.peaksBuffer[cIDX] < conditions.peaksBuffer[pIDX]; + // XSTR ... // - bool isNewVale = conditions.valesBuffer[cIDX] != conditions.valesBuffer[pIDX]; - bool isNewValeOverLast = isNewVale && - conditions.valesBuffer[cIDX] > conditions.valesBuffer[pIDX]; - bool isNewValeUnderLast = isNewVale && - conditions.valesBuffer[cIDX] < conditions.valesBuffer[pIDX]; + // Buffers ... // - // XVWAP ... + Copy( + xstrConditions.strBuffer, + conditions.strBuffer // + ); // - bool isVWapFastBullish = IsVWAPBullish(conditions.vwapFastStateBuffer[cIDX]); - bool isVWapFastBullishPrev = IsVWAPBullish(conditions.vwapFastStateBuffer[pIDX]); + Copy( + xstrConditions.strPriceBuffer, + conditions.strPriceBuffer // + ); // - bool isVWapFastBearish = IsVWAPBearish(conditions.vwapFastStateBuffer[cIDX]); - bool isVWapFastBearishPrev = IsVWAPBearish(conditions.vwapFastStateBuffer[pIDX]); + Copy( + xstrConditions.strUpBuffer, + conditions.strUpBuffer // + ); // - bool isVWapFastNeutural = IsVWAPNeutural(conditions.vwapFastStateBuffer[cIDX]); - bool isVWapFastNeuturalPrev = IsVWAPNeutural(conditions.vwapFastStateBuffer[pIDX]); + Copy( + xstrConditions.strDownBuffer, + conditions.strDownBuffer // + ); // - bool isVWapMidBullish = IsVWAPBullish(conditions.vwapMidStateBuffer[cIDX]); - bool isVWapMidBullishPrev = IsVWAPBullish(conditions.vwapMidStateBuffer[pIDX]); + Copy( + xstrConditions.strStateBuffer, + conditions.strStateBuffer // + ); // - bool isVWapMidBearish = IsVWAPBearish(conditions.vwapMidStateBuffer[cIDX]); - bool isVWapMidBearishPrev = IsVWAPBearish(conditions.vwapMidStateBuffer[pIDX]); + // Conditions ... // - bool isVWapMidNeutural = IsVWAPNeutural(conditions.vwapMidStateBuffer[cIDX]); - bool isVWapMidNeuturalPrev = IsVWAPNeutural(conditions.vwapMidStateBuffer[pIDX]); - - // - bool isVWapSlowBullish = IsVWAPBullish(conditions.vwapSlowStateBuffer[cIDX]); - bool isVWapSlowBullishPrev = IsVWAPBullish(conditions.vwapSlowStateBuffer[pIDX]); - - // - bool isVWapSlowBearish = IsVWAPBearish(conditions.vwapSlowStateBuffer[cIDX]); - bool isVWapSlowBearishPrev = IsVWAPBearish(conditions.vwapSlowStateBuffer[pIDX]); - - // - bool isVWapSlowNeutural = IsVWAPNeutural(conditions.vwapSlowStateBuffer[cIDX]); - bool isVWapSlowNeuturalPrev = IsVWAPNeutural(conditions.vwapSlowStateBuffer[pIDX]); - - // - bool isVWapFastOverMid = conditions.vwapFastBuffer[cIDX] > conditions.vwapMidBuffer[cIDX]; - bool isVWapFastOverMidPrev = conditions.vwapFastBuffer[pIDX] > conditions.vwapMidBuffer[pIDX]; - - // - bool isVWapMidOverSlow = conditions.vwapMidBuffer[cIDX] > conditions.vwapSlowBuffer[cIDX]; - bool isVWapMidOverSlowPrev = conditions.vwapMidBuffer[pIDX] > conditions.vwapSlowBuffer[pIDX]; - - // - bool isVWapFastUnderMid = conditions.vwapFastBuffer[cIDX] < conditions.vwapMidBuffer[cIDX]; - bool isVWapFastUnderMidPrev = conditions.vwapFastBuffer[pIDX] < conditions.vwapMidBuffer[pIDX]; - - // - bool isVWapMidUnderSlow = conditions.vwapMidBuffer[cIDX] < conditions.vwapSlowBuffer[cIDX]; - bool isVWapMidUnderSlowPrev = conditions.vwapMidBuffer[pIDX] < conditions.vwapSlowBuffer[pIDX]; - - // - bool isVWapBullishState = isVWapFastBullish && - isVWapMidBullish && - isVWapSlowBullish; - bool isVWapBullishStatePrev = isVWapFastBullishPrev && - isVWapMidBullishPrev && - isVWapSlowBullishPrev; - - // - bool isVWapBearishState = isVWapFastBearish && - isVWapMidBearish && - isVWapSlowBearish; - bool isVWapBearishStatePrev = isVWapFastBearishPrev && - isVWapMidBearishPrev && - isVWapSlowBearishPrev; - - // - bool isVWapNeuturalState = isVWapFastNeutural && - isVWapMidNeutural && - isVWapSlowNeutural; - bool isVWapNeuturalStatePrev = isVWapFastNeuturalPrev && - isVWapMidNeuturalPrev && - isVWapSlowNeuturalPrev; - - // - bool isVWapBullishOrdered = isVWapFastOverMid && - isVWapMidOverSlow; - bool isVWapBullishOrderedPrev = isVWapFastOverMidPrev && - isVWapMidOverSlowPrev; - - // - bool isVWapBearishOrdered = isVWapFastUnderMid && - isVWapMidUnderSlow; - bool isVWapBearishOrderedPrev = isVWapFastUnderMidPrev && - isVWapMidUnderSlowPrev; - - // - bool isVWapSwitchedToBullishOrdered = isVWapBullishOrdered && - !isVWapBullishOrderedPrev; - bool isVWapSwitchedToBearishOrdered = isVWapBearishOrdered && - !isVWapBearishOrderedPrev; - - // - bool isVWapSwitchedToBullishState = isVWapBullishState && - !isVWapBullishStatePrev; - bool isVWapSwitchedToBearishState = isVWapBearishState && - !isVWapBearishStatePrev; - bool isVWapSwitchedToNeuturalState = isVWapNeuturalState && - !isVWapNeuturalStatePrev; + conditions.isStrBullish = xstrConditions.isStrBullish; + conditions.isStrBearish = xstrConditions.isStrBearish; + conditions.isStrSwitchedToBullish = xstrConditions.isStrSwitchedToBullish; + conditions.isStrSwitchedToBearish = xstrConditions.isStrSwitchedToBearish; // // XDON ... // - // Set ... - conditions.isRSIOverBought = isRSIOverBought; - conditions.isRSICrossedOverOverBought = isRSICrossedOverOverBought; - conditions.isRSICrossedUnderOverBought = isRSICrossedUnderOverBought; - conditions.isRSIOverSold = isRSIOverSold; - conditions.isRSICrossedUnderOverSold = isRSICrossedUnderOverSold; - conditions.isRSICrossedOverOverSold = isRSICrossedOverOverSold; - conditions.isSarBullish = isSarBullish; - conditions.isSarBearish = isSarBearish; - conditions.isSarSwitchedToBullish = isSarSwitchedToBullish; - conditions.isSarSwitchedToBearish = isSarSwitchedToBearish; - conditions.isNewPeak = isNewPeak; - conditions.isNewPeakOverLast = isNewPeakOverLast; - conditions.isNewPeakUnderLast = isNewPeakUnderLast; - conditions.isNewVale = isNewVale; - conditions.isNewValeOverLast = isNewValeOverLast; - conditions.isNewValeUnderLast = isNewValeUnderLast; - conditions.isVWapFastBullish = isVWapFastBullish; - conditions.isVWapFastBearish = isVWapFastBearish; - conditions.isVWapFastNeutural = isVWapFastNeutural; - conditions.isVWapMidBullish = isVWapMidBullish; - conditions.isVWapMidBearish = isVWapMidBearish; - conditions.isVWapMidNeutural = isVWapMidNeutural; - conditions.isVWapSlowBullish = isVWapSlowBullish; - conditions.isVWapSlowBearish = isVWapSlowBearish; - conditions.isVWapSlowNeutural = isVWapSlowNeutural; - conditions.isVWapFastOverMid = isVWapFastOverMid; - conditions.isVWapMidOverSlow = isVWapMidOverSlow; - conditions.isVWapFastUnderMid = isVWapFastUnderMid; - conditions.isVWapMidUnderSlow = isVWapMidUnderSlow; - conditions.isVWapBullishState = isVWapBullishState; - conditions.isVWapBearishState = isVWapBearishState; - conditions.isVWapNeuturalState = isVWapNeuturalState; - conditions.isVWapBullishOrdered = isVWapBullishOrdered; - conditions.isVWapBearishOrdered = isVWapBearishOrdered; - conditions.isVWapSwitchedToBullishOrdered = isVWapSwitchedToBullishOrdered; - conditions.isVWapSwitchedToBearishOrdered = isVWapSwitchedToBearishOrdered; - conditions.isVWapSwitchedToBullishState = isVWapSwitchedToBullishState; - conditions.isVWapSwitchedToBearishState = isVWapSwitchedToBearishState; - conditions.isVWapSwitchedToNeuturalState = isVWapSwitchedToNeuturalState; + // Buffers ... + + // + Copy( + xdonConditions.donOpenUpperBuffer, + conditions.donOpenUpperBuffer // + ); + + // + Copy( + xdonConditions.donOpenLowerBuffer, + conditions.donOpenLowerBuffer // + ); + + // + Copy( + xdonConditions.donHighUpperBuffer, + conditions.donHighUpperBuffer // + ); + + // + Copy( + xdonConditions.donHighLowerBuffer, + conditions.donHighLowerBuffer // + ); + + // + Copy( + xdonConditions.donLowUpperBuffer, + conditions.donLowUpperBuffer // + ); + + // + Copy( + xdonConditions.donLowLowerBuffer, + conditions.donLowLowerBuffer // + ); + + // + Copy( + xdonConditions.donCloseUpperBuffer, + conditions.donCloseUpperBuffer // + ); + + // + Copy( + xdonConditions.donCloseLowerBuffer, + conditions.donCloseLowerBuffer // + ); + + // + // Conditions ... + + // + conditions.isBreakDonLowUpper = xdonConditions.isBreakDonLowUpper; + conditions.isBreakDonLowLower = xdonConditions.isBreakDonLowLower; + conditions.isRejectDonLowUpper = xdonConditions.isRejectDonLowUpper; + conditions.isRejectDonLowLower = xdonConditions.isRejectDonLowLower; + conditions.isBreakDonOpenUpper = xdonConditions.isBreakDonOpenUpper; + conditions.isBreakDonHighUpper = xdonConditions.isBreakDonHighUpper; + conditions.isBreakDonOpenLower = xdonConditions.isBreakDonOpenLower; + conditions.isBreakDonHighLower = xdonConditions.isBreakDonHighLower; + conditions.isRejectDonOpenUpper = xdonConditions.isRejectDonOpenUpper; + conditions.isRejectDonHighUpper = xdonConditions.isRejectDonHighUpper; + conditions.isRejectDonOpenLower = xdonConditions.isRejectDonOpenLower; + conditions.isRejectDonHighLower = xdonConditions.isRejectDonHighLower; + conditions.isBreakDonCloseUpper = xdonConditions.isBreakDonCloseUpper; + conditions.isBreakDonCloseLower = xdonConditions.isBreakDonCloseLower; + conditions.isRejectDonCloseUpper = xdonConditions.isRejectDonCloseUpper; + conditions.isRejectDonCloseLower = xdonConditions.isRejectDonCloseLower; + + // + // XVWAP ... + + // + // Buffers ... + + // + Copy( + xvwapConditions.vwapFastBuffer, + conditions.donOpenUpperBuffer // + ); + + // + Copy( + xvwapConditions.vwapMidBuffer, + conditions.donOpenLowerBuffer // + ); + + // + Copy( + xvwapConditions.vwapSlowBuffer, + conditions.donHighUpperBuffer // + ); + + // + Copy( + xvwapConditions.vwapVolumeBuffer, + conditions.donHighLowerBuffer // + ); + + // + Copy( + xvwapConditions.vwapPriceBuffer, + conditions.donLowUpperBuffer // + ); + + // + Copy( + xvwapConditions.vwapFastStateBuffer, + conditions.donLowLowerBuffer // + ); + + // + Copy( + xvwapConditions.vwapMidStateBuffer, + conditions.donCloseUpperBuffer // + ); + + // + Copy( + xvwapConditions.vwapSlowStateBuffer, + conditions.donCloseLowerBuffer // + ); + + // + // Conditions ... + + // + conditions.isVWapMidBullish = xvwapConditions.isVWapMidBullish; + conditions.isVWapMidBearish = xvwapConditions.isVWapMidBearish; + conditions.isVWapFastBullish = xvwapConditions.isVWapFastBullish; + conditions.isVWapFastBearish = xvwapConditions.isVWapFastBearish; + conditions.isVWapMidNeutural = xvwapConditions.isVWapMidNeutural; + conditions.isVWapSlowBullish = xvwapConditions.isVWapSlowBullish; + conditions.isVWapSlowBearish = xvwapConditions.isVWapSlowBearish; + conditions.isVWapFastOverMid = xvwapConditions.isVWapFastOverMid; + conditions.isVWapMidOverSlow = xvwapConditions.isVWapMidOverSlow; + conditions.isVWapFastNeutural = xvwapConditions.isVWapFastNeutural; + conditions.isVWapSlowNeutural = xvwapConditions.isVWapSlowNeutural; + conditions.isVWapFastUnderMid = xvwapConditions.isVWapFastUnderMid; + conditions.isVWapMidUnderSlow = xvwapConditions.isVWapMidUnderSlow; + conditions.isVWapBullishState = xvwapConditions.isVWapBullishState; + conditions.isVWapBearishState = xvwapConditions.isVWapBearishState; + conditions.isVWapNeuturalState = xvwapConditions.isVWapNeuturalState; + conditions.isVWapBullishOrdered = xvwapConditions.isVWapBullishOrdered; + conditions.isVWapBearishOrdered = xvwapConditions.isVWapBearishOrdered; + conditions.isVWapSwitchedToBullishState = xvwapConditions.isVWapSwitchedToBullishState; + conditions.isVWapSwitchedToBearishState = xvwapConditions.isVWapSwitchedToBearishState; + conditions.isVWapSwitchedToNeuturalState = xvwapConditions.isVWapSwitchedToNeuturalState; + conditions.isVWapSwitchedToBullishOrdered = xvwapConditions.isVWapSwitchedToBullishOrdered; + conditions.isVWapSwitchedToBearishOrdered = xvwapConditions.isVWapSwitchedToBearishOrdered; // return result; @@ -4097,484 +1473,19 @@ class XCX121Helper : public XCBaseHelper // private: // - // Props ... - X121Inputs mInputs; // Inputs ... // - // Buffers ... - double peaksBuffer[]; - double valesBuffer[]; - double sarBuffer[]; - double atrUpperBuffer[]; - double atrLowerBuffer[]; - double vwapFastBuffer[]; - double vwapMidBuffer[]; - double vwapSlowBuffer[]; - double donOpenUpperBuffer[]; - double donOpenLowerBuffer[]; - double donCloseUpperBuffer[]; - double donCloseLowerBuffer[]; - double donHighUpperBuffer[]; - double donHighLowerBuffer[]; - double donLowUpperBuffer[]; - double donLowLowerBuffer[]; - double cHHBuffer[]; - double cLLBuffer[]; - double sHHBuffer[]; - double sLLBuffer[]; - double mHHBuffer[]; - double mLLBuffer[]; - double lHHBuffer[]; - double lLLBuffer[]; - double hHHBuffer[]; - double hLLBuffer[]; - double atrBuffer[]; - double atrUpperRawBuffer[]; - double atrLowerRawBuffer[]; - double vwapVolumeBuffer[]; - double vwapPriceBuffer[]; - double vwapFastStateBuffer[]; - double vwapMidStateBuffer[]; - double vwapSlowStateBuffer[]; - double rsiBuffer[]; + string mSymbol; // Trading Symbol + ENUM_TIMEFRAMES mPeriod; // Trading Period // - // Tools ... - - /** - * Calculate Buffers ... - */ - void Calculate() - { - // - int totalBars = CountBars(); - if (totalBars > 1000) - { - totalBars = 1000; - } - - // - // Buffers ... - - // - // RSI ... - CopyBuffer( - mHandler, - X121_RSI_LINE, - 0, - totalBars, - rsiBuffer - // - ); - - // - // XSAR ... - CopyBuffer( - mHandler, - X121_SAR_LINE, - 0, - totalBars, - sarBuffer - // - ); - - // - // ATR ... - - // - CopyBuffer( - mHandler, - X121_ATR_UPPER_LINE, - 0, - totalBars, - atrUpperBuffer - // - ); - - // - CopyBuffer( - mHandler, - X121_ATR_LOWER_LINE, - 0, - totalBars, - atrLowerBuffer - // - ); - - // - CopyBuffer( - mHandler, - X121_ATR_LINE, - 0, - totalBars, - atrBuffer - // - ); - - // - CopyBuffer( - mHandler, - X121_ATR_UPPER_RAW_LINE, - 0, - totalBars, - atrUpperRawBuffer - // - ); - - // - CopyBuffer( - mHandler, - X121_ATR_LOWER_RAW_LINE, - 0, - totalBars, - atrLowerRawBuffer - // - ); - - // - // XPV ... - - // - // PEAKS ... - CopyBuffer( - mHandler, - X121_PEAKS_LINE, - 0, - totalBars, - peaksBuffer - // - ); - - // - // VALES ... - CopyBuffer( - mHandler, - X121_VALES_LINE, - 0, - totalBars, - valesBuffer - // - ); - - // - // CURRENT ... - - // - // HH ... - CopyBuffer( - mHandler, - X121_CURRENT_HH_LINE, - 0, - totalBars, - cHHBuffer - // - ); - - // - // LL ... - CopyBuffer( - mHandler, - X121_CURRENT_LL_LINE, - 0, - totalBars, - cLLBuffer - // - ); - - // - // SHORT ... - - // - // HH ... - CopyBuffer( - mHandler, - X121_SHORT_HH_LINE, - 0, - totalBars, - sHHBuffer - // - ); - - // - // LL ... - CopyBuffer( - mHandler, - X121_SHORT_LL_LINE, - 0, - totalBars, - sLLBuffer - // - ); - - // - // MEDIUM ... - - // - // HH ... - CopyBuffer( - mHandler, - X121_MEDIUM_HH_LINE, - 0, - totalBars, - mHHBuffer - // - ); - - // - // LL ... - CopyBuffer( - mHandler, - X121_MEDIUM_LL_LINE, - 0, - totalBars, - mLLBuffer - // - ); - - // - // LONG ... - - // - // HH ... - CopyBuffer( - mHandler, - X121_LONG_HH_LINE, - 0, - totalBars, - lHHBuffer - // - ); - - // - // LL ... - CopyBuffer( - mHandler, - X121_LONG_LL_LINE, - 0, - totalBars, - lLLBuffer - // - ); - - // - // HIND ... - - // - // HH ... - CopyBuffer( - mHandler, - X121_HIND_HH_LINE, - 0, - totalBars, - hHHBuffer - // - ); - - // - // LL ... - CopyBuffer( - mHandler, - X121_HIND_LL_LINE, - 0, - totalBars, - hLLBuffer - // - ); - - // - // XVWAP ... - - // - // FAST ... - CopyBuffer( - mHandler, - X121_VWAP_FAST_LINE, - 0, - totalBars, - vwapFastBuffer - // - ); - - // - // FAST STATE ... - CopyBuffer( - mHandler, - X121_VWAP_FAST_STATE_LINE, - 0, - totalBars, - vwapFastStateBuffer - // - ); - - // - // MID ... - CopyBuffer( - mHandler, - X121_VWAP_MID_LINE, - 0, - totalBars, - vwapMidBuffer - // - ); - - // - // MID STATE ... - CopyBuffer( - mHandler, - X121_VWAP_MID_STATE_LINE, - 0, - totalBars, - vwapMidStateBuffer - // - ); - - // - // SLOW ... - CopyBuffer( - mHandler, - X121_VWAP_SLOW_LINE, - 0, - totalBars, - vwapSlowBuffer - // - ); - - // - // SLOW STATE ... - CopyBuffer( - mHandler, - X121_VWAP_SLOW_STATE_LINE, - 0, - totalBars, - vwapSlowStateBuffer - // - ); - - // - // VOLUME ... - CopyBuffer( - mHandler, - X121_VWAP_VOLUME_LINE, - 0, - totalBars, - vwapVolumeBuffer - // - ); - - // - // PRICE ... - CopyBuffer( - mHandler, - X121_VWAP_PRICE_LINE, - 0, - totalBars, - vwapPriceBuffer - // - ); - - // - // XDON ... - - // - // OPEN ... - - // - // Upper ... - CopyBuffer( - mHandler, - X121_DON_OPEN_UPPER_LINE, - 0, - totalBars, - donOpenUpperBuffer - // - ); - - // - // Lower ... - CopyBuffer( - mHandler, - X121_DON_OPEN_LOWER_LINE, - 0, - totalBars, - donOpenLowerBuffer - // - ); - - // - // CLOSE ... - - // - // Upper ... - CopyBuffer( - mHandler, - X121_DON_CLOSE_UPPER_LINE, - 0, - totalBars, - donCloseUpperBuffer - // - ); - - // - // Lower ... - CopyBuffer( - mHandler, - X121_DON_CLOSE_LOWER_LINE, - 0, - totalBars, - donCloseLowerBuffer - // - ); - - // - // HIGH ... - - // - // Upper ... - CopyBuffer( - mHandler, - X121_DON_HIGH_UPPER_LINE, - 0, - totalBars, - donHighUpperBuffer - // - ); - - // - // Lower ... - CopyBuffer( - mHandler, - X121_DON_HIGH_LOWER_LINE, - 0, - totalBars, - donHighLowerBuffer - // - ); - - // - // LOW ... - - // - // Upper ... - CopyBuffer( - mHandler, - X121_DON_LOW_UPPER_LINE, - 0, - totalBars, - donLowUpperBuffer - // - ); - - // - // Lower ... - CopyBuffer( - mHandler, - X121_DON_LOW_LOWER_LINE, - 0, - totalBars, - donLowLowerBuffer - // - ); - } + // Inputs ... + X121Inputs mInputs; + X121XPVInputs xpvInputs; + X121XATRInputs xatrInputs; + X121XDONInputs xdonInputs; + X121XSTRInputs xstrInputs; + X121XVWAPInputs xvwapInputs; }; // \ No newline at end of file diff --git a/Helpers/x-saherelm.x121.xatr.helper.mq5 b/Helpers/x-saherelm.x121.xatr.helper.mq5 new file mode 100644 index 00000000..6833cf82 --- /dev/null +++ b/Helpers/x-saherelm.x121.xatr.helper.mq5 @@ -0,0 +1,1205 @@ +/////////////////////////////////////////////////////// +// +// SaherElm IT Center MQL5 Helper Class Library +// ---------------------------------------------- +// Name: XCX121XATRHelper +// Description: provides all Indicator +// Helper requirements ... +// +// +// 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 + +// +// Imports ... +#include "../Classes/x-saherelm.x-helper.class.mq5" + +// +// Definitions ... + +// +// Definitions ... +enum ENUM_X121_XATR_BUFFERS +{ + // + X121_ATR_UPPER_LINE = 0, + X121_ATR_LOWER_LINE = 1, + X121_ATR_LINE = 2, + X121_ATR_UPPER_RAW_LINE = 3, + X121_ATR_LOWER_RAW_LINE = 4, + X121_RSI_LINE = 5, +}; + +// +// Input Models ... +struct X121XATRInputs +{ + // + // Props ... + + // + // RSI ... + int rsiLength; // Length + double rsiOverSoldLevel; // Over Sold Level + double rsiOverBoughtLevel; // Over Bought Level + ENUM_APPLIED_PRICE rsiAppliedTo; // Applied To + + // + // ATR Detection ... + int atrLength; // Length + double atrMultiplier; // Multiplier + ENUM_APPLIED_PRICE atrUpperAppliedTo; // Upper Zone Applied To + ENUM_APPLIED_PRICE atrLowerAppliedTo; // Lower Zone Applied To + ENUM_X_MA_METHOD atrSmoothingMode; // Smoothing Method + + // + int startCalculationForLastBars; // Calculate Last n Bars + + // + bool showATRUpper; // Show Upper Zone + bool showATRLower; // Show Lower Zone + + // + // Constructor(s) ... + X121XATRInputs() + { + // + Clean(); + } + + // + // Tools ... + + // + // Clean ... + void Clean() + { + // + // RSI ... + rsiLength = 0; + rsiOverSoldLevel = 0; + rsiOverBoughtLevel = 0; + rsiAppliedTo = PRICE_CLOSE; + + // + // ATR ... + atrLength = 0; // Length + atrMultiplier = 0; // Multiplier + atrUpperAppliedTo = PRICE_HIGH; // Upper Zone Applied To + atrLowerAppliedTo = PRICE_LOW; // Lower Zone Applied To + atrSmoothingMode = X_MA_MODE_NONE; // Smoothing Method + + // + startCalculationForLastBars = 0; + + // + showATRUpper = false; // Show Upper Zone + showATRLower = false; // Show Lower Zone + } + + // + // Default ... + void Default() + { + // + // RSI ... + rsiLength = 14; + rsiOverSoldLevel = 30; + rsiOverBoughtLevel = 70; + rsiAppliedTo = PRICE_CLOSE; + + // + // ATR ... + atrLength = 14; // Length + atrMultiplier = 1; // Multiplier + atrUpperAppliedTo = PRICE_HIGH; // Upper Zone Applied To + atrLowerAppliedTo = PRICE_LOW; // Lower Zone Applied To + atrSmoothingMode = X_MA_MODE_EMA; // Smoothing Method + + // + startCalculationForLastBars = 1500; + showATRUpper = true; // Show Upper Zone + showATRLower = true; // Show Lower Zone + } + + // + // Validate ... + bool IsValid() + { + // + bool result = false; + + // + result = + // + atrLength > 0 && + rsiLength > 0 && + atrMultiplier > 0 && + rsiOverSoldLevel > 0 && + rsiOverBoughtLevel > 0 && + startCalculationForLastBars > 0 && + rsiOverSoldLevel < rsiOverBoughtLevel + // + ; + + // + return result; + } + + // + // Retrieve MAx Length ... + int Max() + { + // + int result = 0; + + // + result = MathMax(atrLength, rsiLength); + + // + return result; + } +}; + +// +// Conditions ... +struct X121XATRConditions +{ + // + // Common ... + string symbol; + ENUM_TIMEFRAMES period; + datetime time; + + // + // Buffers ... + double atrUpperBuffer[]; + double atrLowerBuffer[]; + double atrUpperRawBuffer[]; + double atrLowerRawBuffer[]; + double rsiBuffer[]; + double atrBuffer[]; + + // + // Conditions ... + + // + // RSI ... + + // + bool isRSIOverBought; + bool isRSICrossedOverOverBought; + bool isRSICrossedUnderOverBought; + + // + bool isRSIOverSold; + bool isRSICrossedUnderOverSold; + bool isRSICrossedOverOverSold; + + // + // ATR ... + + // + bool isCloseOverATRUper; + bool isCloseOverATRLower; + + // + bool isCloseUnderATRUpper; + bool isCloseUnderATRLower; + + // + bool isRejectUpATRUpper; + bool isRejectDownATRUpper; + + // + bool isRejectUpATRLower; + bool isRejectDownATRLower; + + // + bool isBreakUpATRUpper; + bool isBreakDownATRUpper; + + // + bool isBreakUpATRLower; + bool isBreakDownATRLower; + + // + // bool isCloseLower + + // + // Constructor ... + X121XATRConditions() + { + Clean(); + } + + // + // Tools ... + + /** + * Cleaning Up ... + */ + void Clean() + { + // + // Commons ... + symbol = NULL; + period = NULL; + time = NULL; + + // + // Buffers ... + + // + Clean(rsiBuffer); + Clean(atrBuffer); + Clean(atrUpperBuffer); + Clean(atrLowerBuffer); + Clean(atrUpperRawBuffer); + Clean(atrLowerRawBuffer); + + // + ArraySetAsSeries(rsiBuffer, true); + ArraySetAsSeries(atrBuffer, true); + ArraySetAsSeries(atrUpperBuffer, true); + ArraySetAsSeries(atrLowerBuffer, true); + ArraySetAsSeries(atrUpperRawBuffer, true); + ArraySetAsSeries(atrLowerRawBuffer, true); + + // + // Conditions ... + + // + // RSI ... + + // + isRSIOverBought = false; + isRSICrossedOverOverBought = false; + isRSICrossedUnderOverBought = false; + + // + isRSIOverSold = false; + isRSICrossedUnderOverSold = false; + isRSICrossedOverOverSold = false; + + // + // ATR ... + + // + isCloseOverATRUper = false; + isCloseOverATRLower = false; + + // + isCloseUnderATRUpper = false; + isCloseUnderATRLower = false; + + // + isRejectUpATRUpper = false; + isRejectDownATRUpper = false; + + // + isRejectUpATRLower = false; + isRejectDownATRLower = false; + + // + isBreakUpATRUpper = false; + isBreakDownATRUpper = false; + + // + isBreakUpATRLower = false; + isBreakDownATRLower = false; + + // + // XDON ... + } + + /** + * Generate Conditions Scores ... + * + * @param bullishScore: Double, Directional Scores Reference ... + * @param bearishScore: Double, Directional Scores Reference ... + */ + void GenerateScore( + double &bullishScore, + double &bearishScore // + ) + { + // + bullishScore = 0; + bearishScore = 0; + + // + // TODO: Implement if Required ... + } + + /** + * Generate Summary String for Represent Conditions State ... + * + * @param onlyCommons: Boolean, Just Generate Only Commons Conditions ... + * @param onlyConditions: Boolean, Just Generate Only Conditions ... + * @param includeScores: Boolean, Attach Scores Representations on Result ... + * @param ignoreFalseConditions: Boolean, Ignore False Conditions on Result ... + * @param separator: String, Separate Lines ... + * + * @return ( string ) + */ + string GenerateSummary( + bool onlyCommons = false, + bool onlyConditions = false, + bool includeScores = true, + bool ignoreFalseConditions = true, + string separator = "\n" // + ) + { + // + string result = NULL; + + // + double bullishScore = 0; + double bearishScore = 0; + GenerateScore( + bullishScore, + bearishScore // + ); + + // + string scoresStr = + // + "Scores: " + separator + + "---------------" + separator + + "Bullish: " + ToString(bullishScore) + separator + + "Bearish: " + ToString(bearishScore) + separator + + "" + // + ; + + // + string commonStr = GenerateSpecifiedCommonSummary( + this, + separator, + includeScores // + ); + + // + string conditionsStr = + // + // RSI ... + ToString("isRSIOverBought", isRSIOverBought, ignoreFalseConditions, separator) + + ToString("isRSICrossedOverOverBought", isRSICrossedOverOverBought, ignoreFalseConditions, separator) + + ToString("isRSICrossedUnderOverBought", isRSICrossedUnderOverBought, ignoreFalseConditions, separator) + + ToString("isRSIOverSold", isRSIOverSold, ignoreFalseConditions, separator) + + ToString("isRSICrossedUnderOverSold", isRSICrossedUnderOverSold, ignoreFalseConditions, separator) + + ToString("isRSICrossedOverOverSold", isRSICrossedOverOverSold, ignoreFalseConditions, separator) + + // + // ATR ... + ToString("isCloseOverATRUper", isCloseOverATRUper, ignoreFalseConditions, separator) + + ToString("isCloseOverATRLower", isCloseOverATRLower, ignoreFalseConditions, separator) + + ToString("isCloseUnderATRUpper", isCloseUnderATRUpper, ignoreFalseConditions, separator) + + ToString("isCloseUnderATRLower", isCloseUnderATRLower, ignoreFalseConditions, separator) + + ToString("isRejectUpATRUpper", isRejectUpATRUpper, ignoreFalseConditions, separator) + + ToString("isRejectDownATRUpper", isRejectDownATRUpper, ignoreFalseConditions, separator) + + ToString("isRejectUpATRLower", isRejectUpATRLower, ignoreFalseConditions, separator) + + ToString("isRejectDownATRLower", isRejectDownATRLower, ignoreFalseConditions, separator) + + ToString("isBreakUpATRUpper", isBreakUpATRUpper, ignoreFalseConditions, separator) + + ToString("isBreakDownATRUpper", isBreakDownATRUpper, ignoreFalseConditions, separator) + + ToString("isBreakUpATRLower", isBreakUpATRLower, ignoreFalseConditions, separator) + + ToString("isBreakDownATRLower", isBreakDownATRLower, ignoreFalseConditions, separator) + + // + "" + // + ; + + // + result = + // + "[" + GetTag() + "]" + separator + + (onlyConditions + ? "" + : commonStr) + + (!includeScores + ? "" + : scoresStr) + + " " + separator + + (onlyCommons + ? "" + : conditionsStr) + + "" + // + ; + + // + return result; + } + + /** + * Retrieve nique Tag Identifier ... + * + * @return ( string ) + */ + string GetTag() + { + return GetTypeName(this); + } + + // +}; + +// +// Class ... +class XCX121XATRHelper : public XCBaseHelper +{ + // + // Public ... + public: + // + // Props ... + + // + // Constructors ... + XCX121XATRHelper() + : XCBaseHelper(_Symbol, _Period) + { + } + + // + // Deconstructor ... + ~XCX121XATRHelper() + { + } + + // + // Tools ... + bool Init( + string symbol, // Trading Symbol + ENUM_TIMEFRAMES period, // Trading Period + X121XATRInputs &inputs // Inputs + ) + { + // + bool result = false; + + // + mSymbol = symbol; + mPeriod = period; + + // + result = inputs.IsValid(); + if (!result) + { + return result; + } + + // + ArraySetAsSeries(rsiBuffer, true); + ArraySetAsSeries(atrUpperBuffer, true); + ArraySetAsSeries(atrLowerBuffer, true); + ArraySetAsSeries(atrBuffer, true); + ArraySetAsSeries(atrUpperRawBuffer, true); + ArraySetAsSeries(atrLowerRawBuffer, true); + + // + mInputs = inputs; + + // + mHandler = iCustom( + mSymbol, + mPeriod, + "x-saherelm.x121.xatr", + // + // Inputs ... + // + // Market ... + "", + // + // RSI Detection ... + "", + mInputs.rsiLength, + mInputs.rsiAppliedTo, + // + // ATR Detection ... + "", + mInputs.atrLength, + mInputs.atrMultiplier, + mInputs.atrUpperAppliedTo, + mInputs.atrLowerAppliedTo, + mInputs.atrSmoothingMode, + // + // Presentation ... + "", + mInputs.startCalculationForLastBars, + mInputs.showATRUpper, + mInputs.showATRLower + // + ); + result = mHandler != INVALID_HANDLE; + if (!result) + { + return result; + } + + // + return result; + } + + // + // Inputs ... + + // + X121XATRInputs GetInputs() + { + return mInputs; + } + + // + bool SetInputs( + X121XATRInputs &inputs // Configs + ) + { + // + return Init( + mSymbol, + mPeriod, + inputs + // + ); + } + + // + // Readers ... + + // + // RSI ... + + // + double GetRSI( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(rsiBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return rsiBuffer[barIndex]; + } + + // + int CopyRSI( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + rsiBuffer, + buffer, + forceClean + // + ); + } + + // + // ATR ... + + // + double GetATR( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(atrBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return atrBuffer[barIndex]; + } + + // + int CopyATR( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + atrBuffer, + buffer, + forceClean + // + ); + } + + // + double GetATRUpper( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(atrUpperBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return atrUpperBuffer[barIndex]; + } + + // + int CopyATRUpper( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + atrUpperBuffer, + buffer, + forceClean + // + ); + } + + // + double GetATRUpperRaw( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(atrUpperRawBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return atrUpperRawBuffer[barIndex]; + } + + // + int CopyATRUpperRaw( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + atrUpperRawBuffer, + buffer, + forceClean + // + ); + } + + // + double GetATRLower( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(atrLowerBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return atrLowerBuffer[barIndex]; + } + + // + int CopyATRLower( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + atrLowerBuffer, + buffer, + forceClean + // + ); + } + + // + double GetATRLowerRaw( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(atrLowerRawBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return atrLowerRawBuffer[barIndex]; + } + + // + int CopyATRLowerRaw( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + atrLowerRawBuffer, + buffer, + forceClean + // + ); + } + + // + bool GetConditions( + X121XATRConditions &conditions, // + int barIndex = 0, // + int loopback = 5 // + ) + { + // + bool result = true; + + // + if (loopback < 5) + { + loopback = 5; + } + + // + conditions.Clean(); + + // + conditions.symbol = mSymbol; + conditions.period = mPeriod; + conditions.time = TimeCurrent(); + + // + int zIndex = barIndex; + int cIndex = zIndex + 1; + int pIndex = cIndex + 1; + int ppIndex = pIndex + 1; + + // + XOHCL zBar; + result = zBar.Init( + mSymbol, + mPeriod, + zIndex // + ); + if (!result) + { + return result; + } + + // + XOHCL cBar; + result = cBar.Init( + mSymbol, + mPeriod, + cIndex // + ); + if (!result) + { + return result; + } + + // + XOHCL pBar; + result = pBar.Init( + mSymbol, + mPeriod, + pIndex // + ); + if (!result) + { + return result; + } + + // + // Buffers ... + + // + CopyRSI( + zIndex, + loopback, + conditions.rsiBuffer // + ); + + // + CopyATR( + zIndex, + loopback, + conditions.atrBuffer // + ); + + // + CopyATRUpper( + zIndex, + loopback, + conditions.atrUpperBuffer // + ); + + // + CopyATRUpperRaw( + zIndex, + loopback, + conditions.atrUpperRawBuffer // + ); + + // + CopyATRLower( + zIndex, + loopback, + conditions.atrLowerBuffer // + ); + + // + CopyATRLowerRaw( + zIndex, + loopback, + conditions.atrLowerRawBuffer // + ); + + // + // Conditions ... + + // + int cIDX = 1; + int pIDX = cIDX + 1; + + // + // RSI ... + + // + bool isRSIOverBought = conditions.rsiBuffer[cIDX] > mInputs.rsiOverBoughtLevel; + bool isRSIOverBoughtPrev = conditions.rsiBuffer[pIDX] > mInputs.rsiOverBoughtLevel; + + // + bool isRSICrossedOverOverBought = isRSIOverBought && + !isRSIOverBoughtPrev; + bool isRSICrossedUnderOverBought = !isRSIOverBought && + isRSIOverBoughtPrev; + + // + bool isRSIOverSold = conditions.rsiBuffer[cIDX] < mInputs.rsiOverSoldLevel; + bool isRSIOverSoldPrev = conditions.rsiBuffer[pIDX] < mInputs.rsiOverSoldLevel; + + // + bool isRSICrossedUnderOverSold = isRSIOverSold && + !isRSIOverSoldPrev; + bool isRSICrossedOverOverSold = !isRSIOverSold && + isRSIOverSoldPrev; + + // + // ATR ... + + // + bool isCloseOverATRUper = cBar.close > conditions.atrUpperBuffer[cIDX]; + bool isCloseOverATRLower = cBar.close > conditions.atrLowerBuffer[cIDX]; + + // + bool isCloseUnderATRUpper = cBar.close < conditions.atrUpperBuffer[cIDX]; + bool isCloseUnderATRLower = cBar.close < conditions.atrLowerBuffer[cIDX]; + + // + bool isRejectUpATRUpper = IsBarReject( + atrUpperBuffer[cIDX], + X_DIRECTION_BULLISH, + cBar // + ); + bool isRejectDownATRUpper = IsBarReject( + atrUpperBuffer[cIDX], + X_DIRECTION_BEARISH, + cBar // + ); + + // + bool isRejectUpATRLower = IsBarReject( + atrLowerBuffer[cIDX], + X_DIRECTION_BULLISH, + cBar // + ); + ; + bool isRejectDownATRLower = IsBarReject( + atrLowerBuffer[cIDX], + X_DIRECTION_BEARISH, + cBar // + ); + ; + + // + bool isBreakUpATRUpper = IsBarBreak( + atrUpperBuffer[cIDX], + X_DIRECTION_BULLISH, + cBar // + ); + bool isBreakDownATRUpper = IsBarBreak( + atrUpperBuffer[cIDX], + X_DIRECTION_BEARISH, + cBar // + ); + + // + bool isBreakUpATRLower = IsBarBreak( + atrLowerBuffer[cIDX], + X_DIRECTION_BULLISH, + cBar // + ); + bool isBreakDownATRLower = IsBarBreak( + atrLowerBuffer[cIDX], + X_DIRECTION_BEARISH, + cBar // + ); + + // + conditions.isRSIOverSold = isRSIOverSold; + conditions.isRSIOverBought = isRSIOverBought; + conditions.isRejectUpATRUpper = isRejectUpATRUpper; + conditions.isRejectUpATRLower = isRejectUpATRLower; + conditions.isBreakUpATRUpper = isBreakUpATRUpper; + conditions.isBreakUpATRLower = isBreakUpATRLower; + conditions.isRejectDownATRUpper = isRejectDownATRUpper; + conditions.isRejectDownATRLower = isRejectDownATRLower; + conditions.isCloseOverATRUper = isCloseOverATRUper; + conditions.isCloseOverATRLower = isCloseOverATRLower; + conditions.isBreakDownATRUpper = isBreakDownATRUpper; + conditions.isBreakDownATRLower = isBreakDownATRLower; + conditions.isCloseUnderATRUpper = isCloseUnderATRUpper; + conditions.isCloseUnderATRLower = isCloseUnderATRLower; + conditions.isRSICrossedOverOverSold = isRSICrossedOverOverSold; + conditions.isRSICrossedUnderOverSold = isRSICrossedUnderOverSold; + conditions.isRSICrossedOverOverBought = isRSICrossedOverOverBought; + conditions.isRSICrossedUnderOverBought = isRSICrossedUnderOverBought; + + // + return result; + } + + // + // Protected ... + protected: + // + // Private ... + private: + // + // Props ... + X121XATRInputs mInputs; // Inputs ... + + // + // Buffers ... + double rsiBuffer[]; + double atrUpperBuffer[]; + double atrLowerBuffer[]; + double atrBuffer[]; + double atrUpperRawBuffer[]; + double atrLowerRawBuffer[]; + + // + void Calculate() + { + // + int totalBars = CountBars(); + if (totalBars > 1000) + { + totalBars = 1000; + } + + // + // Buffers ... + + // + // RSI ... + CopyBuffer( + mHandler, + X121_RSI_LINE, + 0, + totalBars, + rsiBuffer + // + ); + + // + // ATR ... + + // + CopyBuffer( + mHandler, + X121_ATR_UPPER_LINE, + 0, + totalBars, + atrUpperBuffer + // + ); + + // + CopyBuffer( + mHandler, + X121_ATR_LOWER_LINE, + 0, + totalBars, + atrLowerBuffer + // + ); + + // + CopyBuffer( + mHandler, + X121_ATR_LINE, + 0, + totalBars, + atrBuffer + // + ); + + // + CopyBuffer( + mHandler, + X121_ATR_UPPER_RAW_LINE, + 0, + totalBars, + atrUpperRawBuffer + // + ); + + // + CopyBuffer( + mHandler, + X121_ATR_LOWER_RAW_LINE, + 0, + totalBars, + atrLowerRawBuffer + // + ); + } +}; + +// +// Tools ... \ No newline at end of file diff --git a/Helpers/x-saherelm.x121.xdon.helper.mq5 b/Helpers/x-saherelm.x121.xdon.helper.mq5 new file mode 100644 index 00000000..32ba9d78 --- /dev/null +++ b/Helpers/x-saherelm.x121.xdon.helper.mq5 @@ -0,0 +1,1325 @@ +/////////////////////////////////////////////////////// +// +// SaherElm IT Center MQL5 Helper Class Library +// ---------------------------------------------- +// Name: XCX121XDONHelper +// Description: provides all Indicator +// Helper requirements ... +// +// +// 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 + +// +// Imports ... +#include "../Classes/x-saherelm.x-helper.class.mq5" + +// +// Definitions ... + +// +// Definitions ... +enum ENUM_X121_XDON_BUFFERS +{ + // + X121_XDON_OPEN_UPPER_LINE = 0, + X121_XDON_OPEN_LOWER_LINE = 1, + X121_XDON_HIGH_UPPER_LINE = 2, + X121_XDON_HIGH_LOWER_LINE = 3, + X121_XDON_LOW_UPPER_LINE = 4, + X121_XDON_LOW_LOWER_LINE = 5, + X121_XDON_CLOSE_UPPER_LINE = 6, + X121_XDON_CLOSE_LOWER_LINE = 7, +}; + +// +// Input Models ... +struct X121XDONInputs +{ + // + // Props ... + + // + int donchainLength; // Donchain Length + + // + int startCalculationForLastBars; // Calculate Last n Bars + + // + bool showUpper; // Show Upper Band + bool showLower; // Show Lower Band + + // + bool showOpen; // Show Open + bool showHigh; // Show High + bool showClose; // Show Close + bool showLow; // Show Low + + // + // Constructor(s) ... + X121XDONInputs() + { + // + Clean(); + } + + // + // Tools ... + + // + // Clean ... + void Clean() + { + // + donchainLength = 0; + + // + startCalculationForLastBars = 0; + + // + showUpper = false; + showLower = false; + + // + showOpen = false; + showHigh = false; + showClose = false; + showLow = false; + } + + // + // Default ... + void Default() + { + // + donchainLength = 40; + + // + startCalculationForLastBars = 1000; + + // + showUpper = true; + showLower = true; + + // + showOpen = true; + showHigh = true; + showClose = true; + showLow = true; + } + + // + // Validate ... + bool IsValid() + { + // + bool result = false; + + // + result = + // + donchainLength > 0 + // + ; + + // + return result; + } + + // + // Retrieve MAx Length ... + int Max() + { + // + int result = 0; + + // + result = MathMax(1, donchainLength); + + // + return result; + } +}; + +// +// Conditions ... +struct X121XDONConditions +{ + // + // Common ... + string symbol; + ENUM_TIMEFRAMES period; + datetime time; + + // + // Buffers ... + double donOpenUpperBuffer[]; + double donOpenLowerBuffer[]; + double donHighUpperBuffer[]; + double donHighLowerBuffer[]; + double donLowUpperBuffer[]; + double donLowLowerBuffer[]; + double donCloseUpperBuffer[]; + double donCloseLowerBuffer[]; + + // + // Conditions ... + + // + bool isRejectDonOpenUpper; + bool isRejectDonHighUpper; + bool isRejectDonLowUpper; + bool isRejectDonCloseUpper; + + // + bool isRejectDonOpenLower; + bool isRejectDonHighLower; + bool isRejectDonLowLower; + bool isRejectDonCloseLower; + + // + bool isBreakDonOpenUpper; + bool isBreakDonHighUpper; + bool isBreakDonLowUpper; + bool isBreakDonCloseUpper; + + // + bool isBreakDonOpenLower; + bool isBreakDonHighLower; + bool isBreakDonLowLower; + bool isBreakDonCloseLower; + + // + // Constructor ... + X121XDONConditions() + { + Clean(); + } + + // + // Tools ... + + /** + * Cleaning Up ... + */ + void Clean() + { + // + // Commons ... + symbol = NULL; + period = NULL; + time = NULL; + + // + // Buffers ... + + // + Clean(donOpenUpperBuffer); + Clean(donOpenLowerBuffer); + Clean(donHighUpperBuffer); + Clean(donHighLowerBuffer); + Clean(donLowUpperBuffer); + Clean(donLowLowerBuffer); + Clean(donCloseUpperBuffer); + Clean(donCloseLowerBuffer); + + // + ArraySetAsSeries(donOpenUpperBuffer, true); + ArraySetAsSeries(donOpenLowerBuffer, true); + ArraySetAsSeries(donHighUpperBuffer, true); + ArraySetAsSeries(donHighLowerBuffer, true); + ArraySetAsSeries(donLowUpperBuffer, true); + ArraySetAsSeries(donLowLowerBuffer, true); + ArraySetAsSeries(donCloseUpperBuffer, true); + ArraySetAsSeries(donCloseLowerBuffer, true); + + // + // Conditions ... + + // + isRejectDonOpenUpper = false; + isRejectDonHighUpper = false; + isRejectDonLowUpper = false; + isRejectDonCloseUpper = false; + + // + isRejectDonOpenLower = false; + isRejectDonHighLower = false; + isRejectDonLowLower = false; + isRejectDonCloseLower = false; + + // + isBreakDonOpenUpper = false; + isBreakDonHighUpper = false; + isBreakDonLowUpper = false; + isBreakDonCloseUpper = false; + + // + isBreakDonOpenLower = false; + isBreakDonHighLower = false; + isBreakDonLowLower = false; + isBreakDonCloseLower = false; + } + + /** + * Generate Conditions Scores ... + * + * @param bullishScore: Double, Directional Scores Reference ... + * @param bearishScore: Double, Directional Scores Reference ... + */ + void GenerateScore( + double &bullishScore, + double &bearishScore // + ) + { + // + bullishScore = 0; + bearishScore = 0; + + // + // TODO: Implement if Required ... + } + + /** + * Generate Summary String for Represent Conditions State ... + * + * @param onlyCommons: Boolean, Just Generate Only Commons Conditions ... + * @param onlyConditions: Boolean, Just Generate Only Conditions ... + * @param includeScores: Boolean, Attach Scores Representations on Result ... + * @param ignoreFalseConditions: Boolean, Ignore False Conditions on Result ... + * @param separator: String, Separate Lines ... + * + * @return ( string ) + */ + string GenerateSummary( + bool onlyCommons = false, + bool onlyConditions = false, + bool includeScores = true, + bool ignoreFalseConditions = true, + string separator = "\n" // + ) + { + // + string result = NULL; + + // + double bullishScore = 0; + double bearishScore = 0; + GenerateScore( + bullishScore, + bearishScore // + ); + + // + string scoresStr = + // + "Scores: " + separator + + "---------------" + separator + + "Bullish: " + ToString(bullishScore) + separator + + "Bearish: " + ToString(bearishScore) + separator + + "" + // + ; + + // + string commonStr = GenerateSpecifiedCommonSummary( + this, + separator, + includeScores // + ); + + // + string conditionsStr = + // + ToString("isRejectDonOpenUpper", isRejectDonOpenUpper, ignoreFalseConditions, separator) + + ToString("isRejectDonHighUpper", isRejectDonHighUpper, ignoreFalseConditions, separator) + + ToString("isRejectDonLowUpper", isRejectDonLowUpper, ignoreFalseConditions, separator) + + ToString("isRejectDonCloseUpper", isRejectDonCloseUpper, ignoreFalseConditions, separator) + + // + ToString("isRejectDonOpenLower", isRejectDonOpenLower, ignoreFalseConditions, separator) + + ToString("isRejectDonHighLower", isRejectDonHighLower, ignoreFalseConditions, separator) + + ToString("isRejectDonLowLower", isRejectDonLowLower, ignoreFalseConditions, separator) + + ToString("isRejectDonCloseLower", isRejectDonCloseLower, ignoreFalseConditions, separator) + + // + ToString("isBreakDonOpenUpper", isBreakDonOpenUpper, ignoreFalseConditions, separator) + + ToString("isBreakDonHighUpper", isBreakDonHighUpper, ignoreFalseConditions, separator) + + ToString("isBreakDonLowUpper", isBreakDonLowUpper, ignoreFalseConditions, separator) + + ToString("isBreakDonCloseUpper", isBreakDonCloseUpper, ignoreFalseConditions, separator) + + // + ToString("isBreakDonOpenLower", isBreakDonOpenLower, ignoreFalseConditions, separator) + + ToString("isBreakDonHighLower", isBreakDonHighLower, ignoreFalseConditions, separator) + + ToString("isBreakDonLowLower", isBreakDonLowLower, ignoreFalseConditions, separator) + + ToString("isBreakDonCloseLower", isBreakDonCloseLower, ignoreFalseConditions, separator) + + // + "" + // + ; + + // + result = + // + "[" + GetTag() + "]" + separator + + (onlyConditions + ? "" + : commonStr) + + (!includeScores + ? "" + : scoresStr) + + " " + separator + + (onlyCommons + ? "" + : conditionsStr) + + "" + // + ; + + // + return result; + } + + /** + * Retrieve nique Tag Identifier ... + * + * @return ( string ) + */ + string GetTag() + { + return GetTypeName(this); + } + + // +}; + +// +// Class ... +class XCX121XDONHelper : public XCBaseHelper +{ + // + // Public ... + public: + // + // Props ... + + // + // Constructors ... + XCX121XDONHelper() + : XCBaseHelper(_Symbol, _Period) + { + } + + // + // Deconstructor ... + ~XCX121XDONHelper() + { + } + + // + // Tools ... + bool Init( + string symbol, // Trading Symbol + ENUM_TIMEFRAMES period, // Trading Period + X121XDONInputs &inputs // Inputs + ) + { + // + bool result = false; + + // + mSymbol = symbol; + mPeriod = period; + + // + result = inputs.IsValid(); + if (!result) + { + return result; + } + + // + ArraySetAsSeries(donOpenUpperBuffer, true); + ArraySetAsSeries(donOpenLowerBuffer, true); + ArraySetAsSeries(donHighUpperBuffer, true); + ArraySetAsSeries(donHighLowerBuffer, true); + ArraySetAsSeries(donLowUpperBuffer, true); + ArraySetAsSeries(donLowLowerBuffer, true); + ArraySetAsSeries(donCloseUpperBuffer, true); + ArraySetAsSeries(donCloseLowerBuffer, true); + + // + mInputs = inputs; + + // + mHandler = iCustom( + mSymbol, + mPeriod, + "x-saherelm.x121.xdon", + // + // Inputs ... + // + // Market ... + "", + mInputs.donchainLength, + // + // Presentation ... + "", + mInputs.startCalculationForLastBars, + // + mInputs.showUpper, + mInputs.showLower, + // + mInputs.showOpen, + mInputs.showHigh, + mInputs.showClose, + mInputs.showLow + // + ); + result = mHandler != INVALID_HANDLE; + if (!result) + { + return result; + } + + // + return result; + } + + // + // Inputs ... + + // + X121XDONInputs GetInputs() + { + return mInputs; + } + + // + bool SetInputs( + X121XDONInputs &inputs // Configs + ) + { + // + return Init( + mSymbol, + mPeriod, + inputs + // + ); + } + + // + // Readers ... + + // + // OPEN ... + + // + // UPPER ... + + // + double GetDonOpenUpper( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(donOpenUpperBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return donOpenUpperBuffer[barIndex]; + } + + // + int CopyDonOpenUpper( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + donOpenUpperBuffer, + buffer, + forceClean + // + ); + } + + // + // LOWER ... + + // + double GetDonOpenLower( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(donOpenLowerBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return donOpenLowerBuffer[barIndex]; + } + + // + int CopyDonOpenLower( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + donOpenLowerBuffer, + buffer, + forceClean + // + ); + } + + // + // CLOSE ... + + // + // UPPER ... + + // + double GetDonCloseUpper( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(donCloseUpperBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return donCloseUpperBuffer[barIndex]; + } + + // + int CopyDonCloseUpper( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + donCloseUpperBuffer, + buffer, + forceClean + // + ); + } + + // + // LOWER ... + + // + double GetDonCloseLower( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(donCloseLowerBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return donCloseLowerBuffer[barIndex]; + } + + // + int CopyDonCloseLower( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + donCloseLowerBuffer, + buffer, + forceClean + // + ); + } + + // + // HIGH ... + + // + // UPPER ... + + // + double GetDonHighUpper( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(donHighUpperBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return donHighUpperBuffer[barIndex]; + } + + // + int CopyDonHighUpper( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + donHighUpperBuffer, + buffer, + forceClean + // + ); + } + + // + // LOWER ... + + // + double GetDonHighLower( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(donHighLowerBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return donHighLowerBuffer[barIndex]; + } + + // + int CopyDonHighLower( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + donHighLowerBuffer, + buffer, + forceClean + // + ); + } + + // + // LOW ... + + // + // UPPER ... + + // + double GetDonLowUpper( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(donLowUpperBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return donLowUpperBuffer[barIndex]; + } + + // + int CopyDonLowUpper( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + donLowUpperBuffer, + buffer, + forceClean + // + ); + } + + // + // LOWER ... + + // + double GetDonLoweLower( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(donLowLowerBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return donLowLowerBuffer[barIndex]; + } + + // + int CopyDonLoweLower( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + donLowLowerBuffer, + buffer, + forceClean + // + ); + } + + // + bool GetConditions( + X121XDONConditions &conditions, // + int barIndex = 0, // + int loopback = 5 // + ) + { + // + bool result = true; + + // + if (loopback < 5) + { + loopback = 5; + } + + // + conditions.Clean(); + + // + conditions.symbol = mSymbol; + conditions.period = mPeriod; + conditions.time = TimeCurrent(); + + // + int zIndex = barIndex; + int cIndex = zIndex + 1; + int pIndex = cIndex + 1; + int ppIndex = pIndex + 1; + + // + XOHCL zBar; + result = zBar.Init( + mSymbol, + mPeriod, + zIndex // + ); + if (!result) + { + return result; + } + + // + XOHCL cBar; + result = cBar.Init( + mSymbol, + mPeriod, + cIndex // + ); + if (!result) + { + return result; + } + + // + XOHCL pBar; + result = pBar.Init( + mSymbol, + mPeriod, + pIndex // + ); + if (!result) + { + return result; + } + + // + // Buffers ... + + // + CopyDonOpenUpper( + zIndex, + loopback, + conditions.donOpenUpperBuffer // + ); + + // + CopyDonOpenLower( + zIndex, + loopback, + conditions.donOpenLowerBuffer // + ); + + // + CopyDonCloseUpper( + zIndex, + loopback, + conditions.donCloseUpperBuffer // + ); + + // + CopyDonCloseLower( + zIndex, + loopback, + conditions.donCloseLowerBuffer // + ); + + // + CopyDonHighUpper( + zIndex, + loopback, + conditions.donHighUpperBuffer // + ); + + // + CopyDonHighLower( + zIndex, + loopback, + conditions.donHighLowerBuffer // + ); + + // + CopyDonLowUpper( + zIndex, + loopback, + conditions.donLowUpperBuffer // + ); + + // + CopyDonLoweLower( + zIndex, + loopback, + conditions.donLowLowerBuffer // + ); + + // + // Conditions ... + + // + int cIDX = 1; + int pIDX = cIDX + 1; + + // + bool isRejectDonOpenUpper = IsBarReject( + donOpenUpperBuffer[cIDX], + X_DIRECTION_BEARISH, + cBar // + ); + bool isRejectDonHighUpper = IsBarReject( + donHighUpperBuffer[cIDX], + X_DIRECTION_BEARISH, + cBar // + ); + bool isRejectDonLowUpper = IsBarReject( + donLowUpperBuffer[cIDX], + X_DIRECTION_BEARISH, + cBar // + ); + bool isRejectDonCloseUpper = IsBarReject( + donCloseUpperBuffer[cIDX], + X_DIRECTION_BEARISH, + cBar // + ); + + // + bool isRejectDonOpenLower = IsBarReject( + donOpenLowerBuffer[cIDX], + X_DIRECTION_BULLISH, + cBar // + ); + bool isRejectDonHighLower = IsBarReject( + donHighLowerBuffer[cIDX], + X_DIRECTION_BULLISH, + cBar // + ); + bool isRejectDonLowLower = IsBarReject( + donLowLowerBuffer[cIDX], + X_DIRECTION_BULLISH, + cBar // + ); + bool isRejectDonCloseLower = IsBarReject( + donCloseLowerBuffer[cIDX], + X_DIRECTION_BULLISH, + cBar // + ); + + // + bool isBreakDonOpenUpper = IsBarBreak( + donOpenUpperBuffer[cIDX], + X_DIRECTION_BEARISH, + cBar // + ); + bool isBreakDonHighUpper = IsBarBreak( + donHighUpperBuffer[cIDX], + X_DIRECTION_BEARISH, + cBar // + ); + bool isBreakDonLowUpper = IsBarBreak( + donLowUpperBuffer[cIDX], + X_DIRECTION_BEARISH, + cBar // + ); + bool isBreakDonCloseUpper = IsBarBreak( + donCloseUpperBuffer[cIDX], + X_DIRECTION_BEARISH, + cBar // + ); + + // + bool isBreakDonOpenLower = IsBarBreak( + donOpenLowerBuffer[cIDX], + X_DIRECTION_BULLISH, + cBar // + ); + bool isBreakDonHighLower = IsBarBreak( + donHighLowerBuffer[cIDX], + X_DIRECTION_BULLISH, + cBar // + ); + bool isBreakDonLowLower = IsBarBreak( + donLowLowerBuffer[cIDX], + X_DIRECTION_BULLISH, + cBar // + ); + bool isBreakDonCloseLower = IsBarBreak( + donCloseLowerBuffer[cIDX], + X_DIRECTION_BULLISH, + cBar // + ); + + // + conditions.isBreakDonLowUpper = isBreakDonLowUpper; + conditions.isBreakDonLowLower = isBreakDonLowLower; + conditions.isRejectDonLowUpper = isRejectDonLowUpper; + conditions.isRejectDonLowLower = isRejectDonLowLower; + conditions.isBreakDonOpenUpper = isBreakDonOpenUpper; + conditions.isBreakDonHighUpper = isBreakDonHighUpper; + conditions.isBreakDonOpenLower = isBreakDonOpenLower; + conditions.isBreakDonHighLower = isBreakDonHighLower; + conditions.isRejectDonOpenUpper = isRejectDonOpenUpper; + conditions.isRejectDonOpenLower = isRejectDonOpenLower; + conditions.isRejectDonHighUpper = isRejectDonHighUpper; + conditions.isRejectDonHighLower = isRejectDonHighLower; + conditions.isBreakDonCloseUpper = isBreakDonCloseUpper; + conditions.isBreakDonCloseLower = isBreakDonCloseLower; + conditions.isRejectDonCloseUpper = isRejectDonCloseUpper; + conditions.isRejectDonCloseLower = isRejectDonCloseLower; + + // + return result; + } + + // + // Protected ... + protected: + // + // Private ... + private: + // + // Props ... + X121XDONInputs mInputs; // Inputs ... + + // + // Buffers ... + double donOpenUpperBuffer[]; + double donOpenLowerBuffer[]; + double donHighUpperBuffer[]; + double donHighLowerBuffer[]; + double donLowUpperBuffer[]; + double donLowLowerBuffer[]; + double donCloseUpperBuffer[]; + double donCloseLowerBuffer[]; + + // + void Calculate() + { + // + int totalBars = CountBars(); + if (totalBars > 1000) + { + totalBars = 1000; + } + // + // OPEN ... + + // + // Upper ... + CopyBuffer( + mHandler, + X121_XDON_OPEN_UPPER_LINE, + 0, + totalBars, + donOpenUpperBuffer + // + ); + + // + // Lower ... + CopyBuffer( + mHandler, + X121_XDON_OPEN_LOWER_LINE, + 0, + totalBars, + donOpenLowerBuffer + // + ); + + // + // CLOSE ... + + // + // Upper ... + CopyBuffer( + mHandler, + X121_XDON_CLOSE_UPPER_LINE, + 0, + totalBars, + donCloseUpperBuffer + // + ); + + // + // Lower ... + CopyBuffer( + mHandler, + X121_XDON_CLOSE_LOWER_LINE, + 0, + totalBars, + donCloseLowerBuffer + // + ); + + // + // HIGH ... + + // + // Upper ... + CopyBuffer( + mHandler, + X121_XDON_HIGH_UPPER_LINE, + 0, + totalBars, + donHighUpperBuffer + // + ); + + // + // Lower ... + CopyBuffer( + mHandler, + X121_XDON_HIGH_LOWER_LINE, + 0, + totalBars, + donHighLowerBuffer + // + ); + + // + // LOW ... + + // + // Upper ... + CopyBuffer( + mHandler, + X121_XDON_LOW_UPPER_LINE, + 0, + totalBars, + donLowUpperBuffer + // + ); + + // + // Lower ... + CopyBuffer( + mHandler, + X121_XDON_LOW_LOWER_LINE, + 0, + totalBars, + donLowLowerBuffer + // + ); + } +}; + +// +// Tools ... \ No newline at end of file diff --git a/Helpers/x-saherelm.x121.xpv.helper.mq5 b/Helpers/x-saherelm.x121.xpv.helper.mq5 new file mode 100644 index 00000000..b40bb770 --- /dev/null +++ b/Helpers/x-saherelm.x121.xpv.helper.mq5 @@ -0,0 +1,2199 @@ +/////////////////////////////////////////////////////// +// +// SaherElm IT Center MQL5 Helper Class Library +// ---------------------------------------------- +// Name: XCX121XPVHelper +// Description: provides all Indicator +// Helper requirements ... +// +// +// 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 + +// +// Imports ... +#include "../Classes/x-saherelm.x-helper.class.mq5" + +// +// Definitions ... + +// +// Definitions ... +enum ENUM_X121_XPV_BUFFERS +{ + // + X121_XPV_PEAK_LINE = 0, + X121_XPV_VALE_LINE = 1, + X121_XPV_SAR_LINE = 2, + X121_XPV_C_HH_LINE = 3, + X121_XPV_C_LL_LINE = 4, + X121_XPV_S_HH_LINE = 5, + X121_XPV_S_LL_LINE = 6, + X121_XPV_M_HH_LINE = 7, + X121_XPV_M_LL_LINE = 8, + X121_XPV_L_HH_LINE = 9, + X121_XPV_L_LL_LINE = 10, + X121_XPV_H_HH_LINE = 11, + X121_XPV_H_LL_LINE = 12, +}; + +// +// Input Models ... +struct X121XPVInputs +{ + // + // Props ... + + // + // Short ... + ENUM_X_PERIOD_METHOD scMethod; // How to Find Period + ENUM_TIMEFRAMES scPeriod; // Time Period + + // + // Medium ... + ENUM_X_PERIOD_METHOD mcMethod; // How to Find Period + ENUM_TIMEFRAMES mcPeriod; // Time Period + + // + // Long ... + ENUM_X_PERIOD_METHOD lcMethod; // How to Find Period + ENUM_TIMEFRAMES lcPeriod; // Time Period + + // + // Hind ... + ENUM_X_PERIOD_METHOD hcMethod; // How to Find Period + ENUM_TIMEFRAMES hcPeriod; // Time Period + + // + // Boundary Detection ... + ENUM_SERIESMODE hhMode; // Highest High Calculation Method + ENUM_SERIESMODE llMode; // Lowest Low Calculation Method + + // + // Parabolic Sar Detection ... + double sarStep; // Step + double sarMax; // Maximum + + // + int startCalculationForLastBars; // Calculate Last n Bars + + // + int sarArrowCode; // Parabolic Sar Arrow Code + int peaksArrowCode; // Peaks Arrow Code + int valesArrowCode; // Vales Arrow Code + + // + bool showSar; // Show Parabolic Sar + bool showPeaks; // Show Peaks + bool showVales; // Show Vales + + // + // Constructor(s) ... + X121XPVInputs() + { + // + Clean(); + } + + // + // Tools ... + + // + // Clean ... + void Clean() + { + // + // Short ... + scMethod = X_PERIOD_NOTHING; + scPeriod = NULL; + + // + // Medium ... + mcMethod = X_PERIOD_NOTHING; + mcPeriod = NULL; + + // + // Long ... + lcMethod = X_PERIOD_NOTHING; + lcPeriod = NULL; + + // + // Hind ... + hcMethod = X_PERIOD_NOTHING; + hcPeriod = NULL; + + // + // Boundary Detection ... + hhMode = MODE_HIGH; + llMode = MODE_LOW; + + // + sarStep = 0; + sarMax = 0; + + // + startCalculationForLastBars = 0; + + // + sarArrowCode = 0; + peaksArrowCode = 0; + valesArrowCode = 0; + + // + showSar = false; + showPeaks = false; + showVales = false; + } + + // + // Default ... + void Default() + { + // + // Short ... + scMethod = X_PERIOD_AUTO; + scPeriod = NULL; + + // + // Medium ... + mcMethod = X_PERIOD_AUTO; + mcPeriod = NULL; + + // + // Long ... + lcMethod = X_PERIOD_AUTO; + lcPeriod = NULL; + + // + // Hind ... + hcMethod = X_PERIOD_AUTO; + hcPeriod = NULL; + + // + // Boundary Detection ... + hhMode = MODE_HIGH; + llMode = MODE_LOW; + + // + sarStep = 0.02; + sarMax = 0.2; + + // + startCalculationForLastBars = 1000; + + // + sarArrowCode = 159; + peaksArrowCode = 159; + valesArrowCode = 159; + + // + showSar = true; + showPeaks = true; + showVales = true; + } + + // + // Validate ... + bool IsValid() + { + // + bool result = false; + + // + result = + // + // SAR ... + sarMax > 0 && + sarStep > 0 && + sarMax > sarStep && + // + // XPV ... + (IsValid(scMethod, scPeriod) && + IsValid(mcMethod, mcPeriod) && + IsValid(lcMethod, lcPeriod) && + IsValid(hcMethod, hcPeriod)) + // + ; + + // + return result; + } + + // + // Retrieve MAx Length ... + int Max() + { + // + int result = 0; + + // + result = MathMax(1, 1); + + // + return result; + } +}; + +// +// Conditions ... +struct X121XPVConditions +{ + // + // Common ... + string symbol; + ENUM_TIMEFRAMES period; + datetime time; + + // + // Buffers ... + double peaksBuffer[]; + double valesBuffer[]; + double sarBuffer[]; + double cHHBuffer[]; + double cLLBuffer[]; + double sHHBuffer[]; + double sLLBuffer[]; + double mHHBuffer[]; + double mLLBuffer[]; + double lHHBuffer[]; + double lLLBuffer[]; + double hHHBuffer[]; + double hLLBuffer[]; + + // + // Conditions ... + + // + // SAR ... + + // + bool isSarBullish; + bool isSarBearish; + + // + bool isSarSwitchedToBullish; + bool isSarSwitchedToBearish; + + // + // XPV ... + + // + bool isNewPeak; + bool isNewPeakOverLast; + bool isNewPeakUnderLast; + + // + bool isNewVale; + bool isNewValeOverLast; + bool isNewValeUnderLast; + + // + // Constructor ... + X121XPVConditions() + { + Clean(); + } + + // + // Tools ... + + /** + * Cleaning Up ... + */ + void Clean() + { + // + // Commons ... + symbol = NULL; + period = NULL; + time = NULL; + + // + // Buffers ... + + // + Clean(peaksBuffer); + Clean(valesBuffer); + Clean(sarBuffer); + Clean(cHHBuffer); + Clean(cLLBuffer); + Clean(sHHBuffer); + Clean(sLLBuffer); + Clean(mHHBuffer); + Clean(mLLBuffer); + Clean(lHHBuffer); + Clean(lLLBuffer); + Clean(hHHBuffer); + Clean(hLLBuffer); + + // + ArraySetAsSeries(peaksBuffer, true); + ArraySetAsSeries(valesBuffer, true); + ArraySetAsSeries(sarBuffer, true); + ArraySetAsSeries(cHHBuffer, true); + ArraySetAsSeries(cLLBuffer, true); + ArraySetAsSeries(sHHBuffer, true); + ArraySetAsSeries(sLLBuffer, true); + ArraySetAsSeries(mHHBuffer, true); + ArraySetAsSeries(mLLBuffer, true); + ArraySetAsSeries(lHHBuffer, true); + ArraySetAsSeries(lLLBuffer, true); + ArraySetAsSeries(hHHBuffer, true); + ArraySetAsSeries(hLLBuffer, true); + + // + // Conditions ... + + // + isSarBullish = false; + isSarBearish = false; + + // + isSarSwitchedToBullish = false; + isSarSwitchedToBearish = false; + + // + isNewPeak = false; + isNewPeakOverLast = false; + isNewPeakUnderLast = false; + + // + isNewVale = false; + isNewValeOverLast = false; + isNewValeUnderLast = false; + } + + /** + * Generate Conditions Scores ... + * + * @param bullishScore: Double, Directional Scores Reference ... + * @param bearishScore: Double, Directional Scores Reference ... + */ + void GenerateScore( + double &bullishScore, + double &bearishScore // + ) + { + // + bullishScore = 0; + bearishScore = 0; + + // + // TODO: Implement if Required ... + } + + /** + * Generate Summary String for Represent Conditions State ... + * + * @param onlyCommons: Boolean, Just Generate Only Commons Conditions ... + * @param onlyConditions: Boolean, Just Generate Only Conditions ... + * @param includeScores: Boolean, Attach Scores Representations on Result ... + * @param ignoreFalseConditions: Boolean, Ignore False Conditions on Result ... + * @param separator: String, Separate Lines ... + * + * @return ( string ) + */ + string GenerateSummary( + bool onlyCommons = false, + bool onlyConditions = false, + bool includeScores = true, + bool ignoreFalseConditions = true, + string separator = "\n" // + ) + { + // + string result = NULL; + + // + double bullishScore = 0; + double bearishScore = 0; + GenerateScore( + bullishScore, + bearishScore // + ); + + // + string scoresStr = + // + "Scores: " + separator + + "---------------" + separator + + "Bullish: " + ToString(bullishScore) + separator + + "Bearish: " + ToString(bearishScore) + separator + + "" + // + ; + + // + string commonStr = GenerateSpecifiedCommonSummary( + this, + separator, + includeScores // + ); + + // + string conditionsStr = + // + ToString("isSarBullish", isSarBullish, ignoreFalseConditions, separator) + + ToString("isSarBearish", isSarBearish, ignoreFalseConditions, separator) + + ToString("isSarSwitchedToBullish", isSarSwitchedToBullish, ignoreFalseConditions, separator) + + ToString("isSarSwitchedToBearish", isSarSwitchedToBearish, ignoreFalseConditions, separator) + + ToString("isNewPeak", isNewPeak, ignoreFalseConditions, separator) + + ToString("isNewPeakOverLast", isNewPeakOverLast, ignoreFalseConditions, separator) + + ToString("isNewPeakUnderLast", isNewPeakUnderLast, ignoreFalseConditions, separator) + + ToString("isNewVale", isNewVale, ignoreFalseConditions, separator) + + ToString("isNewValeOverLast", isNewValeOverLast, ignoreFalseConditions, separator) + + ToString("isNewValeUnderLast", isNewValeUnderLast, ignoreFalseConditions, separator) + + // + "" + // + ; + + // + result = + // + "[" + GetTag() + "]" + separator + + (onlyConditions + ? "" + : commonStr) + + (!includeScores + ? "" + : scoresStr) + + " " + separator + + (onlyCommons + ? "" + : conditionsStr) + + "" + // + ; + + // + return result; + } + + /** + * Retrieve nique Tag Identifier ... + * + * @return ( string ) + */ + string GetTag() + { + return GetTypeName(this); + } + + // +}; + +// +// Class ... +class XCX121XPVHelper : public XCBaseHelper +{ + // + // Public ... + public: + // + // Props ... + + // + // Constructors ... + XCX121XPVHelper() + : XCBaseHelper(_Symbol, _Period) + { + } + + // + // Deconstructor ... + ~XCX121XPVHelper() + { + } + + // + // Tools ... + bool Init( + string symbol, // Trading Symbol + ENUM_TIMEFRAMES period, // Trading Period + X121XPVInputs &inputs // Inputs + ) + { + // + bool result = false; + + // + mSymbol = symbol; + mPeriod = period; + + // + result = inputs.IsValid(); + if (!result) + { + return result; + } + + // + ArraySetAsSeries(peaksBuffer, true); + ArraySetAsSeries(valesBuffer, true); + ArraySetAsSeries(sarBuffer, true); + ArraySetAsSeries(cHHBuffer, true); + ArraySetAsSeries(cLLBuffer, true); + ArraySetAsSeries(sHHBuffer, true); + ArraySetAsSeries(sLLBuffer, true); + ArraySetAsSeries(mHHBuffer, true); + ArraySetAsSeries(mLLBuffer, true); + ArraySetAsSeries(lHHBuffer, true); + ArraySetAsSeries(lLLBuffer, true); + ArraySetAsSeries(hHHBuffer, true); + ArraySetAsSeries(hLLBuffer, true); + + // + mInputs = inputs; + + // + mHandler = iCustom( + mSymbol, + mPeriod, + "x-saherelm.x121.xpv", + // + // Inputs ... + // + // Market ... + "", + // + // Short ... + "", + mInputs.scMethod, + mInputs.scPeriod, + // + // Medium ... + "", + mInputs.mcMethod, + mInputs.mcPeriod, + // + // Long ... + "", + mInputs.lcMethod, + mInputs.lcPeriod, + // + // Hind ... + "", + mInputs.hcMethod, + mInputs.hcPeriod, + // + // Boundary Detection ... + "", + mInputs.hhMode, + mInputs.llMode, + // + // SAr Detection ... + "", + mInputs.sarStep, + mInputs.sarMax, + // + // Presentation ... + "", + // + mInputs.startCalculationForLastBars, + mInputs.sarArrowCode, + mInputs.peaksArrowCode, + mInputs.valesArrowCode, + // + mInputs.showSar, + mInputs.showPeaks, + mInputs.showVales + // + ); + result = mHandler != INVALID_HANDLE; + if (!result) + { + return result; + } + + // + return result; + } + + // + // Inputs ... + + // + X121XPVInputs GetInputs() + { + return mInputs; + } + + // + bool SetInputs( + X121XPVInputs &inputs // Configs + ) + { + // + return Init( + mSymbol, + mPeriod, + inputs + // + ); + } + + // + // Readers ... + + // + // SAR ... + + // + double GetSar( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(sarBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return sarBuffer[barIndex]; + } + + // + int CopySar( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + sarBuffer, + buffer, + forceClean + // + ); + } + + // + // PV ... + + // + // PEAKS ... + + // + double GetPeak( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(peaksBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return peaksBuffer[barIndex]; + } + + // + int CopyPeak( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + peaksBuffer, + buffer, + forceClean + // + ); + } + + // + // VALES ... + + // + double GetVale( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(valesBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return valesBuffer[barIndex]; + } + + // + int CopyVale( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + valesBuffer, + buffer, + forceClean + // + ); + } + + // + // + // + + // + double GetHigherPeak( + double peak, // Peak Source + int barIndex = 0, // Bar Index + int loopback = 576 // Max Allowed Loopback + ) + { + // + double result = 0; + + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + if (loopback < 576) + { + loopback = 576; + } + + // + if (peak <= 0) + { + return result; + } + + // + double iValue = 0; + int index = barIndex; + bool canContinue = true; + while (canContinue) + { + // + iValue = GetPeak(index); + if (iValue > peak) + { + // + result = iValue; + break; + } + + // + canContinue = index < barIndex + loopback; + index++; + } + + // + return result; + } + + // + double GetLowerPeak( + double peak, // Peak Source + int barIndex = 0, // Bar Index + int loopback = 576 // Max Allowed Loopback + ) + { + // + double result = 0; + + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + if (loopback < 576) + { + loopback = 576; + } + + // + if (peak <= 0) + { + return result; + } + + // + double iValue = 0; + int index = barIndex; + bool canContinue = true; + while (canContinue) + { + // + iValue = GetPeak(index); + if (iValue < peak) + { + // + result = iValue; + break; + } + + // + canContinue = index < barIndex + loopback; + index++; + } + + // + return result; + } + + // + double GetHigherVale( + double vale, // Vale Source + int barIndex = 0, // Bar Index + int loopback = 576 // Max Allowed Loopback + ) + { + // + double result = 0; + + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + if (loopback < 576) + { + loopback = 576; + } + + // + if (vale <= 0) + { + return result; + } + + // + double iValue = 0; + int index = barIndex; + bool canContinue = true; + while (canContinue) + { + // + iValue = GetVale(index); + if (iValue > vale) + { + // + result = iValue; + break; + } + + // + canContinue = index < barIndex + loopback; + index++; + } + + // + return result; + } + + // + double GetLowerVale( + double vale, // Vale Source + int barIndex = 0, // Bar Index + int loopback = 576 // Max Allowed Loopback + ) + { + // + double result = 0; + + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + if (loopback < 576) + { + loopback = 576; + } + + // + if (vale <= 0) + { + return result; + } + + // + double iValue = 0; + int index = barIndex; + bool canContinue = true; + while (canContinue) + { + // + iValue = GetVale(index); + if (iValue < vale) + { + // + result = iValue; + break; + } + + // + canContinue = index < barIndex + loopback; + index++; + } + + // + return result; + } + + // + // CURRENT ... + + // + // HH ... + + // + double GetCHH( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(cHHBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return cHHBuffer[barIndex]; + } + + // + int CopyCHH( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + cHHBuffer, + buffer, + forceClean + // + ); + } + + // + // LL ... + + // + double GetCLL( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(cLLBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return cLLBuffer[barIndex]; + } + + // + int CopyCLL( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + cLLBuffer, + buffer, + forceClean + // + ); + } + + // + // SHORT ... + + // + // HH ... + + // + double GetSHH( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(sHHBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return sHHBuffer[barIndex]; + } + + // + int CopySHH( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + sHHBuffer, + buffer, + forceClean + // + ); + } + + // + // LL ... + + // + double GetSLL( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(sLLBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return sLLBuffer[barIndex]; + } + + // + int CopySLL( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + sLLBuffer, + buffer, + forceClean + // + ); + } + + // + // MEDIUM ... + + // + // HH ... + + // + double GetMHH( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(mHHBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return mHHBuffer[barIndex]; + } + + // + int CopyMHH( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + mHHBuffer, + buffer, + forceClean + // + ); + } + + // + // LL ... + + // + double GetMLL( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(mLLBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return mLLBuffer[barIndex]; + } + + // + int CopyMLL( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + mLLBuffer, + buffer, + forceClean + // + ); + } + + // + // LONG ... + + // + // HH ... + + // + double GetLHH( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(lHHBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return lHHBuffer[barIndex]; + } + + // + int CopyLHH( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + lHHBuffer, + buffer, + forceClean + // + ); + } + + // + // LL ... + + // + double GetLLL( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(lLLBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return lLLBuffer[barIndex]; + } + + // + int CopyLLL( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + lLLBuffer, + buffer, + forceClean + // + ); + } + + // + // HIND ... + + // + // HH ... + + // + double GetHHH( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(hHHBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return hHHBuffer[barIndex]; + } + + // + int CopyHHH( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + hHHBuffer, + buffer, + forceClean + // + ); + } + + // + // LL ... + + // + double GetHLL( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(hLLBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return hLLBuffer[barIndex]; + } + + // + int CopyHLL( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + hLLBuffer, + buffer, + forceClean + // + ); + } + + // + // Tools Function ... + + // + double GetLowestPeak( + int barIndex, + int &index, + double &vale, + int loopback = 576 // + ) + { + // + double result = 0; + + // + index = -1; + vale = 0; + + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + if (loopback < 576) + { + loopback = 576; + } + + // + Calculate(); + + // + for (int i = 0; i < barIndex + loopback; i++) + { + // + double iPeak = GetPeak(i); + if (iPeak == 0) + { + break; + } + + // + if (iPeak > 0 && (result == 0 || + result >= iPeak)) + { + // + index = i; + result = iPeak; + vale = GetVale(index); + } + } + + // + return result; + } + + // + double GetHighestPeak( + int barIndex, + int &index, + double &vale, + int loopback = 576 // + ) + { + // + double result = 0; + + // + index = -1; + vale = 0; + + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + if (loopback < 576) + { + loopback = 576; + } + + // + Calculate(); + + // + for (int i = 0; i < barIndex + loopback; i++) + { + // + double iPeak = GetPeak(i); + if (iPeak == 0) + { + break; + } + + // + if (iPeak > 0 && (result == 0 || + result <= iPeak)) + { + // + index = i; + result = iPeak; + vale = GetVale(index); + } + } + + // + return result; + } + + // + double GetLowestVale( + int barIndex, + int &index, + double &peak, + int loopback = 576 // + ) + { + // + double result = 0; + + // + index = -1; + peak = 0; + + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + if (loopback < 576) + { + loopback = 576; + } + + // + Calculate(); + + // + for (int i = 0; i < barIndex + loopback; i++) + { + // + double iPeak = GetVale(i); + if (iPeak == 0) + { + break; + } + + // + if (iPeak > 0 && (result == 0 || + result >= iPeak)) + { + // + index = i; + result = iPeak; + peak = GetPeak(index); + } + } + + // + return result; + } + + // + double GetHighestVale( + int barIndex, + int &index, + double &peak, + int loopback = 576 // + ) + { + // + double result = 0; + + // + index = -1; + peak = 0; + + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + if (loopback < 576) + { + loopback = 576; + } + + // + Calculate(); + + // + for (int i = 0; i < barIndex + loopback; i++) + { + // + double iPeak = GetVale(i); + if (iPeak == 0) + { + break; + } + + // + if (iPeak > 0 && (result == 0 || + result <= iPeak)) + { + // + index = i; + result = iPeak; + peak = GetPeak(index); + } + } + + // + return result; + } + + // + bool GetConditions( + X121XPVConditions &conditions, // + int barIndex = 0, // + int loopback = 5 // + ) + { + // + bool result = true; + + // + if (loopback < 5) + { + loopback = 5; + } + + // + conditions.Clean(); + + // + conditions.symbol = mSymbol; + conditions.period = mPeriod; + conditions.time = TimeCurrent(); + + // + int zIndex = barIndex; + int cIndex = zIndex + 1; + int pIndex = cIndex + 1; + int ppIndex = pIndex + 1; + + // + XOHCL zBar; + result = zBar.Init( + mSymbol, + mPeriod, + zIndex // + ); + if (!result) + { + return result; + } + + // + XOHCL cBar; + result = cBar.Init( + mSymbol, + mPeriod, + cIndex // + ); + if (!result) + { + return result; + } + + // + XOHCL pBar; + result = pBar.Init( + mSymbol, + mPeriod, + pIndex // + ); + if (!result) + { + return result; + } + + // + // Buffers ... + + // + CopySar( + zIndex, + loopback, + conditions.sarBuffer // + ); + + // + CopyPeak( + zIndex, + loopback, + conditions.peaksBuffer // + ); + + // + CopyVale( + zIndex, + loopback, + conditions.valesBuffer // + ); + + // + CopyCHH( + zIndex, + loopback, + conditions.cHHBuffer // + ); + + // + CopyCLL( + zIndex, + loopback, + conditions.cLLBuffer // + ); + + // + CopySHH( + zIndex, + loopback, + conditions.sHHBuffer // + ); + + // + CopySLL( + zIndex, + loopback, + conditions.sLLBuffer // + ); + + // + CopyMHH( + zIndex, + loopback, + conditions.mHHBuffer // + ); + + // + CopyMLL( + zIndex, + loopback, + conditions.mLLBuffer // + ); + + // + CopyLHH( + zIndex, + loopback, + conditions.lHHBuffer // + ); + + // + CopyLLL( + zIndex, + loopback, + conditions.lLLBuffer // + ); + + // + CopyHHH( + zIndex, + loopback, + conditions.hHHBuffer // + ); + + // + CopyHLL( + zIndex, + loopback, + conditions.hLLBuffer // + ); + + // + // Conditions ... + + // + int cIDX = 1; + int pIDX = cIDX + 1; + + // + // SAR ... + + // + bool isSarBullish = conditions.sarBuffer[cIDX] < cBar.low; + bool isSarBullishPrev = conditions.sarBuffer[pIDX] < pBar.low; + + + // + bool isSarBearish = conditions.sarBuffer[cIDX] > cBar.high; + bool isSarBearishPrev = conditions.sarBuffer[pIDX] > pBar.high; + + // + bool isSarSwitchedToBullish = isSarBullish && + !isSarBullishPrev; + bool isSarSwitchedToBearish = isSarBearish && + !isSarBearishPrev; + + // + // XPV ... + + // + bool isNewPeak = conditions.peaksBuffer[cIDX] != conditions.peaksBuffer[pIDX]; + bool isNewPeakOverLast = isNewPeak && + conditions.peaksBuffer[cIDX] > conditions.peaksBuffer[pIDX]; + bool isNewPeakUnderLast = isNewPeak && + conditions.peaksBuffer[cIDX] < conditions.peaksBuffer[pIDX]; + + // + bool isNewVale = conditions.valesBuffer[cIDX] != conditions.valesBuffer[pIDX]; + bool isNewValeOverLast = isNewVale && + conditions.valesBuffer[cIDX] > conditions.valesBuffer[pIDX]; + bool isNewValeUnderLast = isNewVale && + conditions.valesBuffer[cIDX] < conditions.valesBuffer[pIDX]; + + // + conditions.isSarBullish = isSarBullish; + conditions.isSarBearish = isSarBearish; + conditions.isSarSwitchedToBullish = isSarSwitchedToBullish; + conditions.isSarSwitchedToBearish = isSarSwitchedToBearish; + conditions.isNewPeak = isNewPeak; + conditions.isNewPeakOverLast = isNewPeakOverLast; + conditions.isNewPeakUnderLast = isNewPeakUnderLast; + conditions.isNewVale = isNewVale; + conditions.isNewValeOverLast = isNewValeOverLast; + conditions.isNewValeUnderLast = isNewValeUnderLast; + + // + return result; + } + + // + // Protected ... + protected: + // + // Private ... + private: + // + // Props ... + X121XPVInputs mInputs; // Inputs ... + + // + // Buffers ... + double peaksBuffer[]; + double valesBuffer[]; + double sarBuffer[]; + double cHHBuffer[]; + double cLLBuffer[]; + double sHHBuffer[]; + double sLLBuffer[]; + double mHHBuffer[]; + double mLLBuffer[]; + double lHHBuffer[]; + double lLLBuffer[]; + double hHHBuffer[]; + double hLLBuffer[]; + + // + void Calculate() + { + // + int totalBars = CountBars(); + if (totalBars > 1000) + { + totalBars = 1000; + } + + // + // Buffers ... + + // + // SAR ... + CopyBuffer( + mHandler, + X121_XPV_SAR_LINE, + 0, + totalBars, + sarBuffer + // + ); + + // + // XPV ... + + // + // PEAKS ... + CopyBuffer( + mHandler, + X121_XPV_PEAK_LINE, + 0, + totalBars, + peaksBuffer + // + ); + + // + // VALES ... + CopyBuffer( + mHandler, + X121_XPV_VALE_LINE, + 0, + totalBars, + valesBuffer + // + ); + + // + // CURRENT ... + + // + // HH ... + CopyBuffer( + mHandler, + X121_XPV_C_HH_LINE, + 0, + totalBars, + cHHBuffer + // + ); + + // + // LL ... + CopyBuffer( + mHandler, + X121_XPV_C_LL_LINE, + 0, + totalBars, + cLLBuffer + // + ); + + // + // SHORT ... + + // + // HH ... + CopyBuffer( + mHandler, + X121_XPV_S_HH_LINE, + 0, + totalBars, + sHHBuffer + // + ); + + // + // LL ... + CopyBuffer( + mHandler, + X121_XPV_S_LL_LINE, + 0, + totalBars, + sLLBuffer + // + ); + + // + // MEDIUM ... + + // + // HH ... + CopyBuffer( + mHandler, + X121_XPV_M_HH_LINE, + 0, + totalBars, + mHHBuffer + // + ); + + // + // LL ... + CopyBuffer( + mHandler, + X121_XPV_M_LL_LINE, + 0, + totalBars, + mLLBuffer + // + ); + + // + // LONG ... + + // + // HH ... + CopyBuffer( + mHandler, + X121_XPV_L_HH_LINE, + 0, + totalBars, + lHHBuffer + // + ); + + // + // LL ... + CopyBuffer( + mHandler, + X121_XPV_L_LL_LINE, + 0, + totalBars, + lLLBuffer + // + ); + + // + // HIND ... + + // + // HH ... + CopyBuffer( + mHandler, + X121_XPV_H_HH_LINE, + 0, + totalBars, + hHHBuffer + // + ); + + // + // LL ... + CopyBuffer( + mHandler, + X121_XPV_H_LL_LINE, + 0, + totalBars, + hLLBuffer + // + ); + } +}; + +// +// Tools ... \ No newline at end of file diff --git a/Helpers/x-saherelm.x121.xstr.helper.mq5 b/Helpers/x-saherelm.x121.xstr.helper.mq5 new file mode 100644 index 00000000..aed9f729 --- /dev/null +++ b/Helpers/x-saherelm.x121.xstr.helper.mq5 @@ -0,0 +1,983 @@ +/////////////////////////////////////////////////////// +// +// SaherElm IT Center MQL5 Helper Class Library +// ---------------------------------------------- +// Name: XCX121XSTRHelper +// Description: provides all Indicator +// Helper requirements ... +// +// +// 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 + +// +// Imports ... +#include "../Classes/x-saherelm.x-helper.class.mq5" + +// +// Definitions ... + +// +// Definitions ... +enum ENUM_X121_XSTR_BUFFERS +{ + // + X121_XSTR_LINE = 0, + X121_XSTR_ATR_LINE = 2, + X121_XSTR_PRICE_LINE = 3, + X121_XSTR_UP_LINE = 4, + X121_XSTR_DOWN_LINE = 5, + X121_XSTR_STATE_LINE = 6, +}; + +// +// Input Models ... +struct X121XSTRInputs +{ + // + // Props ... + + int strLength; // Length + double strMultiplier; // Multiplier + ENUM_APPLIED_PRICE strAppliedTo; // Applied To + + // + bool showStr; // Show Upper Zone + + // + // Constructor(s) ... + X121XSTRInputs() + { + // + Clean(); + } + + // + // Tools ... + + // + // Clean ... + void Clean() + { + // + strLength = 0; + strMultiplier = 0.0; + strAppliedTo = PRICE_MEDIAN; + + // + showStr = false; + } + + // + // Default ... + void Default() + { + // + strLength = 14; + strMultiplier = 3.0; + strAppliedTo = PRICE_MEDIAN; + + // + showStr = true; + } + + // + // Validate ... + bool IsValid() + { + // + bool result = false; + + // + result = + // + strLength > 0 && + strMultiplier > 0 + // + ; + + // + return result; + } + + // + // Retrieve MAx Length ... + int Max() + { + // + int result = 0; + + // + result = MathMax(1, strLength); + + // + return result; + } +}; + +// +// Conditions ... +struct X121XSTRConditions +{ + // + // Common ... + string symbol; + ENUM_TIMEFRAMES period; + datetime time; + + // + // Buffers ... + double strBuffer[]; + double atrBuffer[]; + double strPriceBuffer[]; + double strUpBuffer[]; + double strDownBuffer[]; + double strStateBuffer[]; + + // + // Conditions ... + + // + bool isStrBullish; + bool isStrBearish; + + // + bool isStrSwitchedToBullish; + bool isStrSwitchedToBearish; + + // + // bool isCloseLower + + // + // Constructor ... + X121XSTRConditions() + { + Clean(); + } + + // + // Tools ... + + /** + * Cleaning Up ... + */ + void Clean() + { + // + // Commons ... + symbol = NULL; + period = NULL; + time = NULL; + + // + // Buffers ... + + // + Clean(strBuffer); + Clean(atrBuffer); + Clean(strPriceBuffer); + Clean(strUpBuffer); + Clean(strDownBuffer); + Clean(strStateBuffer); + + // + ArraySetAsSeries(strBuffer, true); + ArraySetAsSeries(atrBuffer, true); + ArraySetAsSeries(strPriceBuffer, true); + ArraySetAsSeries(strUpBuffer, true); + ArraySetAsSeries(strDownBuffer, true); + ArraySetAsSeries(strStateBuffer, true); + + // + // Conditions ... + + // + isStrBullish = false; + isStrBearish = false; + + // + isStrSwitchedToBullish = false; + isStrSwitchedToBearish = false; + + // + // XDON ... + } + + /** + * Generate Conditions Scores ... + * + * @param bullishScore: Double, Directional Scores Reference ... + * @param bearishScore: Double, Directional Scores Reference ... + */ + void GenerateScore( + double &bullishScore, + double &bearishScore // + ) + { + // + bullishScore = 0; + bearishScore = 0; + + // + // TODO: Implement if Required ... + } + + /** + * Generate Summary String for Represent Conditions State ... + * + * @param onlyCommons: Boolean, Just Generate Only Commons Conditions ... + * @param onlyConditions: Boolean, Just Generate Only Conditions ... + * @param includeScores: Boolean, Attach Scores Representations on Result ... + * @param ignoreFalseConditions: Boolean, Ignore False Conditions on Result ... + * @param separator: String, Separate Lines ... + * + * @return ( string ) + */ + string GenerateSummary( + bool onlyCommons = false, + bool onlyConditions = false, + bool includeScores = true, + bool ignoreFalseConditions = true, + string separator = "\n" // + ) + { + // + string result = NULL; + + // + double bullishScore = 0; + double bearishScore = 0; + GenerateScore( + bullishScore, + bearishScore // + ); + + // + string scoresStr = + // + "Scores: " + separator + + "---------------" + separator + + "Bullish: " + ToString(bullishScore) + separator + + "Bearish: " + ToString(bearishScore) + separator + + "" + // + ; + + // + string commonStr = GenerateSpecifiedCommonSummary( + this, + separator, + includeScores // + ); + + // + string conditionsStr = + // + ToString("isStrBullish", isStrBullish, ignoreFalseConditions, separator) + + ToString("isStrBearish", isStrBearish, ignoreFalseConditions, separator) + + ToString("isStrSwitchedToBullish", isStrSwitchedToBullish, ignoreFalseConditions, separator) + + ToString("isStrSwitchedToBearish", isStrSwitchedToBearish, ignoreFalseConditions, separator) + + // + "" + // + ; + + // + result = + // + "[" + GetTag() + "]" + separator + + (onlyConditions + ? "" + : commonStr) + + (!includeScores + ? "" + : scoresStr) + + " " + separator + + (onlyCommons + ? "" + : conditionsStr) + + "" + // + ; + + // + return result; + } + + /** + * Retrieve nique Tag Identifier ... + * + * @return ( string ) + */ + string GetTag() + { + return GetTypeName(this); + } + + // +}; + +// +// Class ... +class XCX121XSTRHelper : public XCBaseHelper +{ + // + // Public ... + public: + // + // Props ... + + // + // Constructors ... + XCX121XSTRHelper() + : XCBaseHelper(_Symbol, _Period) + { + } + + // + // Deconstructor ... + ~XCX121XSTRHelper() + { + } + + // + // Tools ... + bool Init( + string symbol, // Trading Symbol + ENUM_TIMEFRAMES period, // Trading Period + X121XSTRInputs &inputs // Inputs + ) + { + // + bool result = false; + + // + mSymbol = symbol; + mPeriod = period; + + // + result = inputs.IsValid(); + if (!result) + { + return result; + } + + // + ArraySetAsSeries(strBuffer, true); + ArraySetAsSeries(atrBuffer, true); + ArraySetAsSeries(strPriceBuffer, true); + ArraySetAsSeries(strUpBuffer, true); + ArraySetAsSeries(strDownBuffer, true); + ArraySetAsSeries(strStateBuffer, true); + + // + mInputs = inputs; + + // + mHandler = iCustom( + mSymbol, + mPeriod, + "x-saherelm.x121.xstr", + // + // Inputs ... + // + // Market ... + "", + mInputs.strLength, + mInputs.strMultiplier, + mInputs.strAppliedTo, + // + // Presentation ... + "", + mInputs.showStr + // + ); + result = mHandler != INVALID_HANDLE; + if (!result) + { + return result; + } + + // + return result; + } + + // + // Inputs ... + + // + X121XSTRInputs GetInputs() + { + return mInputs; + } + + // + bool SetInputs( + X121XSTRInputs &inputs // Configs + ) + { + // + return Init( + mSymbol, + mPeriod, + inputs + // + ); + } + + // + // Readers ... + + // + // ATR ... + + // + double GetATR( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(atrBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return atrBuffer[barIndex]; + } + + // + int CopyATR( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + atrBuffer, + buffer, + forceClean + // + ); + } + + // + double GetSTR( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(strBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return strBuffer[barIndex]; + } + + // + int CopySTR( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + strBuffer, + buffer, + forceClean + // + ); + } + + // + double GetSTRState( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(strStateBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return strStateBuffer[barIndex]; + } + + // + int CopySTRState( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + strStateBuffer, + buffer, + forceClean + // + ); + } + + // + double GetSTRPrice( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(strPriceBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return strPriceBuffer[barIndex]; + } + + // + int CopySTRPrice( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + strPriceBuffer, + buffer, + forceClean + // + ); + } + + // + double GetSTRUp( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(strUpBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return strUpBuffer[barIndex]; + } + + // + int CopySTRUp( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + strUpBuffer, + buffer, + forceClean + // + ); + } + + // + double GetSTRDown( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(strDownBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return strDownBuffer[barIndex]; + } + + // + int CopySTRDown( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + strDownBuffer, + buffer, + forceClean + // + ); + } + + // + bool GetConditions( + X121XSTRConditions &conditions, // + int barIndex = 0, // + int loopback = 5 // + ) + { + // + bool result = true; + + // + if (loopback < 5) + { + loopback = 5; + } + + // + conditions.Clean(); + + // + conditions.symbol = mSymbol; + conditions.period = mPeriod; + conditions.time = TimeCurrent(); + + // + int zIndex = barIndex; + int cIndex = zIndex + 1; + int pIndex = cIndex + 1; + int ppIndex = pIndex + 1; + + // + XOHCL zBar; + result = zBar.Init( + mSymbol, + mPeriod, + zIndex // + ); + if (!result) + { + return result; + } + + // + XOHCL cBar; + result = cBar.Init( + mSymbol, + mPeriod, + cIndex // + ); + if (!result) + { + return result; + } + + // + XOHCL pBar; + result = pBar.Init( + mSymbol, + mPeriod, + pIndex // + ); + if (!result) + { + return result; + } + + // + // Buffers ... + + // + CopyATR( + zIndex, + loopback, + conditions.atrBuffer // + ); + + // + CopySTR( + zIndex, + loopback, + conditions.strBuffer // + ); + + // + CopySTRState( + zIndex, + loopback, + conditions.strStateBuffer // + ); + + // + CopySTRPrice( + zIndex, + loopback, + conditions.strPriceBuffer // + ); + + // + CopySTRUp( + zIndex, + loopback, + conditions.strUpBuffer // + ); + + // + CopySTRDown( + zIndex, + loopback, + conditions.strDownBuffer // + ); + + // + // Conditions ... + + // + int cIDX = 1; + int pIDX = cIDX + 1; + + // + bool isStrBullish = strStateBuffer[cIDX] > 0; + bool isStrBullishPrev = strStateBuffer[pIDX] > 0; + + // + bool isStrBearish = strStateBuffer[cIDX] < 0; + bool isStrBearishPrev = strStateBuffer[pIDX] < 0; + + // + bool isStrSwitchedToBullish = isStrBullish && + !isStrBullishPrev; + bool isStrSwitchedToBearish = isStrBearish && + !isStrBearishPrev; + + // + conditions.isStrBullish = isStrBullish; + conditions.isStrBearish = isStrBearish; + conditions.isStrSwitchedToBullish = isStrSwitchedToBullish; + conditions.isStrSwitchedToBearish = isStrSwitchedToBearish; + + // + return result; + } + + // + // Protected ... + protected: + // + // Private ... + private: + // + // Props ... + X121XSTRInputs mInputs; // Inputs ... + + // + // Buffers ... + double strBuffer[]; + double atrBuffer[]; + double strPriceBuffer[]; + double strUpBuffer[]; + double strDownBuffer[]; + double strStateBuffer[]; + + // + void Calculate() + { + // + int totalBars = CountBars(); + if (totalBars > 1000) + { + totalBars = 1000; + } + + // + // Buffers ... + + // + // STR ... + CopyBuffer( + mHandler, + X121_XSTR_LINE, + 0, + totalBars, + strBuffer + // + ); + + // + // State ... + CopyBuffer( + mHandler, + X121_XSTR_STATE_LINE, + 0, + totalBars, + strStateBuffer + // + ); + + // + // Price ... + CopyBuffer( + mHandler, + X121_XSTR_PRICE_LINE, + 0, + totalBars, + strPriceBuffer + // + ); + + // + // Up ... + CopyBuffer( + mHandler, + X121_XSTR_UP_LINE, + 0, + totalBars, + strUpBuffer + // + ); + + // + // STR ... + CopyBuffer( + mHandler, + X121_XSTR_DOWN_LINE, + 0, + totalBars, + strDownBuffer + // + ); + + // + // ATR ... + + // + CopyBuffer( + mHandler, + X121_XSTR_ATR_LINE, + 0, + totalBars, + atrBuffer + // + ); + } +}; + +// +// Tools ... \ No newline at end of file diff --git a/Helpers/x-saherelm.x121.xvwap.helper.mq5 b/Helpers/x-saherelm.x121.xvwap.helper.mq5 new file mode 100644 index 00000000..ef1c17bb --- /dev/null +++ b/Helpers/x-saherelm.x121.xvwap.helper.mq5 @@ -0,0 +1,1423 @@ +/////////////////////////////////////////////////////// +// +// SaherElm IT Center MQL5 Helper Class Library +// ---------------------------------------------- +// Name: XCX121XVWAPHelper +// Description: provides all Indicator +// Helper requirements ... +// +// +// 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 + +// +// Imports ... +#include "../Classes/x-saherelm.x-helper.class.mq5" + +// +// Definitions ... + +// +// Definitions ... +enum ENUM_X121_XVWAP_BUFFERS +{ + // + X121_XVWAP_FAST_LINE = 0, + X121_XVWAP_FAST_STATE_LINE = 8, + X121_XVWAP_MID_LINE = 2, + X121_XVWAP_MID_STATE_LINE = 9, + X121_XVWAP_SLOW_LINE = 4, + X121_XVWAP_SLOW_STATE_LINE = 10, + X121_XVWAP_VOLUME_LINE = 6, + X121_XVWAP_PRICE_LINE = 7, +}; + +// +enum ENUM_XVWAP_STATES +{ + XVWAP_STATE_BULLISH = 1, + XVWAP_STATE_BEARISH = 2, + XVWAP_STATE_NEUTURAL = 3, +}; + +// +// Input Models ... +struct X121XVWAPInputs +{ + // + // Props ... + + int vwapFastLength; // Fast Length + int vwapMidLength; // Mid Length + int vwapSlowLength; // Slow Length + ENUM_APPLIED_PRICE vwapAppliedTo; // Applied To + + // + int startCalculationForLastBars; // Calculate Last n Bars + + // + bool showVWapFast; // Show VWap Fast + bool showVWapMedium; // Show VWap Medium + bool showVWapSlow; // Show VWap Slow + + // + // Constructor(s) ... + X121XVWAPInputs() + { + // + Clean(); + } + + // + // Tools ... + + // + // Clean ... + void Clean() + { + // + vwapFastLength = 0; + vwapMidLength = 0; + vwapSlowLength = 0; + vwapAppliedTo = PRICE_CLOSE; + + // + startCalculationForLastBars = 0; + + // + showVWapFast = false; + showVWapMedium = false; + showVWapSlow = false; + } + + // + // Default ... + void Default() + { + // + vwapFastLength = 20; + vwapMidLength = 40; + vwapSlowLength = 60; + vwapAppliedTo = PRICE_CLOSE; + + // + startCalculationForLastBars = 1000; + + // + showVWapFast = true; + showVWapMedium = true; + showVWapSlow = true; + } + + // + // Validate ... + bool IsValid() + { + // + bool result = false; + + // + result = + // + vwapFastLength > 2 && + vwapMidLength > vwapFastLength && + vwapSlowLength > vwapMidLength + // + ; + + // + return result; + } + + // + // Retrieve MAx Length ... + int Max() + { + // + int result = 0; + + // + result = MathMax(vwapFastLength, vwapMidLength); + result = MathMax(result, vwapSlowLength); + + // + return result; + } +}; + +// +// Conditions ... +struct X121XVWAPConditions +{ + // + // Common ... + string symbol; + ENUM_TIMEFRAMES period; + datetime time; + + // + // Buffers ... + double vwapFastBuffer[]; + double vwapMidBuffer[]; + double vwapSlowBuffer[]; + double vwapVolumeBuffer[]; + double vwapPriceBuffer[]; + double vwapFastStateBuffer[]; + double vwapMidStateBuffer[]; + double vwapSlowStateBuffer[]; + + // + // Conditions ... + + // + bool isVWapFastBullish; + bool isVWapFastBearish; + bool isVWapFastNeutural; + + // + bool isVWapMidBullish; + bool isVWapMidBearish; + bool isVWapMidNeutural; + + // + bool isVWapSlowBullish; + bool isVWapSlowBearish; + bool isVWapSlowNeutural; + + // + bool isVWapFastOverMid; + bool isVWapMidOverSlow; + + // + bool isVWapFastUnderMid; + bool isVWapMidUnderSlow; + + // + bool isVWapBullishState; + bool isVWapBearishState; + bool isVWapNeuturalState; + + // + bool isVWapBullishOrdered; + bool isVWapBearishOrdered; + + // + bool isVWapSwitchedToBullishOrdered; + bool isVWapSwitchedToBearishOrdered; + + // + bool isVWapSwitchedToBullishState; + bool isVWapSwitchedToBearishState; + bool isVWapSwitchedToNeuturalState; + + // + // Constructor ... + X121XVWAPConditions() + { + Clean(); + } + + // + // Tools ... + + /** + * Cleaning Up ... + */ + void Clean() + { + // + // Commons ... + symbol = NULL; + period = NULL; + time = NULL; + + // + // Buffers ... + + // + Clean(vwapFastBuffer); + Clean(vwapMidBuffer); + Clean(vwapSlowBuffer); + Clean(vwapVolumeBuffer); + Clean(vwapPriceBuffer); + Clean(vwapFastStateBuffer); + Clean(vwapMidStateBuffer); + Clean(vwapSlowStateBuffer); + + // + ArraySetAsSeries(vwapFastBuffer, true); + ArraySetAsSeries(vwapMidBuffer, true); + ArraySetAsSeries(vwapSlowBuffer, true); + ArraySetAsSeries(vwapVolumeBuffer, true); + ArraySetAsSeries(vwapPriceBuffer, true); + ArraySetAsSeries(vwapFastStateBuffer, true); + ArraySetAsSeries(vwapMidStateBuffer, true); + ArraySetAsSeries(vwapSlowStateBuffer, true); + + // + // Conditions ... + + // + isVWapFastBullish = false; + isVWapFastBearish = false; + isVWapFastNeutural = false; + + // + isVWapMidBullish = false; + isVWapMidBearish = false; + isVWapMidNeutural = false; + + // + isVWapSlowBullish = false; + isVWapSlowBearish = false; + isVWapSlowNeutural = false; + + // + isVWapFastOverMid = false; + isVWapMidOverSlow = false; + + // + isVWapFastUnderMid = false; + isVWapMidUnderSlow = false; + + // + isVWapBullishState = false; + isVWapBearishState = false; + isVWapNeuturalState = false; + + // + isVWapBullishOrdered = false; + isVWapBearishOrdered = false; + + // + isVWapSwitchedToBullishOrdered = false; + isVWapSwitchedToBearishOrdered = false; + + // + isVWapSwitchedToBullishState = false; + isVWapSwitchedToBearishState = false; + isVWapSwitchedToNeuturalState = false; + } + + /** + * Generate Conditions Scores ... + * + * @param bullishScore: Double, Directional Scores Reference ... + * @param bearishScore: Double, Directional Scores Reference ... + */ + void GenerateScore( + double &bullishScore, + double &bearishScore // + ) + { + // + bullishScore = 0; + bearishScore = 0; + + // + // TODO: Implement if Required ... + } + + /** + * Generate Summary String for Represent Conditions State ... + * + * @param onlyCommons: Boolean, Just Generate Only Commons Conditions ... + * @param onlyConditions: Boolean, Just Generate Only Conditions ... + * @param includeScores: Boolean, Attach Scores Representations on Result ... + * @param ignoreFalseConditions: Boolean, Ignore False Conditions on Result ... + * @param separator: String, Separate Lines ... + * + * @return ( string ) + */ + string GenerateSummary( + bool onlyCommons = false, + bool onlyConditions = false, + bool includeScores = true, + bool ignoreFalseConditions = true, + string separator = "\n" // + ) + { + // + string result = NULL; + + // + double bullishScore = 0; + double bearishScore = 0; + GenerateScore( + bullishScore, + bearishScore // + ); + + // + string scoresStr = + // + "Scores: " + separator + + "---------------" + separator + + "Bullish: " + ToString(bullishScore) + separator + + "Bearish: " + ToString(bearishScore) + separator + + "" + // + ; + + // + string commonStr = GenerateSpecifiedCommonSummary( + this, + separator, + includeScores // + ); + + // + string conditionsStr = + // + ToString("isVWapFastBullish", isVWapFastBullish, ignoreFalseConditions, separator) + + ToString("isVWapFastBearish", isVWapFastBearish, ignoreFalseConditions, separator) + + ToString("isVWapFastNeutural", isVWapFastNeutural, ignoreFalseConditions, separator) + + ToString("isVWapMidBullish", isVWapMidBullish, ignoreFalseConditions, separator) + + ToString("isVWapMidBearish", isVWapMidBearish, ignoreFalseConditions, separator) + + ToString("isVWapMidNeutural", isVWapMidNeutural, ignoreFalseConditions, separator) + + ToString("isVWapSlowBullish", isVWapSlowBullish, ignoreFalseConditions, separator) + + ToString("isVWapSlowBearish", isVWapSlowBearish, ignoreFalseConditions, separator) + + ToString("isVWapSlowNeutural", isVWapSlowNeutural, ignoreFalseConditions, separator) + + ToString("isVWapFastOverMid", isVWapFastOverMid, ignoreFalseConditions, separator) + + ToString("isVWapMidOverSlow", isVWapMidOverSlow, ignoreFalseConditions, separator) + + ToString("isVWapFastUnderMid", isVWapFastUnderMid, ignoreFalseConditions, separator) + + ToString("isVWapMidUnderSlow", isVWapMidUnderSlow, ignoreFalseConditions, separator) + + ToString("isVWapBullishState", isVWapBullishState, ignoreFalseConditions, separator) + + ToString("isVWapBearishState", isVWapBearishState, ignoreFalseConditions, separator) + + ToString("isVWapNeuturalState", isVWapNeuturalState, ignoreFalseConditions, separator) + + ToString("isVWapBullishOrdered", isVWapBullishOrdered, ignoreFalseConditions, separator) + + ToString("isVWapBearishOrdered", isVWapBearishOrdered, ignoreFalseConditions, separator) + + ToString("isVWapSwitchedToBullishOrdered", isVWapSwitchedToBullishOrdered, ignoreFalseConditions, separator) + + ToString("isVWapSwitchedToBearishOrdered", isVWapSwitchedToBearishOrdered, ignoreFalseConditions, separator) + + ToString("isVWapSwitchedToBullishState", isVWapSwitchedToBullishState, ignoreFalseConditions, separator) + + ToString("isVWapSwitchedToBearishState", isVWapSwitchedToBearishState, ignoreFalseConditions, separator) + + ToString("isVWapSwitchedToNeuturalState", isVWapSwitchedToNeuturalState, ignoreFalseConditions, separator) + + // + "" + // + ; + + // + result = + // + "[" + GetTag() + "]" + separator + + (onlyConditions + ? "" + : commonStr) + + (!includeScores + ? "" + : scoresStr) + + " " + separator + + (onlyCommons + ? "" + : conditionsStr) + + "" + // + ; + + // + return result; + } + + /** + * Retrieve nique Tag Identifier ... + * + * @return ( string ) + */ + string GetTag() + { + return GetTypeName(this); + } + + // +}; + +// +// Class ... +class XCX121XVWAPHelper : public XCBaseHelper +{ + // + // Public ... + public: + // + // Props ... + + // + // Constructors ... + XCX121XVWAPHelper() + : XCBaseHelper(_Symbol, _Period) + { + } + + // + // Deconstructor ... + ~XCX121XVWAPHelper() + { + } + + // + // Tools ... + bool Init( + string symbol, // Trading Symbol + ENUM_TIMEFRAMES period, // Trading Period + X121XVWAPInputs &inputs // Inputs + ) + { + // + bool result = false; + + // + mSymbol = symbol; + mPeriod = period; + + // + result = inputs.IsValid(); + if (!result) + { + return result; + } + + // + ArraySetAsSeries(vwapFastBuffer, true); + ArraySetAsSeries(vwapMidBuffer, true); + ArraySetAsSeries(vwapSlowBuffer, true); + ArraySetAsSeries(vwapVolumeBuffer, true); + ArraySetAsSeries(vwapPriceBuffer, true); + ArraySetAsSeries(vwapFastStateBuffer, true); + ArraySetAsSeries(vwapMidStateBuffer, true); + ArraySetAsSeries(vwapSlowStateBuffer, true); + + // + mInputs = inputs; + + // + mHandler = iCustom( + mSymbol, + mPeriod, + "x-saherelm.x121.xvwap", + // + // Inputs ... + // + // Market ... + "", + mInputs.vwapFastLength, + mInputs.vwapMidLength, + mInputs.vwapSlowLength, + mInputs.vwapAppliedTo, + // + // Presentation ... + "", + // + mInputs.startCalculationForLastBars, + // + mInputs.showVWapFast, + mInputs.showVWapMedium, + mInputs.showVWapSlow + // + ); + result = mHandler != INVALID_HANDLE; + if (!result) + { + return result; + } + + // + return result; + } + + // + // Inputs ... + + // + X121XVWAPInputs GetInputs() + { + return mInputs; + } + + // + bool SetInputs( + X121XVWAPInputs &inputs // Configs + ) + { + // + return Init( + mSymbol, + mPeriod, + inputs + // + ); + } + + // + // Readers ... + + // + double GetVWapFast( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(vwapFastBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return vwapFastBuffer[barIndex]; + } + + // + int CopyVWapFast( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + vwapFastBuffer, + buffer, + forceClean + // + ); + } + + // + // STATE FAST ... + + // + double GetVWapFastState( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(vwapFastStateBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return vwapFastStateBuffer[barIndex]; + } + + // + int CopyVWapFastState( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + vwapFastStateBuffer, + buffer, + forceClean + // + ); + } + + // + // MID ... + + // + double GetVWapMid( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(vwapMidBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return vwapMidBuffer[barIndex]; + } + + // + int CopyVWapMid( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + vwapMidBuffer, + buffer, + forceClean + // + ); + } + + // + // STATE MID ... + + // + double GetVWapMidState( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(vwapMidStateBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return vwapMidStateBuffer[barIndex]; + } + + // + int CopyVWapMidState( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + vwapMidStateBuffer, + buffer, + forceClean + // + ); + } + + // + // SLOW ... + + // + double GetVWapSlowBuffer( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(vwapSlowBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return vwapSlowBuffer[barIndex]; + } + + // + int CopyVWapSlow( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + vwapSlowBuffer, + buffer, + forceClean + // + ); + } + + // + // STATE SLOW ... + + // + double GetVWapSlowState( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(vwapSlowStateBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return vwapSlowStateBuffer[barIndex]; + } + + // + int CopyVWapSlowState( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + vwapSlowStateBuffer, + buffer, + forceClean + // + ); + } + + // + // VOLUME ... + + // + double GetVWapVolume( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(vwapVolumeBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return vwapVolumeBuffer[barIndex]; + } + + // + int CopyVWapVolume( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + vwapVolumeBuffer, + buffer, + forceClean + // + ); + } + + // + // PRICE ... + + // + double GetVWapPrice( + int barIndex // Bar Index + ) + { + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + Calculate(); + + // + int count = ArraySize(vwapPriceBuffer); + if (barIndex >= count) + { + barIndex = count - 1; + } + + // + return vwapPriceBuffer[barIndex]; + } + + // + int CopyVWapPrice( + int start, // Start + int count, // Number of Items for read + double &buffer[], // Dest Buffer + bool forceClean = true // Force To Clean buffer + ) + { + // + // Update Calculations ... + Calculate(); + + // + // Copy Items ... + return Copy( + start, + count, + vwapPriceBuffer, + buffer, + forceClean + // + ); + } + + // + // Converts to State ... + ENUM_XVWAP_STATES ToVWAPState(double value) + { + // + ENUM_XVWAP_STATES result = + value == 1 + ? XVWAP_STATE_BULLISH + : value == 2 + ? XVWAP_STATE_BEARISH + : XVWAP_STATE_NEUTURAL; + + // + return result; + } + + // + bool IsVWAPBullish(double value) + { + // + bool result = false; + + // + result = ToVWAPState(value) == XVWAP_STATE_BULLISH; + + // + return result; + } + + // + bool IsVWAPBearish(double value) + { + // + bool result = false; + + // + result = ToVWAPState(value) == XVWAP_STATE_BEARISH; + + // + return result; + } + + // + bool IsVWAPNeutural(double value) + { + // + bool result = false; + + // + result = ToVWAPState(value) == XVWAP_STATE_NEUTURAL; + + // + return result; + } + + // + bool GetConditions( + X121XVWAPConditions &conditions, // + int barIndex = 0, // + int loopback = 5 // + ) + { + // + bool result = true; + + // + if (loopback < 5) + { + loopback = 5; + } + + // + conditions.Clean(); + + // + conditions.symbol = mSymbol; + conditions.period = mPeriod; + conditions.time = TimeCurrent(); + + // + int zIndex = barIndex; + int cIndex = zIndex + 1; + int pIndex = cIndex + 1; + int ppIndex = pIndex + 1; + + // + XOHCL zBar; + result = zBar.Init( + mSymbol, + mPeriod, + zIndex // + ); + if (!result) + { + return result; + } + + // + XOHCL cBar; + result = cBar.Init( + mSymbol, + mPeriod, + cIndex // + ); + if (!result) + { + return result; + } + + // + XOHCL pBar; + result = pBar.Init( + mSymbol, + mPeriod, + pIndex // + ); + if (!result) + { + return result; + } + + // + // Buffers ... + + // + CopyVWapFast( + zIndex, + loopback, + conditions.vwapFastBuffer // + ); + + // + CopyVWapFastState( + zIndex, + loopback, + conditions.vwapFastStateBuffer // + ); + + // + CopyVWapMid( + zIndex, + loopback, + conditions.vwapMidBuffer // + ); + + // + CopyVWapMidState( + zIndex, + loopback, + conditions.vwapMidStateBuffer // + ); + + // + CopyVWapSlow( + zIndex, + loopback, + conditions.vwapSlowBuffer // + ); + + // + CopyVWapSlowState( + zIndex, + loopback, + conditions.vwapSlowStateBuffer // + ); + + // + CopyVWapVolume( + zIndex, + loopback, + conditions.vwapVolumeBuffer // + ); + + // + CopyVWapPrice( + zIndex, + loopback, + conditions.vwapPriceBuffer // + ); + + // + // Conditions ... + + // + int cIDX = 1; + int pIDX = cIDX + 1; + + // + // SAR ... + + // + bool isVWapFastBullish = IsVWAPBullish(conditions.vwapFastStateBuffer[cIDX]); + bool isVWapFastBullishPrev = IsVWAPBullish(conditions.vwapFastStateBuffer[pIDX]); + + // + bool isVWapFastBearish = IsVWAPBearish(conditions.vwapFastStateBuffer[cIDX]); + bool isVWapFastBearishPrev = IsVWAPBearish(conditions.vwapFastStateBuffer[pIDX]); + + // + bool isVWapFastNeutural = IsVWAPNeutural(conditions.vwapFastStateBuffer[cIDX]); + bool isVWapFastNeuturalPrev = IsVWAPNeutural(conditions.vwapFastStateBuffer[pIDX]); + + // + bool isVWapMidBullish = IsVWAPBullish(conditions.vwapMidStateBuffer[cIDX]); + bool isVWapMidBullishPrev = IsVWAPBullish(conditions.vwapMidStateBuffer[pIDX]); + + // + bool isVWapMidBearish = IsVWAPBearish(conditions.vwapMidStateBuffer[cIDX]); + bool isVWapMidBearishPrev = IsVWAPBearish(conditions.vwapMidStateBuffer[pIDX]); + + // + bool isVWapMidNeutural = IsVWAPNeutural(conditions.vwapMidStateBuffer[cIDX]); + bool isVWapMidNeuturalPrev = IsVWAPNeutural(conditions.vwapMidStateBuffer[pIDX]); + + // + bool isVWapSlowBullish = IsVWAPBullish(conditions.vwapSlowStateBuffer[cIDX]); + bool isVWapSlowBullishPrev = IsVWAPBullish(conditions.vwapSlowStateBuffer[pIDX]); + + // + bool isVWapSlowBearish = IsVWAPBearish(conditions.vwapSlowStateBuffer[cIDX]); + bool isVWapSlowBearishPrev = IsVWAPBearish(conditions.vwapSlowStateBuffer[pIDX]); + + // + bool isVWapSlowNeutural = IsVWAPNeutural(conditions.vwapSlowStateBuffer[cIDX]); + bool isVWapSlowNeuturalPrev = IsVWAPNeutural(conditions.vwapSlowStateBuffer[pIDX]); + + // + bool isVWapFastOverMid = conditions.vwapFastBuffer[cIDX] > conditions.vwapMidBuffer[cIDX]; + bool isVWapFastOverMidPrev = conditions.vwapFastBuffer[pIDX] > conditions.vwapMidBuffer[pIDX]; + + // + bool isVWapMidOverSlow = conditions.vwapMidBuffer[cIDX] > conditions.vwapSlowBuffer[cIDX]; + bool isVWapMidOverSlowPrev = conditions.vwapMidBuffer[pIDX] > conditions.vwapSlowBuffer[pIDX]; + + // + bool isVWapFastUnderMid = conditions.vwapFastBuffer[cIDX] < conditions.vwapMidBuffer[cIDX]; + bool isVWapFastUnderMidPrev = conditions.vwapFastBuffer[pIDX] < conditions.vwapMidBuffer[pIDX]; + + // + bool isVWapMidUnderSlow = conditions.vwapMidBuffer[cIDX] < conditions.vwapSlowBuffer[cIDX]; + bool isVWapMidUnderSlowPrev = conditions.vwapMidBuffer[pIDX] < conditions.vwapSlowBuffer[pIDX]; + + // + bool isVWapBullishState = isVWapFastBullish && + isVWapMidBullish && + isVWapSlowBullish; + bool isVWapBullishStatePrev = isVWapFastBullishPrev && + isVWapMidBullishPrev && + isVWapSlowBullishPrev; + + // + bool isVWapBearishState = isVWapFastBearish && + isVWapMidBearish && + isVWapSlowBearish; + bool isVWapBearishStatePrev = isVWapFastBearishPrev && + isVWapMidBearishPrev && + isVWapSlowBearishPrev; + + // + bool isVWapNeuturalState = isVWapFastNeutural && + isVWapMidNeutural && + isVWapSlowNeutural; + bool isVWapNeuturalStatePrev = isVWapFastNeuturalPrev && + isVWapMidNeuturalPrev && + isVWapSlowNeuturalPrev; + + // + bool isVWapBullishOrdered = isVWapFastOverMid && + isVWapMidOverSlow; + bool isVWapBullishOrderedPrev = isVWapFastOverMidPrev && + isVWapMidOverSlowPrev; + + // + bool isVWapBearishOrdered = isVWapFastUnderMid && + isVWapMidUnderSlow; + bool isVWapBearishOrderedPrev = isVWapFastUnderMidPrev && + isVWapMidUnderSlowPrev; + + // + bool isVWapSwitchedToBullishOrdered = isVWapBullishOrdered && + !isVWapBullishOrderedPrev; + bool isVWapSwitchedToBearishOrdered = isVWapBearishOrdered && + !isVWapBearishOrderedPrev; + + // + bool isVWapSwitchedToBullishState = isVWapBullishState && + !isVWapBullishStatePrev; + bool isVWapSwitchedToBearishState = isVWapBearishState && + !isVWapBearishStatePrev; + bool isVWapSwitchedToNeuturalState = isVWapNeuturalState && + !isVWapNeuturalStatePrev; + + // + conditions.isVWapFastBullish = isVWapFastBullish; + conditions.isVWapFastBearish = isVWapFastBearish; + conditions.isVWapFastNeutural = isVWapFastNeutural; + conditions.isVWapMidBullish = isVWapMidBullish; + conditions.isVWapMidBearish = isVWapMidBearish; + conditions.isVWapMidNeutural = isVWapMidNeutural; + conditions.isVWapSlowBullish = isVWapSlowBullish; + conditions.isVWapSlowBearish = isVWapSlowBearish; + conditions.isVWapSlowNeutural = isVWapSlowNeutural; + conditions.isVWapFastOverMid = isVWapFastOverMid; + conditions.isVWapMidOverSlow = isVWapMidOverSlow; + conditions.isVWapFastUnderMid = isVWapFastUnderMid; + conditions.isVWapMidUnderSlow = isVWapMidUnderSlow; + conditions.isVWapBullishState = isVWapBullishState; + conditions.isVWapBearishState = isVWapBearishState; + conditions.isVWapNeuturalState = isVWapNeuturalState; + conditions.isVWapBullishOrdered = isVWapBullishOrdered; + conditions.isVWapBearishOrdered = isVWapBearishOrdered; + conditions.isVWapSwitchedToBullishOrdered = isVWapSwitchedToBullishOrdered; + conditions.isVWapSwitchedToBearishOrdered = isVWapSwitchedToBearishOrdered; + conditions.isVWapSwitchedToBullishState = isVWapSwitchedToBullishState; + conditions.isVWapSwitchedToBearishState = isVWapSwitchedToBearishState; + conditions.isVWapSwitchedToNeuturalState = isVWapSwitchedToNeuturalState; + + // + return result; + } + + // + // Protected ... + protected: + // + // Private ... + private: + // + // Props ... + X121XVWAPInputs mInputs; // Inputs ... + + // + // Buffers ... + double vwapFastBuffer[]; + double vwapMidBuffer[]; + double vwapSlowBuffer[]; + double vwapVolumeBuffer[]; + double vwapPriceBuffer[]; + double vwapFastStateBuffer[]; + double vwapMidStateBuffer[]; + double vwapSlowStateBuffer[]; + + // + void Calculate() + { + // + int totalBars = CountBars(); + if (totalBars > 1000) + { + totalBars = 1000; + } + + // + // Buffers ... + + // + // FAST ... + CopyBuffer( + mHandler, + X121_XVWAP_FAST_LINE, + 0, + totalBars, + vwapFastBuffer + // + ); + + // + // FAST STATE ... + CopyBuffer( + mHandler, + X121_XVWAP_FAST_STATE_LINE, + 0, + totalBars, + vwapFastStateBuffer + // + ); + + // + // MID ... + CopyBuffer( + mHandler, + X121_XVWAP_MID_LINE, + 0, + totalBars, + vwapMidBuffer + // + ); + + // + // MID STATE ... + CopyBuffer( + mHandler, + X121_XVWAP_MID_STATE_LINE, + 0, + totalBars, + vwapMidStateBuffer + // + ); + + // + // SLOW ... + CopyBuffer( + mHandler, + X121_XVWAP_SLOW_LINE, + 0, + totalBars, + vwapSlowBuffer + // + ); + + // + // SLOW STATE ... + CopyBuffer( + mHandler, + X121_XVWAP_SLOW_STATE_LINE, + 0, + totalBars, + vwapSlowStateBuffer + // + ); + + // + // VOLUME ... + CopyBuffer( + mHandler, + X121_XVWAP_VOLUME_LINE, + 0, + totalBars, + vwapVolumeBuffer + // + ); + + // + // PRICE ... + CopyBuffer( + mHandler, + X121_XVWAP_PRICE_LINE, + 0, + totalBars, + vwapPriceBuffer + // + ); + } +}; + +// +// Tools ... \ No newline at end of file diff --git a/Indicators/x-saherelm.x121.xatr.mq5 b/Indicators/x-saherelm.x121.xatr.mq5 new file mode 100644 index 00000000..a506624b --- /dev/null +++ b/Indicators/x-saherelm.x121.xatr.mq5 @@ -0,0 +1,650 @@ +/////////////////////////////////////////////////////// +// +// SaherElm IT Center MQL5 Indicator +// ------------------------------------------------- +// Name: X121 XATR +// Description: XATR ... +// +// +// Maintainer: +// ------------ +// Hadi Khazaee Asl (hadi_khazaee_asl@yahoo.com) +// +////////////////////////////////////////////////////// +// +// Global Properties ... +#property copyright "Copyright 2023, SaherElm IT Center" +#property link "https://saherelm.ir" +#property version "1.00" +#property description "SaherElm X121 XATR Indicator" +#property strict + +// +// Definitions ... + +// +#define ShortName "X121 XATR" + +// +// Includes Common Library ... +#include "../Classes/x-saherelm.x-poi.class.mq5" +#include "../Classes/x-saherelm.x-poi.drawer.class.mq5" +#include "../Libraries/x-saherelm.common.lib.mq5" + +// +// Inputs ... + +// +// Market ... +input group "Market"; + +// +input group "RSI Detection"; +input int rsiLength = 14; // Length +input ENUM_APPLIED_PRICE rsiAppliedTo = PRICE_CLOSE; // Applied To + +// +input group "ATR Detection"; +input int atrLength = 14; // Length +input double atrMultiplier = 1; // Multiplier +input ENUM_APPLIED_PRICE atrUpperAppliedTo = PRICE_HIGH; // Upper Zone Applied To +input ENUM_APPLIED_PRICE atrLowerAppliedTo = PRICE_LOW; // Lower Zone Applied To +input ENUM_X_MA_METHOD atrSmoothingMode = X_MA_MODE_EMA; // Smoothing Method + +// +input group "Presentation"; + +// +input int startCalculationForLastBars = 1000; // Calculate Last n Bars + +// +input bool showAtrUpper = true; // Show Upper Zone +input bool showAtrLower = true; // Show Lower Zone + +// +// Buffers ... + +// +#define hideColorIDX 0 +#define bullishColorIDX 1 +#define bearishColorIDX 2 +#define neuturalColorIDX 3 + +// +#property indicator_chart_window + +// +#property indicator_buffers 6 +#property indicator_plots 2 + +// +// ATR ... + +// +// Upper ... + +// +#define atrUpperBufferIndex 0 +double atrUpperBuffer[]; + +#property indicator_label1 "X121 ATRU" +#property indicator_type1 DRAW_LINE +#property indicator_color1 clrYellow +#property indicator_style1 STYLE_SOLID +#property indicator_width1 2 + +// +// Lower ... + +// +#define atrLowerBufferIndex 1 +double atrLowerBuffer[]; + +#property indicator_label2 "X121 ATRL" +#property indicator_type2 DRAW_LINE +#property indicator_color2 clrYellow +#property indicator_style2 STYLE_SOLID +#property indicator_width2 2 + +// +// Data Buffers ... + +// +int mLastBufferIndex = 1; + +// +// ATR ... + +#define atrBufferIndex mLastBufferIndex + 1 +double atrBuffer[]; + +#define atrUpperRawBufferIndex mLastBufferIndex + 2 +double atrUpperRawBuffer[]; + +#define atrLowerRawBufferIndex mLastBufferIndex + 3 +double atrLowerRawBuffer[]; + +// +// RSI ... +#define rsiBufferIndex mLastBufferIndex + 4 +double rsiBuffer[]; + +// +// Variables, Properties and etc ... + +// +// this counts Available Bars ... +int limit; + +// +int maxLength; + +// +// RSI Handler ... +int rsiHandler = INVALID_HANDLE; + +// +// ATR Handler ... +int atrHandler = INVALID_HANDLE; + +// +bool isStrTrendChanged; +bool isStrStartBearishTrend; +bool isStrStartBullishTrend; + +// +// Event Handlers ... + +/** + * Initialize Indicator ... + * + * @return ( int ) + */ +int OnInit() +{ + // + // Validate Inputs ... + if (!ValidateInputs()) + { + return INIT_PARAMETERS_INCORRECT; + } + + // + // Initialize Indicator Handlers ... + + // + // RSI ... + rsiHandler = iRSI( + _Symbol, + _Period, + rsiLength, + rsiAppliedTo // + ); + bool isInited = rsiHandler != INVALID_HANDLE; + if (!isInited) + { + return INIT_FAILED; + } + + // + // ATR ... + atrHandler = iATR( + _Symbol, + _Period, + atrLength // + ); + isInited = atrHandler != INVALID_HANDLE; + if (!isInited) + { + return INIT_FAILED; + } + + // + // because in some cases we may have more than one input for + // calculation and we must prevent any calculation + // untill we pass the biggest input length, here we get max Input length + // and then wait until pass it ... + maxLength = ExtractMaxLengthOfInputs(); + + // + // Define Index Buffers ... + DefineBuffers(); + + // + // Set Indicator ShortName ... + SetIndicatorName(); + + // + // Init Succeed ... + return INIT_SUCCEEDED; +} + +/** + * De Initialize Indicator ... + * + * @param reason: Integer, De Initialization Reason ... + */ +void OnDeinit(const int reason) +{ + // + // REASON_PROGRAM 0 The EA has stopped working calling the ExpertRemove() function + // REASON_REMOVE 1 Program removed from a chart + // REASON_RECOMPILE 2 Program recompiled + // REASON_CHARTCHANGE 3 A symbol or a chart period is changed + // REASON_CHARTCLOSE 4 Chart closed + // REASON_PARAMETERS 5 Inputs changed by a user + // REASON_ACCOUNT 6 Another account has been activated or reconnection to the trade server has occurred due to changes in the account settings + // REASON_TEMPLATE 7 Another chart template applied + // REASON_INITFAILED 8 The OnInit() handler returned a non-zero value + // REASON_CLOSE 9 Terminal closed + + // + IndicatorRelease(rsiHandler); + IndicatorRelease(atrHandler); +} + +/** + * Calculate Bars ... + * + * @param rates_total: Integer, Total Bars on Chart ... + * @param prev_calculated: Integer, Total Calculated Bars on Charts ... + * @param time: DateTime Array, History of Open Time ... + * @param open: Double Array, History of Open Prices ... + * @param high: Double Array, History of High Prices ... + * @param low: Double Array, History of Low Prices ... + * @param close: Double Array, History of Close Prices ... + * @param tick_volume: Long, History of Tick Volumes on Bar ... + * @param volume: Long, History of Trade Volumes ... + * @param spread: Double, History of Spread Price ... + * + * @return ( int ) + */ +int OnCalculate( + const int rates_total, + const int prev_calculated, + const datetime &time[], + const double &open[], + const double &high[], + const double &low[], + const double &close[], + const long &tick_volume[], + const long &volume[], + const int &spread[] // +) +{ + // + // Prepare Buffers ... + ArraySetAsSeries(time, true); + ArraySetAsSeries(open, true); + ArraySetAsSeries(high, true); + ArraySetAsSeries(low, true); + ArraySetAsSeries(close, true); + ArraySetAsSeries(tick_volume, true); + ArraySetAsSeries(volume, true); + ArraySetAsSeries(spread, true); + + // + // Fill All Buffers by Zero ... + if (prev_calculated == 0) + { + } + + // + // Validate Calculated Bars ... + + // + // RSI ... + int rsiCalculatedBars = BarsCalculated(rsiHandler); + + // + // ATR ... + int atrCalculatedBars = BarsCalculated(atrHandler); + + // + bool isPassedRequiredCalculatedBars = + // + // RSI ... + rsiCalculatedBars >= maxLength && + // + // ATR ... + atrCalculatedBars >= maxLength + // + ; + if (!isPassedRequiredCalculatedBars) + { + return prev_calculated; + } + + // + limit = (prev_calculated > rates_total || prev_calculated <= 0) + ? rates_total + : (rates_total - prev_calculated) + 1; + + // + // Buffers Copy ... + + // + // RSI ... + int copiedRsis = CopyBuffer(rsiHandler, 0, 0, limit, rsiBuffer); + + // + // ATR ... + int copiedAtrs = CopyBuffer(atrHandler, 0, 0, limit, atrBuffer); + + // + // Validate Copied Items ... + bool isPassedRequiredCopiedItems = + // + // + // RSI ... + copiedRsis > 0 && + // + // ATR ... + copiedAtrs > 0 + // + ; + if (!isPassedRequiredCopiedItems) + { + return prev_calculated; + } + + // + // Main Loop ... + for (int i = limit - 1; i >= 0 && !IsStopped(); i--) + { + // + CalculateBuffers( + i, + prev_calculated, + rates_total, + // + open, + high, + close, + low, + tick_volume // + ); + } + + // + return rates_total; +} + +// +// Functions ... + +/** + * Validate Input Args for Initialization ... + * + * @return ( bool ) + */ +bool ValidateInputs() +{ + // + bool result = + // + // RSI ... + rsiLength > 0 && + // + // ATR ... + atrLength > 0 && + atrMultiplier > 0 + // + ; + + // + return result; +} + +/** + * Extract Max Length of Inputs ... + * + * @return ( int ) + */ +int ExtractMaxLengthOfInputs() +{ + // + int result = 0; + + // + result = MathMax(rsiLength, atrLength); + + // + return result; +} + +/** + * Define Required Buffers ... + */ +void DefineBuffers() +{ + // + // ATR ... + + // + // UPPER ... + bool canShowAtrUpper = showAtrUpper; + ENUM_DRAW_TYPE atrUpperDrawType = canShowAtrUpper ? DRAW_LINE : DRAW_NONE; + ArraySetAsSeries(atrUpperBuffer, true); + SetIndexBuffer(atrUpperBufferIndex, atrUpperBuffer, INDICATOR_DATA); + PlotIndexSetDouble(atrUpperBufferIndex, PLOT_EMPTY_VALUE, EMPTY_VALUE); + PlotIndexSetInteger(atrUpperBufferIndex, PLOT_SHOW_DATA, canShowAtrUpper); + PlotIndexSetInteger(atrUpperBufferIndex, PLOT_DRAW_TYPE, atrUpperDrawType); + + // + // LOWER ... + bool canShowAtrLower = showAtrLower; + ENUM_DRAW_TYPE atrLowerDrawType = canShowAtrLower ? DRAW_LINE : DRAW_NONE; + ArraySetAsSeries(atrLowerBuffer, true); + SetIndexBuffer(atrLowerBufferIndex, atrLowerBuffer, INDICATOR_DATA); + PlotIndexSetDouble(atrLowerBufferIndex, PLOT_EMPTY_VALUE, EMPTY_VALUE); + PlotIndexSetInteger(atrLowerBufferIndex, PLOT_SHOW_DATA, canShowAtrLower); + PlotIndexSetInteger(atrLowerBufferIndex, PLOT_DRAW_TYPE, atrLowerDrawType); + + // + // Data Buffers ... + + // + // ATR ... + + // + ArraySetAsSeries(atrBuffer, true); + SetIndexBuffer(atrBufferIndex, atrBuffer, INDICATOR_CALCULATIONS); + + // + ArraySetAsSeries(atrUpperRawBuffer, true); + SetIndexBuffer(atrUpperRawBufferIndex, atrUpperRawBuffer, INDICATOR_CALCULATIONS); + + // + ArraySetAsSeries(atrLowerRawBuffer, true); + SetIndexBuffer(atrLowerRawBufferIndex, atrLowerRawBuffer, INDICATOR_CALCULATIONS); + + // + // RSI ... + + // + ArraySetAsSeries(rsiBuffer, true); + SetIndexBuffer(rsiBufferIndex, rsiBuffer, INDICATOR_CALCULATIONS); +} + +/** + * Set Indicator Short Name and also we can define Buffers Labels ... + */ +void SetIndicatorName() +{ + IndicatorSetString(INDICATOR_SHORTNAME, ShortName); +} + +/** + * Calculate Custom Buffers ... + * + * @param bar_index: Integer, Represent Current Bar ... + * @param prevCalculated: Integer, Represent Previous Calculated Bars ... + * @param ratesTotal: Integer, Represents All Available Bars ... + * @param open: Double Array, History of Open Prices ... + * @param high: Double Array, History of High Prices ... + * @param close: Double Array, History of Close Prices ... + * @param low: Double Array, History of Low Prices ... + * @param tickVolume: Long, History of Tick Volumes on Bar ... + */ +void CalculateBuffers( + int bar_index, // Selected Bar Index + const int prevCalculated, + const int ratesTotal, + const double &open[], + const double &high[], + const double &close[], + const double &low[], + const long &tickVolume[] // +) +{ + // + int barsLimit = startCalculationForLastBars > 0 + ? startCalculationForLastBars + : 0; + // + // bool canCalculate = true; + bool canCalculate = + barsLimit == 0 || + bar_index <= barsLimit; + if (canCalculate) + { + // + CalculateAtrZones( + bar_index, + prevCalculated, + ratesTotal, + open, + high, + close, + low // + ); + } + else + { + FillBuffersZero(bar_index); + } +} + +// +// Custom ... + +/** + * Fill All Bufers to Zero Vlue for Specified Bar Index ... + * + * @param barIndex: Integer ... + */ +void FillBuffersZero(int barIndex) +{ + // + // RSIS ... + rsiBuffer[barIndex] = 0; + + // + // ATRS ... + atrBuffer[barIndex] = 0; + atrUpperBuffer[barIndex] = 0; + atrUpperRawBuffer[barIndex] = 0; + atrUpperBuffer[barIndex] = 0; + atrLowerRawBuffer[barIndex] = 0; +} + +/** + * Calculate ATR Zones ... + * + * @param bar_index: Integer, Represent Current Bar ... + * @param prevCalculated: Integer, Represent Previous Calculated Bars ... + * @param ratesTotal: Integer, Represents All Available Bars ... + * @param open: Double Array, History of Open Prices ... + * @param high: Double Array, History of High Prices ... + * @param close: Double Array, History of Close Prices ... + * @param low: Double Array, History of Low Prices ... + */ +void CalculateAtrZones( + int bar_index, // Selected Bar Index + const int prevCalculated, + const int ratesTotal, + const double &open[], + const double &high[], + const double &close[], + const double &low[] // +) +{ + // + // Select ATr Value ... + double atrValue = atrBuffer[bar_index]; + double appliedAtrMultiplierValue = atrValue * atrMultiplier; + + // + // Select Upper Price ... + double upperPrice = GetAppliedPrice( + atrUpperAppliedTo, + open, + high, + low, + close, + bar_index // + ); + + // + // Select Lower Price ... + double lowerPrice = GetAppliedPrice( + atrLowerAppliedTo, + open, + high, + low, + close, + bar_index // + ); + + // + // Calculate Raw Atrs ... + + // + // Upper ... + double atrUpperRawValue = upperPrice + appliedAtrMultiplierValue; + atrUpperRawBuffer[bar_index] = atrUpperRawValue; + + // + // Lower ... + double atrLowerRawValue = lowerPrice - appliedAtrMultiplierValue; + atrLowerRawBuffer[bar_index] = atrLowerRawValue; + + // + bool canSmooth = atrSmoothingMode != X_MA_MODE_NONE; + if (canSmooth) + { + // + // Upper ... + iMAOnBuffer( + ratesTotal, + prevCalculated, + bar_index, + atrLength, + atrUpperRawBuffer, + atrUpperBuffer, + atrSmoothingMode // + ); + + // + // Lower ... + iMAOnBuffer( + ratesTotal, + prevCalculated, + bar_index, + atrLength, + atrLowerRawBuffer, + atrLowerBuffer, + atrSmoothingMode // + ); + } + else + { + // + // Use Raw Values ... + atrUpperBuffer[bar_index] = atrUpperRawValue; + atrLowerBuffer[bar_index] = atrLowerRawValue; + } +} + +// \ No newline at end of file diff --git a/Indicators/x-saherelm.x121.xdon.mq5 b/Indicators/x-saherelm.x121.xdon.mq5 new file mode 100644 index 00000000..49785d41 --- /dev/null +++ b/Indicators/x-saherelm.x121.xdon.mq5 @@ -0,0 +1,692 @@ +/////////////////////////////////////////////////////// +// +// SaherElm IT Center MQL5 Indicator +// ------------------------------------------------- +// Name: X121 XDON +// Description: XDON ... +// +// +// Maintainer: +// ------------ +// Hadi Khazaee Asl (hadi_khazaee_asl@yahoo.com) +// +////////////////////////////////////////////////////// +// +// Global Properties ... +#property copyright "Copyright 2023, SaherElm IT Center" +#property link "https://saherelm.ir" +#property version "1.00" +#property description "SaherElm X121 XDON Indicator" +#property strict + +// +// Definitions ... + +// +#define ShortName "X121 XDON" + +// +// Includes Common Library ... +#include "../Libraries/x-saherelm.common.lib.mq5" + +// +// Inputs ... + +// +// Market ... +input group "Market"; +input int donchainLength = 40; // Donchain Length + +// +// Presentation ... +input group "Presentation"; + +// +input int startCalculationForLastBars = 1000; // Calculate Last n Bars + +// +input bool showUpper = true; // Show Upper Band +input bool showLower = true; // Show Lower Band + +// +input bool showOpen = true; // Show Open +input bool showHigh = true; // Show High +input bool showClose = true; // Show Close +input bool showLow = true; // Show Low + +// +// Buffers ... + +// +#define hideColorIDX 0 +#define bullishColorIDX 1 +#define bearishColorIDX 2 +#define neuturalColorIDX 3 + +// +#property indicator_chart_window + +// +#property indicator_buffers 8 +#property indicator_plots 8 + +// +// Plot Buffers ... + +// +// Open ... + +// +#define donOpenUpperBufferIndex 0 +double donOpenUpperBuffer[]; + +// +#define donOpenUpperPlotBufferIndex 0 +#property indicator_label1 "X121 O U" +#property indicator_type1 DRAW_LINE +#property indicator_color1 clrCornflowerBlue +#property indicator_width1 1 + +// +#define donOpenLowerBufferIndex 1 +double donOpenLowerBuffer[]; + +// +#define donOpenLowerPlotBufferIndex 1 +#property indicator_label2 "X121 O L" +#property indicator_type2 DRAW_LINE +#property indicator_color2 clrCornflowerBlue +#property indicator_width2 1 + +// +// High ... + +// +#define donHighUpperBufferIndex 2 +double donHighUpperBuffer[]; + +// +#define donHighUpperPlotBufferIndex 2 +#property indicator_label3 "X121 H U" +#property indicator_type3 DRAW_LINE +#property indicator_color3 clrAquamarine +#property indicator_width3 1 + +// +#define donHighLowerBufferIndex 3 +double donHighLowerBuffer[]; + +// +#define donHighLowerPlotBufferIndex 3 +#property indicator_label4 "X121 H L" +#property indicator_type4 DRAW_LINE +#property indicator_color4 clrAquamarine +#property indicator_width4 1 + +// +// Low ... + +// +#define donLowUpperBufferIndex 4 +double donLowUpperBuffer[]; + +// +#define donLowUpperPlotBufferIndex 4 +#property indicator_label5 "X121 L U" +#property indicator_type5 DRAW_LINE +#property indicator_color5 clrDarkOrchid +#property indicator_width5 1 + +// +#define donLowLowerBufferIndex 5 +double donLowLowerBuffer[]; + +// +#define donLowLowerPlotBufferIndex 5 +#property indicator_label6 "X121 L L" +#property indicator_type6 DRAW_LINE +#property indicator_color6 clrDarkOrchid +#property indicator_width6 1 + +// +// Close ... + +// +#define donCloseUpperBufferIndex 6 +double donCloseUpperBuffer[]; + +// +#define donCloseUpperPlotBufferIndex 6 +#property indicator_label7 "X121 C U" +#property indicator_type7 DRAW_LINE +#property indicator_color7 clrCoral +#property indicator_width7 1 + +// +#define donCloseLowerBufferIndex 7 +double donCloseLowerBuffer[]; + +// +#define donCloseLowerPlotBufferIndex 7 +#property indicator_label8 "X121 C L" +#property indicator_type8 DRAW_LINE +#property indicator_color8 clrCoral +#property indicator_width8 1 + +// +// Data Buffers ... + +// +int mLastBufferIndex = 7; + +// +// Variables, Properties and etc ... + +// +// this counts Available Bars ... +int limit; + +// +int maxLength; + +// +// Event Handlers ... + +/** + * Initialize Indicator ... + * + * @return ( int ) + */ +int OnInit() +{ + // + // Validate Inputs ... + if (!ValidateInputs()) + { + return INIT_PARAMETERS_INCORRECT; + } + + // + // Initialize Indicator Handlers ... + + // + // because in some cases we may have more than one input for + // calculation and we must prevent any calculation + // untill we pass the biggest input length, here we get max Input length + // and then wait until pass it ... + maxLength = ExtractMaxLengthOfInputs(); + + // + // Define Index Buffers ... + DefineBuffers(); + + // + // Set Indicator ShortName ... + SetIndicatorName(); + + // + // Init Succeed ... + return INIT_SUCCEEDED; +} + +/** + * De Initialize Indicator ... + * + * @param reason: Integer, De Initialization Reason ... + */ +void OnDeinit(const int reason) +{ + // + // REASON_PROGRAM 0 The EA has stopped working calling the ExpertRemove() function + // REASON_REMOVE 1 Program removed from a chart + // REASON_RECOMPILE 2 Program recompiled + // REASON_CHARTCHANGE 3 A symbol or a chart period is changed + // REASON_CHARTCLOSE 4 Chart closed + // REASON_PARAMETERS 5 Inputs changed by a user + // REASON_ACCOUNT 6 Another account has been activated or reconnection to the trade server has occurred due to changes in the account settings + // REASON_TEMPLATE 7 Another chart template applied + // REASON_INITFAILED 8 The OnInit() handler returned a non-zero value + // REASON_CLOSE 9 Terminal closed +} + +/** + * Calculate Bars ... + * + * @param rates_total: Integer, Total Bars on Chart ... + * @param prev_calculated: Integer, Total Calculated Bars on Charts ... + * @param time: DateTime Array, History of Open Time ... + * @param open: Double Array, History of Open Prices ... + * @param high: Double Array, History of High Prices ... + * @param low: Double Array, History of Low Prices ... + * @param close: Double Array, History of Close Prices ... + * @param tick_volume: Long, History of Tick Volumes on Bar ... + * @param volume: Long, History of Trade Volumes ... + * @param spread: Double, History of Spread Price ... + * + * @return ( int ) + */ +int OnCalculate( + const int rates_total, + const int prev_calculated, + const datetime &time[], + const double &open[], + const double &high[], + const double &low[], + const double &close[], + const long &tick_volume[], + const long &volume[], + const int &spread[] // +) +{ + // + // Prepare Buffers ... + ArraySetAsSeries(time, true); + ArraySetAsSeries(open, true); + ArraySetAsSeries(high, true); + ArraySetAsSeries(low, true); + ArraySetAsSeries(close, true); + ArraySetAsSeries(tick_volume, true); + ArraySetAsSeries(volume, true); + ArraySetAsSeries(spread, true); + + // + // Validate Calculated Bars ... + + // + limit = (prev_calculated > rates_total || prev_calculated <= 0) + ? rates_total + : (rates_total - prev_calculated) + 1; + + // + // Buffers Copy ... + + // + // Main Loop ... + for (int i = limit - 1; i >= 0 && !IsStopped(); i--) + { + // + CalculateBuffers( + i, + prev_calculated, + rates_total, + // + open, + high, + close, + low, + tick_volume // + ); + } + + // + return rates_total; +} + +// +// Functions ... + +/** + * Validate Input Args for Initialization ... + * + * @return ( bool ) + */ +bool ValidateInputs() +{ + // + bool result = false; + + // + result = + // + donchainLength > 0 + // + ; + + // + return result; +} + +/** + * Extract Max Length of Inputs ... + * + * @return ( int ) + */ +int ExtractMaxLengthOfInputs() +{ + // + int result = 0; + + // + return result; +} + +/** + * Define Required Buffers ... + */ +void DefineBuffers() +{ + // + // Plot Buffers ... + // + // Open ... + + // + // UPPER ... + bool canShowCOpenUpper = showUpper && showOpen; + ENUM_DRAW_TYPE donOpenUpperDrawType = canShowCOpenUpper ? DRAW_LINE : DRAW_NONE; + ArraySetAsSeries(donOpenUpperBuffer, true); + SetIndexBuffer(donOpenUpperBufferIndex, donOpenUpperBuffer, INDICATOR_DATA); + PlotIndexSetDouble(donOpenUpperPlotBufferIndex, PLOT_EMPTY_VALUE, EMPTY_VALUE); + PlotIndexSetInteger(donOpenUpperPlotBufferIndex, PLOT_SHOW_DATA, canShowCOpenUpper); + PlotIndexSetInteger(donOpenUpperPlotBufferIndex, PLOT_DRAW_TYPE, donOpenUpperDrawType); + + // + // LOWER ... + bool canShowCOpenLower = showLower && showOpen; + ENUM_DRAW_TYPE donOpenLowerDrawType = canShowCOpenLower ? DRAW_LINE : DRAW_NONE; + ArraySetAsSeries(donOpenLowerBuffer, true); + SetIndexBuffer(donOpenLowerBufferIndex, donOpenLowerBuffer, INDICATOR_DATA); + PlotIndexSetDouble(donOpenLowerPlotBufferIndex, PLOT_EMPTY_VALUE, EMPTY_VALUE); + PlotIndexSetInteger(donOpenLowerPlotBufferIndex, PLOT_SHOW_DATA, canShowCOpenLower); + PlotIndexSetInteger(donOpenLowerPlotBufferIndex, PLOT_DRAW_TYPE, donOpenLowerDrawType); + + // + // Close ... + + // + // UPPER ... + bool canShowCCloseUpper = showUpper && showClose; + ENUM_DRAW_TYPE donCloseUpperDrawType = canShowCCloseUpper ? DRAW_LINE : DRAW_NONE; + ArraySetAsSeries(donCloseUpperBuffer, true); + SetIndexBuffer(donCloseUpperBufferIndex, donCloseUpperBuffer, INDICATOR_DATA); + PlotIndexSetDouble(donCloseUpperPlotBufferIndex, PLOT_EMPTY_VALUE, EMPTY_VALUE); + PlotIndexSetInteger(donCloseUpperPlotBufferIndex, PLOT_SHOW_DATA, canShowCCloseUpper); + PlotIndexSetInteger(donCloseUpperPlotBufferIndex, PLOT_DRAW_TYPE, donCloseUpperDrawType); + + // + // LOWER ... + bool canShowCCloseLower = showLower && showClose; + ENUM_DRAW_TYPE donCloseLowerDrawType = canShowCCloseLower ? DRAW_LINE : DRAW_NONE; + ArraySetAsSeries(donCloseLowerBuffer, true); + SetIndexBuffer(donCloseLowerBufferIndex, donCloseLowerBuffer, INDICATOR_DATA); + PlotIndexSetDouble(donCloseLowerPlotBufferIndex, PLOT_EMPTY_VALUE, EMPTY_VALUE); + PlotIndexSetInteger(donCloseLowerPlotBufferIndex, PLOT_SHOW_DATA, canShowCCloseLower); + PlotIndexSetInteger(donCloseLowerPlotBufferIndex, PLOT_DRAW_TYPE, donCloseLowerDrawType); + + // + // High ... + + // + // UPPER ... + bool canShowCHighUpper = showUpper && showHigh; + ENUM_DRAW_TYPE donHighUpperDrawType = canShowCHighUpper ? DRAW_LINE : DRAW_NONE; + ArraySetAsSeries(donHighUpperBuffer, true); + SetIndexBuffer(donHighUpperBufferIndex, donHighUpperBuffer, INDICATOR_DATA); + PlotIndexSetDouble(donHighUpperPlotBufferIndex, PLOT_EMPTY_VALUE, EMPTY_VALUE); + PlotIndexSetInteger(donHighUpperPlotBufferIndex, PLOT_SHOW_DATA, canShowCHighUpper); + PlotIndexSetInteger(donHighUpperPlotBufferIndex, PLOT_DRAW_TYPE, donHighUpperDrawType); + + // + // LOWER ... + bool canShowCHighLower = showLower && showHigh; + ENUM_DRAW_TYPE donHighLowerDrawType = canShowCHighLower ? DRAW_LINE : DRAW_NONE; + ArraySetAsSeries(donHighLowerBuffer, true); + SetIndexBuffer(donHighLowerBufferIndex, donHighLowerBuffer, INDICATOR_DATA); + PlotIndexSetDouble(donHighLowerPlotBufferIndex, PLOT_EMPTY_VALUE, EMPTY_VALUE); + PlotIndexSetInteger(donHighLowerPlotBufferIndex, PLOT_SHOW_DATA, canShowCHighLower); + PlotIndexSetInteger(donHighLowerPlotBufferIndex, PLOT_DRAW_TYPE, donHighLowerDrawType); + + // + // Low ... + + // + // UPPER ... + bool canShowCLowUpper = showUpper && showLow; + ENUM_DRAW_TYPE donLowUpperDrawType = canShowCLowUpper ? DRAW_LINE : DRAW_NONE; + ArraySetAsSeries(donLowUpperBuffer, true); + SetIndexBuffer(donLowUpperBufferIndex, donLowUpperBuffer, INDICATOR_DATA); + PlotIndexSetDouble(donLowUpperPlotBufferIndex, PLOT_EMPTY_VALUE, EMPTY_VALUE); + PlotIndexSetInteger(donLowUpperPlotBufferIndex, PLOT_SHOW_DATA, canShowCLowUpper); + PlotIndexSetInteger(donLowUpperPlotBufferIndex, PLOT_DRAW_TYPE, donLowUpperDrawType); + + // + // LOWER ... + bool canShowCLowLower = showLower && showLow; + ENUM_DRAW_TYPE donLowLowerDrawType = canShowCLowLower ? DRAW_LINE : DRAW_NONE; + ArraySetAsSeries(donLowLowerBuffer, true); + SetIndexBuffer(donLowLowerBufferIndex, donLowLowerBuffer, INDICATOR_DATA); + PlotIndexSetDouble(donLowLowerPlotBufferIndex, PLOT_EMPTY_VALUE, EMPTY_VALUE); + PlotIndexSetInteger(donLowLowerPlotBufferIndex, PLOT_SHOW_DATA, canShowCLowLower); + PlotIndexSetInteger(donLowLowerPlotBufferIndex, PLOT_DRAW_TYPE, donLowLowerDrawType); + + // + // Data Buffers ... +} + +/** + * Set Indicator Short Name and also we can define Buffers Labels ... + */ +void SetIndicatorName() +{ + IndicatorSetString(INDICATOR_SHORTNAME, ShortName); +} + +/** + * Calculate Custom Buffers ... + * + * @param bar_index: Integer, Represent Current Bar ... + * @param prevCalculated: Integer, Represent Previous Calculated Bars ... + * @param ratesTotal: Integer, Represents All Available Bars ... + * @param open: Double Array, History of Open Prices ... + * @param high: Double Array, History of High Prices ... + * @param close: Double Array, History of Close Prices ... + * @param low: Double Array, History of Low Prices ... + * @param tickVolume: Long, History of Tick Volumes on Bar ... + */ +void CalculateBuffers( + int bar_index, // Selected Bar Index + const int prevCalculated, + const int ratesTotal, + const double &open[], + const double &high[], + const double &close[], + const double &low[], + const long &tickVolume[] // +) +{ + // + int barsLimit = startCalculationForLastBars > 0 + ? startCalculationForLastBars + : 0; + // + // bool canCalculate = true; + bool canCalculate = + barsLimit == 0 || + bar_index <= barsLimit; + if (canCalculate) + { + // + CalculateDonchains( + bar_index, + prevCalculated, + ratesTotal, + open, + high, + close, + low, + tickVolume // + ); + } + else + { + FillBuffersZero(bar_index); + } +} + +// +// Custom ... + +/** + * Fill All Bufers to Zero Vlue for Specified Bar Index ... + * + * @param barIndex: Integer ... + */ +void FillBuffersZero(int barIndex) +{ + // + donOpenUpperBuffer[barIndex] = EMPTY_VALUE; + donOpenLowerBuffer[barIndex] = EMPTY_VALUE; + donCloseUpperBuffer[barIndex] = EMPTY_VALUE; + donCloseLowerBuffer[barIndex] = EMPTY_VALUE; + donHighUpperBuffer[barIndex] = EMPTY_VALUE; + donHighLowerBuffer[barIndex] = EMPTY_VALUE; + donLowUpperBuffer[barIndex] = EMPTY_VALUE; + donLowLowerBuffer[barIndex] = EMPTY_VALUE; +} + +/** + * Calculate Donchain ... + * + * @param bar_index: Integer, Bar Index ... + * @param prevCalculated: Integer, Represent Previous Calculated Bars ... + * @param ratesTotal: Integer, Represents All Available Bars ... + * @param open: Double Array, History of Open Prices ... + * @param high: Double Array, History of High Prices ... + * @param close: Double Array, History of Close Prices ... + * @param low: Double Array, History of Low Prices ... + * @param tickVolume: Long, History of Tick Volumes on Bar ... + * @param _length: Integer, Donchain Length ... + * @param _ouBuffer: Double Array Reference ... + * @param _olBuffer: Double Array Reference ... + * @param _huBuffer: Double Array Reference ... + * @param _hlBuffer: Double Array Reference ... + * @param _luBuffer: Double Array Reference ... + * @param _llBuffer: Double Array Reference ... + * @param _cuBuffer: Double Array Reference ... + * @param _clBuffer: Double Array Reference ... + */ +void CalculateDonchain( + int bar_index, // Selected Bar Index + const int prevCalculated, + const int ratesTotal, + // + const double &open[], + const double &high[], + const double &close[], + const double &low[], + const long &tickVolume[], + // + int _length, + // + double &_ouBuffer[], + double &_olBuffer[], + double &_huBuffer[], + double &_hlBuffer[], + double &_luBuffer[], + double &_llBuffer[], + double &_cuBuffer[], + double &_clBuffer[] // +) +{ + // + double iUpper = 0; + double iLower = 0; + + // + // OPEN ... + + // + int from = bar_index; + + // + iUpper = open[ArrayMaximum(open, from, _length)]; + iLower = open[ArrayMinimum(open, from, _length)]; + + // + _ouBuffer[bar_index] = iUpper; + _olBuffer[bar_index] = iLower; + + // + // HIGH ... + + // + iUpper = high[ArrayMaximum(high, from, _length)]; + iLower = high[ArrayMinimum(high, from, _length)]; + + // + _huBuffer[bar_index] = iUpper; + _hlBuffer[bar_index] = iLower; + + // + // LOW ... + + // + iUpper = low[ArrayMaximum(low, from, _length)]; + iLower = low[ArrayMinimum(low, from, _length)]; + + // + _luBuffer[bar_index] = iUpper; + _llBuffer[bar_index] = iLower; + + // + // CLOSE ... + + // + iUpper = close[ArrayMaximum(close, from, _length)]; + iLower = close[ArrayMinimum(close, from, _length)]; + + // + _cuBuffer[bar_index] = iUpper; + _clBuffer[bar_index] = iLower; +} + +/** + * Calculate Different VWaps ... + * + * @param bar_index: Integer, Represent Current Bar ... + * @param prevCalculated: Integer, Represent Previous Calculated Bars ... + * @param ratesTotal: Integer, Represents All Available Bars ... + * @param open: Double Array, History of Open Prices ... + * @param high: Double Array, History of High Prices ... + * @param close: Double Array, History of Close Prices ... + * @param low: Double Array, History of Low Prices ... + * @param tickVolume: Long, History of Tick Volumes on Bar ... + */ +void CalculateDonchains( + int bar_index, // Selected Bar Index + const int prevCalculated, + const int ratesTotal, + const double &open[], + const double &high[], + const double &close[], + const double &low[], + const long &tickVolume[] // +) +{ + // + CalculateDonchain( + // + bar_index, + prevCalculated, + ratesTotal, + // + open, + high, + close, + low, + tickVolume, + // + donchainLength, + // + donOpenUpperBuffer, + donOpenLowerBuffer, + donHighUpperBuffer, + donHighLowerBuffer, + donLowUpperBuffer, + donLowLowerBuffer, + donCloseUpperBuffer, + donCloseLowerBuffer // + ); +} + +// \ No newline at end of file diff --git a/Indicators/x-saherelm.x121.xpv.mq5 b/Indicators/x-saherelm.x121.xpv.mq5 new file mode 100644 index 00000000..2b2e4b1c --- /dev/null +++ b/Indicators/x-saherelm.x121.xpv.mq5 @@ -0,0 +1,1002 @@ +/////////////////////////////////////////////////////// +// +// SaherElm IT Center MQL5 Indicator +// ------------------------------------------------- +// Name: X121 XPV +// Description: XPV ... +// +// +// Maintainer: +// ------------ +// Hadi Khazaee Asl (hadi_khazaee_asl@yahoo.com) +// +////////////////////////////////////////////////////// +// +// Global Properties ... +#property copyright "Copyright 2023, SaherElm IT Center" +#property link "https://saherelm.ir" +#property version "1.00" +#property description "SaherElm X121 XPV Indicator" +#property strict + +// +// Definitions ... + +// +#define ShortName "X121 XPV" + +// +// Includes Common Library ... +#include "../Libraries/x-saherelm.common.lib.mq5" + +// +// Inputs ... + +// +// Market ... +input group "Market"; + +// +input group "Short"; +input ENUM_X_PERIOD_METHOD scMethod = X_PERIOD_AUTO; // How to Find Period +input ENUM_TIMEFRAMES scPeriod = NULL; // Time Period + +// +input group "Medium"; +input ENUM_X_PERIOD_METHOD mcMethod = X_PERIOD_AUTO; // How to Find Period +input ENUM_TIMEFRAMES mcPeriod = NULL; // Time Period + +// +input group "Long"; +input ENUM_X_PERIOD_METHOD lcMethod = X_PERIOD_AUTO; // How to Find Period +input ENUM_TIMEFRAMES lcPeriod = NULL; // Time Period + +// +input group "Hind"; +input ENUM_X_PERIOD_METHOD hcMethod = X_PERIOD_AUTO; // How to Find Period +input ENUM_TIMEFRAMES hcPeriod = NULL; // Time Period + +// +input group "Boundary Detection"; +input ENUM_SERIESMODE hhMode = MODE_HIGH; // Highest High Calculation Method +input ENUM_SERIESMODE llMode = MODE_LOW; // Lowest Low Calculation Method + +// +input group "Sar Detection"; +input double sarStep = 0.02; // Step +input double sarMax = 0.2; // Maximum + +// +// Presentation ... +input group "Presentation"; + +// +input int startCalculationForLastBars = 1000; // Calculate Last n Bars +input int sarArrowCode = 159; // Parabolic Sar Arrow Code +input int peaksArrowCode = 159; // Peaks Arrow Code +input int valesArrowCode = 159; // Vales Arrow Code + +// +input bool showSar = true; // Show Parabolic Sar +input bool showPeaks = true; // Show Peaks +input bool showVales = true; // Show Vales + +// +// Buffers ... + +// +#define hideColorIDX 0 +#define bullishColorIDX 1 +#define bearishColorIDX 2 +#define neuturalColorIDX 3 + +// +#property indicator_chart_window + +// +#property indicator_buffers 13 +#property indicator_plots 3 + +// +// Plot Buffers ... + +// +// PEAKS ... + +// +#define peaksBufferIndex 0 +double peaksBuffer[]; + +// +#property indicator_label1 "X121 PEAKS" +#property indicator_type1 DRAW_ARROW +#property indicator_color1 clrAqua +#property indicator_width1 1 + +// +// VALES ... + +// +#define valesBufferIndex 1 +double valesBuffer[]; + +// +#property indicator_label2 "X121 VALES" +#property indicator_type2 DRAW_ARROW +#property indicator_color2 clrMagenta +#property indicator_width2 1 + +// +#define sarBufferIndex 2 +double sarBuffer[]; + +// +#property indicator_label3 "X121 SAR" +#property indicator_type3 DRAW_ARROW +#property indicator_color3 clrYellow +#property indicator_width3 1 + +// +// Data Buffers ... + +// +int mLastBufferIndex = 2; + +// +// CURRENT ... + +// +#define cHHBufferIndex mLastBufferIndex + 1 +double cHHBuffer[]; + +// +#define cLLBufferIndex mLastBufferIndex + 2 +double cLLBuffer[]; + +// +// SHORT ... + +// +#define sHHBufferIndex mLastBufferIndex + 3 +double sHHBuffer[]; + +// +#define sLLBufferIndex mLastBufferIndex + 4 +double sLLBuffer[]; + +// +// MEDIUM ... + +// +#define mHHBufferIndex mLastBufferIndex + 5 +double mHHBuffer[]; + +// +#define mLLBufferIndex mLastBufferIndex + 6 +double mLLBuffer[]; + +// +// LONG ... + +// +#define lHHBufferIndex mLastBufferIndex + 7 +double lHHBuffer[]; + +// +#define lLLBufferIndex mLastBufferIndex + 8 +double lLLBuffer[]; + +// +// HIND ... + +// +#define hHHBufferIndex mLastBufferIndex + 9 +double hHHBuffer[]; + +// +#define hLLBufferIndex mLastBufferIndex + 10 +double hLLBuffer[]; + +// +// Variables, Properties and etc ... + +// +// this counts Available Bars ... +int limit; + +// +int maxLength; + +// +// SAR Handler ... +int sarHandler = INVALID_HANDLE; + +// +// XMarketCycle sc; +int mSCLength = 0; +ENUM_TIMEFRAMES mSCPeriod = NULL; + +// +// XMarketCycle mc; +int mMCLength = 0; +ENUM_TIMEFRAMES mMCPeriod = NULL; + +// +// XMarketCycle lc; +int mLCLength = 0; +ENUM_TIMEFRAMES mLCPeriod = NULL; + +// +// XMarketCycle hc; +int mHCLength = 0; +ENUM_TIMEFRAMES mHCPeriod = NULL; + +// +// Event Handlers ... + +/** + * Initialize Indicator ... + * + * @return ( int ) + */ +int OnInit() +{ + // + // Validate Inputs ... + if (!ValidateInputs()) + { + return INIT_PARAMETERS_INCORRECT; + } + + // + // Initialize Indicator Handlers ... + + // + // SAR ... + sarHandler = iSAR( + _Symbol, + _Period, + sarStep, + sarMax // + ); + bool isInited = sarHandler != INVALID_HANDLE; + if (!isInited) + { + return INIT_FAILED; + } + + // + if (!InitMarketCycles()) + { + return INIT_PARAMETERS_INCORRECT; + } + + // + // because in some cases we may have more than one input for + // calculation and we must prevent any calculation + // untill we pass the biggest input length, here we get max Input length + // and then wait until pass it ... + maxLength = ExtractMaxLengthOfInputs(); + + // + // Define Index Buffers ... + DefineBuffers(); + + // + // Set Indicator ShortName ... + SetIndicatorName(); + + // + // Init Succeed ... + return INIT_SUCCEEDED; +} + +/** + * De Initialize Indicator ... + * + * @param reason: Integer, De Initialization Reason ... + */ +void OnDeinit(const int reason) +{ + // + // REASON_PROGRAM 0 The EA has stopped working calling the ExpertRemove() function + // REASON_REMOVE 1 Program removed from a chart + // REASON_RECOMPILE 2 Program recompiled + // REASON_CHARTCHANGE 3 A symbol or a chart period is changed + // REASON_CHARTCLOSE 4 Chart closed + // REASON_PARAMETERS 5 Inputs changed by a user + // REASON_ACCOUNT 6 Another account has been activated or reconnection to the trade server has occurred due to changes in the account settings + // REASON_TEMPLATE 7 Another chart template applied + // REASON_INITFAILED 8 The OnInit() handler returned a non-zero value + // REASON_CLOSE 9 Terminal closed + + // + IndicatorRelease(sarHandler); +} + +/** + * Calculate Bars ... + * + * @param rates_total: Integer, Total Bars on Chart ... + * @param prev_calculated: Integer, Total Calculated Bars on Charts ... + * @param time: DateTime Array, History of Open Time ... + * @param open: Double Array, History of Open Prices ... + * @param high: Double Array, History of High Prices ... + * @param low: Double Array, History of Low Prices ... + * @param close: Double Array, History of Close Prices ... + * @param tick_volume: Long, History of Tick Volumes on Bar ... + * @param volume: Long, History of Trade Volumes ... + * @param spread: Double, History of Spread Price ... + * + * @return ( int ) + */ +int OnCalculate( + const int rates_total, + const int prev_calculated, + const datetime &time[], + const double &open[], + const double &high[], + const double &low[], + const double &close[], + const long &tick_volume[], + const long &volume[], + const int &spread[] // +) +{ + // + // Prepare Buffers ... + ArraySetAsSeries(time, true); + ArraySetAsSeries(open, true); + ArraySetAsSeries(high, true); + ArraySetAsSeries(low, true); + ArraySetAsSeries(close, true); + ArraySetAsSeries(tick_volume, true); + ArraySetAsSeries(volume, true); + ArraySetAsSeries(spread, true); + + // + // Validate Calculated Bars ... + + // + // SAR ... + int sarCalculatedBars = BarsCalculated(sarHandler); + + // + bool isPassedRequiredCalculatedBars = + // + // SAR ... + sarCalculatedBars >= maxLength + // + ; + if (!isPassedRequiredCalculatedBars) + { + return prev_calculated; + } + + // + limit = (prev_calculated > rates_total || prev_calculated <= 0) + ? rates_total + : (rates_total - prev_calculated) + 1; + + // + // Buffers Copy ... + + // + // SAR ... + int copiedSars = CopyBuffer(sarHandler, 0, 0, limit, sarBuffer); + + // + // Validate Copied Items ... + bool isPassedRequiredCopiedItems = + // + // SAR ... + copiedSars > 0 + // + ; + if (!isPassedRequiredCopiedItems) + { + return prev_calculated; + } + + // + // Main Loop ... + for (int i = limit - 1; i >= 0 && !IsStopped(); i--) + { + // + CalculateBuffers( + i, + prev_calculated, + rates_total, + // + open, + high, + close, + low, + tick_volume // + ); + } + + // + return rates_total; +} + +// +// Functions ... + +/** + * Validate Input Args for Initialization ... + * + * @return ( bool ) + */ +bool ValidateInputs() +{ + // + bool result = false; + + // + result = + // + // SAR ... + sarMax > 0 && + sarStep > 0 && + sarMax > sarStep && + // + // XPV ... + (IsValid(scMethod, scPeriod) && + IsValid(mcMethod, mcPeriod) && + IsValid(lcMethod, lcPeriod) && + IsValid(hcMethod, hcPeriod)) + // + ; + + // + return result; +} + +/** + * Extract Max Length of Inputs ... + * + * @return ( int ) + */ +int ExtractMaxLengthOfInputs() +{ + // + int result = 0; + + // + return result; +} + +/** + * Define Required Buffers ... + */ +void DefineBuffers() +{ + // + // Plot Buffers ... + + // + // PEAKS ... + + // + ENUM_DRAW_TYPE peaksDrawType = showPeaks ? DRAW_ARROW : DRAW_NONE; + + // + ArraySetAsSeries(peaksBuffer, true); + SetIndexBuffer(peaksBufferIndex, peaksBuffer, INDICATOR_DATA); + + // + PlotIndexSetInteger(peaksBufferIndex, PLOT_SHOW_DATA, showPeaks); + PlotIndexSetInteger(peaksBufferIndex, PLOT_DRAW_TYPE, peaksDrawType); + + // + PlotIndexSetDouble(peaksBufferIndex, PLOT_EMPTY_VALUE, 0); + PlotIndexSetInteger(peaksBufferIndex, PLOT_ARROW, peaksArrowCode); + + // + // VALES ... + + // + ENUM_DRAW_TYPE valesDrawType = showVales ? DRAW_ARROW : DRAW_NONE; + + // + ArraySetAsSeries(valesBuffer, true); + SetIndexBuffer(valesBufferIndex, valesBuffer, INDICATOR_DATA); + + // + PlotIndexSetInteger(valesBufferIndex, PLOT_SHOW_DATA, showVales); + PlotIndexSetInteger(valesBufferIndex, PLOT_DRAW_TYPE, valesDrawType); + + // + PlotIndexSetDouble(valesBufferIndex, PLOT_EMPTY_VALUE, 0); + PlotIndexSetInteger(valesBufferIndex, PLOT_ARROW, valesArrowCode); + + // + // SAR ... + + // + ENUM_DRAW_TYPE sarDrawType = showSar ? DRAW_ARROW : DRAW_NONE; + + // + ArraySetAsSeries(sarBuffer, true); + SetIndexBuffer(sarBufferIndex, sarBuffer, INDICATOR_DATA); + + // + PlotIndexSetInteger(sarBufferIndex, PLOT_SHOW_DATA, showSar); + PlotIndexSetInteger(sarBufferIndex, PLOT_DRAW_TYPE, sarDrawType); + + // + PlotIndexSetDouble(sarBufferIndex, PLOT_EMPTY_VALUE, 0); + PlotIndexSetInteger(sarBufferIndex, PLOT_ARROW, sarArrowCode); + + // + // Data Buffers ... + + // + // CURRENT ... + + // + ArraySetAsSeries(cHHBuffer, true); + SetIndexBuffer(cHHBufferIndex, cHHBuffer, INDICATOR_CALCULATIONS); + + // + ArraySetAsSeries(cLLBuffer, true); + SetIndexBuffer(cLLBufferIndex, cLLBuffer, INDICATOR_CALCULATIONS); + + // + // SHORT ... + + // + ArraySetAsSeries(sHHBuffer, true); + SetIndexBuffer(sHHBufferIndex, sHHBuffer, INDICATOR_CALCULATIONS); + + // + ArraySetAsSeries(sLLBuffer, true); + SetIndexBuffer(sLLBufferIndex, sLLBuffer, INDICATOR_CALCULATIONS); + + // + // MEDIUM ... + + // + ArraySetAsSeries(mHHBuffer, true); + SetIndexBuffer(mHHBufferIndex, mHHBuffer, INDICATOR_CALCULATIONS); + + // + ArraySetAsSeries(mLLBuffer, true); + SetIndexBuffer(mLLBufferIndex, mLLBuffer, INDICATOR_CALCULATIONS); + + // + // LONG ... + + // + ArraySetAsSeries(lHHBuffer, true); + SetIndexBuffer(lHHBufferIndex, lHHBuffer, INDICATOR_CALCULATIONS); + + // + ArraySetAsSeries(lLLBuffer, true); + SetIndexBuffer(lLLBufferIndex, lLLBuffer, INDICATOR_CALCULATIONS); + + // + // HIND ... + + // + ArraySetAsSeries(hHHBuffer, true); + SetIndexBuffer(hHHBufferIndex, hHHBuffer, INDICATOR_CALCULATIONS); + + // + ArraySetAsSeries(hLLBuffer, true); + SetIndexBuffer(hLLBufferIndex, hLLBuffer, INDICATOR_CALCULATIONS); +} + +/** + * Set Indicator Short Name and also we can define Buffers Labels ... + */ +void SetIndicatorName() +{ + IndicatorSetString(INDICATOR_SHORTNAME, ShortName); +} + +/** + * Calculate Custom Buffers ... + * + * @param bar_index: Integer, Represent Current Bar ... + * @param prevCalculated: Integer, Represent Previous Calculated Bars ... + * @param ratesTotal: Integer, Represents All Available Bars ... + * @param open: Double Array, History of Open Prices ... + * @param high: Double Array, History of High Prices ... + * @param close: Double Array, History of Close Prices ... + * @param low: Double Array, History of Low Prices ... + * @param tickVolume: Long, History of Tick Volumes on Bar ... + */ +void CalculateBuffers( + int bar_index, // Selected Bar Index + const int prevCalculated, + const int ratesTotal, + const double &open[], + const double &high[], + const double &close[], + const double &low[], + const long &tickVolume[] // +) +{ + // + int barsLimit = startCalculationForLastBars > 0 + ? startCalculationForLastBars + : 0; + // + // bool canCalculate = true; + bool canCalculate = + barsLimit == 0 || + bar_index <= barsLimit; + if (canCalculate) + { + // + // Calculate Cycles ... + CalculateCycles(bar_index); + + // + // Calculate Peaks and Vales ... + CalculatePeaksAndVales(bar_index); + } + else + { + FillBuffersZero(bar_index); + } +} + +// +// Custom ... + +/** + * Initial Market Cycles ... + * + * @return ( bool ) + */ +bool InitMarketCycles() +{ + // + bool result = false; + + // + int cPeriodSeconds = PeriodSeconds(_Period); + + // + // Find Cycle Period ... + if (scMethod == X_PERIOD_AUTO) + { + // + // Select Period ... + mSCPeriod = GetCyclePeriod( + X_MARKET_CYCLE_SHORT, + _Period // + ); + } + else + { + mSCPeriod = scPeriod; + } + + // + if (IsValid(mSCPeriod)) + { + mSCLength = PeriodSeconds(mSCPeriod) / cPeriodSeconds; + } + + // + // Find Cycle Period ... + if (mcMethod == X_PERIOD_AUTO) + { + // + // Select Period ... + mMCPeriod = GetCyclePeriod( + X_MARKET_CYCLE_MEDIUM, + _Period // + ); + } + else + { + mMCPeriod = mcPeriod; + } + + // + if (IsValid(mMCPeriod)) + { + mMCLength = PeriodSeconds(mMCPeriod) / cPeriodSeconds; + } + + // + // Find Cycle Period ... + if (lcMethod == X_PERIOD_AUTO) + { + // + // Select Period ... + mLCPeriod = GetCyclePeriod( + X_MARKET_CYCLE_LONG, + _Period // + ); + } + else + { + mLCPeriod = lcPeriod; + } + + // + if (IsValid(mLCPeriod)) + { + mLCLength = PeriodSeconds(mLCPeriod) / cPeriodSeconds; + } + + // + // Find Cycle Period ... + if (hcMethod == X_PERIOD_AUTO) + { + // + // Select Period ... + mHCPeriod = GetCyclePeriod( + X_MARKET_CYCLE_HIND, + _Period // + ); + } + else + { + mHCPeriod = hcPeriod; + } + + // + if (IsValid(mHCPeriod)) + { + mHCLength = PeriodSeconds(mHCPeriod) / cPeriodSeconds; + } + + // + result = mSCLength > 0 && + mMCLength > mSCLength && + mLCLength > mMCLength && + mHCLength > mLCLength; + + // + return result; +} + +/** + * Fill All Bufers to Zero Vlue for Specified Bar Index ... + * + * @param barIndex: Integer ... + */ +void FillBuffersZero(int barIndex) +{ + // + // CURRENT ... + cHHBuffer[barIndex] = EMPTY_VALUE; + cLLBuffer[barIndex] = EMPTY_VALUE; + + // + // SHORT ... + sHHBuffer[barIndex] = EMPTY_VALUE; + sLLBuffer[barIndex] = EMPTY_VALUE; + + // + // MEDIUM ... + mHHBuffer[barIndex] = EMPTY_VALUE; + mLLBuffer[barIndex] = EMPTY_VALUE; + + // + // LONG ... + lHHBuffer[barIndex] = EMPTY_VALUE; + lLLBuffer[barIndex] = EMPTY_VALUE; + + // + // HIND ... + hHHBuffer[barIndex] = EMPTY_VALUE; + hLLBuffer[barIndex] = EMPTY_VALUE; + + // + // PEAKS ... + peaksBuffer[barIndex] = EMPTY_VALUE; + + // + // VALES ... + valesBuffer[barIndex] = EMPTY_VALUE; + + // + // SARS ... + sarBuffer[barIndex] = EMPTY_VALUE; +} + +/** + * Calculate Specified Market Cycle Info ... + * + * @param barIndex: Integer, Bar Index ... + * @param cycle: ENUM_X_MARKET_CYCLES member, Specified Cycle ... + * @param hhBuffer: Highest High Buffer Reference ... + * @param llBuffer: Lowest Low Buffer Reference ... + */ +void CalculateCycle( + int barIndex, + ENUM_X_MARKET_CYCLES cycle, + double &hhBuffer[], + double &llBuffer[] // +) +{ + // + XOHCL bar; + bool isBarInited = bar.Init( + _Symbol, + _Period, + barIndex + // + ); + if (!isBarInited) + { + return; + } + + // + int mLength = 0; + switch (cycle) + { + // + case X_MARKET_CYCLE_SHORT: + mLength = mSCLength; + break; + + // + case X_MARKET_CYCLE_MEDIUM: + mLength = mMCLength; + break; + + // + case X_MARKET_CYCLE_LONG: + mLength = mLCLength; + break; + + // + case X_MARKET_CYCLE_HIND: + mLength = mHCLength; + break; + } + + // + if (mLength == 0) + { + return; + } + + // + // Find Highest High ... + double hhValue = bar.FindHighest( + mLength, + hhMode + // + ); + hhBuffer[barIndex] = hhValue; + + // + // Find Lowest Low ... + double llValue = bar.FindLowest( + mLength, + llMode + // + ); + llBuffer[barIndex] = llValue; +} + +/** + * Claculate Cycles ... + * + * @param barIndex: Integer, Bar Index ... + */ +void CalculateCycles(int barIndex) +{ + // + // SHORT ... + CalculateCycle( + barIndex, + X_MARKET_CYCLE_SHORT, + sHHBuffer, + sLLBuffer // + ); + + // + // MEDIUM ... + CalculateCycle( + barIndex, + X_MARKET_CYCLE_MEDIUM, + mHHBuffer, + mLLBuffer // + ); + + // + // LONG ... + CalculateCycle( + barIndex, + X_MARKET_CYCLE_LONG, + lHHBuffer, + lLLBuffer // + ); + + // + // HIND ... + CalculateCycle( + barIndex, + X_MARKET_CYCLE_HIND, + hHHBuffer, + hLLBuffer // + ); +} + +/** + * Calculate Peaks and Vales ... + * + * @param barIndex: Integer, Bar Index ... + */ +void CalculatePeaksAndVales(int barIndex) +{ + // + int lastIndex = barIndex + 1; + int barsCount = iBars(_Symbol, _Period); + + // + // PEAKS ... + double lastPeak = + lastIndex < barsCount + ? peaksBuffer[lastIndex] + : 0; + + // + double isHH = sHHBuffer[barIndex]; + double imHH = mHHBuffer[barIndex]; + double ilHH = lHHBuffer[barIndex]; + double ihHH = hHHBuffer[barIndex]; + + // + double iHHs[4] = { + isHH, + imHH, + ilHH, + ihHH // + }; + double rValue = GetAverage(iHHs); + bool isPeak = rValue == isHH && + isHH == imHH && + imHH == ilHH && + ilHH == ihHH; + double iPeak = + isPeak + ? rValue + : lastPeak; + peaksBuffer[barIndex] = iPeak; + + // + // VALES ... + double lastVale = + lastIndex < barsCount + ? valesBuffer[lastIndex] + : 0; + + // + double isLL = sLLBuffer[barIndex]; + double imLL = mLLBuffer[barIndex]; + double ilLL = lLLBuffer[barIndex]; + double ihLL = hLLBuffer[barIndex]; + + // + double iLLs[4] = { + isLL, + imLL, + ilLL, + ihLL // + }; + double sValue = GetAverage(iLLs); + bool isVale = sValue == isLL && + isLL == imLL && + imLL == ilLL && + ilLL == ihLL; + double iVale = + isVale + ? sValue + : lastVale; + valesBuffer[barIndex] = iVale; +} + +// \ No newline at end of file diff --git a/Indicators/x-saherelm.x121.xstr.mq5 b/Indicators/x-saherelm.x121.xstr.mq5 new file mode 100644 index 00000000..053725b0 --- /dev/null +++ b/Indicators/x-saherelm.x121.xstr.mq5 @@ -0,0 +1,623 @@ +/////////////////////////////////////////////////////// +// +// SaherElm IT Center MQL5 Indicator +// ------------------------------------------------- +// Name: X121 XSTR +// Description: XSTR ... +// +// +// Maintainer: +// ------------ +// Hadi Khazaee Asl (hadi_khazaee_asl@yahoo.com) +// +////////////////////////////////////////////////////// +// +// Global Properties ... +#property copyright "Copyright 2023, SaherElm IT Center" +#property link "https://saherelm.ir" +#property version "1.00" +#property description "SaherElm X121 XSTR Indicator" +#property strict + +// +// Definitions ... + +// +#define ShortName "X121 XSTR" + +// +// Includes Common Library ... +#include "../Classes/x-saherelm.x-poi.class.mq5" +#include "../Classes/x-saherelm.x-poi.drawer.class.mq5" +#include "../Libraries/x-saherelm.common.lib.mq5" + +// +// Inputs ... + +// +// Market ... +input group "Market"; +input int strLength = 14; // Length +input double strMultiplier = 3; // Multiplier +input ENUM_APPLIED_PRICE strAppliedTo = PRICE_MEDIAN; // Applied To + +// +input group "Presentation"; + +// +input bool showStr = true; // Show Str + +// +// Buffers ... + +// +#define hideColorIDX 0 +#define bullishColorIDX 1 +#define bearishColorIDX 2 +#define neuturalColorIDX 3 + +// +#property indicator_chart_window + +// +#property indicator_buffers 7 +#property indicator_plots 1 + +// +// STR ... +#define strBufferIndex 0 +double strBuffer[]; + +#define strColorBufferIndex 1 +double strColorBuffer[]; + +// +#define strPlotBufferIndex 1 +#property indicator_label1 "X121 STR" +#property indicator_type1 DRAW_COLOR_LINE +#property indicator_color1 CLR_NONE, clrLime, clrRed, clrGray +#property indicator_style1 STYLE_SOLID +#property indicator_width1 2 + +// +// Data Buffers ... + +// +int mLastBufferIndex = 1; + +// +// STR ... + +// +// Atr ... +#define atrBufferIndex mLastBufferIndex + 1 +double atrBuffer[]; + +// +// Price ... +#define strPriceBufferIndex mLastBufferIndex + 2 +double strPriceBuffer[]; + +// +// Up ... +#define strUpBufferIndex mLastBufferIndex + 3 +double strUpBuffer[]; + +// +// Down ... +#define strDownBufferIndex mLastBufferIndex + 4 +double strDownBuffer[]; + +// +// Trend ... +#define strStateBufferIndex mLastBufferIndex + 5 +double strStateBuffer[]; + +// +// Variables, Properties and etc ... + +// +// this counts Available Bars ... +int limit; + +// +int maxLength; + +// +// ATR Handler ... +int atrHandler = INVALID_HANDLE; + +// +bool isStrTrendChanged; +bool isStrStartBearishTrend; +bool isStrStartBullishTrend; + +// +int changeOfTrend; +int startBearishTrend; +int startBullishTrend; + +// +// Event Handlers ... + +/** + * Initialize Indicator ... + * + * @return ( int ) + */ +int OnInit() +{ + // + // Validate Inputs ... + if (!ValidateInputs()) + { + return INIT_PARAMETERS_INCORRECT; + } + + // + // Initialize Indicator Handlers ... + + // + // ATR ... + atrHandler = iATR( + _Symbol, + _Period, + strLength // + ); + bool isInited = atrHandler != INVALID_HANDLE; + if (!isInited) + { + return INIT_FAILED; + } + + // + // because in some cases we may have more than one input for + // calculation and we must prevent any calculation + // untill we pass the biggest input length, here we get max Input length + // and then wait until pass it ... + maxLength = ExtractMaxLengthOfInputs(); + + // + // Define Index Buffers ... + DefineBuffers(); + + // + // Set Indicator ShortName ... + SetIndicatorName(); + + // + // Init Succeed ... + return INIT_SUCCEEDED; +} + +/** + * De Initialize Indicator ... + * + * @param reason: Integer, De Initialization Reason ... + */ +void OnDeinit(const int reason) +{ + // + // REASON_PROGRAM 0 The EA has stopped working calling the ExpertRemove() function + // REASON_REMOVE 1 Program removed from a chart + // REASON_RECOMPILE 2 Program recompiled + // REASON_CHARTCHANGE 3 A symbol or a chart period is changed + // REASON_CHARTCLOSE 4 Chart closed + // REASON_PARAMETERS 5 Inputs changed by a user + // REASON_ACCOUNT 6 Another account has been activated or reconnection to the trade server has occurred due to changes in the account settings + // REASON_TEMPLATE 7 Another chart template applied + // REASON_INITFAILED 8 The OnInit() handler returned a non-zero value + // REASON_CLOSE 9 Terminal closed + + // + IndicatorRelease(atrHandler); +} + +/** + * Calculate Bars ... + * + * @param rates_total: Integer, Total Bars on Chart ... + * @param prev_calculated: Integer, Total Calculated Bars on Charts ... + * @param time: DateTime Array, History of Open Time ... + * @param open: Double Array, History of Open Prices ... + * @param high: Double Array, History of High Prices ... + * @param low: Double Array, History of Low Prices ... + * @param close: Double Array, History of Close Prices ... + * @param tick_volume: Long, History of Tick Volumes on Bar ... + * @param volume: Long, History of Trade Volumes ... + * @param spread: Double, History of Spread Price ... + * + * @return ( int ) + */ +int OnCalculate( + const int rates_total, + const int prev_calculated, + const datetime &time[], + const double &open[], + const double &high[], + const double &low[], + const double &close[], + const long &tick_volume[], + const long &volume[], + const int &spread[] // +) +{ + // + // Prepare Buffers ... + + // + // Fill All Buffers by Zero ... + if (prev_calculated == 0) + { + } + + // + int numOfRequiredAtrs = (prev_calculated > rates_total || prev_calculated < 0) + ? rates_total + : rates_total - prev_calculated; + if (prev_calculated > 0) + { + numOfRequiredAtrs++; + } + + // + // Validate Calculated Bars ... + + // + // ATR ... + int atrCalculatedBars = BarsCalculated(atrHandler); + + // + bool isPassedRequiredCalculatedBars = + // + // ATR ... + atrCalculatedBars >= numOfRequiredAtrs + // + ; + if (!isPassedRequiredCalculatedBars) + { + return prev_calculated; + } + + // + // + // checking for the limit start of calculation of an indicator ... + limit = + (prev_calculated > rates_total || prev_calculated <= 0) + ? maxLength + : prev_calculated - 1; + + // + // Buffers Copy ... + + // + // ATR ... + int copiedAtrs = CopyBuffer(atrHandler, 0, 0, numOfRequiredAtrs, atrBuffer); + + // + // Validate Copied Items ... + bool isPassedRequiredCopiedItems = + // + // ATR ... + copiedAtrs >= numOfRequiredAtrs + // + ; + if (!isPassedRequiredCopiedItems) + { + return prev_calculated; + } + + // + // Main Loop ... + for (int i = limit; i < rates_total && !IsStopped(); i++) + { + // + CalculateBuffers( + i, + prev_calculated, + rates_total, + // + open, + high, + close, + low, + tick_volume // + ); + } + + // + return rates_total; +} + +// +// Functions ... + +/** + * Validate Input Args for Initialization ... + * + * @return ( bool ) + */ +bool ValidateInputs() +{ + // + bool result = + // + // STR ... + strLength > 0 && + strMultiplier > 0 + // + ; + + // + return result; +} + +/** + * Extract Max Length of Inputs ... + * + * @return ( int ) + */ +int ExtractMaxLengthOfInputs() +{ + // + int result = 0; + + // + result = MathMax(1, strLength); + + // + return result; +} + +/** + * Define Required Buffers ... + */ +void DefineBuffers() +{ + // + // STR ... + SetIndexBuffer(strBufferIndex, strBuffer, INDICATOR_DATA); + SetIndexBuffer(strColorBufferIndex, strColorBuffer, INDICATOR_COLOR_INDEX); + + // + // Data Buffers ... + + // + // STR ... + + // + SetIndexBuffer(strUpBufferIndex, strUpBuffer, INDICATOR_CALCULATIONS); + SetIndexBuffer(strDownBufferIndex, strDownBuffer, INDICATOR_CALCULATIONS); + SetIndexBuffer(strPriceBufferIndex, strPriceBuffer, INDICATOR_CALCULATIONS); + SetIndexBuffer(strStateBufferIndex, strStateBuffer, INDICATOR_CALCULATIONS); +} + +/** + * Set Indicator Short Name and also we can define Buffers Labels ... + */ +void SetIndicatorName() +{ + IndicatorSetString(INDICATOR_SHORTNAME, ShortName); +} + +/** + * Calculate Custom Buffers ... + * + * @param bar_index: Integer, Represent Current Bar ... + * @param prevCalculated: Integer, Represent Previous Calculated Bars ... + * @param ratesTotal: Integer, Represents All Available Bars ... + * @param open: Double Array, History of Open Prices ... + * @param high: Double Array, History of High Prices ... + * @param close: Double Array, History of Close Prices ... + * @param low: Double Array, History of Low Prices ... + * @param tickVolume: Long, History of Tick Volumes on Bar ... + */ +void CalculateBuffers( + int bar_index, // Selected Bar Index + const int prevCalculated, + const int ratesTotal, + const double &open[], + const double &high[], + const double &close[], + const double &low[], + const long &tickVolume[] // +) +{ + // + CalculateStr( + bar_index, + prevCalculated, + ratesTotal, + open, + high, + close, + low // + ); +} + +// +// Custom ... + +/** + * Fill All Bufers to Zero Vlue for Specified Bar Index ... + * + * @param barIndex: Integer ... + */ +void FillBuffersZero(int barIndex) +{ + // + // STR ... + strBuffer[barIndex] = 0; + strUpBuffer[barIndex] = 0; + strDownBuffer[barIndex] = 0; + strPriceBuffer[barIndex] = 0; + strColorBuffer[barIndex] = hideColorIDX; + strStateBuffer[barIndex] = hideColorIDX; +} + +/** + * Calculate STR ... + * + * @param bar_index: Integer, Represent Current Bar ... + * @param prevCalculated: Integer, Represent Previous Calculated Bars ... + * @param ratesTotal: Integer, Represents All Available Bars ... + * @param open: Double Array, History of Open Prices ... + * @param high: Double Array, History of High Prices ... + * @param close: Double Array, History of Close Prices ... + * @param low: Double Array, History of Low Prices ... + */ +void CalculateStr( + int bar_index, // Selected Bar Index + const int prevCalculated, + const int ratesTotal, + const double &open[], + const double &high[], + const double &close[], + const double &low[] // +) +{ + // + // Calculated Price ... + double price = GetAppliedPrice( + strAppliedTo, + open, + high, + low, + close, + bar_index // + ); + strPriceBuffer[bar_index] = price; + + // + double atr = atrBuffer[bar_index]; + + // + // Up ... + strUpBuffer[bar_index] = price + (strMultiplier * atr); + + // + // Down ... + strDownBuffer[bar_index] = price - (strMultiplier * atr); + + // + if (close[bar_index] > strUpBuffer[bar_index - 1]) + { + // + strStateBuffer[bar_index] = 1; + if (strStateBuffer[bar_index - 1] == -1) + { + changeOfTrend = 1; + } + } + else if (close[bar_index] < strDownBuffer[bar_index - 1]) + { + // + strStateBuffer[bar_index] = -1; + if (strStateBuffer[bar_index - 1] == 1) + { + changeOfTrend = 1; + } + } + else if (strStateBuffer[bar_index - 1] == 1) + { + // + strStateBuffer[bar_index] = 1; + changeOfTrend = 0; + } + else if (strStateBuffer[bar_index - 1] == -1) + { + // + strStateBuffer[bar_index] = -1; + changeOfTrend = 0; + } + + // + // Down Trend Starting ... + if (strStateBuffer[bar_index] < 0 && strStateBuffer[bar_index - 1] > 0) + { + startBearishTrend = 1; + } + else + { + startBearishTrend = 0; + } + + // + // Up Trend Starting ... + if (strStateBuffer[bar_index] > 0 && strStateBuffer[bar_index - 1] < 0) + { + startBullishTrend = 1; + } + else + { + startBullishTrend = 0; + } + + // + if (strStateBuffer[bar_index] > 0 && strDownBuffer[bar_index] < strDownBuffer[bar_index - 1]) + { + strDownBuffer[bar_index] = strDownBuffer[bar_index - 1]; + } + + // + if (strStateBuffer[bar_index] < 0 && strUpBuffer[bar_index] > strUpBuffer[bar_index - 1]) + { + strUpBuffer[bar_index] = strUpBuffer[bar_index - 1]; + } + + // + if (startBearishTrend == 1) + { + strUpBuffer[bar_index] = strPriceBuffer[bar_index] + (strMultiplier * atr); + } + + // + if (startBullishTrend == 1) + { + strDownBuffer[bar_index] = strPriceBuffer[bar_index] - (strMultiplier * atr); + } + + // + // Draw the indicator ... + + // + double colorIDX = hideColorIDX; + strColorBuffer[bar_index] = colorIDX; + + // + if (strStateBuffer[bar_index] == 1) + { + // + strBuffer[bar_index] = strDownBuffer[bar_index]; + if (changeOfTrend == 1) + { + strBuffer[bar_index - 1] = strBuffer[bar_index - 2]; + changeOfTrend = 0; + } + + // + colorIDX = bullishColorIDX; + } + else if (strStateBuffer[bar_index] == -1) + { + // + strBuffer[bar_index] = strUpBuffer[bar_index]; + if (changeOfTrend == 1) + { + // + strBuffer[bar_index - 1] = strBuffer[bar_index - 2]; + changeOfTrend = 0; + } + + // + colorIDX = bearishColorIDX; + } + + // + if (showStr) + { + strColorBuffer[bar_index] = colorIDX; + } +} + +// \ No newline at end of file diff --git a/Indicators/x-saherelm.x121.xvwap.mq5 b/Indicators/x-saherelm.x121.xvwap.mq5 new file mode 100644 index 00000000..6b636009 --- /dev/null +++ b/Indicators/x-saherelm.x121.xvwap.mq5 @@ -0,0 +1,711 @@ +/////////////////////////////////////////////////////// +// +// SaherElm IT Center MQL5 Indicator +// ------------------------------------------------- +// Name: X121 XVWAP +// Description: XVWAP ... +// +// +// Maintainer: +// ------------ +// Hadi Khazaee Asl (hadi_khazaee_asl@yahoo.com) +// +////////////////////////////////////////////////////// +// +// Global Properties ... +#property copyright "Copyright 2023, SaherElm IT Center" +#property link "https://saherelm.ir" +#property version "1.00" +#property description "SaherElm X121 XVWAP Indicator" +#property strict + +// +// Definitions ... + +// +#define ShortName "X121 XVWAP" + +// +// Includes Common Library ... +#include "../Libraries/x-saherelm.common.lib.mq5" + +// +// Inputs ... + +// +// Market ... +input group "Market"; +input int vwapFastLength = 20; // Fast Length +input int vwapMidLength = 40; // Mid Length +input int vwapSlowLength = 60; // Slow Length +input ENUM_APPLIED_PRICE vwapAppliedTo = PRICE_CLOSE; // Applied To + +// +// Presentation ... +input group "Presentation"; + +// +input int startCalculationForLastBars = 1000; // Calculate Last n Bars + +// +input bool showVWapFast = true; // Show VWap Fast +input bool showVWapMedium = true; // Show VWap Medium +input bool showVWapSlow = true; // Show VWap Slow + +// +// Buffers ... + +// +#define hideColorIDX 0 +#define bullishColorIDX 1 +#define bearishColorIDX 2 +#define neuturalColorIDX 3 + +// +#property indicator_chart_window + +// +#property indicator_buffers 11 +#property indicator_plots 3 + +// +// Plot Buffers ... + +// +// FAST ... +#define vwapFastBufferIndex 0 +double vwapFastBuffer[]; + +#define vwapFastColorBufferIndex 1 +double vwapFastColorBuffer[]; + +// +#define vwapFastPlotBufferIndex 0 +#property indicator_label1 "X121 VWF" +#property indicator_type1 DRAW_COLOR_LINE +#property indicator_color1 CLR_NONE, clrAqua, clrMagenta, clrGray +#property indicator_style1 STYLE_SOLID +#property indicator_width1 2 + +// +// MID ... +#define vwapMidBufferIndex 2 +double vwapMidBuffer[]; + +#define vwapMidColorBufferIndex 3 +double vwapMidColorBuffer[]; + +// +#define vwapMidPlotBufferIndex 1 +#property indicator_label2 "X121 VWM" +#property indicator_type2 DRAW_COLOR_LINE +#property indicator_color2 CLR_NONE, clrGreen, clrRed, clrGray +#property indicator_style2 STYLE_SOLID +#property indicator_width2 2 + +// +// SLOW ... +#define vwapSlowBufferIndex 4 +double vwapSlowBuffer[]; + +#define vwapSlowColorBufferIndex 5 +double vwapSlowColorBuffer[]; + +// +#define vwapSlowPlotBufferIndex 2 +#property indicator_label3 "X121 VWS" +#property indicator_type3 DRAW_COLOR_LINE +#property indicator_color3 CLR_NONE, clrSteelBlue, clrDarkRed, clrGray +#property indicator_style3 STYLE_SOLID +#property indicator_width3 2 + +// +// Data Buffers ... + +// +int mLastBufferIndex = 5; + +// +// Volume ... +#define vwapVolumeBufferIndex mLastBufferIndex + 1 +double vwapVolumeBuffer[]; + +// +// Price ... +#define vwapPriceBufferIndex mLastBufferIndex + 2 +double vwapPriceBuffer[]; + +// +// Fast State ... +#define vwapFastStateBufferIndex mLastBufferIndex + 3 +double vwapFastStateBuffer[]; + +// +// Mid State ... +#define vwapMidStateBufferIndex mLastBufferIndex + 4 +double vwapMidStateBuffer[]; + +// +// Slow State ... +#define vwapSlowStateBufferIndex mLastBufferIndex + 5 +double vwapSlowStateBuffer[]; + +// +// Variables, Properties and etc ... + +// +// this counts Available Bars ... +int limit; + +// +int maxLength; + +// +// Event Handlers ... + +/** + * Initialize Indicator ... + * + * @return ( int ) + */ +int OnInit() +{ + // + // Validate Inputs ... + if (!ValidateInputs()) + { + return INIT_PARAMETERS_INCORRECT; + } + + // + // Initialize Indicator Handlers ... + + // + // because in some cases we may have more than one input for + // calculation and we must prevent any calculation + // untill we pass the biggest input length, here we get max Input length + // and then wait until pass it ... + maxLength = ExtractMaxLengthOfInputs(); + + // + // Define Index Buffers ... + DefineBuffers(); + + // + // Set Indicator ShortName ... + SetIndicatorName(); + + // + // Init Succeed ... + return INIT_SUCCEEDED; +} + +/** + * De Initialize Indicator ... + * + * @param reason: Integer, De Initialization Reason ... + */ +void OnDeinit(const int reason) +{ + // + // REASON_PROGRAM 0 The EA has stopped working calling the ExpertRemove() function + // REASON_REMOVE 1 Program removed from a chart + // REASON_RECOMPILE 2 Program recompiled + // REASON_CHARTCHANGE 3 A symbol or a chart period is changed + // REASON_CHARTCLOSE 4 Chart closed + // REASON_PARAMETERS 5 Inputs changed by a user + // REASON_ACCOUNT 6 Another account has been activated or reconnection to the trade server has occurred due to changes in the account settings + // REASON_TEMPLATE 7 Another chart template applied + // REASON_INITFAILED 8 The OnInit() handler returned a non-zero value + // REASON_CLOSE 9 Terminal closed +} + +/** + * Calculate Bars ... + * + * @param rates_total: Integer, Total Bars on Chart ... + * @param prev_calculated: Integer, Total Calculated Bars on Charts ... + * @param time: DateTime Array, History of Open Time ... + * @param open: Double Array, History of Open Prices ... + * @param high: Double Array, History of High Prices ... + * @param low: Double Array, History of Low Prices ... + * @param close: Double Array, History of Close Prices ... + * @param tick_volume: Long, History of Tick Volumes on Bar ... + * @param volume: Long, History of Trade Volumes ... + * @param spread: Double, History of Spread Price ... + * + * @return ( int ) + */ +int OnCalculate( + const int rates_total, + const int prev_calculated, + const datetime &time[], + const double &open[], + const double &high[], + const double &low[], + const double &close[], + const long &tick_volume[], + const long &volume[], + const int &spread[] // +) +{ + // + // Prepare Buffers ... + ArraySetAsSeries(time, true); + ArraySetAsSeries(open, true); + ArraySetAsSeries(high, true); + ArraySetAsSeries(low, true); + ArraySetAsSeries(close, true); + ArraySetAsSeries(tick_volume, true); + ArraySetAsSeries(volume, true); + ArraySetAsSeries(spread, true); + + // + // Validate Calculated Bars ... + + // + limit = (prev_calculated > rates_total || prev_calculated <= 0) + ? rates_total + : (rates_total - prev_calculated) + 1; + + // + // Buffers Copy ... + + // + // Main Loop ... + for (int i = limit - 1; i >= 0 && !IsStopped(); i--) + { + // + CalculateBuffers( + i, + prev_calculated, + rates_total, + // + open, + high, + close, + low, + tick_volume // + ); + } + + // + return rates_total; +} + +// +// Functions ... + +/** + * Validate Input Args for Initialization ... + * + * @return ( bool ) + */ +bool ValidateInputs() +{ + // + bool result = false; + + // + result = + // + vwapFastLength > 2 && + vwapMidLength > vwapFastLength && + vwapSlowLength > vwapMidLength + // + ; + + // + return result; +} + +/** + * Extract Max Length of Inputs ... + * + * @return ( int ) + */ +int ExtractMaxLengthOfInputs() +{ + // + int result = 0; + + // + // XVWAP ... + result = MathMax(result, vwapFastLength); + result = MathMax(result, vwapMidLength); + result = MathMax(result, vwapSlowLength); + + // + return result; +} + +/** + * Define Required Buffers ... + */ +void DefineBuffers() +{ + // + // Plot Buffers ... + + // + // Fast ... + ArraySetAsSeries(vwapFastBuffer, true); + ArraySetAsSeries(vwapFastColorBuffer, true); + SetIndexBuffer(vwapFastBufferIndex, vwapFastBuffer, INDICATOR_DATA); + SetIndexBuffer(vwapFastColorBufferIndex, vwapFastColorBuffer, INDICATOR_COLOR_INDEX); + + // + // Mid ... + ArraySetAsSeries(vwapMidBuffer, true); + ArraySetAsSeries(vwapMidColorBuffer, true); + SetIndexBuffer(vwapMidBufferIndex, vwapMidBuffer, INDICATOR_DATA); + SetIndexBuffer(vwapMidColorBufferIndex, vwapMidColorBuffer, INDICATOR_COLOR_INDEX); + + // + // Slow ... + ArraySetAsSeries(vwapSlowBuffer, true); + ArraySetAsSeries(vwapSlowColorBuffer, true); + SetIndexBuffer(vwapSlowBufferIndex, vwapSlowBuffer, INDICATOR_DATA); + SetIndexBuffer(vwapSlowColorBufferIndex, vwapSlowColorBuffer, INDICATOR_COLOR_INDEX); + + // + // Data Buffers ... + + // + // Volumes ... + ArraySetAsSeries(vwapVolumeBuffer, true); + SetIndexBuffer(vwapVolumeBufferIndex, vwapVolumeBuffer, INDICATOR_CALCULATIONS); + + // + // Price ... + ArraySetAsSeries(vwapPriceBuffer, true); + SetIndexBuffer(vwapPriceBufferIndex, vwapPriceBuffer, INDICATOR_CALCULATIONS); + + // + // Fast State ... + ArraySetAsSeries(vwapFastStateBuffer, true); + SetIndexBuffer(vwapFastStateBufferIndex, vwapFastStateBuffer, INDICATOR_CALCULATIONS); + + // + // Mid State ... + ArraySetAsSeries(vwapMidStateBuffer, true); + SetIndexBuffer(vwapMidStateBufferIndex, vwapMidStateBuffer, INDICATOR_CALCULATIONS); + + // + // Slow State ... + ArraySetAsSeries(vwapSlowStateBuffer, true); + SetIndexBuffer(vwapSlowStateBufferIndex, vwapSlowStateBuffer, INDICATOR_CALCULATIONS); +} + +/** + * Set Indicator Short Name and also we can define Buffers Labels ... + */ +void SetIndicatorName() +{ + IndicatorSetString(INDICATOR_SHORTNAME, ShortName); +} + +/** + * Calculate Custom Buffers ... + * + * @param bar_index: Integer, Represent Current Bar ... + * @param prevCalculated: Integer, Represent Previous Calculated Bars ... + * @param ratesTotal: Integer, Represents All Available Bars ... + * @param open: Double Array, History of Open Prices ... + * @param high: Double Array, History of High Prices ... + * @param close: Double Array, History of Close Prices ... + * @param low: Double Array, History of Low Prices ... + * @param tickVolume: Long, History of Tick Volumes on Bar ... + */ +void CalculateBuffers( + int bar_index, // Selected Bar Index + const int prevCalculated, + const int ratesTotal, + const double &open[], + const double &high[], + const double &close[], + const double &low[], + const long &tickVolume[] // +) +{ + // + int barsLimit = startCalculationForLastBars > 0 + ? startCalculationForLastBars + : 0; + // + // bool canCalculate = true; + bool canCalculate = + barsLimit == 0 || + bar_index <= barsLimit; + if (canCalculate) + { + // + // Calculate Required VWAP Data Buffers ... + if (ratesTotal - bar_index <= maxLength) + { + // + CalculateVWAPDataBuffers( + bar_index, + prevCalculated, + ratesTotal, + open, + high, + close, + low, + tickVolume // + ); + + // + // Prevent Moving Forward ... + } + else + { + // + CalculateVWAPDataBuffers( + bar_index, + prevCalculated, + ratesTotal, + open, + high, + close, + low, + tickVolume // + ); + + // + CalculateVWAPS( + bar_index, + prevCalculated, + ratesTotal, + open, + high, + close, + low, + tickVolume // + ); + } + } + else + { + FillBuffersZero(bar_index); + } +} + +// +// Custom ... + +/** + * Fill All Bufers to Zero Vlue for Specified Bar Index ... + * + * @param barIndex: Integer ... + */ +void FillBuffersZero(int barIndex) +{ + // + vwapFastBuffer[barIndex] = EMPTY_VALUE; + vwapMidBuffer[barIndex] = EMPTY_VALUE; + vwapSlowBuffer[barIndex] = EMPTY_VALUE; + vwapVolumeBuffer[barIndex] = EMPTY_VALUE; + vwapPriceBuffer[barIndex] = EMPTY_VALUE; + + // + vwapFastColorBuffer[barIndex] = hideColorIDX; + vwapMidColorBuffer[barIndex] = hideColorIDX; + vwapSlowColorBuffer[barIndex] = hideColorIDX; + vwapFastStateBuffer[barIndex] = hideColorIDX; + vwapMidStateBuffer[barIndex] = hideColorIDX; + vwapSlowStateBuffer[barIndex] = hideColorIDX; +} + +/** + * Calculate VWAP Value for Specified Bar ... + * + * @param bar_index: Integer, Represent Current Bar ... + * @param prevCalculated: Integer, Represent Previous Calculated Bars ... + * @param ratesTotal: Integer, Represents All Available Bars ... + * @param open: Double Array, History of Open Prices ... + * @param high: Double Array, History of High Prices ... + * @param close: Double Array, History of Close Prices ... + * @param low: Double Array, History of Low Prices ... + * @param tickVolume: Long, History of Tick Volumes on Bar ... + * @param _length: Integer, Specified VWAP Length ... + * @param _show: Boolean, Specified Show Buffer or not ... + * @param _buffer: Double Array Reference, Points to Buffer ... + * @param _colorBuffer: Double Array Reference, Points to Color Buffer ... + * @param _stateBuffer: Double Array Reference, Points to State Buffer ... + */ +void CalculateVWAP( + int bar_index, // Selected Bar Index + const int prevCalculated, + const int ratesTotal, + const double &open[], + const double &high[], + const double &close[], + const double &low[], + const long &tickVolume[], + // + int _length, // Calculation Length + bool _show, + double &_buffer[], + double &_colorBuffer[], + double &_stateBuffer[] // +) +{ + // + double vSum = 0; + double pSum = 0; + double mSum = 0; + for (int x = 0; x < _length; x++) + { + // + pSum += vwapPriceBuffer[x + bar_index]; + vSum += vwapVolumeBuffer[x + bar_index]; + mSum += vwapPriceBuffer[x + bar_index] * vwapVolumeBuffer[x + bar_index]; + } + + // + double iValue = mSum / vSum; + iValue = NormalizeDouble(iValue, _Digits); + + // + _buffer[bar_index] = iValue; + + // + bool isBullish = low[bar_index] > iValue; + bool isBearish = high[bar_index] < iValue; + + // + double iColor = + isBullish + ? bullishColorIDX + : isBearish + ? bearishColorIDX + : neuturalColorIDX; + + // + _colorBuffer[bar_index] = hideColorIDX; + _stateBuffer[bar_index] = iColor; + if (_show) + { + _colorBuffer[bar_index] = iColor; + } +} + +/** + * Calculate VWAP Required Data Buffers ... + * + * @param bar_index: Integer, Represent Current Bar ... + * @param prevCalculated: Integer, Represent Previous Calculated Bars ... + * @param ratesTotal: Integer, Represents All Available Bars ... + * @param open: Double Array, History of Open Prices ... + * @param high: Double Array, History of High Prices ... + * @param close: Double Array, History of Close Prices ... + * @param low: Double Array, History of Low Prices ... + * @param tickVolume: Long, History of Tick Volumes on Bar ... + */ +void CalculateVWAPDataBuffers( + int bar_index, // Selected Bar Index + const int prevCalculated, + const int ratesTotal, + const double &open[], + const double &high[], + const double &close[], + const double &low[], + const long &tickVolume[] // +) +{ + // + double price = GetAppliedPrice( + vwapAppliedTo, + open, + high, + low, + close, + bar_index // + ); + vwapPriceBuffer[bar_index] = price; + vwapVolumeBuffer[bar_index] = (double)tickVolume[bar_index]; +} + +/** + * Calculate Different VWaps ... + * + * @param bar_index: Integer, Represent Current Bar ... + * @param prevCalculated: Integer, Represent Previous Calculated Bars ... + * @param ratesTotal: Integer, Represents All Available Bars ... + * @param open: Double Array, History of Open Prices ... + * @param high: Double Array, History of High Prices ... + * @param close: Double Array, History of Close Prices ... + * @param low: Double Array, History of Low Prices ... + * @param tickVolume: Long, History of Tick Volumes on Bar ... + */ +void CalculateVWAPS( + int bar_index, // Selected Bar Index + const int prevCalculated, + const int ratesTotal, + const double &open[], + const double &high[], + const double &close[], + const double &low[], + const long &tickVolume[] // +) +{ + // + // Fast ... + CalculateVWAP( + bar_index, + prevCalculated, + ratesTotal, + open, + high, + close, + low, + tickVolume, + // + vwapFastLength, + showVWapFast, + vwapFastBuffer, + vwapFastColorBuffer, + vwapFastStateBuffer // + ); + + // + // Mid ... + CalculateVWAP( + bar_index, + prevCalculated, + ratesTotal, + open, + high, + close, + low, + tickVolume, + // + vwapMidLength, + showVWapMedium, + vwapMidBuffer, + vwapMidColorBuffer, + vwapMidStateBuffer // + ); + + // + // Fast ... + CalculateVWAP( + bar_index, + prevCalculated, + ratesTotal, + open, + high, + close, + low, + tickVolume, + // + vwapSlowLength, + showVWapSlow, + vwapSlowBuffer, + vwapSlowColorBuffer, + vwapSlowStateBuffer // + ); +} + +// \ No newline at end of file diff --git a/Libraries/x-saherelm.common.lib.mq5 b/Libraries/x-saherelm.common.lib.mq5 index 0978b2d3..e35da6de 100644 --- a/Libraries/x-saherelm.common.lib.mq5 +++ b/Libraries/x-saherelm.common.lib.mq5 @@ -1848,96 +1848,6 @@ struct XOHCL return result; } - // - // Check Bar Breaked Up ... - bool IsBreakeUp(double value) - { - // - bool result = false; - - // - result = - value > 0 && - IsValid(); - if (!result) - { - return result; - } - - // - XOHCL pBar; - result = GetPreviousBar(pBar); - if (!result) - { - return result; - } - - // - result = - // - low > value && - ( - // - (pBar.low < value && - pBar.high > value) - // - || - // - (pBar.high < value) - // - ) - // - ; - - // - return result; - } - - // - // Check Bar Breaked Down ... - bool IsBreakeDown(double value) - { - // - bool result = false; - - // - result = - value > 0 && - IsValid(); - if (!result) - { - return result; - } - - // - XOHCL pBar; - result = GetPreviousBar(pBar); - if (!result) - { - return result; - } - - // - result = - // - high < value && - ( - // - (pBar.high > value && - pBar.low < value) - // - || - // - (pBar.low > value) - // - ) - // - ; - - // - return result; - } - // // Other ... string GetTag(string prefix = "") @@ -6462,6 +6372,94 @@ double GetSlope( return result; } +// +// Check Bar Reject Specified Value ... +bool IsBarReject( + double value, + ENUM_X_DIRECTION dir, + XOHCL &bar // +) +{ + // + bool result = false; + + // + result = value > 0 && + bar.IsValid() && + HasDirection(dir); + if (!result) + { + return result; + } + + // + bool isUp = IsBullish(dir); + bool isDown = IsBearish(dir); + + // + result = + isUp + ? bar.low < value && + bar.GetDown() > value + : isDown + ? bar.high > value && + bar.GetUp() < value + : false; + + // + return result; +} + +// +// Check Bar Break Specified Value ... +bool IsBarBreak( + double value, + ENUM_X_DIRECTION dir, + XOHCL &bar // +) +{ + // + bool result = false; + + // + result = value > 0 && + bar.IsValid() && + HasDirection(dir); + if (!result) + { + return result; + } + + // + XOHCL pBar; + result = bar.GetPreviousBar(pBar); + if (!result) + { + return result; + } + + // + bool isUp = IsBullish(dir); + bool isDown = IsBearish(dir); + + // + result = + isUp + ? (bar.GetDown() < value && + bar.GetUp() > value) || + (bar.close > value && + pBar.close < value) + : isDown + ? (bar.GetUp() > value && + bar.GetDown() < value) || + (bar.close < value && + pBar.close > value) + : false; + + // + return result; +} + // // Calculate Fib Level ... double GetFibonacciLevel( diff --git a/X121SMCEA/Classes/x-121.smc.market.cycle.helper.class.mq5 b/X121SMCEA/Classes/x-121.smc.market.cycle.helper.class.mq5 index 82e31f10..67aa1ef5 100644 --- a/X121SMCEA/Classes/x-121.smc.market.cycle.helper.class.mq5 +++ b/X121SMCEA/Classes/x-121.smc.market.cycle.helper.class.mq5 @@ -450,22 +450,26 @@ class XC121SMCCycleHelper : public XCBase // int highestPeakIndex = -1; double highestPeakVale = 0; - double highestPeak = mX121Helper - .GetHighestPeak( - barIndex, - highestPeakIndex, - highestPeakVale // - ); + double highestPeak = + mX121Helper + .xpvHelper + .GetHighestPeak( + barIndex, + highestPeakIndex, + highestPeakVale // + ); // int lowestValeIndex = -1; double lowestValePeak = 0; - double lowestVale = mX121Helper - .GetLowestVale( - barIndex, - lowestValeIndex, - lowestValePeak // - ); + double lowestVale = + mX121Helper + .xpvHelper + .GetLowestVale( + barIndex, + lowestValeIndex, + lowestValePeak // + ); // result = IsValidIndex(highestPeakIndex) && @@ -520,7 +524,11 @@ class XC121SMCCycleHelper : public XCBase } // - bool isBreake = iBar.IsBreakeUp(lowestValePeak); + bool isBreake = IsBarBreak( + lowestValePeak, + X_DIRECTION_BULLISH, + iBar // + ); if (isBreake) { // @@ -545,7 +553,11 @@ class XC121SMCCycleHelper : public XCBase } // - bool isBreake = iBar.IsBreakeDown(highestPeakVale); + bool isBreake = IsBarBreak( + highestPeakVale, + X_DIRECTION_BEARISH, + iBar // + ); if (isBreake) { // @@ -571,7 +583,7 @@ class XC121SMCCycleHelper : public XCBase for (int i = lowestValePeakBreakeUpIndex; i >= barIndex; i--) { // - double iVale = mX121Helper.GetVale(i); + double iVale = mX121Helper.xpvHelper.GetVale(i); // bool isValid = @@ -581,7 +593,7 @@ class XC121SMCCycleHelper : public XCBase { // valeAboveLowestValePeakIndex = i; - valeAboveLowestValePeakPeak = mX121Helper.GetPeak(i); + valeAboveLowestValePeakPeak = mX121Helper.xpvHelper.GetPeak(i); break; } } @@ -595,7 +607,7 @@ class XC121SMCCycleHelper : public XCBase for (int i = highestPeakValeBreakeDownIndex; i >= barIndex; i--) { // - double iPeak = mX121Helper.GetPeak(i); + double iPeak = mX121Helper.xpvHelper.GetPeak(i); // bool isValid = @@ -605,7 +617,7 @@ class XC121SMCCycleHelper : public XCBase { // peakBelowHighestPeakValeIndex = i; - peakBelowHighestPeakValeVale = mX121Helper.GetVale(i); + peakBelowHighestPeakValeVale = mX121Helper.xpvHelper.GetVale(i); break; } } @@ -651,8 +663,8 @@ class XC121SMCCycleHelper : public XCBase bool isInited = GetBar(iBar, i); // - double iPeak = mX121Helper.GetPeak(i); - double iVale = mX121Helper.GetVale(i); + double iPeak = mX121Helper.xpvHelper.GetPeak(i); + double iVale = mX121Helper.xpvHelper.GetVale(i); // bool hasPeakPriceInsideZone = CalculatePriceInsideZones( diff --git a/X121SMCEA/Classes/x-121.smc.x-tradehandler.class.mq5 b/X121SMCEA/Classes/x-121.smc.x-tradehandler.class.mq5 index f6463b89..000a0c22 100644 --- a/X121SMCEA/Classes/x-121.smc.x-tradehandler.class.mq5 +++ b/X121SMCEA/Classes/x-121.smc.x-tradehandler.class.mq5 @@ -3279,9 +3279,9 @@ class XC121SMCTradeHandler : public XCBaseAlert conditions, conditionsObjects, mDrawer, - true, + false, true, // Analyse Price Zones ... - true, // Decision Zone ... + false, // Decision Zone ... true // Only Box ... ); } diff --git a/X121SMCEA/Signals/x-121.smc.xtwpv.signal.lib.mq5 b/X121SMCEA/Signals/x-121.smc.xtwpv.signal.lib.mq5 index c271853b..a87e49f2 100644 --- a/X121SMCEA/Signals/x-121.smc.xtwpv.signal.lib.mq5 +++ b/X121SMCEA/Signals/x-121.smc.xtwpv.signal.lib.mq5 @@ -1096,6 +1096,18 @@ bool DetectX121SMCXTWPVSiganlTrigger( // // Trigger Conditions ... + // + // Detect Bullish Conditions ... + isBullish = + isBullish && + cBar.IsBullish(); + + // + // Detect Bearish Conditions ... + isBearish = + isBearish && + cBar.IsBearish(); + // result = isBullish || isBearish; @@ -1163,7 +1175,7 @@ bool DetectX121SMCXTWPVSiganlTrigger( if (isBullish) { // - double lowerVale = triggerCycleHelper.mX121Helper.GetLowerVale(vale); + double lowerVale = triggerCycleHelper.mX121Helper.xpvHelper.GetLowerVale(vale); if (lowerVale > 0) { // @@ -1176,7 +1188,7 @@ bool DetectX121SMCXTWPVSiganlTrigger( else if (isBearish) { // - double higherPeak = triggerCycleHelper.mX121Helper.GetHigherPeak(peak); + double higherPeak = triggerCycleHelper.mX121Helper.xpvHelper.GetHigherPeak(peak); if (higherPeak > 0) { // diff --git a/X121SMCEA/Strategy/x-121.smc.strategy.class.mq5 b/X121SMCEA/Strategy/x-121.smc.strategy.class.mq5 index dfaefe02..82bc16ab 100644 --- a/X121SMCEA/Strategy/x-121.smc.strategy.class.mq5 +++ b/X121SMCEA/Strategy/x-121.smc.strategy.class.mq5 @@ -614,34 +614,45 @@ class XCX121SMCStrategy : public XCX121SMCBaseStrategy x121Inputs.Default(); // - x121Inputs.scMethod = scMethod; - x121Inputs.scPeriod = scPeriod; - x121Inputs.mcMethod = mcMethod; - x121Inputs.mcPeriod = mcPeriod; - x121Inputs.lcMethod = lcMethod; - x121Inputs.lcPeriod = lcPeriod; - x121Inputs.hcMethod = hcMethod; - x121Inputs.hcPeriod = hcPeriod; + bool isInited = false; // - x121Inputs.showSar = true; - x121Inputs.showPeaks = true; - x121Inputs.showVales = true; - x121Inputs.showVWap = true; - x121Inputs.showDonchain = true; + // XPV ... // - x121Inputs.showOpen = false; - x121Inputs.showHigh = false; - x121Inputs.showClose = true; - x121Inputs.showLow = false; + x121Inputs.xpvInputs.scMethod = scMethod; + x121Inputs.xpvInputs.scPeriod = scPeriod; + x121Inputs.xpvInputs.mcMethod = mcMethod; + x121Inputs.xpvInputs.mcPeriod = mcPeriod; + x121Inputs.xpvInputs.lcMethod = lcMethod; + x121Inputs.xpvInputs.lcPeriod = lcPeriod; + x121Inputs.xpvInputs.hcMethod = hcMethod; + x121Inputs.xpvInputs.hcPeriod = hcPeriod; + + // + // XATR ... + x121Inputs.xatrInputs.showATRUpper = false; + x121Inputs.xatrInputs.showATRLower = false; + + // + // XSTR ... + + // + // XDON ... + x121Inputs.xdonInputs.showOpen = false; + x121Inputs.xdonInputs.showClose = true; + x121Inputs.xdonInputs.showLow = false; + x121Inputs.xdonInputs.showHigh = false; + + // + // XVWAP ... + x121Inputs.xvwapInputs.showVWapFast = true; + x121Inputs.xvwapInputs.showVWapFast = true; + x121Inputs.xvwapInputs.showVWapSlow = false; // // Initialize Cycle Helpers ... - // - bool isInited = false; - // mTriggerCycleHelper = new XC121SMCCycleHelper(); isInited = mTriggerCycleHelper.Init(