Category Trend  Published on 06/06/2023

Corrected Average indicator

Description

The indicator CA (Corrected Average), also known as the Optimal Moving Average, offers the benefit of ensuring that the current value of the time series exceeds the current threshold, which is based on volatility. This ensures that the indicator line accurately tracks the price and helps to avoid false signals in the trend.

Additionally, it helps in identifying trade sentiment zones.


using System;
using cAlgo.API;
using cAlgo.API.Internals;
using cAlgo.API.Indicators;
using cAlgo.Indicators;

namespace cAlgo
{
    [Indicator(IsOverlay = true, TimeZone = TimeZones.UTC, AccessRights = AccessRights.None)]
    public class mCorrectedAverage : Indicator
    {
        [Parameter("Period (14)", DefaultValue = 14, MinValue = 1)]
        public int inpPeriod { get; set; }
        [Parameter("Data Source (close)", DefaultValue = enumPriceTypes.Close)]
        public enumPriceTypes inpPriceType { get; set; }
        [Parameter("Smooth Type (sma)", DefaultValue = MovingAverageType.Simple)]
        public MovingAverageType inpSmoothType { get; set; }

        [Output("CorrectedAverage", LineColor = "Black", PlotType = PlotType.Line, Thickness = 1)]
        public IndicatorDataSeries outCorrectedAverage { get; set; }
        [Output("CorrectedAverageSignal", LineColor = "Transparent", PlotType = PlotType.Line, Thickness = 1)]
        public IndicatorDataSeries outCorrectedAverageSignal { get; set; }
        [Output("CorrectedAverageBullish", LineColor = "Green", PlotType = PlotType.DiscontinuousLine, Thickness = 2)]
        public IndicatorDataSeries outCorrectedAverageBullish { get; set; }
        [Output("CorrectedAverageBearish", LineColor = "Red", PlotType = PlotType.DiscontinuousLine, Thickness = 2)]
        public IndicatorDataSeries outCorrectedAverageBearish { get; set; }

        private IndicatorDataSeries _price, _pricesmooth, _corravg, _polarity;
        private MovingAverage _smooth;
        private StandardDeviation _stddev;
        private double _delta, _coef;


        protected override void Initialize()
        {
            _price = CreateDataSeries();
            _pricesmooth = CreateDataSeries();
            _smooth = Indicators.MovingAverage(_price, inpPeriod, inpSmoothType);
            _stddev = Indicators.StandardDeviation(_price, inpPeriod, inpSmoothType);
            _corravg = CreateDataSeries();
            _polarity = CreateDataSeries();
        }

        public override void Calculate(int i)
        {
            switch(inpPriceType)
            {
                case enumPriceTypes.Open:
                    _price[i] = Bars.OpenPrices[i];
                    break;
                case enumPriceTypes.Close:
                    _price[i] = Bars.ClosePrices[i];
                    break;
                case enumPriceTypes.High:
                    _price[i] = Bars.HighPrices[i];
                    break;
                case enumPriceTypes.Low:
                    _price[i] = Bars.LowPrices[i];
                    break;
                case enumPriceTypes.Median:
                    _price[i] = Bars.MedianPrices[i];
                    break;
                case enumPriceTypes.Typical:
                    _price[i] = Bars.TypicalPrices[i];
                    break;
                case enumPriceTypes.Weighted:
                    _price[i] = Bars.WeightedPrices[i];
                    break;
                default:
                    _price[i] = Bars.ClosePrices[i];
                    break;
            }
        
            _pricesmooth[i] = i>inpPeriod ? _smooth.Result[i] : Bars.ClosePrices[i];
            _delta = i>1 ? ((_corravg[i-1] - _pricesmooth[i]) * (_corravg[i-1] - _pricesmooth[i])) : Bars.ClosePrices[i] - Bars.TypicalPrices[i];
            _coef = (_delta > _stddev.Result[i] * _stddev.Result[i] && _delta != 0 ? 1 - (_stddev.Result[i] * _stddev.Result[i]) / _delta : 0);
            _corravg[i] = i>1 ? _corravg[i-1] + _coef * (_pricesmooth[i] - _corravg[i-1]) : Bars.ClosePrices[i];
            _polarity[i] = i>1 && _corravg[i] > _corravg[i-1] ? +1 : i>1 && _corravg[i] < _corravg[i-1] ? -1 : i>1 ? _polarity[i-1] : +1;

            outCorrectedAverage[i] = _corravg[i];
            outCorrectedAverageSignal[i] = _polarity[i] > 0 ? _corravg[i] - Symbol.PipSize : _polarity[i] < 0 ? _corravg[i] + Symbol.PipSize : _corravg[i];
            outCorrectedAverageBullish[i] = _polarity[i] == +1 ?  _corravg[i] : double.NaN;
            outCorrectedAverageBearish[i] = _polarity[i] == -1 ?  _corravg[i] : double.NaN;
        }
    }

    public enum enumPriceTypes
    {
        Open,
        Close,
        High,
        Low,
        Median,
        Typical,
        Weighted
    }
}

mfejza's avatar
mfejza

Joined on 25.01.2022

  • Distribution: Free
  • Language: C#
  • Trading platform: cTrader Automate
  • File name: mCorrectedAverage.algo
  • Rating: 5
  • Installs: 548
Comments
Log in to add a comment.
mfejza's avatar
mfejza · 7 months ago

This custom indicator is a lag indicator. To use it properly, you should consider the lagging information for further decision-making as a price action confirmation. 

This indicator is also considered a price correction zone when the price is opposite to the indicator signal. 

Implementing a cBot for this indicator is easy, but the most significant problem is the method of managing positions.

Here you have idea how to use it, inside cBot.

using System;
using cAlgo.API;
using cAlgo.API.Internals;
using cAlgo.API.Indicators;
using cAlgo.Indicators;

namespace cAlgo.Robots
{
    [Robot(AccessRights = AccessRights.None)]
    public class NewcBotCA : Robot
    {
        [Parameter("Period (14)", DefaultValue = 14, MinValue = 1)]
        public int inpPeriod { get; set; }
        [Parameter("Data Source (close)", DefaultValue = enumPriceTypes.Close)]
        public enumPriceTypes inpPriceType { get; set; }
        [Parameter("Smooth Type (sma)", DefaultValue = MovingAverageType.Simple)]
        public MovingAverageType inpSmoothType { get; set; }
        
        private mCorrectedAverage _iCA;

        protected override void OnStart()
        {
            _iCA = Indicators.GetIndicator<mCorrectedAverage>(inpPeriod, inpPriceType, inpSmoothType);
        }

        protected override void OnTick()
        {
            if(_iCA.outCorrectedAverage.LastValue > _iCA.outCorrectedAverageSignal.LastValue)
            {
                //Long zone
            }
            
            if(_iCA.outCorrectedAverage.LastValue < _iCA.outCorrectedAverageSignal.LastValue)
            {
                //Short zone
            }
        }

        protected override void OnStop()
        {
            _iCA = null;
        }
    }
}
SH
sharcom · 7 months ago

I would like to add telegram alerts , and even trading program . can any programmer to make it?