Сохранение изображения графика

В MQL-программах часто возникает необходимость документировать текущее стояние самой программы и торгового окружения. Как правило, для этого используется вывод различных аналитических или финансовых показателей в журнал, но некоторые вещи более наглядно представить изображением графика, например, на момент совершения сделки. MQL5 API включает функцию, которая позволяет сохранять изображение графика в файл.

bool ChartScreenShot(long chartId, string filename, int width, int height,
  ENUM_ALIGN_MODE alignment = ALIGN_RIGHT)

Функция делает снимок указанного графика в формате GIF, PNG или BMP в зависимости от расширения в строке с именем файла filename (максимум 63 символа). Скриншот помещается в каталог MQL5/Files.

Параметры width и height задают ширину и высоту изображения в пикселях.

Параметр alignment влияет на то, какая часть графика попадет в файл. Значение ALIGN_RIGHT (по умолчанию) означает, что снимок делается для самых свежих цен (это можно себе представить так, что терминал незаметно делает переход по нажатию End перед снимком). Значение ALIGN_LEFT обеспечивает попадание на изображение баров, начиная с первого, видимого слева в данный момент. Таким образом, если необходимо снять скриншот графика с определенной позиции, то необходимо сначала позиционировать график вручную или при помощи функции ChartNavigate.

Функция ChartScreenShot возвращает true в случае успеха.

Протестируем работу функции в скрипте ChartPanorama.mq5. Его задача — сохранить копию графика от текущего левого видимого бара вплоть до текущего времени. Сместив предварительно начало графика назад на нужную глубину истории, можно получить довольно протяженную панораму. При этом не надо задумываться, какую ширину изображения выбрать. Однако следует иметь в виду, что слишком длинная история потребует огромного изображения, потенциально превышающего возможности графического формата или того или иного программного обеспечения.

Высота изображения будет автоматически определяться равной текущей высоте графика.

void OnStart()
{
   // точная ширина шкалы цен не известна, берем эмпирическим путем
   const int scale = 60;
   
   // вычисляем общую высоту, включая зазоры между окнами
   const int w = (int)ChartGetInteger(0CHART_WINDOWS_TOTAL);
   int height = 0;
   int gutter = 0;
   for(int i = 0i < w; ++i)
   {
      if(i == 1)
      {
         gutter = (int)ChartGetInteger(0CHART_WINDOW_YDISTANCEi) - height;
      }
      height += (int)ChartGetInteger(0CHART_HEIGHT_IN_PIXELSi);
   }
   
   Print("Gutter="gutter", total="gutter * (w - 1));
   height += gutter * (w - 1);
   Print("Height="height);
   
   // вычисляем общую ширину на основе количества пикселей в одном баре,
   // и также включая сдвиг графика от правого края и ширину шкалы
   const int shift = (int)(ChartGetInteger(0CHART_SHIFT) ?
      ChartGetDouble(0CHART_SHIFT_SIZE) * ChartGetInteger(0CHART_WIDTH_IN_PIXELS) / 100 : 0);
   Print("Shift="shift);
   const int pixelPerBar = (int)MathRound(1.0 * ChartGetInteger(0CHART_WIDTH_IN_PIXELS)
      / ChartGetInteger(0CHART_WIDTH_IN_BARS));
   const int width = (int)ChartGetInteger(0CHART_FIRST_VISIBLE_BAR) * pixelPerBar + scale + shift;
   Print("Width="width);
   
   // записываем файл с картинкой в формате PNG
   const string filename = _Symbol + "-" + PeriodToString() + "-panorama.png";
   if(ChartScreenShot(0filenamewidthheightALIGN_LEFT))
   {
      Print("File saved: "filename);
   }
}

Мы могли бы использовать и режим ALIGN_RIGHT, но тогда нужно было бы принудительно отключать сдвиг от правого края, потому что он вычисляется заново для картинки, в зависимости от её размера, и результат будет выглядеть совсем не так, как на экране (отступ справа станет слишком большим, так как он задается в процентах от ширины).

Ниже показан пример журнала после запуска скрипта на графике XAUUSD,H1.

Gutter=2, total=2
Height=440
Shift=74
Width=2086
File saved: XAUUSD-H1-panorama.png

С учетом навигации на не очень отдаленную историю получился следующий скриншот (представлен в виде уменьшенной в 4 раза копии).

Панорама графика

Панорама графика