Files
MQL5Data/Classes/x-saherelm.x-volume.class.mq5
T
2025-04-13 22:16:17 +03:30

792 lines
16 KiB
Plaintext
Raw Blame History

This file contains invisible Unicode characters
This file contains invisible Unicode characters that are indistinguishable to humans but may be processed differently by a computer. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
///////////////////////////////////////////////////////
//
// SaherElm IT Center MQL5 Class Library
// --------------------------------------
// Name: XCVolume
// Description: provides all Requirements for Volume Managing ...
//
//
// Maintainer:
// ------------
// Hadi Khazaee Asl (hadi_khazaee_asl@yahoo.com)
//
//////////////////////////////////////////////////////
//
// Global Properties ...
#property library
#property copyright "Copyright 2023, SaherElm IT Center"
#property link "https://www.saherelm.ir"
#property version "1.00"
#property strict
//
// Template Variables of Inputs for Using ...
// input group "Volume";
// input ENUM_X_VOLUME_SELECT_TYPE eaVolumeSelect = X_VOLUME_STATIC; // Volume Applying Type
// input double eaStaticVoluem = X_MIN_VOLUME; // Static Volume
// input double eaDynamicVolumeStepBalance = 0.0; // Step of Balance for Increase Volume
// input double eaDynamicVolumeStepVolume = X_MIN_VOLUME; // Step of Volume Increasing
// input double eaConstantRiskBalance = 0.0; // Constant Risk Balance per Trade
// input double eaConstantPercent = 0.0; // Constant Percent of Balance Per Trade
// input double eaConstantBalance = 0.0; // Constant Balance for Calculations
// XCVolume *eaVolume;
// eaVolume = new XCVolume();
// bool result = eaVolume.Init(
// eaVolumeSelect,
// eaStaticVoluem,
// eaDynamicVolumeStepBalance,
// eaDynamicVolumeStepVolume,
// eaConstantRiskBalance,
// eaConstantPercent,
// eaConstantBalance //
// );
// if (!result) {
// return INIT_FAILED;
// }
//
// Imports ...
#include "../Classes/x-saherelm.x-account.class.mq5"
#include "../Libraries/x-saherelm.x-trade.lib.mq5"
//
// Definitions ...
#define X_MIN_VOLUME 0.01
//
enum ENUM_X_VOLUME_SELECT_TYPE
{
X_VOLUME_NONE, // None
X_VOLUME_STATIC, // Static Volume
X_VOLUME_CURRENT, // Current Balance
X_VOLUME_EQUITY, // Current Equity
X_VOLUME_CONSTANT // Constant Value
};
//
bool IsValid(ENUM_X_VOLUME_SELECT_TYPE value)
{
//
bool result = false;
//
result = value != X_VOLUME_NONE;
//
return result;
}
//
string ToString(ENUM_X_VOLUME_SELECT_TYPE value)
{
//
string result = NULL;
//
result = EnumToString(value);
//
return result;
}
//
// Implementation ...
class XCVolume : public XCBase
{
//
// Public ...
public:
//
// Props ...
XCAccount *account;
//
// Constructor ...
XCVolume()
{
//
account = new XCAccount();
//
Default();
}
//
// Deconstructor ...
~XCVolume()
{
//
ZeroMemory(account);
}
//
bool Init(
ENUM_X_VOLUME_SELECT_TYPE _SelectType,
double _StaticVolume,
double _DynamicVolumeStepBalance,
double _DynamicVolumeStepVolume,
double _ConstantRiskBalance,
double _ConstantPercent,
double _ConstantBalance //
)
{
//
bool result = false;
//
mVolumeType = _SelectType;
mStaticVolume = _StaticVolume;
mConstantPercent = _ConstantPercent;
mConstantBalance = _ConstantBalance;
mConstantRiskBalance = _ConstantRiskBalance;
mDynamicVolumeStepVolume = _DynamicVolumeStepVolume;
mDynamicVolumeStepBalance = _DynamicVolumeStepBalance;
//
result =
//
CanUseStaticVolume() ||
CanUseDynamicVolume() ||
CanUseConstantRiskBalance() ||
CanUseConstantBalancePercent()
//
;
//
return result;
}
//
// Prperties ...
/**
* Get Volume Calculating Method ...
*
* @return (ENUM_X_VOLUME_SELECT_TYPE)
*/
ENUM_X_VOLUME_SELECT_TYPE VolumeType()
{
return mVolumeType;
}
/**
* Set Volume Calculating Method ...
*
* @param value: ENUM_X_VOLUME_SELECT_TYPE member ...
*/
void VolumeType(ENUM_X_VOLUME_SELECT_TYPE value)
{
mVolumeType = value;
}
/**
* Get Static Volume ...
*
* @return ( double )
*/
double StaticVolume()
{
return mStaticVolume;
}
/**
* Set Static Volume ...
*
* @param value: double
*/
void StaticVolume(double value)
{
//
value = NormalizeDouble(value, 0.01, 1);
//
mStaticVolume = value;
}
/**
* Get Dynamic Volume Step Balance ...
* used to Calculate Final Lottage ...
*
* @return ( double )
*/
double DynamicVolumeStepBalance()
{
return mDynamicVolumeStepBalance;
}
/**
* Set Dynamic Volume Step Balance ...
* used to Calculate Final Lottage ...
*
* @param value: Argument 1
*/
void DynamicVolumeStepBalance(double value)
{
//
value = NormalizeDouble(value, 0);
//
mDynamicVolumeStepBalance = value;
}
/**
* Get Dynamic Volume Step Volume ...
* used to Calculate Final Lottage ...
* how much increase Final Volume based oBalance Step ...
*
* @return ( double )
*/
double DynamicVolumeStepVolume()
{
return mDynamicVolumeStepVolume;
}
/**
* Get Dynamic Volume Step Volume ...
* used to Calculate Final Lottage ...
* how much increase Final Volume based oBalance Step ...
*
* @param value: double
*/
void DynamicVolumeStepVolume(double value)
{
//
value = NormalizeDouble(value, 0.01, 0.1);
//
mDynamicVolumeStepVolume = value;
}
/**
* Get Constant Balance Use for Dyamic Volume Calculation ...
*
* @return ( double )
*/
double ConstantBalance()
{
return mConstantBalance;
}
/**
* Set Constant Balance Use for Dyamic Volume Calculation ...
*
* @param value: Argument 1
*/
void ConstantBalance(double value)
{
//
value = NormalizeDouble(value, 0);
//
mConstantBalance = value;
}
/**
* Get Constant Risk Value Based on Account Currency ...
*
* @return ( double )
*/
double ConstantRiskBalance()
{
return mConstantRiskBalance;
}
/**
* Get Constant Risk Value Based on Account Currency ...
*
* @param value: double
*/
void ConstantRiskBalance(double value)
{
//
value = NormalizeDouble(value, 0);
//
mConstantRiskBalance = value;
}
/**
* Get Constant Percent Based On Selected Balance ...
*
* @return ( double )
*/
double ConstantPercent()
{
return mConstantPercent;
}
/**
* Set Constant Percent Based On Selected Balance ...
*
* @param value: double ...
*/
void ConstantPercent(double value)
{
//
value = NormalizeDouble(value, 0, 100);
//
mConstantPercent = value;
}
//
// Tools ...
/**
* Retrieve Balance based on Provided Volume Type ...
*
* @return ( double )
*/
double GetBalance()
{
//
double result = 0;
//
if (!IsValid(mVolumeType))
{
return result;
}
//
if (mConstantBalance > 0 &&
mVolumeType == X_VOLUME_CONSTANT)
{
result = mConstantBalance;
}
else if (mVolumeType == X_VOLUME_CURRENT)
{
result = account.GetBalance();
}
else if (mVolumeType == X_VOLUME_EQUITY)
{
result = account.GetEquity();
}
//
return result;
}
/**
* Retrieve Balance based on Provided Volume Type ...
*
* @return ( double )
*/
double GetBalance(ENUM_X_VOLUME_SELECT_TYPE type)
{
//
double result = 0;
//
if (!IsValid(type))
{
return result;
}
//
if (mConstantBalance > 0 &&
type == X_VOLUME_CONSTANT)
{
result = mConstantBalance;
}
else if (type == X_VOLUME_CURRENT)
{
result = account.GetBalance();
}
else if (type == X_VOLUME_EQUITY)
{
result = account.GetEquity();
}
//
return result;
}
/**
* Calculate Volume Based On Given Configuration ...
*
* @param symbol: string, Trading Symbol ...
* @param entry: double, Entry Price ...
* @param sl: double, Stop Loss Price ...
*
* @return ( double )
*/
double CalculateVolume(
string symbol,
double entry,
double sl //
)
{
//
double result = X_MIN_VOLUME;
//
bool has = false;
//
// Validate Args ...
has =
sl > 0 &&
entry > 0 &&
IsValid(symbol);
if (!has)
{
return result;
}
//
// Retrieve Balance Type ...
double balance = GetBalance();
double points = GetPoints(symbol);
double riskPrice = MathAbs(entry - sl);
double riskInPoints = riskPrice / points;
//
has = CanUseStaticVolume();
if (has)
{
result = mStaticVolume;
}
//
has = CanUseDynamicVolume();
if (has)
{
//
double multiplier = balance / mDynamicVolumeStepBalance;
if (multiplier < 0)
{
multiplier = 1;
}
//
result = multiplier * mDynamicVolumeStepVolume;
}
//
has = CanUseConstantRiskBalance();
if (has)
{
//
result = account.CalculateVolume(
symbol,
mConstantRiskBalance,
riskInPoints //
);
}
//
has = CanUseConstantBalancePercent();
if (has)
{
//
double riskAmountPerBalance = (mConstantPercent * balance) / 100;
//
result = account.CalculateVolume(
symbol,
riskAmountPerBalance,
riskInPoints //
);
}
//
if (result < X_MIN_VOLUME)
{
result = X_MIN_VOLUME;
}
//
// Normalize Volume ...
result = NormalizeVolume(result, symbol);
//
return result;
}
/**
* Calculate Volume Based On Given Configuration ...
*
* @param signal: XSignal instance reference, provided required Data ...
*
* @return ( double )
*/
double CalculateVolume(XSignal &signal)
{
//
double result = X_MIN_VOLUME;
//
if (!signal.IsValid())
{
return result;
}
//
result = CalculateVolume(
signal.symbol,
signal.entry,
signal.sl //
);
//
return result;
}
/**
* Calculate Specified Percent of Selected Balance for Volume ...
*
* @param percent: double, percent of Balance Risking ...
* @param symbol: string, Trading Symbol ...
* @param entry: double, Entry Price ...
* @param sl: double Stop Loss Price ...
*
* @return ( double )
*/
double CalculateVolume(
ENUM_X_VOLUME_SELECT_TYPE selectType,
double percent,
string symbol,
double entry,
double sl //
)
{
//
double result = X_MIN_VOLUME;
//
bool has = false;
//
// Validate Args ...
has =
sl > 0 &&
entry > 0 &&
percent > 0 &&
IsValid(symbol) &&
IsValid(selectType) &&
(selectType == X_VOLUME_EQUITY ||
selectType == X_VOLUME_CURRENT);
if (!has)
{
return result;
}
//
// Retrieve Balance Type ...
double points = GetPoints(symbol);
double riskPrice = MathAbs(entry - sl);
double balance = GetBalance(selectType);
double riskInPoints = riskPrice / points;
//
double riskAmountPerBalance = (percent * balance) / 100;
//
result = account.CalculateVolume(
symbol,
riskAmountPerBalance,
riskInPoints //
);
//
return result;
}
//
// Protected ...
protected:
//
// Tools ...
/**
* Set Default Props ...
*/
void Default()
{
//
VolumeType(X_VOLUME_STATIC);
StaticVolume(0.01);
//
ConstantBalance(0);
ConstantPercent(0);
ConstantRiskBalance(0);
//
DynamicVolumeStepBalance(0);
DynamicVolumeStepVolume(0.01);
}
/**
* Check Configuration is Valid For Static Volume ...
*
* @return ( bool )
*/
bool CanUseStaticVolume()
{
//
bool result = false;
//
result = IsValid(mVolumeType);
if (!result)
{
return result;
}
//
// Static Volume ...
result =
//
mVolumeType == X_VOLUME_STATIC &&
mStaticVolume > 0 &&
//
mDynamicVolumeStepBalance == 0 &&
//
mConstantBalance == 0 &&
mConstantPercent == 0 &&
mConstantRiskBalance == 0
//
;
//
return result;
}
/**
* Check Configuration is Valid For Dynamic Volume ...
*
* @return ( bool )
*/
bool CanUseDynamicVolume()
{
//
bool result = false;
//
result = IsValid(mVolumeType);
if (!result)
{
return result;
}
//
result =
//
(mVolumeType == X_VOLUME_CURRENT ||
mVolumeType == X_VOLUME_EQUITY ||
(mVolumeType == X_VOLUME_CONSTANT &&
mConstantBalance > 0)) &&
//
mDynamicVolumeStepBalance > 0 &&
mDynamicVolumeStepVolume > 0 &&
//
mStaticVolume == 0 &&
mConstantPercent == 0 &&
mConstantRiskBalance == 0
//
;
//
return result;
}
/**
* Check Configuration is Valid For Constant Risk Balance ...
*
* @return ( bool )
*/
bool CanUseConstantRiskBalance()
{
//
bool result = false;
//
result = IsValid(mVolumeType);
if (!result)
{
return result;
}
//
result =
//
(mVolumeType == X_VOLUME_CURRENT ||
mVolumeType == X_VOLUME_EQUITY ||
(mVolumeType == X_VOLUME_CONSTANT &&
mConstantBalance > 0)) &&
//
mConstantRiskBalance > 0 &&
//
mStaticVolume == 0 &&
mConstantPercent == 0 &&
mDynamicVolumeStepBalance == 0
//
;
//
return result;
}
/**
* Check Configuration is Valid For Constant Risk Percent ...
*
* @return ( bool )
*/
bool CanUseConstantBalancePercent()
{
//
bool result = false;
//
result = IsValid(mVolumeType);
if (!result)
{
return result;
}
//
result =
//
(mVolumeType == X_VOLUME_CURRENT ||
mVolumeType == X_VOLUME_EQUITY ||
(mVolumeType == X_VOLUME_CONSTANT &&
mConstantBalance > 0)) &&
//
mConstantPercent > 0 &&
//
mStaticVolume == 0 &&
mConstantRiskBalance == 0 &&
mDynamicVolumeStepBalance == 0
//
;
//
return result;
}
//
// Private ...
private:
//
// Props ...
//
ENUM_X_VOLUME_SELECT_TYPE mVolumeType; // Balance Type ...
//
// Static Volume ...
double mStaticVolume; // Static Volume ...
//
double mDynamicVolumeStepBalance; // Step of Balance ...
double mDynamicVolumeStepVolume; // Step of Volume ...
//
double mConstantBalance; // Constant Balance ....
double mConstantRiskBalance; // Constant Risk Balance ...
double mConstantPercent; // Constant Percent of Balance ...
};
//