Problem with ChartSetSymbolPeriod()

 

This is a little script that closes all open charts but one in the terminal. I then try to change the time period but it gives an error saying it cannot find the chart.

Any ideas please?

void OnStart()
{
 long currChart, prevchart = ChartFirst();
 
 int i=0,limit=100;
 while(i<limit)
 {
  currChart = ChartNext(prevchart);
  //Print(currChart,"   ",prevchart);
  Sleep(500);
  if(currChart < 0)break;
  //there is another chart
  ChartClose(currChart);
  prevchart = currChart;
  i++;
 }
 
 Print(ChartID());
 bool rs;
 Sleep(1000);
 if(rs == ChartSetSymbolPeriod(ChartID(),NULL,PERIOD_M5))Print(ErrorDescription(GetLastError()
}
 
  1. You are closing all charts except the first. Close all of them, but get the next one before closing current one.
    for (long currChart = ChartFirst(); currChart >= 0;){
       long prevChart = currChart;       // Close this one
       currChart = ChartNext(prevchart); // after getting the next one.
       ChartClose(prevChart);
    }
  2. If ChartID isn't the first, then it has been closed, how do you expect to change a non-existent chart?
 
William Roeder:
  1. You are closing all charts except the first. Close all of them, but get the next one before closing current one.
  2. If ChartID isn't the first, then it has been closed, how do you expect to change a non-existent chart?

1. Yes correct - that's how I chose to do it - but you haven't answered the real problem which is applying changes to the chart after the others have been closed.

2. If the chart was non-existent why did it return a ChartID? - I guess this is the ChartID of where the script was dropped?


If I use your code I then want to open 5 new charts (lets keep it to one for now) and make changes to it like below.

ChartOpen(ChartSymbol(),PERIOD_M15);
ChartApplyTemplate(0,"template.tpl");
Print(ErrorDescription(GetLastError()));

This opens a new chart with M15 timeframe but does not apply the template - 'chart not found' error. Surely opening a new chart must produce an existing chart?

 

If you read the documentation you can see that ChartOpen() function returns the chart ID. ( of the nwly opened chart, or a 0 in case of failure. )

https://www.mql5.com/en/docs/chart_operations/chartopen

This means that:

long chart_id = ChartOpen(ChartSymbol(),PERIOD_M15);

And then you use the ID you got from the return value of ChartOpen() function:

ChartApplyTemplate(chart_id,"template.tpl");
Documentation on MQL5: Chart Operations / ChartOpen
Documentation on MQL5: Chart Operations / ChartOpen
  • www.mql5.com
Chart Operations / ChartOpen - Reference on algorithmic/automated trading language for MetaTrader 5
 
Marco vd Heijden:

If you read the documentation you can see that ChartOpen() function returns the chart ID. ( of the nwly opened chart, or a 0 in case of failure. )

https://www.mql5.com/en/docs/chart_operations/chartopen

This means that:

And then you use the ID you got from the return value of ChartOpen() function:

yep - I did read the documentation which is mostly pathetic unless you're a psychic!

Your code does not work - already tried it.

 

You didn't read the documentation.

Since you were not collecting the chart id in the first place.

If you read the documentation you can see that: https://docs.mql4.com/chart_operations/chartapplytemplate

bool  ChartApplyTemplate(
   long          chart_id,     // Chart ID
   const string  filename      // Template file name
   );

The first parameter is the chart id, and you filled in a zero which means:

[in]  Chart ID. 0 means the current chart.

So you open a new chart and then want to apply the template to the current chart running the program that fired the new chart ?

Makes not sense to me.

ChartApplyTemplate - Chart Operations - MQL4 Reference
ChartApplyTemplate - Chart Operations - MQL4 Reference
  • docs.mql4.com
Applies a specific template from a specified file to the chart. The command is added to chart message queue and executed only after all previous commands have been processed. The Expert Advisor will be unloaded and will not be able to continue operating in case of successful loading of a new template to the chart it is attached to. Live Trading...
 
Marco vd Heijden:

You didn't read the documentation.

Since you were not collecting the chart id in the first place.

If you read the documentation you can see that: https://docs.mql4.com/chart_operations/chartapplytemplate

bool  ChartApplyTemplate(
   long          chart_id,     // Chart ID
   const string  filename      // Template file name
   );

The first parameter is the chart id, and you filled in a zero which means:

[in]  Chart ID. 0 means the current chart.

So you open a new chart and then want to apply the template to the current chart running the program that fired the new chart ?

Makes not sense to me.

Please do not keep saying to read the documentation! I always read the documentation and only come on this forum when I am totally desperate!! - I have tried the code below -  doesn't work - have you even bothered to try it?

What doesn't make sense? I want to open a new chart and apply a template! What's wrong with that?


ChartApplyTemplate(ChartID(),"template.tpl");
 
ChartApplyTemplate(ChartID(),"template.tpl");

This does not Apply a template to a newly opened chart but to the current chart.

It is the exact same mistake you made in your previous try here:

ChartApplyTemplate(0,"template.tpl");

A zero means the current chart.

Please read the documentation.

sd59:

 I have tried the code below -  doesn't work - have you even bothered to try it?

Yes i have tried this code and it successfully applies the saved template to the chart.

//--- apply template
long chart_id = ChartOpen(ChartSymbol(),PERIOD_M15);
ChartApplyTemplate(chart_id,"template.tpl");

Same thing as i posted earlier and it's working fine.

Check to see that the template name exists.

 
Marco vd Heijden:

This does not Apply a template to a newly opened chart but to the current chart.

It is the exact same mistake you made in your previous try here:

A zero means the current chart.

Please read the documentation.

Yes i have tried this code and it successfully applies the saved template to the chart.

Same thing as i posted earlier and it's working fine.

Check to see that the template name exists.

OK I've realised my mistake - just for future reference it would have been easier if you has simply pointed to this under ChartOpen :

Return Value

If successful, it returns the opened chart ID. Otherwise returns 0. To get  error details use the  GetLastError() function.


People make mistakes and please understand that 9/10 people on this forum are not programmers!

For example you say above "A zero means the current chart" - well to me if I open a chart then that is the current chart!?? Seems simple to me but obviously incorrect. Can you see how different interpretations mean different things to different people?

Runtime Errors - Codes of Errors and Warnings - Constants, Enumerations and Structures - MQL4 Reference
Runtime Errors - Codes of Errors and Warnings - Constants, Enumerations and Structures - MQL4 Reference
  • docs.mql4.com
The GetLastError() function return last error code, stored in _LastError predefined variable. This value can be reset using the ResetLastError() function. Error code constants defined at stderror.mqh file. To print text messages use ErrorDescription() function defined at stdlib.mqh file.
 
sd59:

 it would have been easier if you has simply pointed to this under ChartOpen :

I don't know about you but,

Maybe it's time to:

Read the documentation.


 
Marco vd Heijden:

I don't know about you but,

Maybe it's time to:

Read the documentation.


Living in fear of being told to read the documentation again I thought I might as well continue with this! So the code below is simply meant to close all charts (using William Roeder's code) and open 6 new ones with different timeframes.

The CHART_SHIFT & CHART_AUTOSCROLL lines do not work and sometimes the script does not even enter the 'For' loop! It is all very inconsistent.

I did read the documentation for CHART_SHIFT & CHART_AUTOSCROLL and I assume that since 'value' is boolean it is either True or False - it doesn't say!

bool ChartAutoscrollSet(const bool value,const long chart_ID=0)
  {
//--- reset the error value
   ResetLastError();
//--- set property value
   if(!ChartSetInteger(chart_ID,CHART_AUTOSCROLL,0,value))
     {
      //--- display the error message in Experts journal
      Print(__FUNCTION__+", Error Code = ",GetLastError());
      return(false);
     }
//--- successful execution
   return(true);
  }

This is my code:

int tf[5] = {PERIOD_M15,PERIOD_M30,PERIOD_H1,PERIOD_H4,PERIOD_D1};
string symbol = ChartSymbol();

void OnStart()
{
 for (long currChart = ChartFirst(); currChart >= 0;){
 long prevChart = currChart;       // Close this one
 currChart = ChartNext(prevChart); // after getting the next one.
 ChartClose(prevChart);}

 long chart_id = ChartOpen(symbol,PERIOD_M5);
 ChartApplyTemplate(chart_id,"template1.tpl");
 
 for(int i=0;i<5;i++)
 {
  chart_id = ChartOpen(symbol,tf[i]);
  ChartSetInteger(chart_id,CHART_SHIFT,True);
  ChartSetInteger(chart_id,CHART_AUTOSCROLL,True);
  ChartApplyTemplate(chart_id,"template2.tpl");
  Sleep(100);
 }
}
Reason: