Files
MyProEA/Include/Utilities.mqh

106 lines
3.1 KiB
Plaintext

//+------------------------------------------------------------------+
//| Utilities.mqh - Helper utility functions |
//| Price normalization, lot normalization, etc. |
//+------------------------------------------------------------------+
#ifndef __UTILITIES_MQH__
#define __UTILITIES_MQH__
class CUtilities
{
public:
// Normalize price to bid/ask
static double NormalizePrice(const string symbol, double price)
{
double point = SymbolInfoDouble(symbol, SYMBOL_POINT);
int digits = GetDigits(symbol);
return NormalizeDouble(price, digits);
}
// Normalize lot size to contract size step
static double NormalizeLot(const string symbol, double lot)
{
double min_lot = SymbolInfoDouble(symbol, SYMBOL_VOLUME_MIN);
double max_lot = SymbolInfoDouble(symbol, SYMBOL_VOLUME_MAX);
double lot_step = SymbolInfoDouble(symbol, SYMBOL_VOLUME_STEP);
// Guard against invalid broker volume data
if(min_lot <= 0.0 || max_lot <= 0.0 || lot_step <= 0.0 || max_lot < min_lot)
return 0.0;
// Compute precision from volume step
int precision = 0;
double s = lot_step;
const double eps = 1e-9;
while(MathAbs(MathRound(s) - s) > eps && precision < 8)
{
s *= 10.0;
precision++;
}
// Round down to nearest step
double normalized = MathFloor(lot / lot_step) * lot_step;
normalized = NormalizeDouble(normalized, precision);
// If normalized is below minimum, indicate invalid by returning 0.0
if(normalized < min_lot)
return 0.0;
// Clamp to maximum allowed (rounded down to step)
if(normalized > max_lot)
{
normalized = MathFloor(max_lot / lot_step) * lot_step;
normalized = NormalizeDouble(normalized, precision);
if(normalized < min_lot)
return 0.0;
}
return normalized;
}
// Convert points to price distance
static double PointsToPrice(const string symbol, int points)
{
double point = SymbolInfoDouble(symbol, SYMBOL_POINT);
return (double)points * point;
}
// Convert price distance to points
static int PriceToPoints(const string symbol, double price_distance)
{
double point = SymbolInfoDouble(symbol, SYMBOL_POINT);
return (int)(price_distance / point);
}
// Get point value
static double GetPoint(const string symbol)
{
return SymbolInfoDouble(symbol, SYMBOL_POINT);
}
// Get digits
static int GetDigits(const string symbol)
{
long digits = SymbolInfoInteger(symbol, SYMBOL_DIGITS);
if(digits < 0)
digits = 0;
if(digits > 255)
digits = 255;
return (int)digits;
}
// Safe double comparison with precision
static bool DoubleEquals(double a, double b, double tolerance = 0.00001)
{
return MathAbs(a - b) < tolerance;
}
// Get contract size (lot multiplier)
static double GetContractSize(const string symbol)
{
return SymbolInfoDouble(symbol, SYMBOL_TRADE_CONTRACT_SIZE);
}
};
#endif //__UTILITIES_MQH__