...\MQL4\Scripts\PeriodConverter.mq4 ...\MQL4\Scripts\PeriodConverterAllEx.mq4
//+------------------------------------------------------------------+ //+------------------------------------------------------------------+
//|                                              PeriodConverter.mq4 | //|                                              PeriodConverter.mq4 |
//|                   Copyright 2006-2015, MetaQuotes Software Corp. | //|                   Copyright 2006-2015, MetaQuotes Software Corp. |
//|                                        http://www.metaquotes.net | //|                                        http://www.metaquotes.net |
//+------------------------------------------------------------------+ //+------------------------------------------------------------------+
#property copyright   "2006-2015, MetaQuotes Software Corp." #property copyright   "2006-2015, MetaQuotes Software Corp."
#property link        "http://www.mql4.com" #property link        "http://www.mql4.com"
#property description "Period Converter to updated format of history base" #property description "Period Converter to updated format of history base"
#property strict #property strict
.#property show_inputs //#property show_inputs
   
.input int InpPeriodMultiplier=3; // Period multiplier factor //input int InpPeriodMultiplier=3; // Period multiplier factor
  int InpPeriodMultiplier;
int       ExtHandle=-1; int       ExtHandle=-1;
//+------------------------------------------------------------------+ //+------------------------------------------------------------------+
//| script program start function                                    | //| script program start function                                    |
//+------------------------------------------------------------------+ //+------------------------------------------------------------------+
void OnStart() void OnStart()
 {  {
  datetime time0;   datetime time0;
  ulong    last_fpos=0;   ulong    last_fpos=0;
  long     last_volume=0;   long     last_volume=0;
  int      i,start_pos,periodseconds;   int      i,start_pos,periodseconds;
  int      cnt=0;   int      cnt=0;
//---- History header //---- History header
  int      file_version=401;   int      file_version=401;
  string   c_copyright;   string   c_copyright;
  string   c_symbol=Symbol();   string   c_symbol=Symbol();
.   int      i_period=Period()*InpPeriodMultiplier; //   int      i_period=Period()*InpPeriodMultiplier;
    int      i_period;
  int      i_digits=Digits;   int      i_digits=Digits;
  int      i_unused[13];   int      i_unused[13];
  MqlRates rate;   MqlRates rate;
.//---      int      all_period[8]={5,15,30,60,240,1440,10080,43200}; 
    int      j;
    datetime next_bar_time;
  //---
    if(Period() != PERIOD_M1)
      {
       Print("Start Period Must be M1.");
       return;
      }
  //---
    for(j=0;j<ArraySize(all_period);j++)
      {
       InpPeriodMultiplier=all_period[j];
       i_period=Period()*InpPeriodMultiplier;
       Comment(i_period,"min. write...");
  //---
  ExtHandle=FileOpenHistory(c_symbol+(string)i_period+".hst",FILE_BIN|FILE_WRITE|FILE_SHARE_WRITE|FILE_SHARE_READ|FILE_ANSI);   ExtHandle=FileOpenHistory(c_symbol+(string)i_period+".hst",FILE_BIN|FILE_WRITE|FILE_SHARE_WRITE|FILE_SHARE_READ|FILE_ANSI);
  if(ExtHandle<0)   if(ExtHandle<0)
     return;      return;
  c_copyright="(C)opyright 2003, MetaQuotes Software Corp.";   c_copyright="(C)opyright 2003, MetaQuotes Software Corp.";
  ArrayInitialize(i_unused,0);   ArrayInitialize(i_unused,0);
//--- write history file header //--- write history file header
  FileWriteInteger(ExtHandle,file_version,LONG_VALUE);   FileWriteInteger(ExtHandle,file_version,LONG_VALUE);
  FileWriteString(ExtHandle,c_copyright,64);   FileWriteString(ExtHandle,c_copyright,64);
  FileWriteString(ExtHandle,c_symbol,12);   FileWriteString(ExtHandle,c_symbol,12);
  FileWriteInteger(ExtHandle,i_period,LONG_VALUE);   FileWriteInteger(ExtHandle,i_period,LONG_VALUE);
  FileWriteInteger(ExtHandle,i_digits,LONG_VALUE);   FileWriteInteger(ExtHandle,i_digits,LONG_VALUE);
  FileWriteInteger(ExtHandle,0,LONG_VALUE);   FileWriteInteger(ExtHandle,0,LONG_VALUE);
  FileWriteInteger(ExtHandle,0,LONG_VALUE);   FileWriteInteger(ExtHandle,0,LONG_VALUE);
  FileWriteArray(ExtHandle,i_unused,0,13);   FileWriteArray(ExtHandle,i_unused,0,13);
//--- write history file //--- write history file
  periodseconds=i_period*60;   periodseconds=i_period*60;
  start_pos=Bars-1;   start_pos=Bars-1;
  rate.open=Open[start_pos];   rate.open=Open[start_pos];
  rate.low=Low[start_pos];   rate.low=Low[start_pos];
  rate.high=High[start_pos];   rate.high=High[start_pos];
  rate.tick_volume=(long)Volume[start_pos];   rate.tick_volume=(long)Volume[start_pos];
  rate.spread=0;   rate.spread=0;
  rate.real_volume=0;   rate.real_volume=0;
  //--- normalize open time   //--- normalize open time
.   rate.time=Time[start_pos]/periodseconds; //   rate.time=Time[start_pos]/periodseconds;
  rate.time*=periodseconds; //   rate.time*=periodseconds;
    next_bar_time=SetBarTime(rate.time,Time[start_pos],periodseconds);
  for(i=start_pos-1; i>=0; i--)   for(i=start_pos-1; i>=0; i--)
    {     {
     if(IsStopped())      if(IsStopped())
        break;         break;
     time0=Time[i];      time0=Time[i];
.  /*
     //--- history may be updated      //--- history may be updated
     if(i==0)      if(i==0)
       {        {
        //--- modify index if history was updated         //--- modify index if history was updated
        if(RefreshRates())         if(RefreshRates())
           i=iBarShift(NULL,0,time0);            i=iBarShift(NULL,0,time0);
       }        }
.  */
     //---      //---
.      if(time0>=rate.time+periodseconds || i==0) //      if(time0>=rate.time+periodseconds || i==0)
       if(time0>=next_bar_time || i==0)
       {        {
.         if(i==0 && time0<rate.time+periodseconds) //         if(i==0 && time0<rate.time+periodseconds)
          if(i==0 && time0<next_bar_time)
          {           {
           rate.tick_volume+=(long)Volume[0];            rate.tick_volume+=(long)Volume[0];
           if(rate.low>Low[0])            if(rate.low>Low[0])
              rate.low=Low[0];               rate.low=Low[0];
           if(rate.high<High[0])            if(rate.high<High[0])
              rate.high=High[0];               rate.high=High[0];
           rate.close=Close[0];            rate.close=Close[0];
          }           }
        last_fpos=FileTell(ExtHandle);         last_fpos=FileTell(ExtHandle);
        last_volume=(long)Volume[i];         last_volume=(long)Volume[i];
        FileWriteStruct(ExtHandle,rate);         FileWriteStruct(ExtHandle,rate);
        cnt++;         cnt++;
.         if(time0>=rate.time+periodseconds) //         if(time0>=rate.time+periodseconds)
          if(time0>=next_bar_time)
          {           {
.            rate.time=time0/periodseconds; //            rate.time=time0/periodseconds;
           rate.time*=periodseconds; //            rate.time*=periodseconds;
             next_bar_time=SetBarTime(rate.time,time0,periodseconds);
           rate.open=Open[i];            rate.open=Open[i];
           rate.low=Low[i];            rate.low=Low[i];
           rate.high=High[i];            rate.high=High[i];
           rate.close=Close[i];            rate.close=Close[i];
           rate.tick_volume=last_volume;            rate.tick_volume=last_volume;
.             if(i==0)
               {
                FileWriteStruct(ExtHandle,rate);
                cnt++;
               }
          }           }
       }        }
      else       else
       {        {
        rate.tick_volume+=(long)Volume[i];         rate.tick_volume+=(long)Volume[i];
        if(rate.low>Low[i])         if(rate.low>Low[i])
           rate.low=Low[i];            rate.low=Low[i];
        if(rate.high<High[i])         if(rate.high<High[i])
           rate.high=High[i];            rate.high=High[i];
        rate.close=Close[i];         rate.close=Close[i];
       }        }
    }     }
  FileFlush(ExtHandle);   FileFlush(ExtHandle);
  PrintFormat("%d record(s) written",cnt);   PrintFormat("%d record(s) written",cnt);
.  /*
//--- collect incoming ticks //--- collect incoming ticks
  datetime last_time=LocalTime()-5;   datetime last_time=LocalTime()-5;
  long     chart_id=0;   long     chart_id=0;
//--- //---
  while(!IsStopped())   while(!IsStopped())
    {     {
     datetime cur_time=LocalTime();      datetime cur_time=LocalTime();
     //--- check for new rates      //--- check for new rates
     if(RefreshRates())      if(RefreshRates())
       {        {
        time0=Time[0];         time0=Time[0];
        FileSeek(ExtHandle,last_fpos,SEEK_SET);         FileSeek(ExtHandle,last_fpos,SEEK_SET);
        //--- is there current bar?         //--- is there current bar?
        if(time0<rate.time+periodseconds)         if(time0<rate.time+periodseconds)
          {           {
           rate.tick_volume+=(long)Volume[0]-last_volume;            rate.tick_volume+=(long)Volume[0]-last_volume;
           last_volume=(long)Volume[0];            last_volume=(long)Volume[0];
           if(rate.low>Low[0])            if(rate.low>Low[0])
              rate.low=Low[0];               rate.low=Low[0];
           if(rate.high<High[0])            if(rate.high<High[0])
              rate.high=High[0];               rate.high=High[0];
           rate.close=Close[0];            rate.close=Close[0];
          }           }
        else         else
          {           {
           //--- no, there is new bar            //--- no, there is new bar
           rate.tick_volume+=(long)Volume[1]-last_volume;            rate.tick_volume+=(long)Volume[1]-last_volume;
           if(rate.low>Low[1])            if(rate.low>Low[1])
              rate.low=Low[1];               rate.low=Low[1];
           if(rate.high<High[1])            if(rate.high<High[1])
              rate.high=High[1];               rate.high=High[1];
           //--- write previous bar remains            //--- write previous bar remains
           FileWriteStruct(ExtHandle,rate);            FileWriteStruct(ExtHandle,rate);
           last_fpos=FileTell(ExtHandle);            last_fpos=FileTell(ExtHandle);
           //----            //----
           rate.time=time0/periodseconds;            rate.time=time0/periodseconds;
           rate.time*=periodseconds;            rate.time*=periodseconds;
           rate.open=Open[0];            rate.open=Open[0];
           rate.low=Low[0];            rate.low=Low[0];
           rate.high=High[0];            rate.high=High[0];
           rate.close=Close[0];            rate.close=Close[0];
           rate.tick_volume=(long)Volume[0];            rate.tick_volume=(long)Volume[0];
           last_volume=rate.tick_volume;            last_volume=rate.tick_volume;
          }           }
        //----         //----
        FileWriteStruct(ExtHandle,rate);         FileWriteStruct(ExtHandle,rate);
        FileFlush(ExtHandle);         FileFlush(ExtHandle);
        //--- target chart is not found yet. it can be opened via Main menu - File - Open offline         //--- target chart is not found yet. it can be opened via Main menu - File - Open offline
        if(chart_id==0)         if(chart_id==0)
          {           {
           long id=ChartFirst();            long id=ChartFirst();
           while(id>=0)            while(id>=0)
             {              {
              //--- find appropriate offline chart               //--- find appropriate offline chart
              if(ChartSymbol(id)==Symbol() && ChartPeriod(id)==i_period && ChartGetInteger(id,CHART_IS_OFFLINE))               if(ChartSymbol(id)==Symbol() && ChartPeriod(id)==i_period && ChartGetInteger(id,CHART_IS_OFFLINE))
                {                 {
                 chart_id=id;                  chart_id=id;
                 ChartSetInteger(chart_id,CHART_AUTOSCROLL,true);                  ChartSetInteger(chart_id,CHART_AUTOSCROLL,true);
                 ChartSetInteger(chart_id,CHART_SHIFT,true);                  ChartSetInteger(chart_id,CHART_SHIFT,true);
                 ChartNavigate(chart_id,CHART_END);                  ChartNavigate(chart_id,CHART_END);
                 ChartRedraw(chart_id);                  ChartRedraw(chart_id);
                 PrintFormat("Chart window [%s,%d] found",Symbol(),i_period);                  PrintFormat("Chart window [%s,%d] found",Symbol(),i_period);
                 break;                  break;
                }                 }
              //--- enumerate opened charts               //--- enumerate opened charts
              id=ChartNext(id);               id=ChartNext(id);
             }              }
          }           }
        //--- refresh window not frequently than 1 time in 2 seconds         //--- refresh window not frequently than 1 time in 2 seconds
        if(chart_id!=0 && cur_time-last_time>=2)         if(chart_id!=0 && cur_time-last_time>=2)
          {           {
           ChartSetSymbolPeriod(chart_id,Symbol(),i_period);            ChartSetSymbolPeriod(chart_id,Symbol(),i_period);
           last_time=cur_time;            last_time=cur_time;
          }           }
       }        }
     Sleep(50);      Sleep(50);
    }           }      
.  */
  //---
    if(ExtHandle>=0)
      {
       FileClose(ExtHandle);
       ExtHandle=-1;
       cnt=0;
      }
    Comment(i_period,"min. fin!");
    }
//--- //---
 }  }
//+------------------------------------------------------------------+ //+------------------------------------------------------------------+
//|                                                                  | //|                                                                  |
//+------------------------------------------------------------------+ //+------------------------------------------------------------------+
void OnDeinit(const int reason) void OnDeinit(const int reason)
 {  {
//--- //---
  if(ExtHandle>=0)   if(ExtHandle>=0)
    {     {
     FileClose(ExtHandle);      FileClose(ExtHandle);
     ExtHandle=-1;      ExtHandle=-1;
    }     }
//--- //---
.   }
  //+------------------------------------------------------------------+
  //| バーの開始時間を計算する ※戻り値は次のバー開始時間              |
  //+------------------------------------------------------------------+
  datetime SetBarTime(datetime &bar_time,datetime current_time,int periodseconds)
   {
    datetime next_bar_time;
    MqlDateTime mql_date_time;
    switch(periodseconds)
      {
       case 604800:   // Weekly
          bar_time=current_time-current_time%86400; // Daily
          bar_time=bar_time-TimeDayOfWeek(bar_time)*86400;
          next_bar_time=bar_time+periodseconds;
          break;
       case 2592000:  // Monthly
          bar_time=current_time-current_time%86400; // Daily
          bar_time=bar_time-(TimeDay(bar_time)-1)*86400;
          TimeToStruct(bar_time,mql_date_time);
          if(mql_date_time.mon!=12)
             mql_date_time.mon++;
          else
            {
             mql_date_time.year++;
             mql_date_time.mon=1;
            }
          next_bar_time=StructToTime(mql_date_time);
          break;
       default:
          bar_time=current_time-current_time%periodseconds;
          next_bar_time=bar_time+periodseconds;
          break;
      }
    return(next_bar_time);
 }  }
//+------------------------------------------------------------------+ //+------------------------------------------------------------------+