In MQL4 there was IndicatorCounted (), is there an equivalent function in MQL5 to access this value from anywhere in the program?
- www.mql5.com
- So pass it to your functions or store it in a global. What's the problem?
- The real question is why do you think you need it. Do you loop in OnCalculate and pass the bar index to your functions. They shouldn't need to know anything else.
How to do your lookbacks correctly.
- So pass it to your functions or store it in a global. What's the problem?
- The real question is why do you think you need it. Do you loop in OnCalculate and pass the bar index to your functions. They shouldn't need to know anything else.
How to do your lookbacks correctly.
That is why @whroeder1 also stated: "So pass it to your functions or store it in a global ..."
// Untested, uncompiled example code #property strict ... int rates_total_global = 0; // Globally Scoped copy of "rates_total" (if required) int prev_calculated_global = 0; // Globally Scoped copy of "prev_calculated" ... int OnCalculate (const int rates_total, // size of the price[] array const int prev_calculated, // bars handled on a previous call ... ) { rates_total_global = rates_total; // Update Global copy (if required) prev_calculated_global = prev_calculated; // Update Global copy ... // Update and Return currently processed/calculated bar count prev_calculated_global = rates_total; return( rates_total ); } ... void OnTimer() { ... // use "prev_calculated_global" or "rates_total_global" in expressions ... }
That is why @whroeder1 also stated: "So pass it to your functions or store it in a global ..."
Yes, but again, if you want to calculate some indicator of another symbol or another timeframe different from the current chart, and you want to know how many bars have been calculated from that indicator, you should use BarsCalculated (). This function is universal and it is useful for all the cases that you may need (even to be able to be used within an EA or script), instead what @whroeder1 and you propose is only useful for the specific case in which you only want to calculate the bars returned on the previous call of OnCalculate() from the current indicator in the current symbol and current timeframe.
That's why I said that maybe he wanted to develop a MultiSymbol or MultiTimeframe indicator.
Regards.
Yes, but again, if you want to calculate some indicator of another symbol or another timeframe different from the current chart, and you want to know how many bars have been calculated from that indicator, you should use BarsCalculated (). This function is universal and it is useful for all the cases that you may need (even to be able to be used within an EA or script), instead what @whroeder1 and you propose is only useful for the specific case in which you only want to calculate the bars returned on the previous call of OnCalculate() from the current indicator in the current symbol and current timeframe.
That's why I said that maybe he wanted to develop a MultiSymbol or MultiTimeframe indicator.
BarsCalculated() is useful with other indicators, but not within the indicator code itself as you cannot obtain an internal "handle" from within the Indicator code.
For the OP's question, as clearly stated that wanted an alternative for MQL4's IndicatorCounted() and in that respect the use of the global variable is exactly the solution as BarsCalculated() would not work in that situation.
- docs.mql4.com
BarsCalculated() is useful with other indicators, but not within the indicator code itself as you cannot obtain an internal "handle" from within the Indicator code.
For the OP's question, as clearly stated that wanted an alternative for MQL4's IndicatorCounted() and in that respect the use of the global variable is exactly the solution as BarsCalculated() would not work in that situation.
OP asked what is the mql5 function equivalent to mql4 IndCounted(), and it is BarsCalculated(). The
difference between the two is that IndCounted() can only be used based on
the current indicator, and instead BarsCalculated() is universal and can
be used referred to any indicator.
Regarding prev_calculated, it also exists in mql4, and obviously in mql5 it can be used in the same way as in mql4. There
is no difference in this between one language and the other.
Regards.
No, it is NOT universal! It cannot be used within the Indicator itself in reference to itself. That is what IndicatorCounted() was for and which was then replaced by "prev_calculated" for both MQL4+ and MQL5. BarsCalculated() has its use, but it is NOT the MQL5 equivalent. Its purpose is something different. It is NOT the the substitute for IndicatorCounted() and I dare you to prove otherwise and there is no way you will ever be able to use BarsCalculated() to reference itself in an Indicator. It can only be used by way of reference of a handle of an externally implemented Indicator and NEVER within the the implementation code of the the Indicator itself.
- docs.mql4.com
No, it is NOT universal! It cannot be used within the Indicator itself in reference to itself.
Why not ???. For example, you can use ChartIndicatorGet() to retrieve the indicator's own handle, from within its own code. There are also other ways to do it.
Fernando Carreiro:
BarsCalculated() has its use, but it is NOT the MQL5 equivalent. Its purpose is something different. It is NOT the the substitute for IndicatorCounted() and I dare you to prove otherwise and there is no way you will ever be able to use BarsCalculated() to reference itself in an Indicator.
It can only be used by way of reference of a handle of an externally
implemented Indicator and NEVER within the the implementation code of
the the Indicator itself.
The fact that you did not know how to do it, does not mean that it is not possible.
Well, I did not plan to code, but since you challenged me, here's an example:
//+------------------------------------------------------------------+ //| Bars Calculated Ind.mq5 | //| Copyright 2017, Robertomar Trader | //| http://www.tradingunited.es/foro/members/robertomar.html | //+------------------------------------------------------------------+ #property copyright "Copyright 2017, Robertomar Trader" #property link "http://www.tradingunited.es/foro/members/robertomar.html" #property version "1.00" #property indicator_chart_window #property indicator_buffers 1 #property indicator_plots 1 //--- plot Histogram #property indicator_label1 "Histogram" #property indicator_type1 DRAW_HISTOGRAM #property indicator_color1 clrRed #property indicator_style1 STYLE_SOLID #property indicator_width1 1 input int TimerLag = 5; // Timer Lag (in milliseconds) double HistogramBuffer[]; string shortname; int handle; bool timerok; //+------------------------------------------------------------------+ //| Custom indicator initialization function | //+------------------------------------------------------------------+ int OnInit() { SetIndexBuffer(0,HistogramBuffer,INDICATOR_DATA); shortname=MQLInfoString(MQL_PROGRAM_NAME) + "-" + IntegerToString(TimeCurrent()); IndicatorSetString(INDICATOR_SHORTNAME,shortname); timerok = false; ResetLastError(); handle = ChartIndicatorGet(0, ChartWindowFind(), shortname); if(handle == INVALID_HANDLE) { Print("Unable to retrieve the own handle by itself. Error code: ", GetLastError()); return(INIT_FAILED); } Print("Own handle = ", handle); if(EventSetMillisecondTimer(TimerLag)) timerok = true; else { Print("Unable to set Timer. Error code: ", GetLastError()); return(INIT_FAILED); } return(INIT_SUCCEEDED); } void OnDeinit(const int reason) { if(timerok) EventKillTimer(); if(handle != INVALID_HANDLE) IndicatorRelease(handle); } //+------------------------------------------------------------------+ //| Custom indicator iteration function | //+------------------------------------------------------------------+ int OnCalculate (const int rates_total, const int prev_calculated, const int begin, const double& price[]) { int start=prev_calculated-1; if(start<0) start=0; for(int i=start;i<rates_total;i++) { HistogramBuffer[i]=price[i]; } return(rates_total); } void OnTimer() { static int prev_calc = 0; int calc = BarsCalculated(handle); if(calc > prev_calc) { Print("Bars Calculated = ", calc, ", Prev Bars Calculated = ", prev_calc); double buffer[]; ResetLastError(); if(CopyBuffer(handle, 0, 1, 1, buffer) < 1) { Print("Copybuffer failed. Error code: ", GetLastError()); return; } Print("CopyBuffer[1] = ", buffer[0]); prev_calc = calc; } }
As you can see, the indicator can retrieve the handle of itself, and use the BarsCalculated() function with it, and it can also use the CopyBuffer() function to obtain its own values.
Imagine that we want the indicator to do something every time a new candle appears, and only once for each candle (for example, to print indicator values for the newly closed candle in the log). Well, this is the result:
As you can see, everything is correct, we have obtained what we wanted. For a better visual appreciation, I highlighted the printed data for each candle in a different color.
Now imagine that we want to do something similar with the method you proposed (store the values of rates_total and prev_calculated in global variables), and use them in another part of the code (inside the OnTimer () function, for example). For this we use an indicator similar to the previous one:
//+------------------------------------------------------------------+ //| Prev Calculated Global Ind.mq5 | //| Copyright 2017, Robertomar Trader | //| http://www.tradingunited.es/foro/members/robertomar.html | //+------------------------------------------------------------------+ #property copyright "Copyright 2017, Robertomar Trader" #property link "http://www.tradingunited.es/foro/members/robertomar.html" #property version "1.00" #property indicator_chart_window #property indicator_buffers 1 #property indicator_plots 1 //--- plot Histogram #property indicator_label1 "Histogram" #property indicator_type1 DRAW_HISTOGRAM #property indicator_color1 clrRed #property indicator_style1 STYLE_SOLID #property indicator_width1 1 input int TimerLag = 5; // Timer Lag (in milliseconds) double HistogramBuffer[]; string shortname; int rates_total_global, prev_calculated_global; bool timerok; //+------------------------------------------------------------------+ //| Custom indicator initialization function | //+------------------------------------------------------------------+ int OnInit() { SetIndexBuffer(0,HistogramBuffer,INDICATOR_DATA); shortname=MQLInfoString(MQL_PROGRAM_NAME) + "-" + IntegerToString(TimeCurrent()); IndicatorSetString(INDICATOR_SHORTNAME,shortname); timerok = false; if(EventSetMillisecondTimer(TimerLag)) timerok = true; else { Print("Unable to set Timer. Error code: ", GetLastError()); return(INIT_FAILED); } return(INIT_SUCCEEDED); } void OnDeinit(const int reason) { if(timerok) EventKillTimer(); } //+------------------------------------------------------------------+ //| Custom indicator iteration function | //+------------------------------------------------------------------+ int OnCalculate (const int rates_total, const int prev_calculated, const int begin, const double& price[]) { rates_total_global = rates_total; prev_calculated_global = prev_calculated; int start=prev_calculated-1; if(start<0) start=0; for(int i=start;i<rates_total;i++) { HistogramBuffer[i]=price[i]; } /* prev_calculated_global = rates_total; If you put this here, the condition (if rates_total_global > prev_calculated_global) inside Ontimer() is never fulfilled. */ return(rates_total); } void OnTimer() { if(rates_total_global > prev_calculated_global) { Print("Rates total global = ", rates_total_global, ", Prev calculated global = ", prev_calculated_global); int size = ArraySize(HistogramBuffer); if(size >= 2) Print("Histogram Buffer[1] = ", HistogramBuffer[size-2]); } }
First, from the code you showed above, I had to remove the line 'prev_calculated_global = rates_total;' that was just above 'return (rates_total);', because otherwise the condition configured inside OnTimer() was never fulfilled.
Removing this line, the condition is met, but not only once for each candle, but many times for each candle. Here are the results:
As you can see, inside OnTimer(), the condition 'if (rates_total_global > prev_calculated_global)' is fulfilled many times for each candle (not all fit in the image). Therefore, with the method you proposed, we have not achieved the goal we wanted.
These are just examples. Prev_calculated
is useful (I use it a lot) for normal indicators that only use the
OnCalculate() function and only take into account the current
symbol and timeframe candles. But storing these values in
global variables and trying to use them in other functions handled by
other events (such as OnTimer ()) can lead to desynchronization
problems.
Depending on what you want to develop, one or the other is more appropriate.
Conclusions:
1. If you do not know something with certainty, please do not affirm
categorically that it is not possible, that it is false, (do not use uppercase words such as NOT, NEVER, etc.), much less
even challenge someone who does.
2.
I said that BarsCalculated () is the equivalent (extended and
universalized) of IndicatorCounted (), because both are functions
(prev_calculated is not, but it is a variable of constant type passed to
the function that handles the OnCalculate event), also
because both can be used anywhere in the indicator code (which is what
OP requested) and because they serve the same functionality, with the
difference that BarCalculated () is universal and IndicatorCounted ()
could only be used from within the code of the indicator itself. Exactly as I mentioned. This unique difference is motivated by the way in which the indicators are managed in MT5 (that is, by handles).
3.
And yes, as you see, BarsCalculated() is universal, whereas
prev_calculated is not the equivalent of IndicatorCounted(), but it is
another way of doing things, initially implemented in mql5 and later
incorporated also in mql4 (currently it exists and is used equally in both languages) and it has exactly the functionality that I mentioned.
4. I hope that today you have learned something, at least regarding your manners, which are not usually the most appropriate.
Regards.
- www.mql5.com
Jose Francisco Casado Fernandez: Why not ???. For example, you can use ChartIndicatorGet() to retrieve the indicator's own handle, from within its own code. There are also other ways to do it.
The fact that you did not know how to do it, does not mean that it is not possible.
Well, I did not plan to code, but since you challenged me, here's an example:
As you can see, the indicator can retrieve the handle of itself, and use the BarsCalculated() function with it, and it can also use the CopyBuffer() function to obtain its own values.
Imagine that we want the indicator to do something every time a new candle appears, and only once for each candle (for example, to print indicator values for the newly closed candle in the log). Well, this is the result:
As you can see, everything is correct, we have obtained what we wanted. For a better visual appreciation, I highlighted the printed data for each candle in a different color.
Now imagine that we want to do something similar with the method you proposed (store the values of rates_total and prev_calculated in global variables), and use them in another part of the code (inside the OnTimer () function, for example). For this we use an indicator similar to the previous one:
First, from the code you showed above, I had to remove the line 'prev_calculated_global = rates_total;' that was just above 'return (rates_total);', because otherwise the condition configured inside OnTimer() was never fulfilled.
Removing this line, the condition is met, but not only once for each candle, but many times for each candle. Here are the results:
As you can see, inside OnTimer(), the condition 'if (rates_total_global > prev_calculated_global)' is fulfilled many times for each candle (not all fit in the image). Therefore, with the method you proposed, we have not achieved the goal we wanted.
These are just examples. Prev_calculated
is useful (I use it a lot) for normal indicators that only use the
OnCalculate() function and only take into account the current
symbol and timeframe candles. But storing these values in
global variables and trying to use them in other functions handled by
other events (such as OnTimer ()) can lead to desynchronization
problems.
Depending on what you want to develop, one or the other is more appropriate.
Conclusions:
1. If you do not know something with certainty, please do not affirm
categorically that it is not possible, that it is false, (do not use uppercase words such as NOT, NEVER, etc.), much less
even challenge someone who does.
2.
I said that BarsCalculated () is the equivalent (extended and
universalized) of IndicatorCounted (), because both are functions
(prev_calculated is not, but it is a variable of constant type passed to
the function that handles the OnCalculate event), also
because both can be used anywhere in the indicator code (which is what
OP requested) and because they serve the same functionality, with the
difference that BarCalculated () is universal and IndicatorCounted ()
could only be used from within the code of the indicator itself. Exactly as I mentioned. This unique difference is motivated by the way in which the indicators are managed in MT5 (that is, by handles).
3.
And yes, as you see, BarsCalculated() is universal, whereas
prev_calculated is not the equivalent of IndicatorCounted(), but it is
another way of doing things, initially implemented in mql5 and later
incorporated also in mql4 (currently it exists and is used equally in both languages) and it has exactly the functionality that I mentioned.
4. I hope that today you have learned something, at least regarding your forms, which are not usually the most appropriate.
I stand corrected!
EDIT: After looking at your code again and how you "invent" a unique shortname based on time, in order to circumvent the limitations of finding the the handle, I am reconsidering my previous comment.
Sorry, but I can no longer agree as I believe it to be a "forced hack" to get around the situation and I do not consider it a clear, efficient universal solution.
- Free trading apps
- Over 8,000 signals for copying
- Economic news for exploring financial markets
You agree to website policy and terms of use
Hello,
In MQL4 there was IndicatorCounted () whose equivalent in MQL5 is prev_calculated.
But the big difference is that IndicatorCounted () is accessible from anywhere in the program, whereas prev_calculated is only accessible from the OnCalculate event.
Is there an equivalent function in MQL5 to access this value from anywhere in the program?
Regards,
Pierre8r