RealPivot free

by cysecsbin.01 in category Volatility at 13/10/2019
Description

Follow my cTrader Telegram group at https://t.me/cTraderCommunity; everyone can talk about cTrader indicators and algorithm without restrictions, though it is not allowed to spam commercial indicators to sell them. There's also a Discord Server now @ https://discord.gg/5GAPMtp and an Instagram page https://www.instagram.com/ctrader_community/

This is just a different take from Carlos' (https://ctrader.com/algos/indicators/show/2017) pivot points, it's a monthly-weekly-daily classic pivots but with no output series associated, so pivot lines cannot be select by accident.

There's also a bungh of additional features, like the option to draw only certain levels or adding an area between the 2nd and 3rd pivots, just graphical stuff

UPDATE:added other types of pivot, thanks to Roman_Volodko https://ctrader.com/users/profile/Roman_Volodko for help and suggestions received

Added 12Hour TF as well as an option to force the calculation using Closing price instead of typical price

N.B. Code is super compact and probably hard to read for the majority of programmers, i know, i like it this way, sorry.

ERRATA CORRIGE: The indicator has been updated as of 16 october 2019 due to incorrect formulas for r3 and s3 standard pivot

UPDATE: 25/10/2019 indicator now includes 5th and 6th camarilla pivot, and a function to limit the number of historical pivots drawn. The TimeFrame limitation has been removed

Notification Publishing copyrighted material is strictly prohibited. If you believe there is copyrighted material in this section you may use the Copyright Infringement Notification form to submit a claim.
Formula / Source Code
Language: C#
Trading Platform: cAlgocTrader
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 RealPivot : Indicator
    {
        [Parameter("Pivot TF", Group = "Pivots", DefaultValue = PivotTF.Daily)]
        public PivotTF TF { get; set; }
        [Parameter("Pivot Type", Group = "Pivots", DefaultValue = PivotType.Camarilla)]
        public PivotType Type { get; set; }

        [Parameter("Resistances Color", Group = "Style", DefaultValue = "Red")]
        public string RColor { get; set; }
        [Parameter("Supports Color", Group = "Style", DefaultValue = "Lime")]
        public string SColor { get; set; }
        [Parameter("Opacity", Group = "Style", DefaultValue = 100, MaxValue = 100, MinValue = 0)]
        public int Opacity { get; set; }
        [Parameter("Thickness", Group = "Style", DefaultValue = 1, MaxValue = 5, MinValue = 0)]
        public int Thickness { get; set; }

        [Parameter("Draw Labels", Group = "Labels", DefaultValue = true)]
        public bool Labels { get; set; }

        [Parameter("Draw 1s", Group = "Drawing Settings", DefaultValue = true)]
        public bool Draw1s { get; set; }
        [Parameter("Draw 2s", Group = "Drawing Settings", DefaultValue = true)]
        public bool Draw2s { get; set; }
        [Parameter("Draw 3s", Group = "Drawing Settings", DefaultValue = true)]
        public bool Draw3s { get; set; }
        [Parameter("Draw 4s", Group = "Drawing Settings", DefaultValue = true)]
        public bool Draw4s { get; set; }
        [Parameter("Draw 5s", Group = "Drawing Settings", DefaultValue = false)]
        public bool Draw5s { get; set; }
        [Parameter("Draw 6s", Group = "Drawing Settings", DefaultValue = false)]
        public bool Draw6s { get; set; }

        [Parameter("Draw 2-3 Area", Group = "Drawing Settings", DefaultValue = false)]
        public bool DrawArea { get; set; }

        [Parameter("Force Pivot on Close", Group = "Additional Features", DefaultValue = false)]
        public bool PivotOnClose { get; set; }

        [Parameter("n° Historical Pivots (-1 for all)", Group = "Pivots", DefaultValue = -1)]
        public int HistPivot { get; set; }

        public enum PivotTF
        {
            Hour,
            Hour4,
            Hour12,
            Daily,
            Weekly,
            Monthly
        }

        public enum PivotType
        {
            Standard,
            Fibonacci,
            Camarilla,
            Woodie,
            Demark
        }

        private Color SupportColor, ResistanceColor;
        private MarketSeries Series;

        protected override void Initialize()
        {
            Opacity = (int)(255 * 0.01 * Opacity);
            SupportColor = Color.FromArgb(Opacity, Color.FromName(SColor).R, Color.FromName(SColor).G, Color.FromName(SColor).B);
            ResistanceColor = Color.FromArgb(Opacity, Color.FromName(RColor).R, Color.FromName(RColor).G, Color.FromName(RColor).B);
            Series = TF == PivotTF.Hour ? MarketData.GetSeries(TimeFrame.Hour) : TF == PivotTF.Hour4 ? MarketData.GetSeries(TimeFrame.Hour4) : TF == PivotTF.Hour12 ? MarketData.GetSeries(TimeFrame.Hour12) : TF == PivotTF.Daily ? MarketData.GetSeries(TimeFrame.Daily) : TF == PivotTF.Weekly ? MarketData.GetSeries(TimeFrame.Weekly) : MarketData.GetSeries(TimeFrame.Monthly);
        }

        public override void Calculate(int index)
        {
            int index2 = Series.OpenTime.GetIndexByTime(MarketSeries.OpenTime[index]);

            if (Series.Close.Count - index2 > HistPivot && HistPivot != -1)
                return;

            int candleColor = (int)(Math.Abs(Series.Close[index2 - 1] - Series.Open[index2 - 1]) / (Series.Close[index2 - 1] - Series.Open[index2 - 1]));
            double pivot = Type == PivotType.Woodie ? (Series.High[index2 - 1] + Series.Low[index2 - 1] + 2 * Series.Open[index2]) / 4 : Type == PivotType.Demark ? (candleColor == 1 ? Series.High[index2 - 1] * 2 + Series.Low[index2 - 1] + Series.Close[index2 - 1] : candleColor == -1 ? Series.High[index2 - 1] + Series.Low[index2 - 1] * 2 + Series.Close[index2 - 1] : Series.High[index2 - 1] + Series.Low[index2 - 1] + Series.Close[index2 - 1] * 2) : (Series.High[index2 - 1] + Series.Low[index2 - 1] + Series.Close[index2 - 1]) / 3;
            if (PivotOnClose)
                pivot = Series.Close[index2 - 1];
            double range = Series.High[index2 - 1] - Series.Low[index2 - 1];
            double s1 = Type == PivotType.Standard ? 2 * pivot - Series.High[index2 - 1] : Type == PivotType.Fibonacci ? pivot - range * 0.382 : Type == PivotType.Camarilla ? Series.Close[index2 - 1] - 0.0916 * range : Type == PivotType.Woodie ? 2 * pivot - Series.High[index2 - 1] : Type == PivotType.Demark ? pivot / 2 - Series.High[index2 - 1] : 0;
            double r1 = Type == PivotType.Standard ? 2 * pivot - Series.Low[index2 - 1] : Type == PivotType.Fibonacci ? pivot + range * 0.382 : Type == PivotType.Camarilla ? Series.Close[index2 - 1] + 0.0916 * range : Type == PivotType.Woodie ? 2 * pivot - Series.Low[index2 - 1] : Type == PivotType.Demark ? pivot / 2 - Series.Low[index2 - 1] : 0;
            double s2 = Type == PivotType.Standard ? pivot - range : Type == PivotType.Fibonacci ? pivot - range * 0.618 : Type == PivotType.Camarilla ? Series.Close[index2 - 1] - 0.183 * range : Type == PivotType.Woodie ? pivot - range : 0;
            double r2 = Type == PivotType.Standard ? pivot + range : Type == PivotType.Fibonacci ? pivot + range * 0.618 : Type == PivotType.Camarilla ? Series.Close[index2 - 1] + 0.183 * range : Type == PivotType.Woodie ? pivot + range : 0;
            double s3 = Type == PivotType.Standard ? s1 - range : Type == PivotType.Fibonacci ? pivot - range : Type == PivotType.Camarilla ? Series.Close[index2 - 1] - 0.275 * range : Type == PivotType.Woodie ? Series.Low[index2 - 1] - 2 * (Series.High[index2 - 1] - pivot) : 0;
            double r3 = Type == PivotType.Standard ? r1 + range : Type == PivotType.Fibonacci ? pivot + range : Type == PivotType.Camarilla ? Series.Close[index2 - 1] + 0.275 * range : Type == PivotType.Woodie ? Series.High[index2 - 1] + 2 * (pivot - Series.Low[index2 - 1]) : 0;
            double s4 = Type == PivotType.Woodie ? s3 - range : Series.Close[index2 - 1] - 0.55 * range;
            double r4 = Type == PivotType.Woodie ? r3 + range : Series.Close[index2 - 1] + 0.55 * range;
            //EXPERIMENTAL PIVOTS
            double r5 = Series.High[index2 - 1] * Series.Close[index2 - 1] / Series.Low[index2 - 1];
            double s5 = 2 * Series.Close[index2 - 1] - r5;
            double r6 = r5 + 1.618 * (r5 - r4);
            double s6 = 2 * Series.Close[index2 - 1] - r6;
            /////////////////////
            DateTime OpenTime = Series.OpenTime[index2];
            DateTime EndTime = TF == PivotTF.Hour ? OpenTime.AddHours(1) : TF == PivotTF.Hour4 ? OpenTime.AddHours(4) : TF == PivotTF.Hour12 ? OpenTime.AddHours(12) : TF == PivotTF.Daily ? OpenTime.AddDays(1) : TF == PivotTF.Weekly ? OpenTime.AddDays(7) : OpenTime.AddMonths(1);

            pivot /= Type == PivotType.Demark ? 4 : 1;

            Chart.DrawTrendLine("Pivot " + OpenTime, OpenTime, pivot, EndTime, pivot, Color.FromArgb(Opacity, 255, 255, 255), Thickness, LineStyle.Solid);
            if (Draw1s)
                Chart.DrawTrendLine("S1 " + OpenTime, OpenTime, s1, EndTime, s1, SupportColor, Thickness, LineStyle.Dots);
            if (Draw1s)
                Chart.DrawTrendLine("R1 " + OpenTime, OpenTime, r1, EndTime, r1, ResistanceColor, Thickness, LineStyle.Dots);
            if (Type != PivotType.Demark)
            {
                if (Draw2s)
                    Chart.DrawTrendLine("S2 " + OpenTime, OpenTime, s2, EndTime, s2, SupportColor, Thickness, LineStyle.DotsRare);
                if (Draw3s)
                    Chart.DrawTrendLine("S3 " + OpenTime, OpenTime, s3, EndTime, s3, SupportColor, Thickness, LineStyle.DotsVeryRare);
                if (Draw2s)
                    Chart.DrawTrendLine("R2 " + OpenTime, OpenTime, r2, EndTime, r2, ResistanceColor, Thickness, LineStyle.DotsRare);
                if (Draw3s)
                    Chart.DrawTrendLine("R3 " + OpenTime, OpenTime, r3, EndTime, r3, ResistanceColor, Thickness, LineStyle.DotsVeryRare);
            }
            if (Type == PivotType.Camarilla || Type == PivotType.Woodie)
                if (Draw4s)
                {
                    Chart.DrawTrendLine("R4 " + OpenTime, OpenTime, r4, EndTime, r4, ResistanceColor, Thickness, LineStyle.DotsVeryRare);
                    Chart.DrawTrendLine("S4 " + OpenTime, OpenTime, s4, EndTime, s4, SupportColor, Thickness, LineStyle.DotsVeryRare);
                }
            if (Type == PivotType.Camarilla)
            {
                if (Draw5s)
                {
                    Chart.DrawTrendLine("R5 " + OpenTime, OpenTime, r5, EndTime, r5, ResistanceColor, Thickness, LineStyle.DotsVeryRare);
                    Chart.DrawTrendLine("S5 " + OpenTime, OpenTime, s5, EndTime, s5, SupportColor, Thickness, LineStyle.DotsVeryRare);
                }
                if (Draw6s)
                {
                    Chart.DrawTrendLine("R6 " + OpenTime, OpenTime, r6, EndTime, r6, ResistanceColor, Thickness, LineStyle.DotsVeryRare);
                    Chart.DrawTrendLine("S6 " + OpenTime, OpenTime, s6, EndTime, s6, SupportColor, Thickness, LineStyle.DotsVeryRare);
                }
            }

            if (DrawArea)
            {
                Chart.DrawRectangle("R Area " + OpenTime, OpenTime, r2, EndTime, r3, Color.FromArgb(50, ResistanceColor.R, ResistanceColor.G, ResistanceColor.B)).IsFilled = true;
                Chart.DrawRectangle("S Area " + OpenTime, OpenTime, s2, EndTime, s3, Color.FromArgb(50, SupportColor.R, SupportColor.G, SupportColor.B)).IsFilled = true;
            }

            if (Labels)
            {
                string tf = " - ";
                switch (TF)
                {
                    case PivotTF.Hour:
                        tf += "H1";
                        break;
                    case PivotTF.Hour4:
                        tf += "H4";
                        break;
                    case PivotTF.Hour12:
                        tf += "H12";
                        break;
                    case PivotTF.Daily:
                        tf += "D";
                        break;
                    case PivotTF.Weekly:
                        tf += "W";
                        break;
                    case PivotTF.Monthly:
                        tf += "M";
                        break;
                }
                Chart.DrawText("Label P " + OpenTime, "P - " + Math.Round(pivot, Symbol.Digits) + tf, OpenTime, pivot, Color.FromArgb(Opacity, 255, 255, 255));
                if (Draw1s)
                    Chart.DrawText("Label S1 " + OpenTime, "S1 - " + Math.Round(s1, Symbol.Digits) + tf, OpenTime, s1, SupportColor);
                if (Draw1s)
                    Chart.DrawText("Label R1 " + OpenTime, "R1 - " + Math.Round(r1, Symbol.Digits) + tf, OpenTime, r1, ResistanceColor);
                if (Type != PivotType.Demark)
                {
                    if (Draw2s)
                        Chart.DrawText("Label S2 " + OpenTime, "S2 - " + Math.Round(s2, Symbol.Digits) + tf, OpenTime, s2, SupportColor);
                    if (Draw3s)
                        Chart.DrawText("Label S3 " + OpenTime, "S3 - " + Math.Round(s3, Symbol.Digits) + tf, OpenTime, s3, SupportColor);
                    if (Draw2s)
                        Chart.DrawText("Label R2 " + OpenTime, "R2 - " + Math.Round(r2, Symbol.Digits) + tf, OpenTime, r2, ResistanceColor);
                    if (Draw3s)
                        Chart.DrawText("Label R3 " + OpenTime, "R3 - " + Math.Round(r3, Symbol.Digits) + tf, OpenTime, r3, ResistanceColor);
                }
                if (Type == PivotType.Camarilla || Type == PivotType.Woodie)
                    if (Draw4s)
                    {
                        Chart.DrawText("Label S4 " + OpenTime, "S4 - " + Math.Round(s4, Symbol.Digits) + tf, OpenTime, s4, SupportColor);
                        Chart.DrawText("Label R4 " + OpenTime, "R4 - " + Math.Round(r4, Symbol.Digits) + tf, OpenTime, r4, ResistanceColor);
                    }
                if (Type == PivotType.Camarilla)
                {
                    if (Draw5s)
                    {
                        Chart.DrawText("Label S5 " + OpenTime, "S5 - " + Math.Round(s5, Symbol.Digits) + tf, OpenTime, s5, SupportColor);
                        Chart.DrawText("Label R5 " + OpenTime, "R5 - " + Math.Round(r5, Symbol.Digits) + tf, OpenTime, r5, ResistanceColor);
                    }
                    if (Draw6s)
                    {
                        Chart.DrawText("Label S6 " + OpenTime, "S6 - " + Math.Round(s6, Symbol.Digits) + tf, OpenTime, s6, SupportColor);
                        Chart.DrawText("Label R6 " + OpenTime, "R6 - " + Math.Round(r6, Symbol.Digits) + tf, OpenTime, r6, ResistanceColor);
                    }
                }
            }
        }

        private bool CheckError()
        {
            return TF == PivotTF.Hour && TimeFrame >= TimeFrame.Hour ? true : TF == PivotTF.Hour4 && TimeFrame >= TimeFrame.Hour4 ? true : TF == PivotTF.Daily && TimeFrame >= TimeFrame.Daily ? true : TF == PivotTF.Weekly && TimeFrame >= TimeFrame.Weekly ? true : false;
        }

    }
}
Comments

louisbrowne - September 12, 2021 @ 23:41

Insanely good pivot point plugin, well done

firemyst - June 24, 2022 @ 05:21

This is a great indicator. However, it would be a lot more efficient and less resource intensive if the code was updated to only calculate the pivot points when the "index" for the pivot time frame that's selected changes.

For example, if I'm on the 4-hour time frame, and have the daily pivot point selected, why does it have to be calculated on every tick? It's not going to change until the next day.

I would suggest implementing logic where you have a global class variable called something like "int previousIndex", and when the current pivot timeframe index is > previousIndex in the Calculate method:

1) run the calculations

2) set previousIndex to the current pivot time frame index.

3) until current pivot time frame index is > previousIndex, you can skip all the logic in Calculate.

Boom!

You just saved all the CPU calculations having to be done every tick and your indicator just became that much faster. :-)

0