700 lines
12 KiB
Plaintext
700 lines
12 KiB
Plaintext
///////////////////////////////////////////////////////
|
|
//
|
|
// SaherElm IT Center MQL5 Seriallize Library
|
|
// ---------------------------------------
|
|
// Name: XPOILib
|
|
// Description: All models related to POIs ...
|
|
//
|
|
//
|
|
// Maintainer:
|
|
// ------------
|
|
// Hadi Khazaee Asl (hadi_khazaee_asl@yahoo.com)
|
|
//
|
|
//////////////////////////////////////////////////////
|
|
//
|
|
// Global Properties ...
|
|
#property library
|
|
#property copyright "Copyright `023, SaherElm IT Center"
|
|
#property link "https://www.saherelm.ir"
|
|
#property version "1.00"
|
|
#property strict
|
|
|
|
//
|
|
// Imports ...
|
|
#include "../Classes/x-saherelm.base.class.mq5"
|
|
#include <Arrays/ArrayObj.mqh>
|
|
|
|
//
|
|
// Definitions ...
|
|
|
|
//
|
|
struct XBoxZone
|
|
{
|
|
//
|
|
// Props ...
|
|
string symbol;
|
|
ENUM_TIMEFRAMES period;
|
|
|
|
//
|
|
double upper;
|
|
double lower;
|
|
|
|
//
|
|
datetime at;
|
|
datetime from;
|
|
datetime to;
|
|
|
|
//
|
|
string type;
|
|
ENUM_X_DIRECTION dir;
|
|
|
|
//
|
|
// Constructor ...
|
|
XBoxZone()
|
|
{
|
|
Clean();
|
|
}
|
|
|
|
//
|
|
// Tools ...
|
|
|
|
/**
|
|
* Cleanup Model ...
|
|
*/
|
|
void Clean()
|
|
{
|
|
//
|
|
upper = 0;
|
|
lower = 0;
|
|
to = NULL;
|
|
at = NULL;
|
|
from = NULL;
|
|
symbol = NULL;
|
|
period = NULL;
|
|
dir = X_DIRECTION_NONE;
|
|
|
|
//
|
|
ZeroMemory(this);
|
|
}
|
|
|
|
/**
|
|
* Validate Model ...
|
|
*
|
|
* @return ( bool )
|
|
*/
|
|
bool IsValid()
|
|
{
|
|
//
|
|
bool result = false;
|
|
|
|
//
|
|
result =
|
|
//
|
|
upper > 0 &&
|
|
lower > 0 &&
|
|
from < to &&
|
|
IsValid(to) &&
|
|
upper >= lower &&
|
|
IsValid(from) &&
|
|
IsValid(symbol) &&
|
|
IsValid(period)
|
|
//
|
|
;
|
|
|
|
//
|
|
return result;
|
|
}
|
|
|
|
/**
|
|
* Check Box is Bullish or not ...
|
|
*
|
|
* @return ( bool )
|
|
*/
|
|
bool IsBullish()
|
|
{
|
|
return IsValid() &&
|
|
IsBullish(dir);
|
|
}
|
|
|
|
/**
|
|
* Check Box is Bearish or not ...
|
|
*
|
|
* @return ( bool )
|
|
*/
|
|
bool IsBearish()
|
|
{
|
|
return IsValid() &&
|
|
IsBearish(dir);
|
|
}
|
|
|
|
/**
|
|
* Clone Box by Provided Source ...
|
|
*
|
|
* @return ( bool )
|
|
*/
|
|
bool Clone(XBoxZone &source)
|
|
{
|
|
//
|
|
bool result = false;
|
|
|
|
//
|
|
Clean();
|
|
result = source.IsValid();
|
|
if (!result)
|
|
{
|
|
return result;
|
|
}
|
|
|
|
//
|
|
// Filling Props ...
|
|
to = source.to;
|
|
dir = source.dir;
|
|
from = source.from;
|
|
type = source.type;
|
|
upper = source.upper;
|
|
lower = source.lower;
|
|
symbol = source.symbol;
|
|
period = source.period;
|
|
|
|
//
|
|
result = IsValid();
|
|
if (!result)
|
|
{
|
|
Clean();
|
|
}
|
|
|
|
//
|
|
return result;
|
|
}
|
|
|
|
/**
|
|
* Check Box is Same as Other ...
|
|
*
|
|
* @param item: XBoxZone instance Resource ...
|
|
*
|
|
* @return ( bool )
|
|
*/
|
|
bool IsSameAs(XBoxZone &item)
|
|
{
|
|
//
|
|
return IsValid() &&
|
|
item.IsValid() &&
|
|
dir == item.dir &&
|
|
from == item.from &&
|
|
type == item.type &&
|
|
lower == item.lower &&
|
|
upper == item.upper &&
|
|
symbol == item.symbol &&
|
|
period == item.period;
|
|
}
|
|
|
|
/**
|
|
* Retrieve Box Age ...
|
|
*
|
|
* @param forPeriod: ENUM_TIMEFRAMES member ...
|
|
*
|
|
* @return ( int )
|
|
*/
|
|
int GetAge(
|
|
ENUM_TIMEFRAMES forPeriod = NULL //
|
|
)
|
|
{
|
|
//
|
|
int result = 0;
|
|
|
|
//
|
|
if (!IsValid())
|
|
{
|
|
return result;
|
|
}
|
|
|
|
//
|
|
if (!IsValid(forPeriod))
|
|
{
|
|
forPeriod = period;
|
|
}
|
|
|
|
//
|
|
result = iBarShift(
|
|
symbol,
|
|
forPeriod,
|
|
from //
|
|
);
|
|
|
|
//
|
|
return result;
|
|
}
|
|
|
|
/**
|
|
* Calculate Box Middle Price ...
|
|
*
|
|
* @return ( double )
|
|
*/
|
|
double GetMid()
|
|
{
|
|
//
|
|
double result = 0;
|
|
|
|
//
|
|
if (!IsValid())
|
|
{
|
|
return result;
|
|
}
|
|
|
|
//
|
|
double diffAvg = (upper - lower) / 2;
|
|
result = lower + diffAvg;
|
|
result = NormalizePrice(result, symbol);
|
|
|
|
//
|
|
return result;
|
|
}
|
|
|
|
/**
|
|
* Calculate Box Leg N Price ...
|
|
* N default is 2
|
|
*
|
|
* @param leg: int ...
|
|
*
|
|
* @return ( double )
|
|
*/
|
|
double GetLeg(int leg = 2)
|
|
{
|
|
//
|
|
double result = 0;
|
|
|
|
//
|
|
leg = NormalizeInt(leg, 2);
|
|
|
|
//
|
|
if (!IsValid())
|
|
{
|
|
return result;
|
|
}
|
|
|
|
//
|
|
double range = (upper - lower) * leg;
|
|
result =
|
|
IsBullish()
|
|
? upper + range
|
|
: lower - range;
|
|
result = NormalizePrice(result, symbol);
|
|
|
|
//
|
|
return result;
|
|
}
|
|
|
|
/**
|
|
* Calculate Box Range ...
|
|
*
|
|
* @return ( double )
|
|
*/
|
|
double GetRange()
|
|
{
|
|
//
|
|
double result = 0;
|
|
|
|
//
|
|
if (!IsValid())
|
|
{
|
|
return result;
|
|
}
|
|
|
|
//
|
|
result = (upper - lower);
|
|
result = NormalizePrice(result, symbol);
|
|
|
|
//
|
|
return result;
|
|
}
|
|
|
|
/**
|
|
* Extract Rejection Price based on Box Direction ...
|
|
*
|
|
* @return ( double )
|
|
*/
|
|
double GetRejection()
|
|
{
|
|
//
|
|
double result = 0;
|
|
|
|
//
|
|
if (!IsValid())
|
|
{
|
|
return result;
|
|
}
|
|
|
|
//
|
|
result =
|
|
IsBullish()
|
|
? upper
|
|
: lower;
|
|
|
|
//
|
|
return result;
|
|
}
|
|
|
|
/**
|
|
* To Bar Index ...
|
|
*
|
|
* @return ( int )
|
|
*/
|
|
int ToIndex(
|
|
ENUM_TIMEFRAMES forPeriod = NULL //
|
|
)
|
|
{
|
|
//
|
|
int result = -1;
|
|
|
|
//
|
|
if (!IsValid())
|
|
{
|
|
return result;
|
|
}
|
|
|
|
//
|
|
if (!IsValid(forPeriod))
|
|
{
|
|
forPeriod = period;
|
|
}
|
|
|
|
//
|
|
result = GetBarIndex(
|
|
symbol,
|
|
forPeriod,
|
|
to //
|
|
);
|
|
|
|
//
|
|
return result;
|
|
}
|
|
|
|
/**
|
|
* Retrieve To Bar ...
|
|
*
|
|
* @return ( bool )
|
|
*/
|
|
bool ToBar(XOHCL &bar)
|
|
{
|
|
//
|
|
bool result = false;
|
|
|
|
//
|
|
bar.Clean();
|
|
|
|
//
|
|
int idx = ToIndex();
|
|
|
|
//
|
|
result =
|
|
IsValid() &&
|
|
IsValidIndex(idx);
|
|
if (!result)
|
|
{
|
|
return result;
|
|
}
|
|
|
|
//
|
|
result = bar.Init(
|
|
symbol,
|
|
period,
|
|
idx //
|
|
);
|
|
|
|
//
|
|
return result;
|
|
}
|
|
|
|
/**
|
|
* From Bar Index ...
|
|
*
|
|
* @return ( int )
|
|
*/
|
|
int FromIndex(
|
|
ENUM_TIMEFRAMES forPeriod = NULL //
|
|
)
|
|
{
|
|
//
|
|
int result = -1;
|
|
|
|
//
|
|
if (!IsValid())
|
|
{
|
|
return result;
|
|
}
|
|
|
|
//
|
|
if (!IsValid(forPeriod))
|
|
{
|
|
forPeriod = period;
|
|
}
|
|
|
|
//
|
|
result = GetBarIndex(
|
|
symbol,
|
|
forPeriod,
|
|
from //
|
|
);
|
|
|
|
//
|
|
return result;
|
|
}
|
|
|
|
/**
|
|
* Retrieve From Bar ...
|
|
*
|
|
* @return ( bool )
|
|
*/
|
|
bool FromBar(XOHCL &bar)
|
|
{
|
|
//
|
|
bool result = false;
|
|
|
|
//
|
|
bar.Clean();
|
|
|
|
//
|
|
int idx = FromIndex();
|
|
|
|
//
|
|
result =
|
|
IsValid() &&
|
|
IsValidIndex(idx);
|
|
if (!result)
|
|
{
|
|
return result;
|
|
}
|
|
|
|
//
|
|
result = bar.Init(
|
|
symbol,
|
|
period,
|
|
idx //
|
|
);
|
|
|
|
//
|
|
return result;
|
|
}
|
|
|
|
/**
|
|
* Retrieve Unique Identifier ...
|
|
*
|
|
* @return ( string )
|
|
*/
|
|
string GetTag()
|
|
{
|
|
//
|
|
int digits = GetDigits(symbol);
|
|
double nUpper = NormalizeDouble(NormalizePrice(upper, symbol), digits);
|
|
double nLower = NormalizeDouble(NormalizePrice(lower, symbol), digits);
|
|
|
|
//
|
|
string typeStr = IsValid(type)
|
|
? type
|
|
: "XBOX";
|
|
string result =
|
|
//
|
|
typeStr + "_" +
|
|
ToString(dir) + "_" +
|
|
symbol + "_" +
|
|
ToString(period) + "_" +
|
|
ToString(nUpper) + "_" +
|
|
ToString(nLower)
|
|
//
|
|
;
|
|
|
|
//
|
|
return result;
|
|
}
|
|
|
|
/**
|
|
* Retrieve Unique Middle Identifier ...
|
|
*
|
|
* @return ( string )
|
|
*/
|
|
string GetMiddleTag()
|
|
{
|
|
//
|
|
int digits = GetDigits(symbol);
|
|
double nMid = NormalizeDouble(NormalizePrice(GetMid(), symbol), digits);
|
|
|
|
//
|
|
string typeStr = IsValid(type)
|
|
? type
|
|
: "XBOX";
|
|
string result =
|
|
//
|
|
typeStr + "_" +
|
|
"Mid_" +
|
|
ToString(dir) + "_" +
|
|
symbol + "_" +
|
|
ToString(period) + "_" +
|
|
ToString(nMid)
|
|
//
|
|
;
|
|
|
|
//
|
|
return result;
|
|
}
|
|
};
|
|
|
|
//
|
|
struct XDirectionShift
|
|
{
|
|
//
|
|
// Props ...
|
|
string type;
|
|
datetime at;
|
|
double after;
|
|
double before;
|
|
string symbol;
|
|
ENUM_TIMEFRAMES period;
|
|
ENUM_X_DIRECTION shiftTo;
|
|
|
|
//
|
|
// Constructor ...
|
|
XDirectionShift()
|
|
{
|
|
Clean();
|
|
}
|
|
|
|
//
|
|
// Tools ...
|
|
|
|
//
|
|
// Cleanup ...
|
|
void Clean()
|
|
{
|
|
//
|
|
at = NULL;
|
|
after = 0;
|
|
before = 0;
|
|
type = NULL;
|
|
symbol = NULL;
|
|
period = NULL;
|
|
shiftTo = X_DIRECTION_NONE;
|
|
|
|
//
|
|
ZeroMemory(this);
|
|
}
|
|
|
|
//
|
|
// Validate ...
|
|
bool IsValid()
|
|
{
|
|
//
|
|
bool result = false;
|
|
|
|
//
|
|
result =
|
|
after > 0 &&
|
|
IsValid(at) &&
|
|
IsValid(type) &&
|
|
after != before &&
|
|
IsValid(symbol) &&
|
|
IsValid(period) &&
|
|
HasDirection(shiftTo);
|
|
|
|
//
|
|
return result;
|
|
}
|
|
|
|
//
|
|
// Get Bar Index of Direction Shift ...
|
|
int Index()
|
|
{
|
|
//
|
|
int result = -1;
|
|
|
|
//
|
|
// Validate ...
|
|
if (!IsValid())
|
|
{
|
|
return result;
|
|
}
|
|
|
|
//
|
|
// Retrieve Bar Index ...
|
|
result = GetBarIndex(
|
|
symbol,
|
|
period,
|
|
at //
|
|
);
|
|
|
|
//
|
|
return result;
|
|
}
|
|
|
|
//
|
|
// Get At Bar ...
|
|
bool AtBar(XOHCL &bar)
|
|
{
|
|
//
|
|
bool result = false;
|
|
|
|
//
|
|
// Normalize ...
|
|
bar.Clean();
|
|
|
|
//
|
|
// Validate ...
|
|
result = IsValid();
|
|
if (!result)
|
|
{
|
|
return result;
|
|
}
|
|
|
|
//
|
|
int idx = Index();
|
|
if (IsValidIndex(idx))
|
|
{
|
|
//
|
|
result = bar.Init(
|
|
symbol,
|
|
period,
|
|
idx //
|
|
);
|
|
}
|
|
|
|
//
|
|
result = bar.IsValid();
|
|
|
|
//
|
|
return result;
|
|
}
|
|
|
|
//
|
|
// Check Same ...
|
|
bool IsSameAs(XDirectionShift &item)
|
|
{
|
|
//
|
|
bool result = false;
|
|
|
|
//
|
|
result = IsValid() &&
|
|
item.IsValid();
|
|
if (!result)
|
|
{
|
|
return result;
|
|
}
|
|
|
|
//
|
|
result =
|
|
//
|
|
at == item.at &&
|
|
type == item.type &&
|
|
after == item.after &&
|
|
before == item.before &&
|
|
symbol == item.symbol &&
|
|
period == item.period &&
|
|
shiftTo == item.shiftTo
|
|
//
|
|
;
|
|
|
|
//
|
|
return result;
|
|
}
|
|
};
|
|
|
|
//
|