
- MQL5で複数出力のあるデータを取得できない
- MQL5でiCustomの使い方が分からない
- 簡単なサンプルがほしい
MT5は高機能でオシャレになっているのに、流行らない理由としては単純にMT4に慣れすぎているからだと思います。
そして、MQL5はわかりやすいサンプルコードが本当に少ないです。ググっても欲しいコードが見つかりません。
開発目線で考えると同じプログラムを作るのであれば、圧倒的にMQL4の方が簡単です。わざわざ難しい方で作るメリットが無いんですよね・・・
あまりにサンプルが少ないので、ちょっとした作り込みもやる気にならないのはマズいと思うので、少し動作確認できたことを備忘録として残しておきます。
- MQL5のハンドルについて
- MQL5のiCustomでデータを取得するサンプル
サンプルコード
- 開発環境:MQL5
- 対象インジケータ:SuperTrend
- 出力バッファ数:3
- 取得バッファ番号:2
[0]Filling
[1]Filling
[2]SuperTrend
次のコードをコピペでコンパイル実行可能です。
//+------------------------------------------------------------------+
//| test.mq5 |
//| Copyright 2022, MetaQuotes Ltd. |
//| https://www.mql5.com |
//+------------------------------------------------------------------+
#property copyright "Copyright 2022, MetaQuotes Ltd."
#property link "https://www.mql5.com"
#property version "1.00"
#property indicator_chart_window
int handle;
double Buffer[];
//+------------------------------------------------------------------+
//| Custom indicator initialization function |
//+------------------------------------------------------------------+
int OnInit()
{
handle = iCustom(Symbol(),Period(), "Downloads\\supertrend",10,3.0,false);
return(INIT_SUCCEEDED);
}
//+------------------------------------------------------------------+
//| 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(CopyBuffer(handle,2,0,iBars(Symbol(),PERIOD_CURRENT),Buffer)<=0)
{
Print("Buufer Error :" + IntegerToString(GetLastError()));
}
ArraySetAsSeries(Buffer,true);
Print(Buffer[0]);
return(rates_total);
}
iCustom部分
MT5のiCustomの仕様です。詳しくはiCustomを確認してください。

指標入力パラメータの部分にインジケータのパラメータをセットします。

SuperTrendは次の入力パラメータになっていますので、同じようにセットします。
handle = iCustom(Symbol(),Period(), "Downloads\\supertrend",10,3.0,false);
MT5では「ハンドル」という概念が追加されていて、インジケータそのものがハンドルに格納されるイメージで考えてください。
ハンドルにはデータのメモリ番地が格納されており、直接ハンドル内のデータを触ることはできません。
CopyBuffer部分
ハンドルからデータを取得する処理です。
ArraySetAsSeriesはバッファ内のデータを時系列にソート?してくれるようですが、まだ詳しく調べていません。おまじない代わりにセットで使ってくださいw
if(CopyBuffer(handle,2,0,iBars(Symbol(),PERIOD_CURRENT),Buffer)<=0)
{
Print("Buufer Error :" + IntegerToString(GetLastError()));
}
ArraySetAsSeries(Buffer,true);
今回は、「[2]SuperTrend」を取得したかったので2番目を指定した実装になっていますが、0番目や1番目を取得したいときは指標バッファ番号を変更してください。
CopyBuffer(handle,0,0,iBars(Symbol(),PERIOD_CURRENT),Buffer)//0番目
CopyBuffer(handle,1,0,iBars(Symbol(),PERIOD_CURRENT),Buffer)//1番目
CopyBuffer(handle,2,0,iBars(Symbol(),PERIOD_CURRENT),Buffer)//2番目
CopyBuffer(handle,n,0,iBars(Symbol(),PERIOD_CURRENT),Buffer)//n番目
MQL5のCopyBufferの仕様です。詳しくはCopyBufferを参照してください。

データ操作部分
データ操作に関してはMQL4と同じように扱えます。Bufferをループすることも可能です。
Print(Buffer[0]);
MQL4からMQL5の違い
MQL4では一行で簡単にデータを取得できていたのに、MQL5では一手間増えています。
double hoge = iCustom(Symbol(),Period(), "Downloads/SuperTrend",10,3.0,0,0);
OnInitでハンドルを取得し、OnCalculateでデータをコピーして使う。かなり面倒くさいです・・・
次のコードはMQL5のMacdの一部ですが、標準インジケーターも同じようにハンドルで使っています。
//--- get MA handles
ExtFastMaHandle=iMA(NULL,0,InpFastEMA,0,MODE_EMA,InpAppliedPrice);
ExtSlowMaHandle=iMA(NULL,0,InpSlowEMA,0,MODE_EMA,InpAppliedPrice);
MT5で開発を行うなら必須の知識になりますので、どうぞご活用ください。