diff --git a/Experts/RangeBars_ExampleEA.mq5 b/Experts/RangeBars_ExampleEA.mq5 index 2413f24..731432d 100644 --- a/Experts/RangeBars_ExampleEA.mq5 +++ b/Experts/RangeBars_ExampleEA.mq5 @@ -1,10 +1,12 @@ -#property copyright "Copyright 2017-18, AZ-iNVEST" -#property link "http://www.az-invest.eu" -#property version "2.06" +#property copyright "Copyright 2017-2020, Level Up Software" +#property link "https://www.az-invest.eu" +#property version "2.07" #property description "Example EA showing the way to use the RangeBars class defined in RangeBars.mqh" +input int InpRSIPeriod = 14; // RSI period + // -// SHOW_INDICATOR_INPUTS *NEEDS* to be defined, if the EA needs to be *tested in MT5's backtester* +// SHOW_INDICATOR_INPUTS *NEEDS* to be defined, if the sEA needs to be *tested in MT5's backtester* // ------------------------------------------------------------------------------------------------- // Using '#define SHOW_INDICATOR_INPUTS' will show the RangeBars indicator's inputs // NOT using the '#define SHOW_INDICATOR_INPUTS' statement will read the settigns a chart with @@ -20,22 +22,17 @@ #include // // To use the RangeBars indicator in your EA you need do instantiate the indicator class (RangeBars) -// and call the Init() method in your EA's OnInit() function. -// Don't forget to release the indicator when you're done by calling the Deinit() method. -// Example shown in OnInit & OnDeinit functions below: +// and call the Init() and Deinit() methods in your EA's OnInit() and OnDeinit() functions. +// Example shown below // -RangeBars * rangeBars; +RangeBars rangeBars(MQLInfoInteger((int)MQL5_TESTING) ? false : true); //+------------------------------------------------------------------+ //| Expert initialization function | //+------------------------------------------------------------------+ int OnInit() { - rangeBars = new RangeBars(MQLInfoInteger((int)MQL5_TESTING) ? false : true); - if(rangeBars == NULL) - return(INIT_FAILED); - rangeBars.Init(); if(rangeBars.GetHandle() == INVALID_HANDLE) return(INIT_FAILED); @@ -51,11 +48,7 @@ int OnInit() //+------------------------------------------------------------------+ void OnDeinit(const int reason) { - if(rangeBars != NULL) - { - rangeBars.Deinit(); - delete rangeBars; - } + rangeBars.Deinit(); // // your custom code goes here... @@ -70,8 +63,22 @@ void OnDeinit(const int reason) //+------------------------------------------------------------------+ //| Expert tick function | //+------------------------------------------------------------------+ + +int rsiHandle = INVALID_HANDLE; // Handle for the external RSI indicator + void OnTick() { + // + // Initialize all additional indicators here! (not in the OnInit() function). + // Otherwise they will not work in the backtest. + // When backtesting please select the "Daily" timeframe. + // + + if(rsiHandle == INVALID_HANDLE) + { + rsiHandle = iCustom(_Symbol, _Period, "RangeBars\\RangeBars_RSI", InpRSIPeriod, true); + } + // // It is considered good trading & EA coding practice to perform calculations // when a new bar is fully formed. @@ -96,7 +103,7 @@ void OnTick() double MA1[]; // array to be filled by values of the first moving average double MA2[]; // array to be filled by values of the second moving average - if(rangeBars.GetMA1(MA1,startAtBar,numberOfBars) && rangeBars.GetMA2(MA2,startAtBar,numberOfBars)) + if(rangeBars.GetMA(RANGEBAR_MA1, MA1, startAtBar, numberOfBars) && rangeBars.GetMA(RANGEBAR_MA2, MA2, startAtBar, numberOfBars)) { // // Values are stored in the MA1 and MA2 arrays and are now ready for use @@ -182,64 +189,23 @@ void OnTick() } // - // Getting Donchain channel values is done using the - // GetDonchian(double &HighArray[], double &MidArray[], double &LowArray[], int start, int count) - // method. Example below: + // Getting the values of the channel indicator (Donchain, Bullinger Bands, Keltner or Super Trend) is done using + // GetChannel(double &HighArray[], double &MidArray[], double &LowArray[], int start, int count) + // Example below: // - double HighArray[]; // This array will store the values of the high band - double MidArray[]; // This array will store the values of the middle band - double LowArray[]; // This array will store the values of the low band + double HighArray[]; // This array will store the values of the channel's high band + double MidArray[]; // This array will store the values of the channel's middle band + double LowArray[]; // This array will store the values of the channel's low band startAtBar = 1; // get values starting from the last completed bar. numberOfBars = 20; // gat a total of 20 values (for 20 bars starting from bar 1 (last completed)) - if(rangeBars.GetDonchian(HighArray,MidArray,LowArray,startAtBar,numberOfBars)) + if(rangeBars.GetChannel(HighArray,MidArray,LowArray,startAtBar,numberOfBars)) { // - // Apply your Donchian channel logic here... - // - } - - // - // Getting Bollinger Bands values is done using the - // GetBollingerBands(double &HighArray[], double &MidArray[], double &LowArray[], int start, int count) - // method. Example below: - // - - // HighArray[] array will store the values of the high band - // MidArray[] array will store the values of the middle band - // LowArray[] array will store the values of the low band - - startAtBar = 1; // get values starting from the last completed bar. - numberOfBars = 10; // gat a total of 10 values (for 10 bars starting from bar 1 (last completed)) - - if(rangeBars.GetBollingerBands(HighArray,MidArray,LowArray,startAtBar,numberOfBars)) - { - // - // Apply your Bollinger Bands logic here... + // Apply your logic here... // } - - // - // Getting SuperTrend values is done using the - // GetSuperTrend(double &SuperTrendHighArray[], double &SuperTrendArray[], double &SuperTrendLowArray[], int start, int count) - // method. Example below: - // - - // HighArray[] array will store the values of the high SuperTrend line - // MidArray[] array will store the values of the SuperTrend value - // LowArray[] array will store the values of the low SuperTrend line - - startAtBar = 1; // get values starting from the last completed bar. - numberOfBars = 3; // gat a total of 3 values (for 3 bars starting from bar 1 (last completed)) - - if(rangeBars.GetSuperTrend(HighArray,MidArray,LowArray,startAtBar,numberOfBars)) - { - // - // Apply your SuperTrend logic here... - // - } - } } diff --git a/Experts/RangeBars_ExampleEA2.mq5 b/Experts/RangeBars_ExampleEA2.mq5 index 162945e..4e2e734 100644 --- a/Experts/RangeBars_ExampleEA2.mq5 +++ b/Experts/RangeBars_ExampleEA2.mq5 @@ -1,6 +1,6 @@ -#property copyright "Copyright 2017-18, AZ-iNVEST" -#property link "http://www.az-invest.eu" -#property version "1.10" +#property copyright "Copyright 2017-2020, Level Up Software" +#property link "https://www.az-invest.eu" +#property version "1.11" #property description "Example EA: Trading based on RangeBars SuperTrend signals." #property description "One trade at a time. Each trade has TP & SL" @@ -39,7 +39,7 @@ ulong currentTicket; // the RangeBars indicator attached. // -//#define SHOW_INDICATOR_INPUTS +#define SHOW_INDICATOR_INPUTS // // You need to include the RangeBars.mqh header file @@ -48,12 +48,11 @@ ulong currentTicket; #include // // To use the RangeBars indicator in your EA you need do instantiate the indicator class (RangeBars) -// and call the Init() method in your EA's OnInit() function. -// Don't forget to release the indicator when you're done by calling the Deinit() method. -// Example shown in OnInit & OnDeinit functions below: +// and call the Init() and Deinit() methods in your EA's OnInit() and OnDeinit() functions. +// Example shown below // -RangeBars * rangeBars; +RangeBars rangeBars(MQLInfoInteger((int)MQL5_TESTING) ? false : true); CMarketOrder * marketOrder; //+------------------------------------------------------------------+ @@ -61,10 +60,6 @@ CMarketOrder * marketOrder; //+------------------------------------------------------------------+ int OnInit() { - rangeBars = new RangeBars(MQLInfoInteger((int)MQL5_TESTING) ? false : true); - if(rangeBars == NULL) - return(INIT_FAILED); - rangeBars.Init(); if(rangeBars.GetHandle() == INVALID_HANDLE) return(INIT_FAILED); @@ -93,11 +88,7 @@ int OnInit() //+------------------------------------------------------------------+ void OnDeinit(const int reason) { - if(rangeBars != NULL) - { - rangeBars.Deinit(); - delete rangeBars; - } + rangeBars.Deinit(); // // delete MarketOrder class @@ -130,7 +121,7 @@ void OnTick() // // Getting SuperTrend values is done using the - // GetSuperTrend(double &SuperTrendHighArray[], double &SuperTrendArray[], double &SuperTrendLowArray[], int start, int count) + // GetChannel(double &HighArray[], double &MidArray[], double &LowArray[], int start, int count) // method. Example below: // @@ -141,7 +132,7 @@ void OnTick() int startAtBar = 1; // get values starting from the last completed bar. int numberOfBars = 2; // gat a total of 3 values (for 3 bars starting from bar 1 (last completed)) - if(rangeBars.GetSuperTrend(HighArray,MidArray,LowArray,startAtBar,numberOfBars)) + if(rangeBars.GetChannel(HighArray,MidArray,LowArray,startAtBar,numberOfBars)) { // // Read signal bar's time for optional debug log diff --git a/Include/AZ-INVEST/SDK/CommonSettings.mqh b/Include/AZ-INVEST/SDK/CommonSettings.mqh index ecc262b..3272d23 100644 Binary files a/Include/AZ-INVEST/SDK/CommonSettings.mqh and b/Include/AZ-INVEST/SDK/CommonSettings.mqh differ diff --git a/Include/AZ-INVEST/SDK/CustomChartInputs.mqh b/Include/AZ-INVEST/SDK/CustomChartInputs.mqh new file mode 100644 index 0000000..2a6f609 Binary files /dev/null and b/Include/AZ-INVEST/SDK/CustomChartInputs.mqh differ diff --git a/Include/AZ-INVEST/SDK/CustomChartSettingsBase.mqh b/Include/AZ-INVEST/SDK/CustomChartSettingsBase.mqh new file mode 100644 index 0000000..11d7d66 Binary files /dev/null and b/Include/AZ-INVEST/SDK/CustomChartSettingsBase.mqh differ diff --git a/Include/AZ-INVEST/SDK/ICustomChartSettings.mqh b/Include/AZ-INVEST/SDK/ICustomChartSettings.mqh new file mode 100644 index 0000000..252f1ce Binary files /dev/null and b/Include/AZ-INVEST/SDK/ICustomChartSettings.mqh differ diff --git a/Include/AZ-INVEST/SDK/RangeBarCustomChartSettings.mqh b/Include/AZ-INVEST/SDK/RangeBarCustomChartSettings.mqh new file mode 100644 index 0000000..5b03fd6 --- /dev/null +++ b/Include/AZ-INVEST/SDK/RangeBarCustomChartSettings.mqh @@ -0,0 +1,117 @@ +#include + +#ifdef DEVELOPER_VERSION + #define CUSTOM_CHART_NAME "RangeBars_TEST" +#else + #define CUSTOM_CHART_NAME "Range Bars" +#endif + +// +// Tick chart specific settings +// +#ifdef SHOW_INDICATOR_INPUTS + #ifdef MQL5_MARKET_DEMO // hardcoded values + + int barSizeInTicks = 180; // Range bar size (in points) + ENUM_BOOL atrEnabled = false; // Enable ATR based bar size calculation + ENUM_TIMEFRAMES atrTimeFrame = PERIOD_D1; // Use ATR period + int atrPeriod = 14; // ATR period + int atrPercentage = 10; // Use percentage of ATR + int showNumberOfDays = 7; // Show history for number of days + ENUM_BOOL resetOpenOnNewTradingDay = true; // Synchronize first bar's open on new day + + #else // user defined settings + + + input int barSizeInTicks = 100; // Range bar size (in points) + input ENUM_BOOL atrEnabled = false; // Enable ATR based bar size calculation + ENUM_TIMEFRAMES atrTimeFrame = PERIOD_D1; // Use ATR period + input int atrPeriod = 14; // ATR period + input int atrPercentage = 10; // Use percentage of ATR + + input int showNumberOfDays = 5; // Show history for number of days + input ENUM_BOOL resetOpenOnNewTradingDay = true; // Synchronize first bar's open on new day + + #endif +#else // don't SHOW_INDICATOR_INPUTS + int barSizeInTicks = 180; // Range bar size (in points) + ENUM_BOOL atrEnabled = false; // Enable ATR based bar size calculation + ENUM_TIMEFRAMES atrTimeFrame = PERIOD_D1; // Use ATR period + int atrPeriod = 14; // ATR period + int atrPercentage = 10; // Use percentage of ATR + int showNumberOfDays = 7; // Show history for number of days + ENUM_BOOL resetOpenOnNewTradingDay = true; // Synchronize first bar's open on new day +#endif + +// +// Remaining settings are located in the include file below. +// These are common for all custom charts +// +#include + +struct RANGEBAR_SETTINGS +{ + int barSizeInTicks; + ENUM_BOOL atrEnabled; + ENUM_TIMEFRAMES atrTimeFrame; + int atrPeriod; + int atrPercentage; + int showNumberOfDays; + ENUM_BOOL resetOpenOnNewTradingDay; +}; + + +class CRangeBarCustomChartSettigns : public CCustomChartSettingsBase +{ + protected: + + RANGEBAR_SETTINGS settings; + + public: + + CRangeBarCustomChartSettigns(); + ~CRangeBarCustomChartSettigns(); + + RANGEBAR_SETTINGS GetCustomChartSettings() { return this.settings; }; + + virtual void SetCustomChartSettings(); + virtual string GetSettingsFileName(); + virtual uint CustomChartSettingsToFile(int handle); + virtual uint CustomChartSettingsFromFile(int handle); +}; + +void CRangeBarCustomChartSettigns::CRangeBarCustomChartSettigns() +{ + settingsFileName = GetSettingsFileName(); +} + +void CRangeBarCustomChartSettigns::~CRangeBarCustomChartSettigns() +{ +} + +string CRangeBarCustomChartSettigns::GetSettingsFileName() +{ + return CUSTOM_CHART_NAME+(string)ChartID()+".set"; +} + +uint CRangeBarCustomChartSettigns::CustomChartSettingsToFile(int file_handle) +{ + return FileWriteStruct(file_handle,this.settings); +} + +uint CRangeBarCustomChartSettigns::CustomChartSettingsFromFile(int file_handle) +{ + return FileReadStruct(file_handle,this.settings); +} + +void CRangeBarCustomChartSettigns::SetCustomChartSettings() +{ + settings.barSizeInTicks = barSizeInTicks; + + settings.atrEnabled = atrEnabled; + settings.atrTimeFrame = atrTimeFrame; + settings.atrPeriod = atrPeriod; + settings.atrPercentage = atrPercentage; + settings.showNumberOfDays = showNumberOfDays; + settings.resetOpenOnNewTradingDay = resetOpenOnNewTradingDay; +} diff --git a/Include/AZ-INVEST/SDK/RangeBarIndicator.mqh b/Include/AZ-INVEST/SDK/RangeBarIndicator.mqh index 1d91b50..86645a8 100644 --- a/Include/AZ-INVEST/SDK/RangeBarIndicator.mqh +++ b/Include/AZ-INVEST/SDK/RangeBarIndicator.mqh @@ -1,9 +1,10 @@ -#property copyright "Copyright 2017, AZ-iNVEST" +#property copyright "Copyright 2018-2020, Level Up Software" #property link "http://www.az-invest.eu" -#property version "2.02" +#property version "3.00" input bool UseOnRangeBarChart = true; // Use this indicator on RangeBar chart +//#define DEVELOPER_VERSION #include class RangeBarIndicator @@ -19,8 +20,12 @@ class RangeBarIndicator bool useAppliedPrice; ENUM_APPLIED_PRICE applied_price; + bool firstRun; bool dataReady; + datetime prevTime; + int prevRatesTotal; + public: datetime Time[]; @@ -34,8 +39,21 @@ class RangeBarIndicator double Buy_volume[]; double Sell_volume[]; double BuySell_volume[]; + + datetime GetTime(int index) { return GetArrayValueDateTime(Time, index); }; + double GetOpen(int index) { return GetArrayValueDouble(Open, index); }; + double GetLow(int index) { return GetArrayValueDouble(Low, index); }; + double GetHigh(int index) { return GetArrayValueDouble(High, index); }; + double GetClose(int index) { return GetArrayValueDouble(Close, index); }; + double GetPrice(int index) { return GetArrayValueDouble(Price, index); }; + long GetTick_volume(int index) { return GetArrayValueLong(Tick_volume, index); }; + long GetReal_volume(int index) { return GetArrayValueLong(Real_volume, index); }; + double GetBuy_volume(int index) { return GetArrayValueDouble(Buy_volume, index); }; + double GetSell_volume(int index) { return GetArrayValueDouble(Sell_volume, index); }; + double GetBuySell_volume(int index) { return GetArrayValueDouble(BuySell_volume, index); }; + bool IsNewBar; - + RangeBarIndicator(); ~RangeBarIndicator(); @@ -44,8 +62,11 @@ class RangeBarIndicator void SetGetVolumeBreakdownFlag() { this.getVolumeBreakdown = true; }; void SetGetTimeFlag() { this.getTime = true; }; - bool OnCalculate(const int rates_total,const int prev_calculated, const datetime &_Time[]); + bool OnCalculate(const int _rates_total,const int _prev_calculated, const datetime &_Time[], const double &_Close[]); + void OnDeinit(const int reason); + bool BufferSynchronizationCheck(const double &buffer[]); int GetPrevCalculated() { return prev_calculated; }; + int GetRatesTotal() { return ArraySize(Open); }; void BufferShiftLeft(double &buffer[]); private: @@ -67,6 +88,9 @@ class RangeBarIndicator ENUM_TIMEFRAMES TFMigrate(int tf); datetime iTime(string symbol,int tf,int index); + double GetArrayValueDouble(double &arr[], int index); + long GetArrayValueLong(long &arr[], int index); + datetime GetArrayValueDateTime(datetime &arr[], int index); }; RangeBarIndicator::RangeBarIndicator(void) @@ -80,6 +104,9 @@ RangeBarIndicator::RangeBarIndicator(void) getTime = false; dataReady = false; + firstRun = true; + prevTime = 0; + prevRatesTotal = 0; } RangeBarIndicator::~RangeBarIndicator(void) @@ -112,10 +139,8 @@ bool RangeBarIndicator::NeedsReload(void) return false; } -bool RangeBarIndicator::OnCalculate(const int _rates_total,const int _prev_calculated, const datetime &_Time[]) +bool RangeBarIndicator::OnCalculate(const int _rates_total,const int _prev_calculated, const datetime &_Time[], const double &_Close[]) { - static bool firstRun = true; - if(firstRun) { Canvas_IsNewBar(_Time); @@ -153,36 +178,25 @@ bool RangeBarIndicator::OnCalculate(const int _rates_total,const int _prev_calcu { GetOLHC(0,_rates_total); firstRun = false; - NeedsReload(); } if(NeedsReload() || !this.dataReady) { GetOLHC(0,_rates_total); this.prev_calculated = 0; - - if(NeedsReload() || !this.dataReady) - { - Print("NeedsReload/DataReady block failed"); - return false; - } + firstRun = true; + ChartSetSymbolPeriod(ChartID(), _Symbol, _Period); // try to force reload + return false; } - - /* - if(needsReload || IsNewBar || canvasIsNewTime || (change != 0)) - { - Print("reload="+needsReload+", renkoisnewbar="+IsNewBar+", canvasIsNewTime="+canvasIsNewTime+", change="+change); - GetOLHC(0,_rates_total); - this.prev_calculated = ArraySize(this.Open); - return true; - } - */ + bool change = Canvas_RatesTotalChangedBy(_rates_total); + if(change != 0) { #ifdef DISPLAY_DEBUG_MSG Print("rates total changed to:"+_rates_total); #endif + if(change == 1) { #ifdef DISPLAY_DEBUG_MSG @@ -197,7 +211,8 @@ bool RangeBarIndicator::OnCalculate(const int _rates_total,const int _prev_calcu #endif GetOLHC(0,_rates_total); } - this.prev_calculated = 0;//_prev_calculated; + + this.prev_calculated = 0; Canvas_IsNewBar(_Time); return true; } @@ -211,7 +226,7 @@ bool RangeBarIndicator::OnCalculate(const int _rates_total,const int _prev_calcu { GetOLHC(0,_rates_total); this.prev_calculated = 0; - return true; ///////// false + return true; } OLHCShiftRight(); @@ -224,9 +239,9 @@ bool RangeBarIndicator::OnCalculate(const int _rates_total,const int _prev_calcu { GetOLHC(0,_rates_total); this.prev_calculated = 0; + firstRun = true; return true; } - // // Only recalculate last bar @@ -238,6 +253,19 @@ bool RangeBarIndicator::OnCalculate(const int _rates_total,const int _prev_calcu return true; } +bool RangeBarIndicator::BufferSynchronizationCheck(const double &buffer[]) +{ + if(ArraySize(buffer) != ArraySize(Close)) + { + #ifdef DEVELOPER_VERSION + Print("### buffers out of synch - refreshing..."); + #endif + return false; + } + + return true; +} + int RangeBarIndicator::GetOLHC(int start, int count) { if((start == 0) && (count == 0) && dataReady) @@ -255,6 +283,7 @@ int RangeBarIndicator::GetOLHC(int start, int count) this.Low[last] = tempRates[0].low; this.High[last] = tempRates[0].high; this.Close[last] = tempRates[0].close; + if(getTime) { this.Time[last] = tempRates[0].time; @@ -300,10 +329,13 @@ void RangeBarIndicator::OLHCShiftRight() this.High[i] = this.High[i-1]; this.Low[i] = this.Low[i-1]; this.Close[i] = this.Close[i-1]; + if(getTime) this.Time[i] = this.Time[i-1]; + if(useAppliedPrice) this.Price[i] = this.Price[i-1]; + if(getVolumes) { this.Tick_volume[i] = this.Tick_volume[i-1]; @@ -324,8 +356,10 @@ void RangeBarIndicator::OLHCShiftRight() if(getTime) this.Time[0] = 0; + if(useAppliedPrice) this.Price[0] = 0.0; + if(getVolumes) { this.Tick_volume[0] = 0.0; @@ -353,8 +387,10 @@ void RangeBarIndicator::OLHCResize() if(getTime) ArrayResize(this.Time,count+1); + if(useAppliedPrice) ArrayResize(this.Price,count+1); + if(getVolumes) { ArrayResize(this.Tick_volume,count+1); @@ -376,8 +412,6 @@ bool RangeBarIndicator::Canvas_IsNewBar(const datetime &_Time[]) datetime now = _Time[0]; ArraySetAsSeries(_Time,false); - static datetime prevTime = 0; - if(prevTime != now) { prevTime = now; @@ -389,8 +423,6 @@ bool RangeBarIndicator::Canvas_IsNewBar(const datetime &_Time[]) bool RangeBarIndicator::Canvas_IsRatesTotalChanged(int ratesTotalNow) { - static int prevRatesTotal = 0; - if(prevRatesTotal == 0) prevRatesTotal = ratesTotalNow; @@ -406,7 +438,6 @@ bool RangeBarIndicator::Canvas_IsRatesTotalChanged(int ratesTotalNow) int RangeBarIndicator::Canvas_RatesTotalChangedBy(int ratesTotalNow) { int changedBy = 0; - static int prevRatesTotal = 0; if(prevRatesTotal == 0) prevRatesTotal = ratesTotalNow; @@ -464,11 +495,11 @@ int RangeBarIndicator::GetOLHCForIndicatorCalc(double &o[],double &l[],double &h handle = rangeBars.GetHandle(); if(handle == INVALID_HANDLE) return -1; - int _count = CopyBuffer(handle,RANGEBAR_OPEN,start,count,temp); - if(_count == -1) + + int __count = CopyBuffer(handle,RANGEBAR_OPEN,start,count,temp); + if(__count == -1) { - int errorCode = GetLastError(); - if(errorCode == ERR_INDICATOR_DATA_NOT_FOUND) + if(GetLastError() == ERR_INDICATOR_DATA_NOT_FOUND) { Print("Waiting for buffers ready flag"); return -2; @@ -477,95 +508,109 @@ int RangeBarIndicator::GetOLHCForIndicatorCalc(double &o[],double &l[],double &h return -1; } - if(_count < count) + if(__count < count) { #ifdef DISPLAY_DEBUG_MSG - Print("Fixing offset (req:"+count+" res:"+_count+")"); + Print("Fixing offset (req:"+count+" res:"+__count+")"); #endif ArrayInitialize(o,0x0); ArrayInitialize(l,0x0); ArrayInitialize(h,0x0); ArrayInitialize(c,0x0); + if(getTime) ArrayInitialize(t,0x0); + if(getVolumes) { ArrayInitialize(tickVolume,0x0); ArrayInitialize(realVolume,0x0); } + if(getVolumeBreakdown) { ArrayInitialize(buyVolume,0x0); ArrayInitialize(sellVolume,0x0); ArrayInitialize(buySellVolume,0x0); } + // less data - indicator requres more - ArrayCopy(o,temp,(count-_count),0); + ArrayCopy(o,temp,(count-__count),0); - if(CopyBuffer(handle,RANGEBAR_LOW,start,_count,temp) == -1) + if(CopyBuffer(handle,RANGEBAR_LOW,start,__count,temp) == -1) return -1; - ArrayCopy(l,temp,(count-_count),0); + ArrayCopy(l,temp,(count-__count),0); - if(CopyBuffer(handle,RANGEBAR_HIGH,start,_count,temp) == -1) + if(CopyBuffer(handle,RANGEBAR_HIGH,start,__count,temp) == -1) return -1; - ArrayCopy(h,temp,(count-_count),0); + ArrayCopy(h,temp,(count-__count),0); - if(CopyBuffer(handle,RANGEBAR_CLOSE,start,_count,temp) == -1) + if(CopyBuffer(handle,RANGEBAR_CLOSE,start,__count,temp) == -1) return -1; - ArrayCopy(c,temp,(count-_count),0); + + ArrayCopy(c,temp,(count-__count),0); if(getTime) { - if(CopyBuffer(handle,RANGEBAR_BAR_OPEN_TIME,start,_count,temp) == -1) + if(CopyBuffer(handle,RANGEBAR_BAR_OPEN_TIME,start,__count,temp) == -1) return -1; - ArrayCopy(t,temp,(count-_count),0); + + ArrayCopy(t,temp,(count-__count),0); } if(getVolumes) { - if(CopyBuffer(handle,RANGEBAR_TICK_VOLUME,start,_count,temp) == -1) + if(CopyBuffer(handle,RANGEBAR_TICK_VOLUME,start,__count,temp) == -1) return -1; - ArrayCopy(tickVolume,temp,(count-_count),0); + + ArrayCopy(tickVolume,temp,(count-__count),0); - if(CopyBuffer(handle,RANGEBAR_REAL_VOLUME,start,_count,temp) == -1) + if(CopyBuffer(handle,RANGEBAR_REAL_VOLUME,start,__count,temp) == -1) return -1; - ArrayCopy(realVolume,temp,(count-_count),0); + + ArrayCopy(realVolume,temp,(count-__count),0); } #ifdef P_RANGEBAR_BR #ifdef P_RANGEBAR_BR_PRO if(getVolumeBreakdown) { - if(CopyBuffer(handle,RANGEBAR_BUY_VOLUME,start,_count,temp) == -1) + if(CopyBuffer(handle,RANGEBAR_BUY_VOLUME,start,__count,temp) == -1) return -1; - ArrayCopy(buyVolume,temp,(count-_count),0); + + ArrayCopy(buyVolume,temp,(count-__count),0); - if(CopyBuffer(handle,RANGEBAR_SELL_VOLUME,start,_count,temp) == -1) + if(CopyBuffer(handle,RANGEBAR_SELL_VOLUME,start,__count,temp) == -1) return -1; - ArrayCopy(sellVolume,temp,(count-_count),0); + + ArrayCopy(sellVolume,temp,(count-__count),0); - if(CopyBuffer(handle,RANGEBAR_BUYSELL_VOLUME,start,_count,temp) == -1) + if(CopyBuffer(handle,RANGEBAR_BUYSELL_VOLUME,start,__count,temp) == -1) return -1; - ArrayCopy(buySellVolume,temp,(count-_count),0); + + ArrayCopy(buySellVolume,temp,(count-__count),0); } #else #endif #else if(getVolumeBreakdown) { - if(CopyBuffer(handle,RANGEBAR_BUY_VOLUME,start,_count,temp) == -1) + if(CopyBuffer(handle,RANGEBAR_BUY_VOLUME,start,__count,temp) == -1) return -1; - ArrayCopy(buyVolume,temp,(count-_count),0); + + ArrayCopy(buyVolume,temp,(count-__count),0); - if(CopyBuffer(handle,RANGEBAR_SELL_VOLUME,start,_count,temp) == -1) + if(CopyBuffer(handle,RANGEBAR_SELL_VOLUME,start,__count,temp) == -1) return -1; - ArrayCopy(sellVolume,temp,(count-_count),0); + + ArrayCopy(sellVolume,temp,(count-__count),0); - if(CopyBuffer(handle,RANGEBAR_BUYSELL_VOLUME,start,_count,temp) == -1) + if(CopyBuffer(handle,RANGEBAR_BUYSELL_VOLUME,start,__count,temp) == -1) return -1; - ArrayCopy(buySellVolume,temp,(count-_count),0); + + ArrayCopy(buySellVolume,temp,(count-__count),0); } #endif @@ -574,10 +619,13 @@ int RangeBarIndicator::GetOLHCForIndicatorCalc(double &o[],double &l[],double &h { if(CopyBuffer(handle,RANGEBAR_OPEN,start,count,o) == -1) return -1; + if(CopyBuffer(handle,RANGEBAR_LOW,start,count,l) == -1) return -1; + if(CopyBuffer(handle,RANGEBAR_HIGH,start,count,h) == -1) return -1; + if(CopyBuffer(handle,RANGEBAR_CLOSE,start,count,c) == -1) return -1; @@ -585,6 +633,7 @@ int RangeBarIndicator::GetOLHCForIndicatorCalc(double &o[],double &l[],double &h { if(CopyBuffer(handle,RANGEBAR_BAR_OPEN_TIME,start,count,temp) == -1) return -1; + ArrayCopy(t,temp); } @@ -592,9 +641,12 @@ int RangeBarIndicator::GetOLHCForIndicatorCalc(double &o[],double &l[],double &h { if(CopyBuffer(handle,RANGEBAR_TICK_VOLUME,start,count,temp) == -1) return -1; + ArrayCopy(tickVolume,temp); + if(CopyBuffer(handle,RANGEBAR_REAL_VOLUME,start,count,temp) == -1) return -1; + ArrayCopy(realVolume,temp); } @@ -604,14 +656,17 @@ int RangeBarIndicator::GetOLHCForIndicatorCalc(double &o[],double &l[],double &h { if(CopyBuffer(handle,RANGEBAR_BUY_VOLUME,start,count,temp) == -1) return -1; + ArrayCopy(buyVolume,temp); if(CopyBuffer(handle,RANGEBAR_SELL_VOLUME,start,count,temp) == -1) return -1; + ArrayCopy(sellVolume,temp); if(CopyBuffer(handle,RANGEBAR_BUYSELL_VOLUME,start,count,temp) == -1) return -1; + ArrayCopy(buySellVolume,temp); } #else @@ -621,14 +676,17 @@ int RangeBarIndicator::GetOLHCForIndicatorCalc(double &o[],double &l[],double &h { if(CopyBuffer(handle,RANGEBAR_BUY_VOLUME,start,count,temp) == -1) return -1; + ArrayCopy(buyVolume,temp); if(CopyBuffer(handle,RANGEBAR_SELL_VOLUME,start,count,temp) == -1) return -1; + ArrayCopy(sellVolume,temp); if(CopyBuffer(handle,RANGEBAR_BUYSELL_VOLUME,start,count,temp) == -1) return -1; + ArrayCopy(buySellVolume,temp); } #endif @@ -645,11 +703,11 @@ int RangeBarIndicator::GetOLHCAndApplPriceForIndicatorCalc(double &o[],double &l { dataReady = true; - int _count = GetOLHCForIndicatorCalc(o,l,h,c,t,tickVolume,realVolume,buyVolume,sellVolume,buySellVolume,start,count); - if(_count < 0) + int __count = GetOLHCForIndicatorCalc(o,l,h,c,t,tickVolume,realVolume,buyVolume,sellVolume,buySellVolume,start,count); + if(__count < 0) { dataReady = false; - return _count; + return __count; } if(applied_price == PRICE_CLOSE) { @@ -669,22 +727,25 @@ int RangeBarIndicator::GetOLHCAndApplPriceForIndicatorCalc(double &o[],double &l } else { - if(ArrayResize(price,_count) == -1) + if(ArrayResize(price,__count) == -1) return -1; - for(int i=0; i<_count; i++) + for(int i=0; i<__count; i++) { price[i] = CalcAppliedPrice(o[i],l[i],h[i],c[i],_applied_price); } } - return _count; + return __count; } +// TFMigrate: +// https://www.mql5.com/en/forum/2842#comment_39496 +// ENUM_TIMEFRAMES RangeBarIndicator::TFMigrate(int tf) - { +{ switch(tf) - { + { case 0: return(PERIOD_CURRENT); case 1: return(PERIOD_M1); case 5: return(PERIOD_M5); @@ -712,18 +773,30 @@ ENUM_TIMEFRAMES RangeBarIndicator::TFMigrate(int tf) case 16408: return(PERIOD_D1); case 32769: return(PERIOD_W1); case 49153: return(PERIOD_MN1); + default: return(PERIOD_CURRENT); - } - } + } +} datetime RangeBarIndicator::iTime(string symbol,int tf,int index) { - if(index < 0) return(-1); + if(index < 0) + { + return(-1); + } + ENUM_TIMEFRAMES timeframe=TFMigrate(tf); + datetime Arr[]; - if(CopyTime(symbol, timeframe, index, 1, Arr)>0) - return(Arr[0]); - else return(-1); + + if(CopyTime(symbol, timeframe, index, 1, Arr) > 0) + { + return(Arr[0]); + } + else + { + return(-1); + } } // @@ -778,3 +851,43 @@ void RangeBarIndicator::BufferShiftLeft(double &buffer[]) buffer[i-1] = buffer[i]; } + +long RangeBarIndicator::GetArrayValueLong(long &arr[], int index) +{ + int size = ArraySize(arr); + if(index < size) + { + return(arr[index]); + } + else + { + return(false); + } +} + +double RangeBarIndicator::GetArrayValueDouble(double &arr[], int index) +{ + int size = ArraySize(arr); + if(index < size) + { + return(arr[index]); + } + else + { + return(false); + } +} + +datetime RangeBarIndicator::GetArrayValueDateTime(datetime &arr[], int index) +{ + int size = ArraySize(arr); + if(index < size) + { + return(arr[index]); + } + else + { + return(false); + } +} + diff --git a/Include/AZ-INVEST/SDK/RangeBarSettings.mqh b/Include/AZ-INVEST/SDK/RangeBarSettings.mqh deleted file mode 100644 index 41f0205..0000000 --- a/Include/AZ-INVEST/SDK/RangeBarSettings.mqh +++ /dev/null @@ -1,387 +0,0 @@ -#property copyright "Copyright 2017, AZ-iNVEST" -#property link "http://www.az-invest.eu" - -#include -#define CUSTOM_CHART_NAME "Range Bars" - -#ifdef SHOW_INDICATOR_INPUTS - -#ifdef MQL5_MARKET_DEMO - int barSizeInTicks = 180; // Range bar size (in points) - ENUM_BOOL atrEnabled = false; // Enable ATR based bar size calculation - ENUM_TIMEFRAMES atrTimeFrame = PERIOD_D1; // Use ATR period - int atrPeriod = 14; // ATR period - int atrPercentage = 10; // Use percentage of ATR - ENUM_BOOL useRealVolume = false; // Use real volume ( false for FX ) - ENUM_TICK_PRICE_TYPE plotPrice = tickBid; // Build chart using - int showNumberOfDays = 7; // Show history for number of days - ENUM_BOOL resetOpenOnNewTradingDay = true; // Synchronize first bar's open on new day - - #ifdef USE_CUSTOM_SYMBOL - string customChartName = ""; // Override default custom chart name with - string applyTemplate = "default"; // Apply template to custom chart - #endif -#else - input int barSizeInTicks = 100; // Range bar size (in points) - input ENUM_BOOL atrEnabled = false; // Enable ATR based bar size calculation - ENUM_TIMEFRAMES atrTimeFrame = PERIOD_D1; // Use ATR period - input int atrPeriod = 14; // ATR period - input int atrPercentage = 10; // Use percentage of ATR - ENUM_BOOL useRealVolume = false; // Use real volume ( false for FX ) - ENUM_TICK_PRICE_TYPE plotPrice = tickBid; // Build chart using - input int showNumberOfDays = 14; // Show history for number of days - input ENUM_BOOL resetOpenOnNewTradingDay = true; // Synchronize first bar's open on new day - - #ifdef USE_CUSTOM_SYMBOL - input string customChartName = ""; // Override default custom chart name with - input string applyTemplate = "default"; // Apply template to custom chart - #endif -#endif - - - #ifndef USE_CUSTOM_SYMBOL - input double TopBottomPaddingPercentage = 0.30; // Use padding top/bottom (0.0 - 1.0) - input ENUM_PIVOT_POINTS showPivots = ppNone; // Show pivot levels - input ENUM_PIVOT_TYPE pivotPointCalculationType = ppHLC3; // Pivot point calculation method - input color RColor = clrDodgerBlue; // Resistance line color - input color PColor = clrGold; // Pivot line color - input color SColor = clrFireBrick; // Support line color - input color PDHColor = clrHotPink; // Previous day's high - input color PDLColor = clrLightSkyBlue; // Previous day's low - input color PDCColor = clrGainsboro; // Previous day's close - input ENUM_BOOL showNextBarLevels = true; // Show current bar's close projections - input color HighThresholdIndicatorColor = clrLime; // Bullish bar projection color - input color LowThresholdIndicatorColor = clrRed; // Bearish bar projection color - input ENUM_BOOL showCurrentBarOpenTime = true; // Display chart info and current bar's open time - input color InfoTextColor = clrNONE; // Current bar's open time info color - - input ENUM_BOOL NewBarAlert = false; // Alert on new a bar - input ENUM_BOOL ReversalBarAlert = false; // Alert on reversal bar - input ENUM_BOOL MaCrossAlert = false; // Alert on MA crossover - input ENUM_BOOL UseAlertWindow = false; // Display alert in Alert Window - input ENUM_BOOL UseSound = false; // Play sound on alert - input ENUM_BOOL UsePushNotifications = false; // Send alert via push notification to a smartphone - - input string SoundFileBull = "news.wav"; // Use sound file for bullish bar close - input string SoundFileBear = "timeout.wav"; // Use sound file for bearish bar close - input ENUM_BOOL MA1on = false; // Show first MA - input int MA1period = 20; // 1st MA period - input ENUM_MA_METHOD_EXT MA1method = _MODE_SMA; // 1st MA method - input ENUM_APPLIED_PRICE MA1applyTo = PRICE_CLOSE; // 1st MA apply to - input int MA1shift = 0; // 1st MA shift - input ENUM_BOOL MA2on = false; // Show second MA - input int MA2period = 50; // 2nd MA period - input ENUM_MA_METHOD_EXT MA2method = _MODE_EMA; // 2nd MA method - input ENUM_APPLIED_PRICE MA2applyTo = PRICE_CLOSE; // 2nd MA apply to - input int MA2shift = 0; // 2nd MA shift - input ENUM_BOOL MA3on = false; // Show third MA - input int MA3period = 20; // 3rd MA period - input ENUM_MA_METHOD_EXT MA3method = _VWAP_TICKVOL; // 3rd MA method - input ENUM_APPLIED_PRICE MA3applyTo = PRICE_CLOSE; // 3rd MA apply to - input int MA3shift = 0; // 3rd MA shift - input ENUM_CHANNEL_TYPE ShowChannel = _None; // Show Channel - input string Channel_Settings = "-------------------"; // Channel settings - input int DonchianPeriod = 20; // Donchian Channel period - input ENUM_APPLIED_PRICE BBapplyTo = PRICE_CLOSE; // Bollinger Bands apply to - input int BollingerBandsPeriod = 20; // Bollinger Bands period - input double BollingerBandsDeviations = 2.0; // Bollinger Bands deviations - input int SuperTrendPeriod = 10; // Super Trend period - input double SuperTrendMultiplier=1.7; // Super Trend multiplier - input string Misc_Settings = "-------------------"; // Misc settings - input ENUM_BOOL DisplayAsBarChart = false; // Display as bar chart - input ENUM_BOOL ShiftObj = false; // Shift objects with chart - input ENUM_BOOL UsedInEA = false; // Indicator used in EA via iCustom() - #endif -#else - - // - // This block should always be set to the following values - // - - double TopBottomPaddingPercentage = 0; - ENUM_PIVOT_POINTS showPivots = ppNone; - ENUM_PIVOT_TYPE pivotPointCalculationType = ppHLC3; - color RColor = clrNONE; - color PColor = clrNONE; - color SColor = clrNONE; - color PDHColor = clrNONE; - color PDLColor = clrNONE; - color PDCColor = clrNONE; - ENUM_BOOL showNextBarLevels = false; - color HighThresholdIndicatorColor = clrNONE; - color LowThresholdIndicatorColor = clrNONE; - ENUM_BOOL showCurrentBarOpenTime = false; - color InfoTextColor = clrNONE; - - ENUM_BOOL NewBarAlert = false; - ENUM_BOOL ReversalBarAlert = false; - ENUM_BOOL MaCrossAlert = false; - ENUM_BOOL UseAlertWindow = false; - ENUM_BOOL UseSound = false; - ENUM_BOOL UsePushNotifications = false; - - string SoundFileBull = ""; - string SoundFileBear = ""; - ENUM_BOOL DisplayAsBarChart = true; - ENUM_BOOL ShiftObj = false; - ENUM_BOOL UsedInEA = true; // This should always be set to TRUE for EAs & Indicators - - // - // - // - - -#endif - -struct RANGEBAR_SETTINGS -{ - int barSizeInTicks; - ENUM_BOOL atrEnabled; - ENUM_TIMEFRAMES atrTimeFrame; - int atrPeriod; - int atrPercentage; - ENUM_BOOL useRealVolume; - ENUM_TICK_PRICE_TYPE plotPrice; - int showNumberOfDays; - ENUM_BOOL resetOpenOnNewTradingDay; -}; - -class RangeBarSettings -{ - protected: - - string settingsFileName; - string chartTypeFileName; - - RANGEBAR_SETTINGS settings; - CHART_INDICATOR_SETTINGS chartIndicatorSettings; - ALERT_INFO_SETTINGS alertInfoSettings; - - public: - - RangeBarSettings(void); - ~RangeBarSettings(void); - - RANGEBAR_SETTINGS GetRangeBarSettings(void); - ALERT_INFO_SETTINGS GetAlertInfoSettings(void); - CHART_INDICATOR_SETTINGS GetChartIndicatorSettings(void); - - void Set(void); - - void Save(void); - bool Load(void); - void Delete(void); - bool Changed(void); -}; - -void RangeBarSettings::RangeBarSettings(void) -{ - this.settingsFileName = CUSTOM_CHART_NAME+(string)ChartID()+".set"; - this.chartTypeFileName = (string)ChartID()+".id"; -} - -void RangeBarSettings::~RangeBarSettings(void) -{ - -} - -void RangeBarSettings::Save(void) -{ - if(IS_TESTING || this.chartIndicatorSettings.UsedInEA) - return; - - this.Delete(); - - // - // Store indicator settings - // - - int handle = FileOpen(this.settingsFileName,FILE_SHARE_READ|FILE_WRITE|FILE_BIN); - uint result = 0; - - result += FileWriteStruct(handle,this.settings); - result += FileWriteStruct(handle,this.chartIndicatorSettings); - //FileWriteStruct(handle,this.alertInfoSettings); - FileClose(handle); - - // - // Store chart type identifier - // - /* - handle = FileOpen(this.chartTypeFileName,FILE_SHARE_READ|FILE_WRITE|FILE_ANSI); - FileWriteString(handle,CUSTOM_CHART_NAME); - FileClose(handle); - */ -} - -void RangeBarSettings::Delete(void) -{ - if(IS_TESTING || this.chartIndicatorSettings.UsedInEA) - return; - - if(FileIsExist(this.settingsFileName)) - FileDelete(this.settingsFileName); -} - -bool RangeBarSettings::Load(void) -{ -#ifdef SHOW_INDICATOR_INPUTS - Set(); - return true; -#else - - if(!FileIsExist(this.settingsFileName)) - return false; - - int handle = FileOpen(this.settingsFileName,FILE_SHARE_READ|FILE_BIN); - if(handle == INVALID_HANDLE) - return false; - - if(FileReadStruct(handle,this.settings) <= 0) - { - Print("Failed loading settings(1)!"); - FileClose(handle); - return false; - } - - if(FileReadStruct(handle,this.chartIndicatorSettings) <= 0) - { - Print("Failed loading settings(2)!"); - FileClose(handle); - return false; - } - /* - if(FileReadStruct(handle,this.alertInfoSettings) <= 0) - { - Print("Failed loading settings(3)!"); - FileClose(handle); - return false; - } - */ - - FileClose(handle); - return true; - -#endif -} - -ALERT_INFO_SETTINGS RangeBarSettings::GetAlertInfoSettings(void) -{ - return this.alertInfoSettings; -} - -CHART_INDICATOR_SETTINGS RangeBarSettings::GetChartIndicatorSettings(void) -{ - return this.chartIndicatorSettings; -} - -RANGEBAR_SETTINGS RangeBarSettings::GetRangeBarSettings(void) -{ - return this.settings; -} - -void RangeBarSettings::Set(void) -{ -#ifdef SHOW_INDICATOR_INPUTS - - settings.barSizeInTicks = barSizeInTicks; - settings.atrEnabled = atrEnabled; - settings.atrTimeFrame = atrTimeFrame; - settings.atrPeriod = atrPeriod; - settings.atrPercentage = atrPercentage; - settings.useRealVolume = useRealVolume; - settings.plotPrice = plotPrice; - settings.showNumberOfDays = showNumberOfDays; - settings.resetOpenOnNewTradingDay = resetOpenOnNewTradingDay; - - // - // - // - - #ifndef USE_CUSTOM_SYMBOL - chartIndicatorSettings.MA1on = MA1on; - chartIndicatorSettings.MA1period = MA1period; - chartIndicatorSettings.MA1method = MA1method; - chartIndicatorSettings.MA1applyTo = MA1applyTo; - chartIndicatorSettings.MA1shift = MA1shift; - chartIndicatorSettings.MA2on = MA2on; - chartIndicatorSettings.MA2period = MA2period; - chartIndicatorSettings.MA2method = MA2method; - chartIndicatorSettings.MA2applyTo = MA2applyTo; - chartIndicatorSettings.MA2shift = MA2shift; - /* - chartIndicatorSettings.ShowVWAP = ShowVWAP; - chartIndicatorSettings.VWAP_Period = VWAP_Period; - chartIndicatorSettings.VWAPapplyTo = VWAPapplyTo; - chartIndicatorSettings.VWAPvolume = VWAPvolume; - */ - chartIndicatorSettings.MA3on = MA3on; - chartIndicatorSettings.MA3period = MA3period; - chartIndicatorSettings.MA3method = MA3method; - chartIndicatorSettings.MA3applyTo = MA3applyTo; - chartIndicatorSettings.MA3shift = MA3shift; - chartIndicatorSettings.ShowChannel = ShowChannel; - chartIndicatorSettings.DonchianPeriod = DonchianPeriod; - chartIndicatorSettings.BBapplyTo = BBapplyTo; - chartIndicatorSettings.BollingerBandsPeriod = BollingerBandsPeriod; - chartIndicatorSettings.BollingerBandsDeviations = BollingerBandsDeviations; - chartIndicatorSettings.SuperTrendPeriod = SuperTrendPeriod; - chartIndicatorSettings.SuperTrendMultiplier = SuperTrendMultiplier; - chartIndicatorSettings.ShiftObj = ShiftObj; - chartIndicatorSettings.UsedInEA = UsedInEA; - - // - // - // - - alertInfoSettings.TopBottomPaddingPercentage = TopBottomPaddingPercentage; - alertInfoSettings.showPiovots = showPivots; - alertInfoSettings.pivotPointCalculationType = pivotPointCalculationType; - alertInfoSettings.Rcolor = RColor; - alertInfoSettings.Pcolor = PColor; - alertInfoSettings.Scolor = SColor; - alertInfoSettings.PDHColor = PDHColor; - alertInfoSettings.PDLColor = PDLColor; - alertInfoSettings.PDCColor = PDCColor; - alertInfoSettings.showNextBarLevels = showNextBarLevels; - alertInfoSettings.HighThresholdIndicatorColor = HighThresholdIndicatorColor; - alertInfoSettings.LowThresholdIndicatorColor = LowThresholdIndicatorColor; - alertInfoSettings.showCurrentBarOpenTime = showCurrentBarOpenTime; - alertInfoSettings.InfoTextColor = InfoTextColor; - - alertInfoSettings.NewBarAlert = NewBarAlert; - alertInfoSettings.ReversalBarAlert = ReversalBarAlert; - alertInfoSettings.MaCrossAlert = MaCrossAlert ; - alertInfoSettings.UseAlertWindow = UseAlertWindow; - alertInfoSettings.UseSound = UseSound; - alertInfoSettings.UsePushNotifications = UsePushNotifications; - - alertInfoSettings.SoundFileBull = SoundFileBull; - alertInfoSettings.SoundFileBear = SoundFileBear; - alertInfoSettings.DisplayAsBarChart = DisplayAsBarChart; - #endif -#endif -} - -bool RangeBarSettings::Changed(void) -{ - if(MQLInfoInteger((int)MQL5_TESTING)) - return false; - - static datetime prevFileTime = 0; - - if(!FileIsExist(this.settingsFileName)) - return false; - - int handle = FileOpen(this.settingsFileName,FILE_SHARE_READ|FILE_BIN); - datetime currFileTime = (datetime)FileGetInteger(handle,FILE_CREATE_DATE); - FileClose(handle); - - if(prevFileTime != currFileTime) - { - prevFileTime = currFileTime; - return true; - } - - return false; -} diff --git a/Include/AZ-INVEST/SDK/RangeBars.mqh b/Include/AZ-INVEST/SDK/RangeBars.mqh index b46e1d1..3d27b4b 100644 --- a/Include/AZ-INVEST/SDK/RangeBars.mqh +++ b/Include/AZ-INVEST/SDK/RangeBars.mqh @@ -1,48 +1,48 @@ -//+------------------------------------------------------------------+ -//| RangeBars.mqh ver:2.03.0 | -//| Copyright 2017, AZ-iNVEST | -//| http://www.az-invest.eu | -//+------------------------------------------------------------------+ -#property copyright "Copyright 2017, AZ-iNVEST" +#property copyright "Copyright 2018-2020, Level Up Software" #property link "http://www.az-invest.eu" -//#define RANGEBAR_INDICATOR_NAME "RangeBars\\RangeBarsOverlay213" -#define RANGEBAR_INDICATOR_NAME "Market\\Range Bars Charting" +#ifdef DEVELOPER_VERSION + #define RANGEBAR_INDICATOR_NAME "RangeBars\\RangeBarsOverlay300" +#else + #define RANGEBAR_INDICATOR_NAME "Market\\Range Bars Charting" +#endif #define RANGEBAR_OPEN 00 #define RANGEBAR_HIGH 01 #define RANGEBAR_LOW 02 #define RANGEBAR_CLOSE 03 #define RANGEBAR_BAR_COLOR 04 -#define RANGEBAR_MA1 05 -#define RANGEBAR_MA2 06 -#define RANGEBAR_MA3 07 -#define RANGEBAR_CHANNEL_HIGH 08 -#define RANGEBAR_CHANNEL_MID 09 -#define RANGEBAR_CHANNEL_LOW 10 -#define RANGEBAR_BAR_OPEN_TIME 11 -#define RANGEBAR_TICK_VOLUME 12 -#define RANGEBAR_REAL_VOLUME 13 -#define RANGEBAR_BUY_VOLUME 14 -#define RANGEBAR_SELL_VOLUME 15 -#define RANGEBAR_BUYSELL_VOLUME 16 +#define RANGEBAR_SESSION_RECT_H 05 +#define RANGEBAR_SESSION_RECT_L 06 +#define RANGEBAR_MA1 07 +#define RANGEBAR_MA2 08 +#define RANGEBAR_MA3 09 +#define RANGEBAR_MA4 10 +#define RANGEBAR_CHANNEL_HIGH 11 +#define RANGEBAR_CHANNEL_MID 12 +#define RANGEBAR_CHANNEL_LOW 13 +#define RANGEBAR_BAR_OPEN_TIME 14 +#define RANGEBAR_TICK_VOLUME 15 +#define RANGEBAR_REAL_VOLUME 16 +#define RANGEBAR_BUY_VOLUME 17 +#define RANGEBAR_SELL_VOLUME 18 +#define RANGEBAR_BUYSELL_VOLUME 19 +#define RANGEBAR_RUNTIME_ID 20 -#include +#include class RangeBars { private: - RangeBarSettings * rangeBarSettings; + CRangeBarCustomChartSettigns * rangeBarSettings; - // - // Median renko indicator handle - // - - int rangeBarsHandle; + int rangeBarsHandle; // range bar indicator handle string rangeBarsSymbol; bool usedByIndicatorOnRangeBarChart; + datetime prevBarTime; + public: RangeBars(); @@ -53,49 +53,60 @@ class RangeBars int Init(); void Deinit(); bool Reload(); - + void ReleaseHandle(); + int GetHandle(void) { return rangeBarsHandle; }; + double GetRuntimeId(); + + bool IsNewBar(); + bool GetMqlRates(MqlRates &ratesInfoArray[], int start, int count); bool GetBuySellVolumeBreakdown(double &buy[], double &sell[], double &buySell[], int start, int count); + bool GetMA(int MaBufferId, double &MA[], int start, int count); + bool GetChannel(double &HighArray[], double &MidArray[], double &LowArray[], int start, int count); + + // The following 6 functions are deprecated, please use GetMA & GetChannelData functions instead bool GetMA1(double &MA[], int start, int count); bool GetMA2(double &MA[], int start, int count); bool GetMA3(double &MA[], int start, int count); bool GetDonchian(double &HighArray[], double &MidArray[], double &LowArray[], int start, int count); bool GetBollingerBands(double &HighArray[], double &MidArray[], double &LowArray[], int start, int count); bool GetSuperTrend(double &SuperTrendHighArray[], double &SuperTrendArray[], double &SuperTrendLowArray[], int start, int count); - - bool IsNewBar(); + // private: - bool GetChannel(double &HighArray[], double &MidArray[], double &LowArray[], int start, int count); int GetIndicatorHandle(void); + bool GetChannelData(double &HighArray[], double &MidArray[], double &LowArray[], int start, int count); }; RangeBars::RangeBars(void) { #define CONSTRUCTOR1 - rangeBarSettings = new RangeBarSettings(); + rangeBarSettings = new CRangeBarCustomChartSettigns(); rangeBarsHandle = INVALID_HANDLE; rangeBarsSymbol = _Symbol; usedByIndicatorOnRangeBarChart = false; + prevBarTime = 0; } RangeBars::RangeBars(bool isUsedByIndicatorOnRangeBarChart) { - rangeBarSettings = new RangeBarSettings(); + rangeBarSettings = new CRangeBarCustomChartSettigns(); rangeBarsHandle = INVALID_HANDLE; rangeBarsSymbol = _Symbol; usedByIndicatorOnRangeBarChart = isUsedByIndicatorOnRangeBarChart; + prevBarTime = 0; } RangeBars::RangeBars(string symbol) { #define CONSTRUCTOR2 - rangeBarSettings = new RangeBarSettings(); + rangeBarSettings = new CRangeBarCustomChartSettigns(); rangeBarsHandle = INVALID_HANDLE; rangeBarsSymbol = symbol; usedByIndicatorOnRangeBarChart = false; + prevBarTime = 0; } RangeBars::~RangeBars(void) @@ -104,6 +115,14 @@ RangeBars::~RangeBars(void) delete rangeBarSettings; } +void RangeBars::ReleaseHandle() +{ + if(rangeBarsHandle != INVALID_HANDLE) + { + IndicatorRelease(rangeBarsHandle); + } +} + // // Function for initializing the median renko indicator handle // @@ -117,6 +136,9 @@ int RangeBars::Init() // // Indicator on RangeBar chart uses the values of the RangeBar chart for calculations // + + IndicatorRelease(rangeBarsHandle); + rangeBarsHandle = GetIndicatorHandle(); return rangeBarsHandle; } @@ -157,28 +179,21 @@ int RangeBars::Init() // Load settings from EA inputs // rangeBarSettings.Load(); - #else - // - // Save indicator inputs for use by EA attached to same chart. - // - rangeBarSettings.Save(); #endif } } - RANGEBAR_SETTINGS s = rangeBarSettings.GetRangeBarSettings(); + RANGEBAR_SETTINGS s = rangeBarSettings.GetCustomChartSettings(); CHART_INDICATOR_SETTINGS cis = rangeBarSettings.GetChartIndicatorSettings(); - //RangeBarSettings.Debug(); - - rangeBarsHandle = iCustom(this.rangeBarsSymbol,_Period,RANGEBAR_INDICATOR_NAME, + rangeBarsHandle = iCustom(this.rangeBarsSymbol, _Period, RANGEBAR_INDICATOR_NAME, s.barSizeInTicks, s.atrEnabled, //s.atrTimeFrame, s.atrPeriod, s.atrPercentage, - s.showNumberOfDays, - s.resetOpenOnNewTradingDay, + s.showNumberOfDays, s.resetOpenOnNewTradingDay, + TradingSessionTime, TopBottomPaddingPercentage, showPivots, pivotPointCalculationType, @@ -188,55 +203,57 @@ int RangeBars::Init() PDHColor, PDLColor, PDCColor, - showNextBarLevels, - HighThresholdIndicatorColor, - LowThresholdIndicatorColor, showCurrentBarOpenTime, - InfoTextColor, - NewBarAlert, - ReversalBarAlert, - MaCrossAlert, - UseAlertWindow, - UseSound, - UsePushNotifications, + AlertMeWhen, + AlertNotificationType, SoundFileBull, SoundFileBear, cis.MA1on, + cis.MA1lineType, cis.MA1period, cis.MA1method, cis.MA1applyTo, cis.MA1shift, - cis.MA2on, + cis.MA1priceLabel, + cis.MA2on, + cis.MA2lineType, cis.MA2period, cis.MA2method, cis.MA2applyTo, cis.MA2shift, - cis.MA3on, + cis.MA2priceLabel, + cis.MA3on, + cis.MA3lineType, cis.MA3period, cis.MA3method, cis.MA3applyTo, cis.MA3shift, + cis.MA3priceLabel, + cis.MA4on, + cis.MA4lineType, + cis.MA4period, + cis.MA4method, + cis.MA4applyTo, + cis.MA4shift, + cis.MA4priceLabel, cis.ShowChannel, - "", - cis.DonchianPeriod, - cis.BBapplyTo, - cis.BollingerBandsPeriod, - cis.BollingerBandsDeviations, - cis.SuperTrendPeriod, - cis.SuperTrendMultiplier, - "", - DisplayAsBarChart, - ShiftObj, - UsedInEA); - + cis.ChannelPeriod, + cis.ChannelAtrPeriod, + cis.ChannelAppliedPrice, + cis.ChannelMultiplier, + cis.ChannelBandsDeviations, + cis.ChannelPriceLabel, + cis.ChannelMidPriceLabel, + true); // used in EA + // DisplayAsBarChart & ShiftObj let at defaults if(rangeBarsHandle == INVALID_HANDLE) { - Print("RangeBar indicator init failed on error ",GetLastError()); + Print(RANGEBAR_INDICATOR_NAME+" indicator init failed on error ",GetLastError()); } else { - Print("RangeBar indicator init OK"); + Print(RANGEBAR_INDICATOR_NAME+" indicator init OK"); } return rangeBarsHandle; @@ -248,14 +265,36 @@ int RangeBars::Init() bool RangeBars::Reload() { - if(rangeBarSettings.Changed()) + bool actionNeeded = false; + int temp = GetIndicatorHandle(); + + if(temp != rangeBarsHandle) { - if(Init() == INVALID_HANDLE) - return false; - - return true; + IndicatorRelease(rangeBarsHandle); + rangeBarsHandle = INVALID_HANDLE; + + actionNeeded = true; } + if(rangeBarSettings.Changed(GetRuntimeId())) + { + actionNeeded = true; + } + + if(actionNeeded) + { + if(rangeBarsHandle != INVALID_HANDLE) + { + IndicatorRelease(rangeBarsHandle); + rangeBarsHandle = INVALID_HANDLE; + } + + if(Init() == INVALID_HANDLE) + return false; + + return true; + } + return false; } @@ -271,9 +310,9 @@ void RangeBars::Deinit() if(!usedByIndicatorOnRangeBarChart) { if(IndicatorRelease(rangeBarsHandle)) - Print("RangeBar indicator handle released"); + Print(RANGEBAR_INDICATOR_NAME+" indicator handle released"); else - Print("Failed to release RangeBar indicator handle"); + Print("Failed to release "+RANGEBAR_INDICATOR_NAME+" indicator handle"); } } @@ -283,13 +322,13 @@ void RangeBars::Deinit() bool RangeBars::IsNewBar() { - MqlRates currentBar[1]; - static datetime prevBarTime; - + MqlRates currentBar[1]; GetMqlRates(currentBar,0,1); if(currentBar[0].time == 0) + { return false; + } if(prevBarTime < currentBar[0].time) { @@ -297,7 +336,8 @@ bool RangeBars::IsNewBar() return true; } - return false;} + return false; +} // // Get "count" Renko MqlRates into "ratesInfoArray[]" array starting from "start" bar @@ -380,23 +420,12 @@ bool RangeBars::GetBuySellVolumeBreakdown(double &buy[], double &sell[], double if(ArrayResize(bs,count) == -1) return false; -#ifdef P_RANGEBAR_BR - #ifdef P_RANGEBAR_BR_PRO if(CopyBuffer(rangeBarsHandle,RANGEBAR_BUY_VOLUME,start,count,b) == -1) return false; if(CopyBuffer(rangeBarsHandle,RANGEBAR_SELL_VOLUME,start,count,s) == -1) return false; if(CopyBuffer(rangeBarsHandle,RANGEBAR_BUYSELL_VOLUME,start,count,bs) == -1) return false; - #endif -#else - if(CopyBuffer(rangeBarsHandle,RANGEBAR_BUY_VOLUME,start,count,b) == -1) - return false; - if(CopyBuffer(rangeBarsHandle,RANGEBAR_SELL_VOLUME,start,count,s) == -1) - return false; - if(CopyBuffer(rangeBarsHandle,RANGEBAR_BUYSELL_VOLUME,start,count,bs) == -1) - return false; -#endif if(ArrayResize(buy,count) == -1) return false; @@ -418,16 +447,48 @@ bool RangeBars::GetBuySellVolumeBreakdown(double &buy[], double &sell[], double ArrayFree(bs); return true; - - } +// +// Get "count" values for MaBufferId buffer into "MA[]" array starting from "start" bar +// + +bool RangeBars::GetMA(int MaBufferId, double &MA[], int start, int count) +{ + double tempMA[]; + if(ArrayResize(tempMA, count) == -1) + return false; + + if(ArrayResize(MA, count) == -1) + return false; + + if(MaBufferId != RANGEBAR_MA1 && MaBufferId != RANGEBAR_MA2 && MaBufferId != RANGEBAR_MA3 && MaBufferId != RANGEBAR_MA4) + { + Print("Incorrect MA buffer id specified in "+__FUNCTION__); + return false; + } + + if(CopyBuffer(rangeBarsHandle, MaBufferId,start,count,tempMA) == -1) + { + return false; + } + + for(int i=0; i -RangeBarIndicator rangeBarsIndicator; +RangeBarIndicator customChartIndicator; // // @@ -99,39 +99,15 @@ int OnCalculate(const int rates_total, const int &Spread[]) { // - // Process data through MedianRenko indicator - // - if(!rangeBarsIndicator.OnCalculate(rates_total,prev_calculated,Time)) + if(!customChartIndicator.OnCalculate(rates_total,prev_calculated,Time,Close)) return(0); - // - // Make the following modifications in the code below: - // - // rangeBarsIndicator.GetPrevCalculated() should be used instead of prev_calculated - // - // rangeBarsIndicator.Open[] should be used instead of open[] - // rangeBarsIndicator.Low[] should be used instead of low[] - // rangeBarsIndicator.High[] should be used instead of high[] - // rangeBarsIndicator.Close[] should be used instead of close[] - // - // rangeBarsIndicator.IsNewBar (true/false) informs you if a renko brick completed - // - // rangeBarsIndicator.Time[] shold be used instead of Time[] for checking the renko bar time. - // (!) rangeBarsIndicator.SetGetTimeFlag() must be called in OnInit() for rangeBarsIndicator.Time[] to be used - // - // rangeBarsIndicator.Tick_volume[] should be used instead of TickVolume[] - // rangeBarsIndicator.Real_volume[] should be used instead of Volume[] - // (!) rangeBarsIndicator.SetGetVolumesFlag() must be called in OnInit() for Tick_volume[] & Real_volume[] to be used - // - // rangeBarsIndicator.Price[] should be used instead of Price[] - // (!) rangeBarsIndicator.SetUseAppliedPriceFlag(ENUM_APPLIED_PRICE _applied_price) must be called in OnInit() for rangeBarsIndicator.Price[] to be used - // + if(!customChartIndicator.BufferSynchronizationCheck(Close)) + return(0); - int _prev_calculated = rangeBarsIndicator.GetPrevCalculated(); + int _prev_calculated = customChartIndicator.GetPrevCalculated(); - // - // // //--- checking for bars count @@ -151,11 +127,11 @@ int OnCalculate(const int rates_total, for(int i=start;i -RangeBarIndicator rangeBarsIndicator; +RangeBarIndicator customChartIndicator; // // @@ -72,39 +72,15 @@ int OnCalculate(const int rates_total, const int &spread[]) { // - // Process data through MedianRenko indicator - // - - if(!rangeBarsIndicator.OnCalculate(rates_total,prev_calculated,time)) + + if(!customChartIndicator.OnCalculate(rates_total,prev_calculated,time,close)) return(0); - // - // Make the following modifications in the code below: - // - // rangeBarsIndicator.GetPrevCalculated() should be used instead of prev_calculated - // - // rangeBarsIndicator.Open[] should be used instead of open[] - // rangeBarsIndicator.Low[] should be used instead of low[] - // rangeBarsIndicator.High[] should be used instead of high[] - // rangeBarsIndicator.Close[] should be used instead of close[] - // - // rangeBarsIndicator.IsNewBar (true/false) informs you if a renko brick completed - // - // rangeBarsIndicator.Time[] shold be used instead of Time[] for checking the renko bar time. - // (!) rangeBarsIndicator.SetGetTimeFlag() must be called in OnInit() for rangeBarsIndicator.Time[] to be used - // - // rangeBarsIndicator.Tick_volume[] should be used instead of TickVolume[] - // rangeBarsIndicator.Real_volume[] should be used instead of Volume[] - // (!) rangeBarsIndicator.SetGetVolumesFlag() must be called in OnInit() for Tick_volume[] & Real_volume[] to be used - // - // rangeBarsIndicator.Price[] should be used instead of Price[] - // (!) rangeBarsIndicator.SetUseAppliedPriceFlag(ENUM_APPLIED_PRICE _applied_price) must be called in OnInit() for rangeBarsIndicator.Price[] to be used - // + if(!customChartIndicator.BufferSynchronizationCheck(close)) + return(0); - int _prev_calculated = rangeBarsIndicator.GetPrevCalculated(); + int _prev_calculated = customChartIndicator.GetPrevCalculated(); - // - // // int i,limit; @@ -118,7 +94,7 @@ int OnCalculate(const int rates_total, ExtATRBuffer[0]=0.0; //--- filling out the array of True Range values for each period for(i=1;i #include -RangeBarIndicator rangeBarsIndicator; - +RangeBarIndicator customChartIndicator; // // @@ -54,11 +51,8 @@ void OnInit() //--- get handles //ExtFastSMAHandle=iMA(NULL,0,5,0,MODE_SMA,PRICE_MEDIAN); //ExtSlowSMAHandle=iMA(NULL,0,34,0,MODE_SMA,PRICE_MEDIAN); - // renko mod -// ExtFastSMAHandle=iCustom(Symbol(),_Period,"RangeBars\\Indicators\\RangeBars_MA",5,0,MODE_SMA,PRICE_MEDIAN,true); -// ExtSlowSMAHandle=iCustom(Symbol(),_Period,"RangeBars\\Indicators\\RangeBars_MA",34,0,MODE_SMA,PRICE_MEDIAN,true); - ExtFastSMAHandle=iCustom(Symbol(),_Period,"RangeBars\\RangeBars_MA",5,0,MODE_SMA,PRICE_MEDIAN,true); - ExtSlowSMAHandle=iCustom(Symbol(),_Period,"RangeBars\\RangeBars_MA",34,0,MODE_SMA,PRICE_MEDIAN,true); +// -- Set applied price to MEDIAN as required by AO indicator + customChartIndicator.SetUseAppliedPriceFlag(PRICE_MEDIAN); //---- initialization done } //+------------------------------------------------------------------+ @@ -80,48 +74,21 @@ int OnCalculate(const int rates_total, if(rates_total<=DATA_LIMIT) return(0);// not enough bars for calculation -//--- not all data may be calculated - int calculated=BarsCalculated(ExtFastSMAHandle); - if(calculatedrates_total || _prev_calculated<0) to_copy=rates_total; - else - { - to_copy=rates_total-prev_calculated; - if(_prev_calculated>0) to_copy++; - } -//--- get FastSMA buffer +//--- get Fast MA buffer + if(IsStopped()) return(0); //Checking for stop flag + SimpleMAOnBuffer(rates_total,_prev_calculated,0,5,customChartIndicator.Price,ExtFastBuffer); +//--- get Slow MA buffer if(IsStopped()) return(0); //Checking for stop flag - if(CopyBuffer(ExtFastSMAHandle,0,0,to_copy,ExtFastBuffer)<=0) - { - Print("Getting fast SMA is failed! Error",GetLastError()); - return(0); - } -//--- get SlowSMA buffer - if(IsStopped()) return(0); //Checking for stop flag - if(CopyBuffer(ExtSlowSMAHandle,0,0,to_copy,ExtSlowBuffer)<=0) - { - Print("Getting slow SMA is failed! Error",GetLastError()); - return(0); - } + SimpleMAOnBuffer(rates_total,_prev_calculated,0,35,customChartIndicator.Price,ExtSlowBuffer); + //--- first calculation or number of bars was changed int i,limit; if(_prev_calculated<=DATA_LIMIT) diff --git a/Indicators/RangeBars/RangeBars_BB_MACD.mq5 b/Indicators/RangeBars/RangeBars_BB_MACD.mq5 new file mode 100644 index 0000000..7888d92 Binary files /dev/null and b/Indicators/RangeBars/RangeBars_BB_MACD.mq5 differ diff --git a/Indicators/RangeBars/RangeBars_BollingerBandsMacd.mq5 b/Indicators/RangeBars/RangeBars_BollingerBandsMacd.mq5 new file mode 100644 index 0000000..a35e93d Binary files /dev/null and b/Indicators/RangeBars/RangeBars_BollingerBandsMacd.mq5 differ diff --git a/Indicators/RangeBars/RangeBars_CCI.mq5 b/Indicators/RangeBars/RangeBars_CCI.mq5 index 7b6f5ed..0e297c5 100644 --- a/Indicators/RangeBars/RangeBars_CCI.mq5 +++ b/Indicators/RangeBars/RangeBars_CCI.mq5 @@ -34,7 +34,7 @@ double ExtCCIBuffer[]; // #include -RangeBarIndicator rangeBarsIndicator; +RangeBarIndicator customChartIndicator; // // @@ -50,7 +50,7 @@ void OnInit() // Indicator uses Price[] array for calculations so we need to set this in the MedianRenkoIndicator class // - rangeBarsIndicator.SetUseAppliedPriceFlag(InpApplyToPrice); + customChartIndicator.SetUseAppliedPriceFlag(InpApplyToPrice); // // @@ -100,33 +100,36 @@ int OnCalculate(const int rates_total,const int prev_calculated, // Process data through MedianRenko indicator // - if(!rangeBarsIndicator.OnCalculate(rates_total,prev_calculated,Time)) + if(!customChartIndicator.OnCalculate(rates_total,prev_calculated,Time,Close)) + return(0); + + if(!customChartIndicator.BufferSynchronizationCheck(Close)) return(0); // // Make the following modifications in the code below: // - // rangeBarsIndicator.GetPrevCalculated() should be used instead of prev_calculated + // customChartIndicator.GetPrevCalculated() should be used instead of prev_calculated // - // rangeBarsIndicator.Open[] should be used instead of open[] - // rangeBarsIndicator.Low[] should be used instead of low[] - // rangeBarsIndicator.High[] should be used instead of high[] - // rangeBarsIndicator.Close[] should be used instead of close[] + // customChartIndicator.Open[] should be used instead of open[] + // customChartIndicator.Low[] should be used instead of low[] + // customChartIndicator.High[] should be used instead of high[] + // customChartIndicator.Close[] should be used instead of close[] // - // rangeBarsIndicator.IsNewBar (true/false) informs you if a renko brick completed + // customChartIndicator.IsNewBar (true/false) informs you if a renko brick completed // - // rangeBarsIndicator.Time[] shold be used instead of Time[] for checking the renko bar time. - // (!) rangeBarsIndicator.SetGetTimeFlag() must be called in OnInit() for rangeBarsIndicator.Time[] to be used + // customChartIndicator.Time[] shold be used instead of Time[] for checking the renko bar time. + // (!) customChartIndicator.SetGetTimeFlag() must be called in OnInit() for customChartIndicator.Time[] to be used // - // rangeBarsIndicator.Tick_volume[] should be used instead of TickVolume[] - // rangeBarsIndicator.Real_volume[] should be used instead of Volume[] - // (!) rangeBarsIndicator.SetGetVolumesFlag() must be called in OnInit() for Tick_volume[] & Real_volume[] to be used + // customChartIndicator.Tick_volume[] should be used instead of TickVolume[] + // customChartIndicator.Real_volume[] should be used instead of Volume[] + // (!) customChartIndicator.SetGetVolumesFlag() must be called in OnInit() for Tick_volume[] & Real_volume[] to be used // - // rangeBarsIndicator.Price[] should be used instead of Price[] - // (!) rangeBarsIndicator.SetUseAppliedPriceFlag(ENUM_APPLIED_PRICE _applied_price) must be called in OnInit() for rangeBarsIndicator.Price[] to be used + // customChartIndicator.Price[] should be used instead of Price[] + // (!) customChartIndicator.SetUseAppliedPriceFlag(ENUM_APPLIED_PRICE _applied_price) must be called in OnInit() for customChartIndicator.Price[] to be used // - int _prev_calculated = rangeBarsIndicator.GetPrevCalculated(); + int _prev_calculated = customChartIndicator.GetPrevCalculated(); // // @@ -150,13 +153,13 @@ int OnCalculate(const int rates_total,const int prev_calculated, for(i=pos;i -RangeBarIndicator rangeBarsIndicator; +RangeBarIndicator customChartIndicator; // // @@ -66,39 +66,15 @@ int OnCalculate(const int rates_total,const int prev_calculated, const int &Spread[]) { // - // Process data through MedianRenko indicator - // - if(!rangeBarsIndicator.OnCalculate(rates_total,prev_calculated,Time)) + if(!customChartIndicator.OnCalculate(rates_total,prev_calculated,Time,Close)) return(0); - // - // Make the following modifications in the code below: - // - // rangeBarsIndicator.GetPrevCalculated() should be used instead of prev_calculated - // - // rangeBarsIndicator.Open[] should be used instead of open[] - // rangeBarsIndicator.Low[] should be used instead of low[] - // rangeBarsIndicator.High[] should be used instead of high[] - // rangeBarsIndicator.Close[] should be used instead of close[] - // - // rangeBarsIndicator.IsNewBar (true/false) informs you if a renko brick completed - // - // rangeBarsIndicator.Time[] shold be used instead of Time[] for checking the renko bar time. - // (!) rangeBarsIndicator.SetGetTimeFlag() must be called in OnInit() for rangeBarsIndicator.Time[] to be used - // - // rangeBarsIndicator.Tick_volume[] should be used instead of TickVolume[] - // rangeBarsIndicator.Real_volume[] should be used instead of Volume[] - // (!) rangeBarsIndicator.SetGetVolumesFlag() must be called in OnInit() for Tick_volume[] & Real_volume[] to be used - // - // rangeBarsIndicator.Price[] should be used instead of Price[] - // (!) rangeBarsIndicator.SetUseAppliedPriceFlag(ENUM_APPLIED_PRICE _applied_price) must be called in OnInit() for rangeBarsIndicator.Price[] to be used - // + if(!customChartIndicator.BufferSynchronizationCheck(Close)) + return(0); + + int _prev_calculated = customChartIndicator.GetPrevCalculated(); - int _prev_calculated = rangeBarsIndicator.GetPrevCalculated(); - - // - // // int i,limit; @@ -118,13 +94,13 @@ int OnCalculate(const int rates_total,const int prev_calculated, for(i=limit; irangeBarsIndicator.High[i+1] && rangeBarsIndicator.High[i]>rangeBarsIndicator.High[i+2] && rangeBarsIndicator.High[i]>=rangeBarsIndicator.High[i-1] && rangeBarsIndicator.High[i]>=rangeBarsIndicator.High[i-2]) - ExtUpperBuffer[i]=rangeBarsIndicator.High[i]; + if(customChartIndicator.High[i]>customChartIndicator.High[i+1] && customChartIndicator.High[i]>customChartIndicator.High[i+2] && customChartIndicator.High[i]>=customChartIndicator.High[i-1] && customChartIndicator.High[i]>=customChartIndicator.High[i-2]) + ExtUpperBuffer[i]=customChartIndicator.High[i]; else ExtUpperBuffer[i]=EMPTY_VALUE; //---- Lower Fractal - if(rangeBarsIndicator.Low[i] +RangeBarIndicator customChartIndicator; +// +// + +enum enMaTypes +{ + ma_sma, // Simple moving average + ma_ema, // Exponential moving average + ma_smma, // Smoothed MA + ma_lwma // Linear weighted MA +}; +enum enFilterWhat +{ + flt_prc, // Filter the prices + flt_val, // Filter the averages value + flt_all // Filter all +}; + ENUM_TIMEFRAMES TimeFrame = PERIOD_CURRENT; // Time frame +input int AvgPeriod = 10; // Average period +input enMaTypes AvgType = ma_sma; // Average method +input double Filter = 0; // Filter to use (<=0 for no filter) +input enFilterWhat FilterOn = flt_prc; // Filter : +input bool alertsOn = false; // Turn alerts on? +input bool alertsOnCurrent = true; // Alert on current bar? +input bool alertsMessage = true; // Display messageas on alerts? +input bool alertsSound = false; // Play sound on alerts? +input bool alertsEmail = false; // Send email on alerts? +input bool alertsNotify = false; // Send push notification on alerts? +input bool Interpolate = true; // Interpolate mtf data ? + +double sup[],supc[],mid[],fup[],fdn[],_count[]; +ENUM_TIMEFRAMES timeFrame; +string indName; + +//------------------------------------------------------------------ +// +//------------------------------------------------------------------ +// +// +// +// +// + +int OnInit() +{ + SetIndexBuffer(0,fup,INDICATOR_DATA); + SetIndexBuffer(1,fdn,INDICATOR_DATA); + SetIndexBuffer(2,mid,INDICATOR_DATA); + SetIndexBuffer(3,sup,INDICATOR_DATA); + SetIndexBuffer(4,supc,INDICATOR_COLOR_INDEX); + SetIndexBuffer(5,_count,INDICATOR_CALCULATIONS); + + // + // + // + // + // + + customChartIndicator.SetGetTimeFlag(); + +// timeFrame = MathMax(_Period,TimeFrame); + indName = getIndicatorName(); + IndicatorSetString(INDICATOR_SHORTNAME,periodToString(timeFrame)+" Gann high/low activator("+string(AvgPeriod)+")"); + return(0); +} + +//------------------------------------------------------------------ +// +//------------------------------------------------------------------ +// +// +// +// +// + +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[]) +{ + if (Bars(_Symbol,_Period)fup[i]) ? 1 : (pclose0) + { + workFil[i][instanceNo+_fchange] = MathAbs(workFil[i][instanceNo+_fvalue]-workFil[i-1][instanceNo+_fvalue]); + workFil[i][instanceNo+_fachang] = workFil[i][instanceNo+_fchange]; + + double fdev=0, fdif=0; + for (int k=1; k=0; k++) workFil[i][instanceNo+_fachang] += workFil[i-k][instanceNo+_fchange]; workFil[i][instanceNo+_fachang] /= (double)period; + for (int k=0; k=0; k++) fdev += MathPow(workFil[i-k][instanceNo+_fchange]-workFil[i-k][instanceNo+_fachang],2); fdev = MathSqrt(fdev/(double)period); fdif = filter*fdev; + if (MathAbs(workFil[i][instanceNo+_fvalue]-workFil[i-1][instanceNo+_fvalue])=0; k++) workSma[r][instanceNo+1] += workSma[r-k][instanceNo+0]; + workSma[r][instanceNo+1] /= 1.0*k; + return(workSma[r][instanceNo+1]); +} + +// +// +// +// +// + +double workEma[][_maWorkBufferx1]; +double iEma(double price, double period, int r, int _bars, int instanceNo=0) +{ + if (period<=1) return(price); + if (ArrayRange(workEma,0)!= _bars) ArrayResize(workEma,_bars); + + // + // + // + // + // + + workEma[r][instanceNo] = price; + double alpha = 2.0 / (1.0+period); + if (r>0) + workEma[r][instanceNo] = workEma[r-1][instanceNo]+alpha*(price-workEma[r-1][instanceNo]); + return(workEma[r][instanceNo]); +} + +// +// +// +// +// + +double workSmma[][_maWorkBufferx1]; +double iSmma(double price, double period, int r, int _bars, int instanceNo=0) +{ + if (period<=1) return(price); + if (ArrayRange(workSmma,0)!= _bars) ArrayResize(workSmma,_bars); + + // + // + // + // + // + + if (r=0; k++) + { + double weight = period-k; + sumw += weight; + sum += weight*workLwma[r-k][instanceNo]; + } + return(sum/sumw); +} + +//------------------------------------------------------------------ +// +//------------------------------------------------------------------ +// +// +// +// +// + +string getIndicatorName() +{ + string progPath = MQL5InfoString(MQL5_PROGRAM_PATH); int start=-1; + while (true) + { + int foundAt = StringFind(progPath,"\\",start+1); + if (foundAt>=0) + start = foundAt; + else break; + } + + string indicatorName = StringSubstr(progPath,start+1); + indicatorName = StringSubstr(indicatorName,0,StringLen(indicatorName)-4); + return(indicatorName); +} + +// +// +// +// +// + +int _tfsPer[]={PERIOD_M1,PERIOD_M2,PERIOD_M3,PERIOD_M4,PERIOD_M5,PERIOD_M6,PERIOD_M10,PERIOD_M12,PERIOD_M15,PERIOD_M20,PERIOD_M30,PERIOD_H1,PERIOD_H2,PERIOD_H3,PERIOD_H4,PERIOD_H6,PERIOD_H8,PERIOD_H12,PERIOD_D1,PERIOD_W1,PERIOD_MN1}; +string _tfsStr[]={"1 minute","2 minutes","3 minutes","4 minutes","5 minutes","6 minutes","10 minutes","12 minutes","15 minutes","20 minutes","30 minutes","1 hour","2 hours","3 hours","4 hours","6 hours","8 hours","12 hours","daily","weekly","monthly"}; +string periodToString(int period) +{ + if (period==PERIOD_CURRENT) + period = _Period; + int i; for(i=0;i -RangeBarIndicator rangeBarsIndicator; +RangeBarIndicator customChartIndicator; // // @@ -97,42 +97,18 @@ int OnCalculate(const int rates_total, if(rates_totalNormalizeDouble(MaHighBuffer[i+1],_Digits)) TrendBuffer[i]=1; - if(NormalizeDouble(rangeBarsIndicator.Close[i],_Digits)NormalizeDouble(MaHighBuffer[i+1],_Digits)) TrendBuffer[i]=1; + if(NormalizeDouble(customChartIndicator.Close[i],_Digits) -RangeBarIndicator rangeBarsIndicator; +RangeBarIndicator customChartIndicator; // // @@ -67,36 +67,14 @@ int OnCalculate(const int rates_total, int i,limit; // - // Process data through MedianRenko indicator - // - - if(!rangeBarsIndicator.OnCalculate(rates_total,prev_calculated,time)) + + if(!customChartIndicator.OnCalculate(rates_total,prev_calculated,time,close)) return(0); - // - // Make the following modifications in the code below: - // - // rangeBarsIndicator.GetPrevCalculated() should be used instead of prev_calculated - // - // rangeBarsIndicator.Open[] should be used instead of open[] - // rangeBarsIndicator.Low[] should be used instead of low[] - // rangeBarsIndicator.High[] should be used instead of high[] - // rangeBarsIndicator.Close[] should be used instead of close[] - // - // rangeBarsIndicator.IsNewBar (true/false) informs you if a renko brick completed - // - // rangeBarsIndicator.Time[] shold be used instead of Time[] for checking the renko bar time. - // (!) rangeBarsIndicator.SetGetTimeFlag() must be called in OnInit() for rangeBarsIndicator.Time[] to be used - // - // rangeBarsIndicator.Tick_volume[] should be used instead of TickVolume[] - // rangeBarsIndicator.Real_volume[] should be used instead of Volume[] - // (!) rangeBarsIndicator.SetGetVolumesFlag() must be called in OnInit() for Tick_volume[] & Real_volume[] to be used - // - // rangeBarsIndicator.Price[] should be used instead of Price[] - // (!) rangeBarsIndicator.SetUseAppliedPriceFlag(ENUM_APPLIED_PRICE _applied_price) must be called in OnInit() for rangeBarsIndicator.Price[] to be used - // + if(!customChartIndicator.BufferSynchronizationCheck(close)) + return(0); - int _prev_calculated = rangeBarsIndicator.GetPrevCalculated(); + int _prev_calculated = customChartIndicator.GetPrevCalculated(); // // @@ -106,10 +84,10 @@ int OnCalculate(const int rates_total, if(_prev_calculated==0) { //--- set first candle - ExtLBuffer[0]=rangeBarsIndicator.Low[0]; - ExtHBuffer[0]=rangeBarsIndicator.High[0]; - ExtOBuffer[0]=rangeBarsIndicator.Open[0]; - ExtCBuffer[0]=rangeBarsIndicator.Close[0]; + ExtLBuffer[0]=customChartIndicator.Low[0]; + ExtHBuffer[0]=customChartIndicator.High[0]; + ExtOBuffer[0]=customChartIndicator.Open[0]; + ExtCBuffer[0]=customChartIndicator.Close[0]; limit=1; } else limit=_prev_calculated-1; @@ -118,9 +96,9 @@ int OnCalculate(const int rates_total, for(i=limit;i -RangeBarIndicator rangeBarsIndicator; +RangeBarIndicator customChartIndicator; // // @@ -115,36 +115,14 @@ int OnCalculate(const int rates_total, const int &spread[]) { // - // Process data through MedianRenko indicator - // - if(!rangeBarsIndicator.OnCalculate(rates_total,prev_calculated,time)) + if(!customChartIndicator.OnCalculate(rates_total,prev_calculated,time,close)) return(0); - // - // Make the following modifications in the code below: - // - // rangeBarsIndicator.GetPrevCalculated() should be used instead of prev_calculated - // - // rangeBarsIndicator.Open[] should be used instead of open[] - // rangeBarsIndicator.Low[] should be used instead of low[] - // rangeBarsIndicator.High[] should be used instead of high[] - // rangeBarsIndicator.Close[] should be used instead of close[] - // - // rangeBarsIndicator.IsNewBar (true/false) informs you if a renko brick completed - // - // rangeBarsIndicator.Time[] shold be used instead of Time[] for checking the renko bar time. - // (!) rangeBarsIndicator.SetGetTimeFlag() must be called in OnInit() for rangeBarsIndicator.Time[] to be used - // - // rangeBarsIndicator.Tick_volume[] should be used instead of TickVolume[] - // rangeBarsIndicator.Real_volume[] should be used instead of Volume[] - // (!) rangeBarsIndicator.SetGetVolumesFlag() must be called in OnInit() for Tick_volume[] & Real_volume[] to be used - // - // rangeBarsIndicator.Price[] should be used instead of Price[] - // (!) rangeBarsIndicator.SetUseAppliedPriceFlag(ENUM_APPLIED_PRICE _applied_price) must be called in OnInit() for rangeBarsIndicator.Price[] to be used - // + if(!customChartIndicator.BufferSynchronizationCheck(close)) + return(0); - int _prev_calculated = rangeBarsIndicator.GetPrevCalculated(); + int _prev_calculated = customChartIndicator.GetPrevCalculated(); // // @@ -157,20 +135,20 @@ int OnCalculate(const int rates_total, //--- for(int i=limit;i +RangeBarIndicator customChartIndicator; + +//+------------------------------------------------------------------+ +void OnInit() + { + SetIndexBuffer(0, ExtLRBuffer, INDICATOR_DATA); + PlotIndexSetInteger(0, PLOT_DRAW_BEGIN, LRPeriod-1); + + IndicatorSetString (INDICATOR_SHORTNAME,"Linear Regression"); + IndicatorSetInteger(INDICATOR_DIGITS,_Digits+1); + + customChartIndicator.SetUseAppliedPriceFlag(PRICE_CLOSE); + + } +//+------------------------------------------------------------------+ +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 &TickVolume[], + const long &Volume[], + const int &Spread[]) + { + + //////////////////////////////////////////////////////////////////////// + + if(!customChartIndicator.OnCalculate(rates_total,prev_calculated,Time,Close)) + return(0); + + if(!customChartIndicator.BufferSynchronizationCheck(Close)) + return(0); + + int _prev_calculated = customChartIndicator.GetPrevCalculated(); + + //////////////////////////////////////////////////////////////////////// + + if (rates_total < LRPeriod) + return(0); + + int limit = _prev_calculated ? _prev_calculated-1 : LRPeriod-1; + + // The cycle along the calculated bars + for (int bar = limit; bar < rates_total; bar++) + { + double lrvalue = 0; // the linear regression value in this bar + double Sx=0, Sy=0, Sxy=0, Sxx=0; + + // Finding intermediate values-sums + Sx = 0; + Sy = 0; + Sxx = 0; + Sxy = 0; + for (int x = 1; x <= LRPeriod; x++) + { + double y = customChartIndicator.GetPrice(bar-LRPeriod+x); + Sx += x; + Sy += y; + Sxx += x*x; + Sxy += x*y; + } + + // Regression ratios + double a = (LRPeriod * Sxy - Sx * Sy) / (LRPeriod * Sxx - Sx * Sx); + double b = (Sy - a * Sx) / LRPeriod; + + lrvalue = a*LRPeriod + b; + + // Saving regression results + ExtLRBuffer[bar] = lrvalue; + } + + return(rates_total); + } +//+------------------------------------------------------------------+ \ No newline at end of file diff --git a/Indicators/RangeBars/RangeBars_MA.mq5 b/Indicators/RangeBars/RangeBars_MA.mq5 index dd5e69b..83a1b77 100644 --- a/Indicators/RangeBars/RangeBars_MA.mq5 +++ b/Indicators/RangeBars/RangeBars_MA.mq5 @@ -26,7 +26,7 @@ double ExtLineBuffer[]; // #include -RangeBarIndicator rangeBarsIndicator; +RangeBarIndicator customChartIndicator; // // @@ -169,7 +169,7 @@ void OnInit() // Indicator uses Price[] array for calculations so we need to set this in the MedianRenkoIndicator class // - rangeBarsIndicator.SetUseAppliedPriceFlag(InpAppliedPrice); + customChartIndicator.SetUseAppliedPriceFlag(InpAppliedPrice); // // @@ -197,40 +197,16 @@ int OnCalculate(const int rates_total,const int prev_calculated, { // - // Process data through MedianRenko indicator - // - if(!rangeBarsIndicator.OnCalculate(rates_total,prev_calculated,Time)) + if(!customChartIndicator.OnCalculate(rates_total,prev_calculated,Time,Close)) return(0); - // - // Make the following modifications in the code below: - // - // rangeBarsIndicator.GetPrevCalculated() should be used instead of prev_calculated - // - // rangeBarsIndicator.Open[] should be used instead of open[] - // rangeBarsIndicator.Low[] should be used instead of low[] - // rangeBarsIndicator.High[] should be used instead of high[] - // rangeBarsIndicator.Close[] should be used instead of close[] - // - // rangeBarsIndicator.IsNewBar (true/false) informs you if a renko brick completed - // - // rangeBarsIndicator.Time[] shold be used instead of Time[] for checking the renko bar time. - // (!) rangeBarsIndicator.SetGetTimeFlag() must be called in OnInit() for rangeBarsIndicator.Time[] to be used - // - // rangeBarsIndicator.Tick_volume[] should be used instead of TickVolume[] - // rangeBarsIndicator.Real_volume[] should be used instead of Volume[] - // (!) rangeBarsIndicator.SetGetVolumesFlag() must be called in OnInit() for Tick_volume[] & Real_volume[] to be used - // - // rangeBarsIndicator.Price[] should be used instead of Price[] - // (!) rangeBarsIndicator.SetUseAppliedPriceFlag(ENUM_APPLIED_PRICE _applied_price) must be called in OnInit() for rangeBarsIndicator.Price[] to be used - // + if(!customChartIndicator.BufferSynchronizationCheck(Close)) + return(0); - int _prev_calculated = rangeBarsIndicator.GetPrevCalculated(); + int _prev_calculated = customChartIndicator.GetPrevCalculated(); int _begin = 0; - // - // // //--- check for bars count @@ -246,10 +222,10 @@ int OnCalculate(const int rates_total,const int prev_calculated, //--- calculation switch(InpMAMethod) { - case MODE_EMA: CalculateEMA(rates_total,_prev_calculated,_begin,rangeBarsIndicator.Price); break; - case MODE_LWMA: CalculateLWMA(rates_total,_prev_calculated,_begin,rangeBarsIndicator.Price); break; - case MODE_SMMA: CalculateSmoothedMA(rates_total,_prev_calculated,_begin,rangeBarsIndicator.Price); break; - case MODE_SMA: CalculateSimpleMA(rates_total,_prev_calculated,_begin,rangeBarsIndicator.Price); break; + case MODE_EMA: CalculateEMA(rates_total,_prev_calculated,_begin,customChartIndicator.Price); break; + case MODE_LWMA: CalculateLWMA(rates_total,_prev_calculated,_begin,customChartIndicator.Price); break; + case MODE_SMMA: CalculateSmoothedMA(rates_total,_prev_calculated,_begin,customChartIndicator.Price); break; + case MODE_SMA: CalculateSimpleMA(rates_total,_prev_calculated,_begin,customChartIndicator.Price); break; } //--- return value of prev_calculated for next call return(rates_total); diff --git a/Indicators/RangeBars/RangeBars_MACD.mq5 b/Indicators/RangeBars/RangeBars_MACD.mq5 index eef03e8..bb153a5 100644 --- a/Indicators/RangeBars/RangeBars_MACD.mq5 +++ b/Indicators/RangeBars/RangeBars_MACD.mq5 @@ -6,6 +6,8 @@ #property copyright "2009, MetaQuotes Software Corp." #property link "http://www.mql5.com" #property description "Moving Average Convergence/Divergence" +#property description "Adapted for use with TickChart by Artur Zas." + #include //--- indicator settings #property indicator_separate_window @@ -35,17 +37,8 @@ double ExtFastMaBuffer[]; double ExtSlowMaBuffer[]; double ExtMacdBuffer[]; -// -// -// - #include -RangeBarIndicator rangeBarsIndicator; - -// -// -// - +RangeBarIndicator customChartIndicator; //+------------------------------------------------------------------+ //| Custom indicator initialization function | @@ -79,53 +72,44 @@ int OnCalculate(const int rates_total,const int prev_calculated, const long &Volume[], const int &Spread[]) { - // - // Precoess data through MedianRenko indicator - // - if(!rangeBarsIndicator.OnCalculate(rates_total,prev_calculated,Time)) + if(!customChartIndicator.OnCalculate(rates_total,prev_calculated,Time,Close)) + return(0); + + if(!customChartIndicator.BufferSynchronizationCheck(Close)) return(0); - - // - // Make the following modifications in the code below: - // - // rangeBarsIndicator.GetPrevCalculated() should be used instead of prev_calculated - // rangeBarsIndicator.Open[] should be used instead of open[] - // rangeBarsIndicator.Low[] should be used instead of low[] - // rangeBarsIndicator.High[] should be used instead of high[] - // rangeBarsIndicator.Close[] should be used instead of close[] - // - int _prev_calculated = rangeBarsIndicator.GetPrevCalculated(); + int _prev_calculated = customChartIndicator.GetPrevCalculated(); + int _rates_total = customChartIndicator.GetRatesTotal(); - // - // - // - + + //--- check for data - if(rates_totalrates_total || _prev_calculated<0) to_copy=rates_total; + if(_prev_calculated>_rates_total || _prev_calculated<0) to_copy=_rates_total; else { - to_copy=rates_total-_prev_calculated; + to_copy=_rates_total-_prev_calculated; if(_prev_calculated>0) to_copy++; } + //--- get Fast EMA buffer if(IsStopped()) return(0); //Checking for stop flag - ExponentialMAOnBuffer(rates_total,_prev_calculated,0,InpFastEMA,rangeBarsIndicator.Close,ExtFastMaBuffer); + ExponentialMAOnBuffer(_rates_total,_prev_calculated,0,InpFastEMA,customChartIndicator.Close,ExtFastMaBuffer); //--- get SlowSMA buffer if(IsStopped()) return(0); //Checking for stop flag - ExponentialMAOnBuffer(rates_total,_prev_calculated,0,InpSlowEMA,rangeBarsIndicator.Close,ExtSlowMaBuffer); + ExponentialMAOnBuffer(_rates_total,_prev_calculated,0,InpSlowEMA,customChartIndicator.Close,ExtSlowMaBuffer); //--- int limit; if(_prev_calculated==0) limit=0; else limit=_prev_calculated-1; //--- calculate MACD - for(int i=limit;i 0) @@ -140,8 +124,9 @@ int OnCalculate(const int rates_total,const int prev_calculated, } } //--- calculate Signal - SimpleMAOnBuffer(rates_total,_prev_calculated,0,InpSignalSMA,ExtMacdBuffer,ExtSignalBuffer); + SimpleMAOnBuffer(_rates_total,_prev_calculated,0,InpSignalSMA,ExtMacdBuffer,ExtSignalBuffer); //--- OnCalculate done. Return new _prev_calculated. + return(rates_total); } //+------------------------------------------------------------------+ diff --git a/Indicators/RangeBars/RangeBars_MACD_Line.mq5 b/Indicators/RangeBars/RangeBars_MACD_Line.mq5 index a248be0..ceaa4b7 100644 --- a/Indicators/RangeBars/RangeBars_MACD_Line.mq5 +++ b/Indicators/RangeBars/RangeBars_MACD_Line.mq5 @@ -6,6 +6,8 @@ #property copyright "2009, MetaQuotes Software Corp." #property link "http://www.mql5.com" #property description "Moving Average Convergence/Divergence" +#property description "Adapted for use with TickChart by Artur Zas." + #include //--- indicator settings #property indicator_separate_window @@ -31,15 +33,11 @@ double ExtFastMaBuffer[]; double ExtSlowMaBuffer[]; double ExtMacdBuffer[]; -// -// // #include RangeBarIndicator customChartIndicator; -// -// // //+------------------------------------------------------------------+ @@ -78,11 +76,15 @@ int OnCalculate(const int rates_total,const int prev_calculated, // Precoess data through MedianRenko indicator // - if(!customChartIndicator.OnCalculate(rates_total,prev_calculated,Time)) + if(!customChartIndicator.OnCalculate(rates_total,prev_calculated,Time,Close)) + return(0); + + if(!customChartIndicator.BufferSynchronizationCheck(Close)) return(0); int _prev_calculated = customChartIndicator.GetPrevCalculated(); - + int _rates_total = customChartIndicator.GetRatesTotal(); + // // // @@ -98,6 +100,7 @@ int OnCalculate(const int rates_total,const int prev_calculated, to_copy=rates_total-_prev_calculated; if(_prev_calculated>0) to_copy++; } + //--- get Fast EMA buffer if(IsStopped()) return(0); //Checking for stop flag ExponentialMAOnBuffer(rates_total,_prev_calculated,0,InpFastEMA,customChartIndicator.Close,ExtFastMaBuffer); diff --git a/Indicators/RangeBars/RangeBars_Momentum.mq5 b/Indicators/RangeBars/RangeBars_Momentum.mq5 index cf0da5a..67354e6 100644 --- a/Indicators/RangeBars/RangeBars_Momentum.mq5 +++ b/Indicators/RangeBars/RangeBars_Momentum.mq5 @@ -26,7 +26,7 @@ int ExtMomentumPeriod; // #include -RangeBarIndicator rangeBarsIndicator; +RangeBarIndicator customChartIndicator; // // @@ -40,7 +40,7 @@ void OnInit() // Indicator uses Price[] array for calculations so we need to set this in the MedianRenkoIndicator class // - rangeBarsIndicator.SetUseAppliedPriceFlag(InpApplyToPrice); + customChartIndicator.SetUseAppliedPriceFlag(InpApplyToPrice); // // @@ -88,39 +88,15 @@ int OnCalculate(const int rates_total,const int prev_calculated, static int begin = 0; // - // Process data through MedianRenko indicator - // - - if(!rangeBarsIndicator.OnCalculate(rates_total,prev_calculated,Time)) + + if(!customChartIndicator.OnCalculate(rates_total,prev_calculated,Time,Close)) return(0); - // - // Make the following modifications in the code below: - // - // rangeBarsIndicator.GetPrevCalculated() should be used instead of prev_calculated - // - // rangeBarsIndicator.Open[] should be used instead of open[] - // rangeBarsIndicator.Low[] should be used instead of low[] - // rangeBarsIndicator.High[] should be used instead of high[] - // rangeBarsIndicator.Close[] should be used instead of close[] - // - // rangeBarsIndicator.IsNewBar (true/false) informs you if a renko brick completed - // - // rangeBarsIndicator.Time[] shold be used instead of Time[] for checking the renko bar time. - // (!) rangeBarsIndicator.SetGetTimeFlag() must be called in OnInit() for rangeBarsIndicator.Time[] to be used - // - // rangeBarsIndicator.Tick_volume[] should be used instead of TickVolume[] - // rangeBarsIndicator.Real_volume[] should be used instead of Volume[] - // (!) rangeBarsIndicator.SetGetVolumesFlag() must be called in OnInit() for Tick_volume[] & Real_volume[] to be used - // - // rangeBarsIndicator.Price[] should be used instead of Price[] - // (!) rangeBarsIndicator.SetUseAppliedPriceFlag(ENUM_APPLIED_PRICE _applied_price) must be called in OnInit() for rangeBarsIndicator.Price[] to be used - // + if(!customChartIndicator.BufferSynchronizationCheck(Close)) + return(0); - int _prev_calculated = rangeBarsIndicator.GetPrevCalculated(); + int _prev_calculated = customChartIndicator.GetPrevCalculated(); - // - // // //--- start calculation @@ -137,8 +113,8 @@ int OnCalculate(const int rates_total,const int prev_calculated, //--- main cycle for(int i=pos;i 0) - ExtMomentumBuffer[i]=rangeBarsIndicator.Price[i]*100/rangeBarsIndicator.Price[i-ExtMomentumPeriod]; + if(customChartIndicator.Price[i-ExtMomentumPeriod] > 0) + ExtMomentumBuffer[i]=customChartIndicator.Price[i]*100/customChartIndicator.Price[i-ExtMomentumPeriod]; } //--- OnCalculate done. Return new prev_calculated. diff --git a/Indicators/RangeBars/RangeBars_NRTR.mq5 b/Indicators/RangeBars/RangeBars_NRTR.mq5 new file mode 100644 index 0000000..c466b34 --- /dev/null +++ b/Indicators/RangeBars/RangeBars_NRTR.mq5 @@ -0,0 +1,213 @@ + + +//+------------------------------------------------------------------+ +//| iNRTR.mq5 | +//| MetaQuotes Software Corp. | +//| http://www.mql5.com | +//+------------------------------------------------------------------+ +#property copyright "MetaQuotes Software Corp." +#property link "http://www.mql5.com" +#property version "1.00" +#property indicator_chart_window +#property indicator_buffers 6 +#property indicator_plots 4 +//--- plot Support +#property indicator_label1 "Support" +#property indicator_type1 DRAW_ARROW +#property indicator_color1 DodgerBlue +#property indicator_style1 STYLE_SOLID +#property indicator_width1 2 +//--- plot Resistance +#property indicator_label2 "Resistance" +#property indicator_type2 DRAW_ARROW +#property indicator_color2 Red +#property indicator_style2 STYLE_SOLID +#property indicator_width2 2 +//--- plot UpTarget +#property indicator_label3 "UpTarget" +#property indicator_type3 DRAW_ARROW +#property indicator_color3 RoyalBlue +#property indicator_style3 STYLE_SOLID +#property indicator_width3 2 +//--- plot DnTarget +#property indicator_label4 "DnTarget" +#property indicator_type4 DRAW_ARROW +#property indicator_color4 Crimson +#property indicator_style4 STYLE_SOLID +#property indicator_width4 2 +//--- input parameters +input int period = 40; /*period*/ // ATR period in bars +input double k = 2.0; /*k*/ // ATR change coefficient +//--- indicator buffers +double SupportBuffer[]; +double ResistanceBuffer[]; +double UpTargetBuffer[]; +double DnTargetBuffer[]; +double Trend[]; +double ATRBuffer[]; +int Handle; + +// +// +// + +#include +RangeBarIndicator customChartIndicator; + +// +// +// + +//+------------------------------------------------------------------+ +//| Custom indicator initialization function | +//+------------------------------------------------------------------+ +int OnInit() + { +//--- indicator buffers mapping + SetIndexBuffer(0,SupportBuffer,INDICATOR_DATA); + PlotIndexSetInteger(0,PLOT_ARROW,159); + + SetIndexBuffer(1,ResistanceBuffer,INDICATOR_DATA); + PlotIndexSetInteger(1,PLOT_ARROW,159); + + SetIndexBuffer(2,UpTargetBuffer,INDICATOR_DATA); + PlotIndexSetInteger(2,PLOT_ARROW,158); + + SetIndexBuffer(3,DnTargetBuffer,INDICATOR_DATA); + PlotIndexSetInteger(3,PLOT_ARROW,158); + + SetIndexBuffer(4,Trend,INDICATOR_DATA); + SetIndexBuffer(5,ATRBuffer,INDICATOR_CALCULATIONS); + + PlotIndexSetDouble(1,PLOT_EMPTY_VALUE,0); + PlotIndexSetDouble(2,PLOT_EMPTY_VALUE,0); + PlotIndexSetDouble(3,PLOT_EMPTY_VALUE,0); + PlotIndexSetDouble(4,PLOT_EMPTY_VALUE,0); + PlotIndexSetDouble(5,PLOT_EMPTY_VALUE,0); + + Handle=iATR(_Symbol,PERIOD_CURRENT,period); + +//--- + 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[] + ) + { + // + + if(!customChartIndicator.OnCalculate(rates_total,prev_calculated,time,close)) + return(0); + + if(!customChartIndicator.BufferSynchronizationCheck(close)) + return(0); + + int _prev_calculated = customChartIndicator.GetPrevCalculated(); + + // + // + // + + static bool error=true; + int start; + if(_prev_calculated==0) + { + error=true; + } + if(error) + { + ArrayInitialize(Trend,0); + ArrayInitialize(UpTargetBuffer,0); + ArrayInitialize(DnTargetBuffer,0); + ArrayInitialize(SupportBuffer,0); + ArrayInitialize(ResistanceBuffer,0); + start=period; + error=false; + } + else + { + start=_prev_calculated-1; + } + if(CopyBuffer(Handle,0,0,rates_total-start,ATRBuffer)==-1) + { + error=true; + return(0); + } + for(int i=start;iUpTargetBuffer[i]) + { + UpTargetBuffer[i]=customChartIndicator.Close[i]; + SupportBuffer[i]=customChartIndicator.Close[i]-k*ATRBuffer[i]; + } + if(customChartIndicator.Close[i]ResistanceBuffer[i]) + { + UpTargetBuffer[i]=customChartIndicator.Close[i]; + SupportBuffer[i]=customChartIndicator.Close[i]-k*ATRBuffer[i]; + Trend[i]=2; + DnTargetBuffer[i]=0; + ResistanceBuffer[i]=0; + } + break; + case 0: + UpTargetBuffer[i]=customChartIndicator.Close[i]; + DnTargetBuffer[i]=customChartIndicator.Close[i]; + Trend[i]=1; + break; + case 1: + if(customChartIndicator.Low[i]>UpTargetBuffer[i]) + { + UpTargetBuffer[i]=customChartIndicator.Close[i]; + SupportBuffer[i]=customChartIndicator.Close[i]-k*ATRBuffer[i]; + Trend[i]=2; + DnTargetBuffer[i]=0; + } + if(customChartIndicator.High[i] -RangeBarIndicator customIndicator; +RangeBarIndicator customChartIndicator; // // @@ -42,7 +42,7 @@ void OnInit() IndicatorSetInteger(INDICATOR_DIGITS,0); //---- OnInit done - customIndicator.SetGetVolumesFlag(); + customChartIndicator.SetGetVolumesFlag(); } //+------------------------------------------------------------------+ @@ -63,10 +63,13 @@ int OnCalculate(const int rates_total, // Process data through RangeBar indicator // - if(!customIndicator.OnCalculate(rates_total,prev_calculated,time)) + if(!customChartIndicator.OnCalculate(rates_total,prev_calculated,time,close)) + return(0); + + if(!customChartIndicator.BufferSynchronizationCheck(close)) return(0); - int _prev_calculated = customIndicator.GetPrevCalculated(); + int _prev_calculated = customChartIndicator.GetPrevCalculated(); // // @@ -84,14 +87,14 @@ int OnCalculate(const int rates_total, { pos=1; if(InpVolumeType==VOLUME_TICK) - ExtOBVBuffer[0]=(double)customIndicator.Tick_volume[0]; - else ExtOBVBuffer[0]=(double)customIndicator.Real_volume[0]; + ExtOBVBuffer[0]=(double)customChartIndicator.Tick_volume[0]; + else ExtOBVBuffer[0]=(double)customChartIndicator.Real_volume[0]; } //--- main cycle if(InpVolumeType==VOLUME_TICK) - CalculateOBV(pos,rates_total,customIndicator.Close,customIndicator.Tick_volume); + CalculateOBV(pos,rates_total,customChartIndicator.Close,customChartIndicator.Tick_volume); else - CalculateOBV(pos,rates_total,customIndicator.Close,customIndicator.Real_volume); + CalculateOBV(pos,rates_total,customChartIndicator.Close,customChartIndicator.Real_volume); //---- OnCalculate done. Return new prev_calculated. return(rates_total); } diff --git a/Indicators/RangeBars/RangeBars_ParabolicSAR.mq5 b/Indicators/RangeBars/RangeBars_ParabolicSAR.mq5 index 53d0e94..67975f6 100644 --- a/Indicators/RangeBars/RangeBars_ParabolicSAR.mq5 +++ b/Indicators/RangeBars/RangeBars_ParabolicSAR.mq5 @@ -29,7 +29,7 @@ double ExtSarMaximum; // #include -RangeBarIndicator rangeBarsIndicator; +RangeBarIndicator customChartIndicator; // // @@ -91,39 +91,15 @@ int OnCalculate(const int rates_total, return(0); // - // Process data through MedianRenko indicator - // - if(!rangeBarsIndicator.OnCalculate(rates_total,prev_calculated,time)) + if(!customChartIndicator.OnCalculate(rates_total,prev_calculated,time,close)) return(0); - // - // Make the following modifications in the code below: - // - // rangeBarsIndicator.GetPrevCalculated() should be used instead of prev_calculated - // - // rangeBarsIndicator.Open[] should be used instead of open[] - // rangeBarsIndicator.Low[] should be used instead of low[] - // rangeBarsIndicator.High[] should be used instead of high[] - // rangeBarsIndicator.Close[] should be used instead of close[] - // - // rangeBarsIndicator.IsNewBar (true/false) informs you if a renko brick completed - // - // rangeBarsIndicator.Time[] shold be used instead of Time[] for checking the renko bar time. - // (!) rangeBarsIndicator.SetGetTimeFlag() must be called in OnInit() for rangeBarsIndicator.Time[] to be used - // - // rangeBarsIndicator.Tick_volume[] should be used instead of TickVolume[] - // rangeBarsIndicator.Real_volume[] should be used instead of Volume[] - // (!) rangeBarsIndicator.SetGetVolumesFlag() must be called in OnInit() for Tick_volume[] & Real_volume[] to be used - // - // rangeBarsIndicator.Price[] should be used instead of Price[] - // (!) rangeBarsIndicator.SetUseAppliedPriceFlag(ENUM_APPLIED_PRICE _applied_price) must be called in OnInit() for rangeBarsIndicator.Price[] to be used - // + if(!customChartIndicator.BufferSynchronizationCheck(close)) + return(0); + + int _prev_calculated = customChartIndicator.GetPrevCalculated(); - int _prev_calculated = rangeBarsIndicator.GetPrevCalculated(); - - // - // // //--- detect current position @@ -135,12 +111,12 @@ int OnCalculate(const int rates_total, pos=1; ExtAFBuffer[0]=ExtSarStep; ExtAFBuffer[1]=ExtSarStep; - ExtSARBuffer[0]=rangeBarsIndicator.High[0]; + ExtSARBuffer[0]=customChartIndicator.High[0]; ExtLastRevPos=0; ExtDirectionLong=false; - ExtSARBuffer[1]=GetHigh(pos,ExtLastRevPos,rangeBarsIndicator.High); - ExtEPBuffer[0]=rangeBarsIndicator.Low[pos]; - ExtEPBuffer[1]=rangeBarsIndicator.Low[pos]; + ExtSARBuffer[1]=GetHigh(pos,ExtLastRevPos,customChartIndicator.High); + ExtEPBuffer[0]=customChartIndicator.Low[pos]; + ExtEPBuffer[1]=customChartIndicator.Low[pos]; } //---main cycle for(int i=pos;irangeBarsIndicator.Low[i]) + if(ExtSARBuffer[i]>customChartIndicator.Low[i]) { //--- switch to SHORT ExtDirectionLong=false; - ExtSARBuffer[i]=GetHigh(i,ExtLastRevPos,rangeBarsIndicator.High); - ExtEPBuffer[i]=rangeBarsIndicator.Low[i]; + ExtSARBuffer[i]=GetHigh(i,ExtLastRevPos,customChartIndicator.High); + ExtEPBuffer[i]=customChartIndicator.Low[i]; ExtLastRevPos=i; ExtAFBuffer[i]=ExtSarStep; } } else { - if(ExtSARBuffer[i]ExtEPBuffer[i-1] && i!=ExtLastRevPos) + if(customChartIndicator.High[i]>ExtEPBuffer[i-1] && i!=ExtLastRevPos) { - ExtEPBuffer[i]=rangeBarsIndicator.High[i]; + ExtEPBuffer[i]=customChartIndicator.High[i]; ExtAFBuffer[i]=ExtAFBuffer[i-1]+ExtSarStep; if(ExtAFBuffer[i]>ExtSarMaximum) ExtAFBuffer[i]=ExtSarMaximum; @@ -193,15 +169,15 @@ int OnCalculate(const int rates_total, //--- calculate SAR for tomorrow ExtSARBuffer[i+1]=ExtSARBuffer[i]+ExtAFBuffer[i]*(ExtEPBuffer[i]-ExtSARBuffer[i]); //--- check for SAR - if(ExtSARBuffer[i+1]>rangeBarsIndicator.Low[i] || ExtSARBuffer[i+1]>rangeBarsIndicator.Low[i-1]) - ExtSARBuffer[i+1]=MathMin(rangeBarsIndicator.Low[i],rangeBarsIndicator.Low[i-1]); + if(ExtSARBuffer[i+1]>customChartIndicator.Low[i] || ExtSARBuffer[i+1]>customChartIndicator.Low[i-1]) + ExtSARBuffer[i+1]=MathMin(customChartIndicator.Low[i],customChartIndicator.Low[i-1]); } else { //--- check for new Low - if(rangeBarsIndicator.Low[i]ExtSarMaximum) ExtAFBuffer[i]=ExtSarMaximum; @@ -218,8 +194,8 @@ int OnCalculate(const int rates_total, //--- calculate SAR for tomorrow ExtSARBuffer[i+1]=ExtSARBuffer[i]+ExtAFBuffer[i]*(ExtEPBuffer[i]-ExtSARBuffer[i]); //--- check for SAR - if(ExtSARBuffer[i+1] -RangeBarIndicator rangeBarsIndicator; +RangeBarIndicator customChartIndicator; // // @@ -57,7 +57,7 @@ void OnInit() // Indicator uses Price[] array for calculations so we need to set this in the MedianRenkoIndicator class // - rangeBarsIndicator.SetUseAppliedPriceFlag(PRICE_CLOSE); + customChartIndicator.SetUseAppliedPriceFlag(PRICE_CLOSE); // // @@ -80,36 +80,14 @@ int OnCalculate(const int rates_total,const int prev_calculated, { // - // Process data through MedianRenko indicator - // - if(!rangeBarsIndicator.OnCalculate(rates_total,prev_calculated,Time)) + if(!customChartIndicator.OnCalculate(rates_total,prev_calculated,Time,Close)) return(0); - // - // Make the following modifications in the code below: - // - // rangeBarsIndicator.GetPrevCalculated() should be used instead of prev_calculated - // - // rangeBarsIndicator.Open[] should be used instead of open[] - // rangeBarsIndicator.Low[] should be used instead of low[] - // rangeBarsIndicator.High[] should be used instead of high[] - // rangeBarsIndicator.Close[] should be used instead of close[] - // - // rangeBarsIndicator.IsNewBar (true/false) informs you if a renko brick completed - // - // rangeBarsIndicator.Time[] shold be used instead of Time[] for checking the renko bar time. - // (!) rangeBarsIndicator.SetGetTimeFlag() must be called in OnInit() for rangeBarsIndicator.Time[] to be used - // - // rangeBarsIndicator.Tick_volume[] should be used instead of TickVolume[] - // rangeBarsIndicator.Real_volume[] should be used instead of Volume[] - // (!) rangeBarsIndicator.SetGetVolumesFlag() must be called in OnInit() for Tick_volume[] & Real_volume[] to be used - // - // rangeBarsIndicator.Price[] should be used instead of Price[] - // (!) rangeBarsIndicator.SetUseAppliedPriceFlag(ENUM_APPLIED_PRICE _applied_price) must be called in OnInit() for rangeBarsIndicator.Price[] to be used - // + if(!customChartIndicator.BufferSynchronizationCheck(Close)) + return(0); - int _prev_calculated = rangeBarsIndicator.GetPrevCalculated(); + int _prev_calculated = customChartIndicator.GetPrevCalculated(); // // @@ -125,10 +103,10 @@ int OnCalculate(const int rates_total,const int prev_calculated, //--- the main loop of calculations for(int i=pos;i -RangeBarIndicator rangeBarsIndicator; +RangeBarIndicator customChartIndicator; // // @@ -78,39 +78,15 @@ int OnCalculate(const int rates_total,const int prev_calculated, const int &Spread[]) { // - // Process data through MedianRenko indicator - // - if(!rangeBarsIndicator.OnCalculate(rates_total,prev_calculated,Time)) + if(!customChartIndicator.OnCalculate(rates_total,prev_calculated,Time,Close)) return(0); - // - // Make the following modifications in the code below: - // - // rangeBarsIndicator.GetPrevCalculated() should be used instead of prev_calculated - // - // rangeBarsIndicator.Open[] should be used instead of open[] - // rangeBarsIndicator.Low[] should be used instead of low[] - // rangeBarsIndicator.High[] should be used instead of high[] - // rangeBarsIndicator.Close[] should be used instead of close[] - // - // rangeBarsIndicator.IsNewBar (true/false) informs you if a renko brick completed - // - // rangeBarsIndicator.Time[] shold be used instead of Time[] for checking the renko bar time. - // (!) rangeBarsIndicator.SetGetTimeFlag() must be called in OnInit() for rangeBarsIndicator.Time[] to be used - // - // rangeBarsIndicator.Tick_volume[] should be used instead of TickVolume[] - // rangeBarsIndicator.Real_volume[] should be used instead of Volume[] - // (!) rangeBarsIndicator.SetGetVolumesFlag() must be called in OnInit() for Tick_volume[] & Real_volume[] to be used - // - // rangeBarsIndicator.Price[] should be used instead of Price[] - // (!) rangeBarsIndicator.SetUseAppliedPriceFlag(ENUM_APPLIED_PRICE _applied_price) must be called in OnInit() for rangeBarsIndicator.Price[] to be used - // + if(!customChartIndicator.BufferSynchronizationCheck(Close)) + return(0); - int _prev_calculated = rangeBarsIndicator.GetPrevCalculated(); + int _prev_calculated = customChartIndicator.GetPrevCalculated(); - // - // // int i,pos; @@ -122,7 +98,7 @@ int OnCalculate(const int rates_total,const int prev_calculated, ArraySetAsSeries(ExtRSIBuffer,false); ArraySetAsSeries(ExtPosBuffer,false); ArraySetAsSeries(ExtNegBuffer,false); - ArraySetAsSeries(rangeBarsIndicator.Close,false); + ArraySetAsSeries(customChartIndicator.Close,false); //--- preliminary calculations pos=_prev_calculated-1; if(pos<=InpRSIPeriod) @@ -138,7 +114,7 @@ int OnCalculate(const int rates_total,const int prev_calculated, ExtRSIBuffer[i]=0.0; ExtPosBuffer[i]=0.0; ExtNegBuffer[i]=0.0; - diff=rangeBarsIndicator.Close[i]-rangeBarsIndicator.Close[i-1]; + diff=customChartIndicator.Close[i]-customChartIndicator.Close[i-1]; if(diff>0) sump+=diff; else @@ -162,7 +138,7 @@ int OnCalculate(const int rates_total,const int prev_calculated, //--- the main loop of calculations for(i=pos; i0.0?diff:0.0))/InpRSIPeriod; ExtNegBuffer[i]=(ExtNegBuffer[i-1]*(InpRSIPeriod-1)+(diff<0.0?-diff:0.0))/InpRSIPeriod; if(ExtNegBuffer[i]!=0.0) diff --git a/Indicators/RangeBars/RangeBars_StdDev.mq5 b/Indicators/RangeBars/RangeBars_StdDev.mq5 new file mode 100644 index 0000000..7da75df --- /dev/null +++ b/Indicators/RangeBars/RangeBars_StdDev.mq5 @@ -0,0 +1,157 @@ +//+------------------------------------------------------------------+ +//| StdDev.mq5 | +//| Copyright 2009-2017, MetaQuotes Software Corp. | +//| http://www.mql5.com | +//+------------------------------------------------------------------+ +#property copyright "2009-2017, MetaQuotes Software Corp." +#property link "http://www.mql5.com" +#property description "Standard Deviation" +#property description "Adapted for use with TickChart by Artur Zas." + +#property indicator_separate_window +#property indicator_buffers 2 +#property indicator_plots 1 +#property indicator_type1 DRAW_LINE +#property indicator_color1 MediumSeaGreen +#property indicator_style1 STYLE_SOLID +//--- input parametrs +input int InpStdDevPeriod=20; // Period +input int InpStdDevShift=0; // Shift +input ENUM_MA_METHOD InpMAMethod=MODE_SMA; // Method +input ENUM_APPLIED_PRICE InpPrice=PRICE_CLOSE; // Apply to +//---- buffers +double ExtStdDevBuffer[]; +double ExtMABuffer[]; +//--- global variables +int ExtStdDevPeriod,ExtStdDevShift; + +#include +#include +RangeBarIndicator customChartIndicator; + +//+------------------------------------------------------------------+ +//| Custom indicator initialization function | +//+------------------------------------------------------------------+ +void OnInit() + { +//--- check for input values + if(InpStdDevPeriod<=1) + { + ExtStdDevPeriod=20; + printf("Incorrect value for input variable InpStdDevPeriod=%d. Indicator will use value=%d for calculations.",InpStdDevPeriod,ExtStdDevPeriod); + } + else ExtStdDevPeriod=InpStdDevPeriod; + if(InpStdDevShift<0) + { + ExtStdDevShift=0; + printf("Incorrect value for input variable InpStdDevShift=%d. Indicator will use value=%d for calculations.",InpStdDevShift,ExtStdDevShift); + } + else ExtStdDevShift=InpStdDevShift; +//--- set indicator short name + IndicatorSetString(INDICATOR_SHORTNAME,"StdDev("+string(ExtStdDevPeriod)+")"); +//---- define indicator buffers as indexes + SetIndexBuffer(0,ExtStdDevBuffer); + SetIndexBuffer(1,ExtMABuffer,INDICATOR_CALCULATIONS); +//--- set index label + PlotIndexSetString(0,PLOT_LABEL,"StdDev("+string(ExtStdDevPeriod)+")"); +//--- set index shift + PlotIndexSetInteger(0,PLOT_SHIFT,ExtStdDevShift); +//---- + + customChartIndicator.SetUseAppliedPriceFlag(InpPrice); + } +//+------------------------------------------------------------------+ +//| 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 &TickVolume[], + const long &Volume[], + const int &Spread[]) + { +//--- variables of indicator + int pos; +//--- set draw begin + PlotIndexSetInteger(0,PLOT_DRAW_BEGIN,ExtStdDevPeriod-1);//+begin); +//--- check for rates count + if(rates_total -RangeBarIndicator rangeBarsIndicator; +RangeBarIndicator customChartIndicator; // // @@ -82,11 +82,13 @@ int OnCalculate(const int rates_total,const int prev_calculated, // // - if(!rangeBarsIndicator.OnCalculate(rates_total,prev_calculated,Time)) + if(!customChartIndicator.OnCalculate(rates_total,prev_calculated,Time,Close)) return(0); + if(!customChartIndicator.BufferSynchronizationCheck(Close)) + return(0); - int _prev_calculated = rangeBarsIndicator.GetPrevCalculated(); + int _prev_calculated = customChartIndicator.GetPrevCalculated(); // // @@ -116,8 +118,8 @@ int OnCalculate(const int rates_total,const int prev_calculated, double dmax=-1000000.0; for(k=i-InpKPeriod+1;k<=i;k++) { - if(dmin>rangeBarsIndicator.Low[k]) dmin=rangeBarsIndicator.Low[k]; - if(dmaxcustomChartIndicator.Low[k]) dmin=customChartIndicator.Low[k]; + if(dmax -RangeBarIndicator rangeBarsIndicator; +RangeBarIndicator customChartIndicator; // // @@ -98,7 +98,7 @@ int OnInit() IndicatorSetString(INDICATOR_SHORTNAME," VEMA Wilder's DMI ("+string(AdxPeriod)+")"); - rangeBarsIndicator.SetGetVolumesFlag(); + customChartIndicator.SetGetVolumesFlag(); return(0); } @@ -136,39 +136,15 @@ int OnCalculate(const int rates_total, const int& spread[]) { // - // Process data through MedianRenko indicator - // - if(!rangeBarsIndicator.OnCalculate(rates_total,prev_calculated,time)) + if(!customChartIndicator.OnCalculate(rates_total,prev_calculated,time,close)) return(0); - // - // Make the following modifications in the code below: - // - // rangeBarsIndicator.GetPrevCalculated() should be used instead of prev_calculated - // - // rangeBarsIndicator.Open[] should be used instead of open[] - // rangeBarsIndicator.Low[] should be used instead of low[] - // rangeBarsIndicator.High[] should be used instead of high[] - // rangeBarsIndicator.Close[] should be used instead of close[] - // - // rangeBarsIndicator.IsNewBar (true/false) informs you if a renko brick completed - // - // rangeBarsIndicator.Time[] shold be used instead of Time[] for checking the renko bar time. - // (!) rangeBarsIndicator.SetGetTimeFlag() must be called in OnInit() for rangeBarsIndicator.Time[] to be used - // - // rangeBarsIndicator.Tick_volume[] should be used instead of TickVolume[] - // rangeBarsIndicator.Real_volume[] should be used instead of Volume[] - // (!) rangeBarsIndicator.SetGetVolumesFlag() must be called in OnInit() for Tick_volume[] & Real_volume[] to be used - // - // rangeBarsIndicator.Price[] should be used instead of Price[] - // (!) rangeBarsIndicator.SetUseAppliedPriceFlag(ENUM_APPLIED_PRICE _applied_price) must be called in OnInit() for rangeBarsIndicator.Price[] to be used - // + if(!customChartIndicator.BufferSynchronizationCheck(close)) + return(0); - int _prev_calculated = rangeBarsIndicator.GetPrevCalculated(); + int _prev_calculated = customChartIndicator.GetPrevCalculated(); - // - // // if (ArrayRange(averages,0)!=rates_total) ArrayResize(averages,rates_total); @@ -182,16 +158,16 @@ int OnCalculate(const int rates_total, double sf = 1.0/(double)AdxPeriod; for (int i=(int)MathMax(_prev_calculated-1,1); i DeltaLo) && (DeltaHi > 0)) plusDM = DeltaHi; diff --git a/Indicators/RangeBars/RangeBars_VWAP_lite.mq5 b/Indicators/RangeBars/RangeBars_VWAP_lite.mq5 index 156b7a1..1ff98fc 100644 --- a/Indicators/RangeBars/RangeBars_VWAP_lite.mq5 +++ b/Indicators/RangeBars/RangeBars_VWAP_lite.mq5 @@ -61,7 +61,7 @@ enum PRICE_TYPE // #include -RangeBarIndicator rangeBarsIndicator; +RangeBarIndicator customChartIndicator; #define VWAP_Daily "cc__VWAP_Daily" #define VWAP_Weekly "cc__VWAP_Weekly" @@ -169,8 +169,8 @@ int OnInit() ObjectSetString(0,VWAP_Monthly,OBJPROP_TEXT," "); } - rangeBarsIndicator.SetGetVolumesFlag(); - rangeBarsIndicator.SetGetTimeFlag(); + customChartIndicator.SetGetVolumesFlag(); + customChartIndicator.SetGetTimeFlag(); return(INIT_SUCCEEDED); } @@ -199,36 +199,16 @@ int OnCalculate(const int rates_total, { // - // Process data through MedianRenko indicator + // Process data through Tick Chat indicator // - if(!rangeBarsIndicator.OnCalculate(rates_total,prev_calculated,time)) + if(!customChartIndicator.OnCalculate(rates_total,prev_calculated,time,close)) + return(0); + + if(!customChartIndicator.BufferSynchronizationCheck(close)) return(0); - // - // Make the following modifications in the code below: - // - // rangeBarsIndicator.GetPrevCalculated() should be used instead of prev_calculated - // - // rangeBarsIndicator.Open[] should be used instead of open[] - // rangeBarsIndicator.Low[] should be used instead of low[] - // rangeBarsIndicator.High[] should be used instead of high[] - // rangeBarsIndicator.Close[] should be used instead of close[] - // - // rangeBarsIndicator.IsNewBar (true/false) informs you if a renko brick completed - // - // rangeBarsIndicator.Time[] shold be used instead of Time[] for checking the renko bar time. - // (!) rangeBarsIndicator.SetGetTimeFlag() must be called in OnInit() for rangeBarsIndicator.Time[] to be used - // - // rangeBarsIndicator.Tick_volume[] should be used instead of TickVolume[] - // rangeBarsIndicator.Real_volume[] should be used instead of Volume[] - // (!) rangeBarsIndicator.SetGetVolumesFlag() must be called in OnInit() for Tick_volume[] & Real_volume[] to be used - // - // rangeBarsIndicator.Price[] should be used instead of Price[] - // (!) rangeBarsIndicator.SetUseAppliedPriceFlag(ENUM_APPLIED_PRICE _applied_price) must be called in OnInit() for rangeBarsIndicator.Price[] to be used - // - - int _prev_calculated = rangeBarsIndicator.GetPrevCalculated(); + int _prev_calculated = customChartIndicator.GetPrevCalculated(); // // @@ -240,7 +220,7 @@ int OnCalculate(const int rates_total, LastTimePeriod=PERIOD_CURRENT; } - if(rates_total>_prev_calculated || bIsFirstRun || Calc_Every_Tick || (_prev_calculated == 0) || rangeBarsIndicator.IsNewBar) + if(rates_total>_prev_calculated || bIsFirstRun || Calc_Every_Tick || (_prev_calculated == 0) ||customChartIndicator.IsNewBar) { nIdxDaily = 0; nIdxWeekly = 0; @@ -260,22 +240,22 @@ int OnCalculate(const int rates_total, VWAP_Buffer_Weekly[nIdx]=EMPTY_VALUE; VWAP_Buffer_Monthly[nIdx]=EMPTY_VALUE; - if(rangeBarsIndicator.Time[nIdx] < 86400) + if(customChartIndicator.Time[nIdx] < 86400) continue; - if(CreateDateTime(DAILY,rangeBarsIndicator.Time[nIdx])!=dtLastDay) + if(CreateDateTime(DAILY,customChartIndicator.Time[nIdx])!=dtLastDay) { nIdxDaily=nIdx; nSumDailyTPV = 0; nSumDailyVol = 0; } - if(CreateDateTime(WEEKLY,rangeBarsIndicator.Time[nIdx])!=dtLastWeek) + if(CreateDateTime(WEEKLY,customChartIndicator.Time[nIdx])!=dtLastWeek) { nIdxWeekly=nIdx; nSumWeeklyTPV = 0; nSumWeeklyVol = 0; } - if(CreateDateTime(MONTHLY,rangeBarsIndicator.Time[nIdx])!=dtLastMonth) + if(CreateDateTime(MONTHLY,customChartIndicator.Time[nIdx])!=dtLastMonth) { nIdxMonthly=nIdx; nSumMonthlyTPV = 0; @@ -289,45 +269,45 @@ int OnCalculate(const int rates_total, switch(Price_Type) { case OPEN: - nPriceArr[nIdx]=rangeBarsIndicator.Open[nIdx]; + nPriceArr[nIdx]=customChartIndicator.Open[nIdx]; break; case CLOSE: - nPriceArr[nIdx]=rangeBarsIndicator.Close[nIdx]; + nPriceArr[nIdx]=customChartIndicator.Close[nIdx]; break; case HIGH: - nPriceArr[nIdx]=rangeBarsIndicator.High[nIdx]; + nPriceArr[nIdx]=customChartIndicator.High[nIdx]; break; case LOW: - nPriceArr[nIdx]=rangeBarsIndicator.Low[nIdx]; + nPriceArr[nIdx]=customChartIndicator.Low[nIdx]; break; case HIGH_LOW: - nPriceArr[nIdx]=(rangeBarsIndicator.High[nIdx]+rangeBarsIndicator.Low[nIdx])/2; + nPriceArr[nIdx]=(customChartIndicator.High[nIdx]+customChartIndicator.Low[nIdx])/2; break; case OPEN_CLOSE: - nPriceArr[nIdx]=(rangeBarsIndicator.Open[nIdx]+rangeBarsIndicator.Close[nIdx])/2; + nPriceArr[nIdx]=(customChartIndicator.Open[nIdx]+customChartIndicator.Close[nIdx])/2; break; case CLOSE_HIGH_LOW: - nPriceArr[nIdx]=(rangeBarsIndicator.Close[nIdx]+rangeBarsIndicator.High[nIdx]+rangeBarsIndicator.Low[nIdx])/3; + nPriceArr[nIdx]=(customChartIndicator.Close[nIdx]+customChartIndicator.High[nIdx]+customChartIndicator.Low[nIdx])/3; break; case OPEN_CLOSE_HIGH_LOW: - nPriceArr[nIdx]=(rangeBarsIndicator.Open[nIdx]+rangeBarsIndicator.Close[nIdx]+rangeBarsIndicator.High[nIdx]+rangeBarsIndicator.Low[nIdx])/4; + nPriceArr[nIdx]=(customChartIndicator.Open[nIdx]+customChartIndicator.Close[nIdx]+customChartIndicator.High[nIdx]+customChartIndicator.Low[nIdx])/4; break; default: - nPriceArr[nIdx]=(rangeBarsIndicator.Close[nIdx]+rangeBarsIndicator.High[nIdx]+rangeBarsIndicator.Low[nIdx])/3; + nPriceArr[nIdx]=(customChartIndicator.Close[nIdx]+customChartIndicator.High[nIdx]+customChartIndicator.Low[nIdx])/3; break; } - if((rangeBarsIndicator.Tick_volume[nIdx] > 0) && (rangeBarsIndicator.Real_volume[nIdx] == 0)) + if((customChartIndicator.Tick_volume[nIdx] > 0) && (customChartIndicator.Real_volume[nIdx] == 0)) { - // Print("tick vol = "+rangeBarsIndicator.Tick_volume[nIdx]); - nTotalTPV[nIdx] = (nPriceArr[nIdx] * rangeBarsIndicator.Tick_volume[nIdx]); - nTotalVol[nIdx] = (double)rangeBarsIndicator.Tick_volume[nIdx]; + // Print("tick vol = "+customChartIndicator.Tick_volume[nIdx]); + nTotalTPV[nIdx] = (nPriceArr[nIdx] * customChartIndicator.Tick_volume[nIdx]); + nTotalVol[nIdx] = (double)customChartIndicator.Tick_volume[nIdx]; } - else if(rangeBarsIndicator.Real_volume[nIdx] && rangeBarsIndicator.Tick_volume[nIdx] ) + else if(customChartIndicator.Real_volume[nIdx] && customChartIndicator.Tick_volume[nIdx] ) { - // Print("real vol = "+rangeBarsIndicator.Real_volume[nIdx]); - nTotalTPV[nIdx] = (nPriceArr[nIdx] * rangeBarsIndicator.Real_volume[nIdx]); - nTotalVol[nIdx] = (double)rangeBarsIndicator.Real_volume[nIdx]; + // Print("real vol = "+customChartIndicator.Real_volume[nIdx]); + nTotalTPV[nIdx] = (nPriceArr[nIdx] * customChartIndicator.Real_volume[nIdx]); + nTotalVol[nIdx] = (double)customChartIndicator.Real_volume[nIdx]; } if(Enable_Daily && (nIdx>=nIdxDaily)) @@ -375,9 +355,9 @@ int OnCalculate(const int rates_total, } } - dtLastDay=CreateDateTime(DAILY,rangeBarsIndicator.Time[nIdx]); - dtLastWeek=CreateDateTime(WEEKLY,rangeBarsIndicator.Time[nIdx]); - dtLastMonth=CreateDateTime(MONTHLY,rangeBarsIndicator.Time[nIdx]); + dtLastDay=CreateDateTime(DAILY,customChartIndicator.Time[nIdx]); + dtLastWeek=CreateDateTime(WEEKLY,customChartIndicator.Time[nIdx]); + dtLastMonth=CreateDateTime(MONTHLY,customChartIndicator.Time[nIdx]); } bIsFirstRun=false; diff --git a/Indicators/RangeBars/RangeBars_WPR.mq5 b/Indicators/RangeBars/RangeBars_WPR.mq5 index fe92808..a999bc0 100644 Binary files a/Indicators/RangeBars/RangeBars_WPR.mq5 and b/Indicators/RangeBars/RangeBars_WPR.mq5 differ diff --git a/Indicators/RangeBars/RangeBars_ZigZag.mq5 b/Indicators/RangeBars/RangeBars_ZigZag.mq5 index b1c920b..8fde55b 100644 --- a/Indicators/RangeBars/RangeBars_ZigZag.mq5 +++ b/Indicators/RangeBars/RangeBars_ZigZag.mq5 @@ -31,7 +31,7 @@ double deviation; // deviation in points // #include -RangeBarIndicator rangeBarsIndicator; +RangeBarIndicator customChartIndicator; // // @@ -132,16 +132,15 @@ int OnCalculate(const int rates_total, const int &spread[]) { // - // Process data through MedianRenko indicator - // - - if(!rangeBarsIndicator.OnCalculate(rates_total,prev_calculated,time)) + + if(!customChartIndicator.OnCalculate(rates_total,prev_calculated,time,close)) return(0); - int _prev_calculated = rangeBarsIndicator.GetPrevCalculated(); + if(!customChartIndicator.BufferSynchronizationCheck(close)) + return(0); + + int _prev_calculated = customChartIndicator.GetPrevCalculated(); - // - // // int i=0; @@ -204,12 +203,12 @@ int OnCalculate(const int rates_total, //--- searching High and Low for(shift=limit;shiftdeviation) val=0.0; + if((customChartIndicator.Low[shift]-val)>deviation) val=0.0; else { for(back=1;back<=ExtBackstep;back++) @@ -219,14 +218,14 @@ int OnCalculate(const int rates_total, } } } - if(rangeBarsIndicator.Low[shift]==val) LowMapBuffer[shift]=val; else LowMapBuffer[shift]=0.0; + if(customChartIndicator.Low[shift]==val) LowMapBuffer[shift]=val; else LowMapBuffer[shift]=0.0; //--- high - val=rangeBarsIndicator.High[iHighest(rangeBarsIndicator.High,ExtDepth,shift)]; + val=customChartIndicator.High[iHighest(customChartIndicator.High,ExtDepth,shift)]; if(val==lasthigh) val=0.0; else { lasthigh=val; - if((val-rangeBarsIndicator.High[shift])>deviation) val=0.0; + if((val-customChartIndicator.High[shift])>deviation) val=0.0; else { for(back=1;back<=ExtBackstep;back++) @@ -236,7 +235,7 @@ int OnCalculate(const int rates_total, } } } - if(rangeBarsIndicator.High[shift]==val) HighMapBuffer[shift]=val; else HighMapBuffer[shift]=0.0; + if(customChartIndicator.High[shift]==val) HighMapBuffer[shift]=val; else HighMapBuffer[shift]=0.0; } //--- last preparation @@ -262,7 +261,7 @@ int OnCalculate(const int rates_total, { if(HighMapBuffer[shift]!=0) { - lasthigh=rangeBarsIndicator.High[shift]; + lasthigh=customChartIndicator.High[shift]; lasthighpos=shift; whatlookfor=Sill; ZigzagBuffer[shift]=lasthigh; @@ -270,7 +269,7 @@ int OnCalculate(const int rates_total, } if(LowMapBuffer[shift]!=0) { - lastlow=rangeBarsIndicator.Low[shift]; + lastlow=customChartIndicator.Low[shift]; lastlowpos=shift; whatlookfor=Pike; ZigzagBuffer[shift]=lastlow; diff --git a/Indicators/RangeBars/RangeBars_dt_oscillator.mq5 b/Indicators/RangeBars/RangeBars_dt_oscillator.mq5 index 8737b07..06e74ad 100644 --- a/Indicators/RangeBars/RangeBars_dt_oscillator.mq5 +++ b/Indicators/RangeBars/RangeBars_dt_oscillator.mq5 @@ -60,7 +60,7 @@ double dtosf2[]; // #include -RangeBarIndicator rangeBarsIndicator; +RangeBarIndicator customChartIndicator; // // @@ -110,33 +110,36 @@ int OnCalculate(const int rates_total,const int prev_calculated, // Process data through MedianRenko indicator // - if(!rangeBarsIndicator.OnCalculate(rates_total,prev_calculated,Time)) + if(!customChartIndicator.OnCalculate(rates_total,prev_calculated,Time,Close)) + return(0); + + if(!customChartIndicator.BufferSynchronizationCheck(Close)) return(0); // // Make the following modifications in the code below: // - // rangeBarsIndicator.GetPrevCalculated() should be used instead of prev_calculated + // customChartIndicator.GetPrevCalculated() should be used instead of prev_calculated // - // rangeBarsIndicator.Open[] should be used instead of open[] - // rangeBarsIndicator.Low[] should be used instead of low[] - // rangeBarsIndicator.High[] should be used instead of high[] - // rangeBarsIndicator.Close[] should be used instead of close[] + // customChartIndicator.Open[] should be used instead of open[] + // customChartIndicator.Low[] should be used instead of low[] + // customChartIndicator.High[] should be used instead of high[] + // customChartIndicator.Close[] should be used instead of close[] // - // rangeBarsIndicator.IsNewBar (true/false) informs you if a renko brick completed + // customChartIndicator.IsNewBar (true/false) informs you if a renko brick completed // - // rangeBarsIndicator.Time[] shold be used instead of Time[] for checking the renko bar time. - // (!) rangeBarsIndicator.SetGetTimeFlag() must be called in OnInit() for rangeBarsIndicator.Time[] to be used + // customChartIndicator.Time[] shold be used instead of Time[] for checking the renko bar time. + // (!) customChartIndicator.SetGetTimeFlag() must be called in OnInit() for customChartIndicator.Time[] to be used // - // rangeBarsIndicator.Tick_volume[] should be used instead of TickVolume[] - // rangeBarsIndicator.Real_volume[] should be used instead of Volume[] - // (!) rangeBarsIndicator.SetGetVolumesFlag() must be called in OnInit() for Tick_volume[] & Real_volume[] to be used + // customChartIndicator.Tick_volume[] should be used instead of TickVolume[] + // customChartIndicator.Real_volume[] should be used instead of Volume[] + // (!) customChartIndicator.SetGetVolumesFlag() must be called in OnInit() for Tick_volume[] & Real_volume[] to be used // - // rangeBarsIndicator.Price[] should be used instead of Price[] - // (!) rangeBarsIndicator.SetUseAppliedPriceFlag(ENUM_APPLIED_PRICE _applied_price) must be called in OnInit() for rangeBarsIndicator.Price[] to be used + // customChartIndicator.Price[] should be used instead of Price[] + // (!) customChartIndicator.SetUseAppliedPriceFlag(ENUM_APPLIED_PRICE _applied_price) must be called in OnInit() for customChartIndicator.Price[] to be used // - int _prev_calculated = rangeBarsIndicator.GetPrevCalculated(); + int _prev_calculated = customChartIndicator.GetPrevCalculated(); // // @@ -155,7 +158,7 @@ int OnCalculate(const int rates_total,const int prev_calculated, for (int i=(int)MathMax(_prev_calculated-1,0); i -RangeBarIndicator rangeBarsIndicator; +RangeBarIndicator customChartIndicator; // // // + //+------------------------------------------------------------------+ //| Custom indicator initialization function | //+------------------------------------------------------------------+ @@ -43,7 +46,7 @@ void OnInit() //---- indicator digits IndicatorSetInteger(INDICATOR_DIGITS,0); - rangeBarsIndicator.SetGetVolumesFlag(); + customChartIndicator.SetGetVolumesFlag(); //---- } //+------------------------------------------------------------------+ @@ -63,38 +66,41 @@ int OnCalculate(const int rates_total, //---check for rates total if(rates_total<2) return(0); - + // - // Process data through MedianRenko indicator + // Process data through XTickChart indicator // - if(!rangeBarsIndicator.OnCalculate(rates_total,prev_calculated,time)) + if(!customChartIndicator.OnCalculate(rates_total,prev_calculated,time,close)) return(0); - + + if(!customChartIndicator.BufferSynchronizationCheck(close)) + return(0); + // // Make the following modifications in the code below: // - // rangeBarsIndicator.GetPrevCalculated() should be used instead of prev_calculated + // customChartIndicator.GetPrevCalculated() should be used instead of prev_calculated // - // rangeBarsIndicator.Open[] should be used instead of open[] - // rangeBarsIndicator.Low[] should be used instead of low[] - // rangeBarsIndicator.High[] should be used instead of high[] - // rangeBarsIndicator.Close[] should be used instead of close[] + // customChartIndicator.Open[] should be used instead of open[] + // customChartIndicator.Low[] should be used instead of low[] + // customChartIndicator.High[] should be used instead of high[] + // customChartIndicator.Close[] should be used instead of close[] // - // rangeBarsIndicator.IsNewBar (true/false) informs you if a renko brick completed + // customChartIndicator.IsNewBar (true/false) informs you if a bar has completed // - // rangeBarsIndicator.Time[] shold be used instead of Time[] for checking the renko bar time. - // (!) rangeBarsIndicator.SetGetTimeFlag() must be called in OnInit() for rangeBarsIndicator.Time[] to be used + // customChartIndicator.Time[] shold be used instead of Time[] for checking the tick chart bar time. + // (!) customChartIndicator.SetGetTimeFlag() must be called in OnInit() for customChartIndicator.Time[] to be used // - // rangeBarsIndicator.Tick_volume[] should be used instead of TickVolume[] - // rangeBarsIndicator.Real_volume[] should be used instead of Volume[] - // (!) rangeBarsIndicator.SetGetVolumesFlag() must be called in OnInit() for Tick_volume[] & Real_volume[] to be used + // customChartIndicator.Tick_volume[] should be used instead of TickVolume[] + // customChartIndicator.Real_volume[] should be used instead of Volume[] + // (!) customChartIndicator.SetGetVolumesFlag() must be called in OnInit() for Tick_volume[] & Real_volume[] to be used // - // rangeBarsIndicator.Price[] should be used instead of Price[] - // (!) rangeBarsIndicator.SetUseAppliedPriceFlag(ENUM_APPLIED_PRICE _applied_price) must be called in OnInit() for rangeBarsIndicator.Price[] to be used + // customChartIndicator.Price[] should be used instead of Price[] + // (!) customChartIndicator.SetUseAppliedPriceFlag(ENUM_APPLIED_PRICE _applied_price) must be called in OnInit() for customChartIndicator.Price[] to be used // - int _prev_calculated = rangeBarsIndicator.GetPrevCalculated(); + int _prev_calculated = customChartIndicator.GetPrevCalculated(); // // @@ -105,10 +111,11 @@ int OnCalculate(const int rates_total, //--- correct position if(start<1) start=1; //--- main cycle + if(InpVolumeType==VOLUME_TICK) - CalculateVolume(start,rates_total,rangeBarsIndicator.Tick_volume); + CalculateVolume(start,rates_total,customChartIndicator.Tick_volume); else - CalculateVolume(start,rates_total,rangeBarsIndicator.Real_volume); + CalculateVolume(start,rates_total,customChartIndicator.Real_volume); //--- OnCalculate done. Return new prev_calculated. return(rates_total); }