今回は前回の記事「【MQL5】チャート上にアローを表示するプログラム【簡単】」で作成したアローの結果を表示するプログラムを作成していきます。
前回のプログラムにバッファーを追加して、表示するアローを増やすだけの簡単なお仕事です笑
ですが、前回の記事のプログラムは矢印が多すぎて見づらいので、10回に1回矢印を表示させ、その結果を次のローソク足に表示するプログラムを作成していきます。
今回も前回と同様にプログラムを確認するためのMQ5とEX5を下記の添付しておきますので、参考にしていただけたらと思います。
ソースコード
今回は下記のコードをもとに解説していきます。
前回の記事は細かく説明しすぎて、わかりづらかったかもしれないので、今回はソースコードに各行の解説を記載しています。コードの解説以降、詳しい説明が必要な部分だけを抜粋して説明していきます。
//+------------------------------------------------------------------+
//| DrawArrow.mq5 |
//| Copyright 2022, Bomcler. |
//| https://bomcler.net |
//+------------------------------------------------------------------+
#property copyright "Bomcler"
#property link "https://bomcler.net"
#property version "1.00"
#property indicator_chart_window
//----バッファーの数の指定
#property indicator_buffers 4
#property indicator_plots 4
//---- 1つ目のバッファーの色や、線の種類、大きさ等を指定しています。
#property indicator_type1 DRAW_ARROW
#property indicator_color1 clrYellow ←黄色
#property indicator_style1 STYLE_SOLID
#property indicator_width1 3
//---- 2つ目のバッファーの色や、線の種類、大きさ等を指定しています。
#property indicator_type2 DRAW_ARROW
#property indicator_color2 clrYellow
#property indicator_style2 STYLE_SOLID
#property indicator_width2 3
//---- 3つ目のバッファーの色や、線の種類、大きさ等を指定しています。
#property indicator_type3 DRAW_ARROW
#property indicator_color3 clrWhite ←白
#property indicator_style3 STYLE_SOLID
#property indicator_width3 3
//---- 4つ目のバッファーの色や、線の種類、大きさ等を指定しています。
#property indicator_type4 DRAW_ARROW
#property indicator_color4 clrWhite
#property indicator_style4 STYLE_SOLID
#property indicator_width4 3
double UpArrow[]; ←上矢印のバッファーを格納する配列
double DownArrow[]; ←下矢印のバッファーを格納する配列
double Winner[]; ←〇のバッファーを格納する配列
double Lose[]; ←×のバッファーを格納する配列
//+------------------------------------------------------------------+
//| Custom indicator initialization function |
//+------------------------------------------------------------------+
int OnInit() {
//--- 各配列とバッファーを連携させ、表示する画像の種類を指定している
SetIndexBuffer(0,UpArrow,INDICATOR_DATA);
PlotIndexSetInteger(0,PLOT_ARROW,233);
SetIndexBuffer(1,DownArrow,INDICATOR_DATA);
PlotIndexSetInteger(1,PLOT_ARROW,234);
SetIndexBuffer(2,Winner,INDICATOR_DATA);
PlotIndexSetInteger(2,PLOT_ARROW,161);
SetIndexBuffer(3,Lose,INDICATOR_DATA);
PlotIndexSetInteger(3,PLOT_ARROW,251);
//---
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[]) {
int pos = prev_calculated;
if(pos == rates_total)
pos--;
for(pos; pos<rates_total; pos++) {
//----10回に1回矢印を表示させるプログラム
//----また、陽線だったら上矢印、陰線だったら下矢印を表示させます。
if(pos % 10 == 0) {
if(close[pos] > open[pos])
UpArrow[pos] = low[pos] - 10*Point();
else if(close[pos] < open[pos])
DownArrow[pos] = high[pos] + 10*Point();
}
//----一つ前の矢印が矢印の向きと同じならば〇を違う場合は×を表示させます。
if(pos > 0) {
if(UpArrow[pos-1] > 0) {
if(close[pos] > open[pos])
Winner[pos] = high[pos] + 10*Point();
else if(close[pos] < open[pos])
Lose[pos] = low[pos] - 10*Point();
} else if(DownArrow[pos-1] > 0) {
if(close[pos] < open[pos])
Winner[pos] = low[pos] - 10*Point();
else if(close[pos] > open[pos])
Lose[pos] = high[pos] + 10*Point();
}
}
}
return(rates_total);
}
//+------------------------------------------------------------------+
10本に一本だけアローを表示させる仕組み
これは10で割ってあまりが0の時に処理をするように書けば簡単に実装できます。
この部分を修正することによって5分に1回エントリー判断をすることや、30分に1回処理を実行するなど応用がきく部分になるので、覚えておいて損はないです。
if(pos % 10 == 0) {
if(close[pos] > open[pos])
UpArrow[pos] = low[pos] - 10*Point();
else if(close[pos] < open[pos])
DownArrow[pos] = high[pos] + 10*Point();
}
変数posはローソク足のインデックスが格納されています。
この変数posの10で割った時のあまりが0であればif文の中の処理を実行するように記述しています。
ローソク足が存在しない場合にエラーとなる場合の対処
変数posが0の場合、一本前のローソク足は「ー1」本目になります。このー1本目というのは存在しないローソク足なので、エラーになってしまいます。
今回はこの一本だけなので、変数posが0の場合は判定しないように記述すれば対処できます。
if(pos > 0) {
この一文で対処できます。
判定結果による〇と×の切り分けのコード
これはif文を用いてコードを記述します。
if(UpArrow[pos-1] > 0) { ←上矢印が表示されているかどうかを判定
if(close[pos] > open[pos]) ←陽線かどうかを判定
Winner[pos] = high[pos] + 10*Point(); 〇を表示
else if(close[pos] < open[pos]) ←陰線かどうかを判定
Lose[pos] = low[pos] - 10*Point(); ×を表示
} else if(DownArrow[pos-1] > 0) { ←下矢印が表示されているかどうかを判定
if(close[pos] < open[pos]) ← 陰線かどうかを判定
Winner[pos] = low[pos] - 10*Point(); 〇を表示
else if(close[pos] > open[pos]) ←陽線かどうかを判定
Lose[pos] = high[pos] + 10*Point(); ×を表示
}
上記のコードに1行ずつの解説を乗せていますので、参考にしてください。
英語ばかりでよくわかりませんが、日本語にすれば簡単な条件分岐だと思います。
まとめ
今回新たに学ぶところはあまりありませんでしたが、バッファーを増やせば表示させるマークを増やすことができる点と、エラーをどのように対処するかを考えるいい機会だったと思います。
もっと複雑な場合はエラーを取得し、エラーの内容によっては処理をスキップして次の処理へ進むなどの処理を記述してもいいかもしれません。しかし、すべてのエラーを無視するようなプログラムは重大なバグを見逃してしまうかもしれませんので、最終手段だと思っておきましょう。
コメント