//+------------------------------------------------------------------+ //| StochasticFast_Calculator.mqh| //| Calculation engine for Standard and Heikin Ashi Fast Stochastic. | //| Copyright 2025, xxxxxxxx | //+------------------------------------------------------------------+ #property copyright "Copyright 2025, xxxxxxxx" #include //+==================================================================+ //| | //| CLASS 1: CStochasticFastCalculator (Base Class) | //| | //+==================================================================+ class CStochasticFastCalculator { protected: int m_k_period, m_d_period; ENUM_MA_METHOD m_d_ma_type; double m_src_high[], m_src_low[], m_src_close[]; double Highest(int period, int current_pos); double Lowest(int period, int current_pos); virtual bool PrepareSourceData(int rates_total, const double &open[], const double &high[], const double &low[], const double &close[]); public: CStochasticFastCalculator(void) {}; virtual ~CStochasticFastCalculator(void) {}; bool Init(int k_p, int d_p, ENUM_MA_METHOD d_ma); void Calculate(int rates_total, const double &open[], const double &high[], const double &low[], const double &close[], double &k_buffer[], double &d_buffer[]); }; //+------------------------------------------------------------------+ //| CStochasticFastCalculator: Initialization | //+------------------------------------------------------------------+ bool CStochasticFastCalculator::Init(int k_p, int d_p, ENUM_MA_METHOD d_ma) { m_k_period = (k_p < 1) ? 1 : k_p; m_d_period = (d_p < 1) ? 1 : d_p; m_d_ma_type = d_ma; return true; } //+------------------------------------------------------------------+ //| CStochasticFastCalculator: Main Calculation Method (Shared Logic)| //+------------------------------------------------------------------+ void CStochasticFastCalculator::Calculate(int rates_total, const double &open[], const double &high[], const double &low[], const double &close[], double &k_buffer[], double &d_buffer[]) { if(rates_total <= m_k_period + m_d_period) return; if(!PrepareSourceData(rates_total, open, high, low, close)) return; //--- STEP 1: Calculate %K (Fast %K) for(int i = m_k_period - 1; i < rates_total; i++) { double highest_h = Highest(m_k_period, i); double lowest_l = Lowest(m_k_period, i); double range = highest_h - lowest_l; if(range > 0) k_buffer[i] = (m_src_close[i] - lowest_l) / range * 100.0; else k_buffer[i] = (i > 0) ? k_buffer[i-1] : 50.0; } //--- STEP 2: Calculate %D (Signal Line) by smoothing %K int d_start = m_k_period + m_d_period - 2; for(int i = d_start; i < rates_total; i++) { switch(m_d_ma_type) { case MODE_EMA: case MODE_SMMA: if(i == d_start) { double sum=0; for(int j=0; j0) d_buffer[i]=sum/w_sum;} break; default: {double sum=0; for(int j=0; j m_src_low[index]) res = m_src_low[index]; } return(res); } //+==================================================================+ //| | //| CLASS 2: CStochasticFastCalculator_HA (Heikin Ashi) | //| | //+==================================================================+ class CStochasticFastCalculator_HA : public CStochasticFastCalculator { private: CHeikinAshi_Calculator m_ha_calculator; protected: virtual bool PrepareSourceData(int rates_total, const double &open[], const double &high[], const double &low[], const double &close[]) override; }; //+------------------------------------------------------------------+ //| CStochasticFastCalculator_HA: Prepares the HA source data. | //+------------------------------------------------------------------+ bool CStochasticFastCalculator_HA::PrepareSourceData(int rates_total, const double &open[], const double &high[], const double &low[], const double &close[]) { double ha_open[]; ArrayResize(ha_open, rates_total); ArrayResize(m_src_high, rates_total); ArrayResize(m_src_low, rates_total); ArrayResize(m_src_close, rates_total); m_ha_calculator.Calculate(rates_total, open, high, low, close, ha_open, m_src_high, m_src_low, m_src_close); return true; } //+------------------------------------------------------------------+ //+------------------------------------------------------------------+