Skip to content

Commit

Permalink
GetLowest() and GetHighest() now uses passed mode to retrieve proper …
Browse files Browse the repository at this point in the history
…Candle's OHLCVT value.

Also moved ENUM_INDI_CANDLE_MODE enum into separate file.
  • Loading branch information
nseam committed Sep 13, 2024
1 parent d4ef76e commit aeb62f4
Show file tree
Hide file tree
Showing 5 changed files with 151 additions and 72 deletions.
51 changes: 47 additions & 4 deletions Indicator/Indicator.h
Original file line number Diff line number Diff line change
Expand Up @@ -32,11 +32,13 @@ struct IndicatorParams;
#include "Indicator.enum.h"
#include "Indicator.struct.h"
#include "Indicator.struct.serialize.h"
#include "IndicatorCandle.enum.h"
#include "IndicatorData.h"

// Includes.
#include "../Indicators/DrawIndicator.mqh"
#include "../Math/Math.h"
#include "../Platform/Chart/Chart.define.h"
#include "../Refs.mqh"
#include "../Serializer/Serializer.h"
#include "../Serializer/SerializerCsv.h"
Expand Down Expand Up @@ -161,13 +163,19 @@ class Indicator : public IndicatorData {
* Returns the highest bar's index (shift).
*/
int GetHighest(int mode, int count = WHOLE_ARRAY, int start_bar = 0) override {
if (GetCandle() != THIS_PTR) {
Alert("You can only use ", __FUNCTION__, " on the Candle-based indicator! ", GetFullName(),
" is not a Candle indicator.");
DebugBreak();
return -1;
}

int max_idx = -1;
double max = -DBL_MAX;
int last_bar = count == WHOLE_ARRAY ? (int)(GetBarShift(GetLastBarTime())) : (start_bar + count - 1);

for (int shift = start_bar; shift <= last_bar; ++shift) {
IndicatorDataEntry _entry = GetEntry(shift);
double value = _entry.GetMax<double>(GetModeCount());
double value = GetValue<double>((int)GetCandleIndicatorMode(mode), shift);
if (value > max) {
max = value;
max_idx = shift;
Expand All @@ -181,13 +189,19 @@ class Indicator : public IndicatorData {
* Returns the lowest bar's index (shift).
*/
int GetLowest(int mode, int count = WHOLE_ARRAY, int start_bar = 0) override {
if (GetCandle() != THIS_PTR) {
Alert("You can only use ", __FUNCTION__, " on the Candle-based indicator! ", GetFullName(),
" is not a Candle indicator.");
DebugBreak();
return -1;
}

int min_idx = -1;
double min = DBL_MAX;
int last_bar = count == WHOLE_ARRAY ? (int)(GetBarShift(GetLastBarTime())) : (start_bar + count - 1);

for (int shift = start_bar; shift <= last_bar; ++shift) {
IndicatorDataEntry _entry = GetEntry(shift);
double value = _entry.GetMin<double>(GetModeCount());
double value = GetValue<double>((int)GetCandleIndicatorMode(mode), shift);
if (value < min) {
min = value;
min_idx = shift;
Expand All @@ -197,6 +211,35 @@ class Indicator : public IndicatorData {
return min_idx;
}

/**
* Converts Series Array Indentifier into mode index to be retrieved from Candle indicator.
*
* Possible values:
* MODE_OPEN, MODE_LOW, MODE_HIGH, MODE_CLOSE, MODE_VOLUME, MODE_TIME.
*/
ENUM_INDI_CANDLE_MODE GetCandleIndicatorMode(int _series_array_id) {
switch (_series_array_id) {
case MODE_OPEN:
return INDI_CANDLE_MODE_PRICE_OPEN;
case MODE_LOW:
return INDI_CANDLE_MODE_PRICE_LOW;
case MODE_HIGH:
return INDI_CANDLE_MODE_PRICE_HIGH;
case MODE_CLOSE:
return INDI_CANDLE_MODE_PRICE_CLOSE;
case MODE_VOLUME:
case MODE_REAL_VOLUME:
return INDI_CANDLE_MODE_VOLUME;
case MODE_TIME:
return INDI_CANDLE_MODE_TIME;
default:
Alert("Unsupported mode ", IntegerToString(_series_array_id), ", for ", __FUNCTION__, "");
DebugBreak();
}

return (ENUM_INDI_CANDLE_MODE)0;
}

/* Setters */

/**
Expand Down
48 changes: 48 additions & 0 deletions Indicator/IndicatorCandle.enum.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,48 @@
//+------------------------------------------------------------------+
//| EA31337 framework |
//| Copyright 2016-2024, EA31337 Ltd |
//| https://ea31337.github.io |
//+------------------------------------------------------------------+

/*
* This file is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*
*/

/**
* @file
* Includes IndicatorCandle's enums.
*/

#ifndef __MQL__
// Allows the preprocessor to include a header file when it is needed.
#pragma once
#endif

// Indicator modes.
enum ENUM_INDI_CANDLE_MODE {
INDI_CANDLE_MODE_PRICE_OPEN,
INDI_CANDLE_MODE_PRICE_HIGH,
INDI_CANDLE_MODE_PRICE_LOW,
INDI_CANDLE_MODE_PRICE_CLOSE,
INDI_CANDLE_MODE_SPREAD,
INDI_CANDLE_MODE_TICK_VOLUME,
INDI_CANDLE_MODE_TIME,
INDI_CANDLE_MODE_VOLUME,
FINAL_INDI_CANDLE_MODE_ENTRY,
// Following modes are dynamically calculated.
INDI_CANDLE_MODE_PRICE_MEDIAN,
INDI_CANDLE_MODE_PRICE_TYPICAL,
INDI_CANDLE_MODE_PRICE_WEIGHTED,
};
18 changes: 1 addition & 17 deletions Indicator/IndicatorCandle.h
Original file line number Diff line number Diff line change
Expand Up @@ -36,6 +36,7 @@
#include "../Storage/ValueStorage.time.h"
#include "../Storage/ValueStorage.volume.h"
#include "Indicator.h"
#include "IndicatorCandle.enum.h"
#include "IndicatorCandle.provider.h"
#include "IndicatorData.h"
#include "TickBarCounter.h"
Expand All @@ -44,23 +45,6 @@
#define INDI_CANDLE_HISTORY_SIZE 86400
#endif

// Indicator modes.
enum ENUM_INDI_CANDLE_MODE {
INDI_CANDLE_MODE_PRICE_OPEN,
INDI_CANDLE_MODE_PRICE_HIGH,
INDI_CANDLE_MODE_PRICE_LOW,
INDI_CANDLE_MODE_PRICE_CLOSE,
INDI_CANDLE_MODE_SPREAD,
INDI_CANDLE_MODE_TICK_VOLUME,
INDI_CANDLE_MODE_TIME,
INDI_CANDLE_MODE_VOLUME,
FINAL_INDI_CANDLE_MODE_ENTRY,
// Following modes are dynamically calculated.
INDI_CANDLE_MODE_PRICE_MEDIAN,
INDI_CANDLE_MODE_PRICE_TYPICAL,
INDI_CANDLE_MODE_PRICE_WEIGHTED,
};

/**
* Class to deal with candle indicators.
*/
Expand Down
102 changes: 53 additions & 49 deletions Platform/Chart/Chart.define.h
Original file line number Diff line number Diff line change
Expand Up @@ -26,8 +26,8 @@
*/

#ifndef __MQL__
// Allows the preprocessor to include a header file when it is needed.
#pragma once
// Allows the preprocessor to include a header file when it is needed.
#pragma once
#endif

/* Defines */
Expand Down Expand Up @@ -56,51 +56,55 @@
#define MN1B (1 << MN1) // Monthly

#ifndef __MQL4__
// Chart.
#define CHART_BAR 0
#define CHART_CANDLE 1
//---
#ifndef MODE_ASCEND
#define MODE_ASCEND 0
#endif
#ifndef MODE_DESCEND
#define MODE_DESCEND 1
#endif
//---
#define MODE_LOW 1
#define MODE_HIGH 2
// --
#define MODE_OPEN 0
#define MODE_CLOSE 3
#define MODE_VOLUME 4
#define MODE_REAL_VOLUME 5
// --
#define MODE_TIME 5
#define MODE_BID 9
#define MODE_ASK 10
#define MODE_POINT 11
#define MODE_DIGITS 12
#define MODE_SPREAD 13
#define MODE_STOPLEVEL 14
#define MODE_LOTSIZE 15
#define MODE_TICKVALUE 16
#define MODE_TICKSIZE 17
#define MODE_SWAPLONG 18
#define MODE_SWAPSHORT 19
#define MODE_STARTING 20
#define MODE_EXPIRATION 21
#define MODE_TRADEALLOWED 22
#define MODE_TICK_SIZE 21
#define MODE_TICK_VALUE 22
#define MODE_MINLOT 23
#define MODE_LOTSTEP 24
#define MODE_MAXLOT 25
#define MODE_SWAPTYPE 26
#define MODE_PROFITCALCMODE 27
#define MODE_MARGINCALCMODE 28
#define MODE_MARGININIT 29
#define MODE_MARGINMAINTENANCE 30
#define MODE_MARGINHEDGED 31
#define MODE_MARGINREQUIRED 32
#define MODE_FREEZELEVEL 33
// Chart.
#define CHART_BAR 0
#define CHART_CANDLE 1
//---
#ifndef MODE_ASCEND
#define MODE_ASCEND 0
#endif
#ifndef MODE_DESCEND
#define MODE_DESCEND 1
#endif
//---
#define MODE_LOW 1
#define MODE_HIGH 2
// --
#define MODE_OPEN 0
#define MODE_CLOSE 3
#define MODE_VOLUME 4
// --
#define MODE_TIME \
6 // Used to retrieve time from Candle indicator. Changed value from 5 to 6 in order to prevent conflicts with
// MODE_REAL_VOLUME.
#define MODE_BID 9
#define MODE_ASK 10
#define MODE_POINT 11
#define MODE_DIGITS 12
#define MODE_SPREAD 13
#define MODE_STOPLEVEL 14
#define MODE_LOTSIZE 15
#define MODE_TICKVALUE 16
#define MODE_TICKSIZE 17
#define MODE_SWAPLONG 18
#define MODE_SWAPSHORT 19
#define MODE_STARTING 20
#define MODE_EXPIRATION 21
#define MODE_TRADEALLOWED 22
#define MODE_TICK_SIZE 21
#define MODE_TICK_VALUE 22
#define MODE_MINLOT 23
#define MODE_LOTSTEP 24
#define MODE_MAXLOT 25
#define MODE_SWAPTYPE 26
#define MODE_PROFITCALCMODE 27
#define MODE_MARGINCALCMODE 28
#define MODE_MARGININIT 29
#define MODE_MARGINMAINTENANCE 30
#define MODE_MARGINHEDGED 31
#define MODE_MARGINREQUIRED 32
#define MODE_FREEZELEVEL 33
#else
// #ifdef __MQL4__
#define MODE_REAL_VOLUME 7
#endif
4 changes: 2 additions & 2 deletions tests/StrategyTest-RSI.mq5
Original file line number Diff line number Diff line change
Expand Up @@ -70,8 +70,8 @@ class Stg_RSI : public Strategy {
IndiRSIParams _iparams = _indi.GetParams();
double _trail = _level * Market().GetPipSize();
int _direction = Order::OrderDirection(_cmd, _mode);
return _direction > 0 ? (float)_indi.GetPrice(PRICE_HIGH, _indi.GetHighest<double>(_iparams.GetPeriod() * 2))
: (float)_indi.GetPrice(PRICE_LOW, _indi.GetLowest<double>(_iparams.GetPeriod() * 2));
return _direction > 0 ? (float)_indi.GetPrice(PRICE_HIGH, _indi.GetHighest(_iparams.GetPeriod() * 2))
: (float)_indi.GetPrice(PRICE_LOW, _indi.GetLowest(_iparams.GetPeriod() * 2));
}

virtual void OnPeriod(unsigned int _periods = DATETIME_NONE) {
Expand Down

0 comments on commit aeb62f4

Please sign in to comment.