Indicator · Pine Script v5 · On the chart

ZigCycleBarCount 2024-2

by mikeyhu70· code credited to Trader_Morry

This indicator draws a zig-zag of swing highs and lows on the price chart using depth, deviation and backstep settings, and labels each leg with its bar count and optional price.

View on GitHub

Repaints

GitHub stars1on the repository
Pine versionv5runs as is
Lines of code195
Settings11inputs
LicenceNone statedfile: MPL-2.0
Last update6 months ago15 Apr 2026

Add It to Your TradingView Chart

  1. 1Copy the scriptPress Copy script above, or the copy button on the code below.
  2. 2Open the Pine EditorOpen a TradingView chart and choose Pine Editor at the bottom of the screen.
  3. 3Paste over the templateCreate a new indicator, select all of the template text and paste. Press Save and give it a name.
  4. 4Add it to the chartPress Add to chart, then adjust the settings with the gear icon next to its name.

Source Code

195 lines of Pine Script v5 from Cycle/ZigCycleBarCount 2024.ps, published under MPL-2.0 (file header). Keep the author's credit and licence lines when you reuse it.

ZigCycleBarCount 2024.ps
// This source code is subject to the terms of the Mozilla Public License 2.0 at https://mozilla.org/MPL/2.0/
// © Trader_Morry

//@version=5

////////
// Title 
indicator('ZigCycleBarCount 2024-2', 'ZigCyclBarCnt', true, format.price, max_labels_count=51, max_lines_count=50)


////////
// Input values 
// [
//Depth = input.int(12, 'Depth', minval=1, step=1)
//Deviation = input.int(5, 'Deviation', minval=1, step=1)
//Backstep = input.int(3, 'Backstep', minval=2, step=1)
//line_thick = input.int(2, 'Line Thickness', minval=1, maxval=4)
Depth = input.int(17, 'Depth', minval=1, step=1)
Deviation = input.int(5, 'Deviation', minval=1, step=1)
Backstep = input.int(3, 'Backstep', minval=2, step=1)
line_thick = input.int(1, 'Line Thickness', minval=1, maxval=4)
upcolor = input(#84e5f2, 'Bull Color')
dncolor = input(#ff52df, 'Bear Color')
repaint = input(true, 'Repaint Levels')
showHHLL = input(false, 'Show HH/LL')
showSwing = input.bool(false, title="show upswing and downswing (repaint only)")
price = input(true, 'Price Values')
Label_Style = input.string(title='Label Style', defval='TEXT', options=['BALLOON', 'TEXT'])
// ]

////////
// Hidden input values
// [
// ]

//////// 
// Making
// [
var last_h = 1
last_h += 1
var last_l = 1
last_l += 1
var lw = 1
var hg = 1
lw += 1
hg += 1
p_lw = -ta.lowestbars(Depth)
p_hg = -ta.highestbars(Depth)
lowing = lw == p_lw or low - low[p_lw] > Deviation * syminfo.mintick
highing = hg == p_hg or high[p_hg] - high > Deviation * syminfo.mintick
lh = ta.barssince(not highing[1])
ll = ta.barssince(not lowing[1])
down = ta.barssince(not(lh > ll)) >= Backstep
lower = low[lw] > low[p_lw]
higher = high[hg] < high[p_hg]
if lw != p_lw and (not down[1] or lower)
    lw := p_lw < hg ? p_lw : 0
    lw
if hg != p_hg and (down[1] or higher)
    hg := p_hg < lw ? p_hg : 0
    hg

line zz = na
label point = na
label state = na
x1 = down ? lw : hg
y1 = down ? low[lw] : high[hg]

var zigBarCount = 0  // once at init
var t_zigBarCount = 0  // once at init
var zigBarCount2 = 0  // once at init
var t_zigBarCount2 = 0  // once at init

if down == down[1]
    if repaint
        label.delete(point[1])
        line.delete(zz[1])
        label.delete(state[1])
    down
if down != down[1]
    if down
        last_h := hg
        last_h
    else
        last_l := lw
        last_l
    if not repaint
        nx = down ? last_h : last_l
        zigBarCount := bar_index - nx - (bar_index - (down ? last_l : last_h))
        zigBarCount2 := bar_index - nx - (bar_index - (down ? last_h : last_l))
        zz := line.new(bar_index - nx, down ? high[nx] : low[nx], bar_index - (down ? last_l : last_h), down ? low[last_l] : high[last_h], width=line_thick, color=down ? upcolor : dncolor)
        // Making text
        string _text = "\n\n"
        if showHHLL
            _text := down ? high[nx] > high[last_h[1]] ? 'HH' : 'LH' : low[nx] < low[last_l[1]] ? 'LL' : 'HL'
            _text := _text + '\n\n\n'
        if price
            //_text := down ? _text + str.tostring(high[nx]) + '\n' + 'C=' + str.tostring(zigBarCount) : _text + str.tostring(low[nx]) + '\n' + 'C=' + str.tostring(zigBarCount) 
            _text := down ? _text + str.tostring(low[x1]) + '\n' + 'C=' + str.tostring(zigBarCount) + '{ Since H:' + str.tostring(zigBarCount2) + '}' : '\n' + _text + str.tostring(high[x1]) + '\n' + 'C=' + str.tostring(zigBarCount) + '{ Since L:' + str.tostring(zigBarCount2) + '}'
        else    
            _text := _text + str.tostring(zigBarCount) 
            
        // Show label
        if Label_Style == 'BALLOON'
            point := label.new(bar_index - nx, down ? high[nx] : low[nx], _text, style=down ? label.style_label_down : label.style_label_up, size=size.small, color=down ? upcolor : dncolor, textcolor=color.black, tooltip=down ? high[nx] > high[last_h[1]] ? 'Higher High' : 'Lower High' : low[nx] < low[last_l[1]] ? 'Lower Low' : 'Higher Low')
            point
        else
            //point := label.new(bar_index - nx, na, _text, style=label.style_none, yloc=down ? yloc.abovebar : yloc.belowbar, size=size.normal, color=down ? upcolor : dncolor, textcolor=color.blue, tooltip=down ? high[nx] > high[last_h[1]] ? 'Higher High' : 'Lower High' : low[nx] < low[last_l[1]] ? 'Lower Low' : 'Higher Low')
            point := label.new(bar_index - x1, na, _text, style=label.style_none, yloc=down ? yloc.belowbar : yloc.abovebar, size=size.small, color=down ? dncolor : upcolor, textcolor=down ? upcolor : dncolor, tooltip=down ? low[x1] < low[last_l] ? 'Lower Low' : 'Higher Low' : high[x1] > high[last_h] ? 'Higher High' : 'Lower High')
            point
    down

    

if repaint
    // last_h:last_lのどちらかが0なら縦に線を引くように変更する
//    if (last_h==0) or (last_l==0)
//        zigBarCount := (bar_index-x1) - (bar_index-(down?last_h:last_l))-1
//        if zigBarCount < 0
//            zz := line.new(bar_index-(down?last_h:last_l)-1, down ? high[last_h]-1 : low[last_l]-1, bar_index-x1, y1, width=line_thick, color=down?dncolor:upcolor)
//            t_zigBarCount := 0
//        else
//            zz := line.new(bar_index-(down?last_h:last_l), down ? high[last_h]-1 : low[last_l]-1, bar_index-x1, y1, width=line_thick, color=down?dncolor:upcolor)
//            t_zigBarCount := zigBarCount
//    else
    zigBarCount := bar_index - x1 - (bar_index - (down ? last_l : last_h))
    zigBarCount2 := bar_index - x1 - (bar_index - (down ? last_h : last_l))
    if zigBarCount < 0
        if showSwing
            zz := line.new(bar_index - (down ? last_h : last_l) - 1, down ? high[last_h] : low[last_l], bar_index - x1, y1, width=line_thick, color=down ? dncolor : upcolor)
        t_zigBarCount := 0
        t_zigBarCount
    else
        if showSwing
            zz := line.new(bar_index - (down ? last_h : last_l), down ? high[last_h] : low[last_l], bar_index - x1, y1, width=line_thick, color=down ? dncolor : upcolor)
        t_zigBarCount := zigBarCount
        t_zigBarCount

    zigBarCount := t_zigBarCount

    // Making text
    string _text = "\n\n\n"
    if showHHLL
        _text := down ? low[x1] < low[last_l] ? 'LL' : 'HL' : high[x1] > high[last_h] ? 'HH' : 'LH'
        _text := _text + '\n\n'
    if price
        _text := down ? _text + str.tostring(low[x1]) + '\n' + 'C=' + str.tostring(zigBarCount) + '{ Since H:' + str.tostring(zigBarCount2) + '}' : '\n' + _text + str.tostring(high[x1]) + '\n' + 'C=' + str.tostring(zigBarCount) + '{ Since L:' + str.tostring(zigBarCount2) + '}'
    else
        _text := _text + str.tostring(zigBarCount)

    // Show label
    if Label_Style == 'BALLOON'
        point := label.new(bar_index - x1, y1, _text, style=down ? label.style_label_up : label.style_label_down, size=size.small, color=down ? dncolor : upcolor, textcolor=color.black, tooltip=down ? low[x1] < low[last_l] ? 'Lower Low' : 'Higher Low' : high[x1] > high[last_h] ? 'Higher High' : 'Lower High')
        point
    else
        point := label.new(bar_index - x1, na, _text, style=label.style_none, yloc=down ? yloc.belowbar : yloc.abovebar, size=size.small, color=down ? dncolor : upcolor, textcolor=down ? upcolor : dncolor, tooltip=down ? low[x1] < low[last_l] ? 'Lower Low' : 'Higher Low' : high[x1] > high[last_h] ? 'Higher High' : 'Lower High')
        point

    // At the end of your script, add the following to display the label only on the last bar
    if barstate.islast
        var string infoText = "\n\n\n\n\n"
        //var int barsSinceLastHigh = na
        //var int barsSinceLastLow = na

        //if not na(lastHighBarIndex)
            //barsSinceLastHigh := bar_index - lastHighBarIndex
        //infoText += "H: " + str.tostring((down ? last_h : last_l)) + " | X1:" + str.tostring(x1) + " | "

       // if not na(lastLowBarIndex)
            //barsSinceLastLow := bar_index - lastLowBarIndex
        //infoText += "L: " + str.tostring((down ? last_l : last_h)) + "\n"

        if down
            infoText += "H: " + str.tostring(last_h) + " (" + str.tostring(x1) + ")" + "\n"
            infoText += "L: " + str.tostring(x1) + " (" + str.tostring(last_h) + ")" + "\n"
        else
            infoText += "L: " + str.tostring(last_l) + " (" + str.tostring(x1) + ")" + "\n"
            infoText += "H: " + str.tostring(x1) + " (" + str.tostring(last_l) + ")" + "\n"

        label.delete(state)
        state:=label.new(bar_index, low, infoText, style=label.style_none, textcolor=color.yellow, size=size.small, yloc=yloc.belowbar)  // Set the label to appear below the bar
        state
// ]


////////
// Bull or Bear notifications
// [
bear = down
//bgcolor(bear?color.red:color.lime, title="Scanning Direction")

alertcondition(bear != bear[1], 'Direction Changed', 'Zigzag on {{ticker}} direction changed at {{time}}')
alertcondition(bear != bear[1] and not bear, 'Bullish Direction', 'Zigzag on {{ticker}} bullish direction at {{time}}')
alertcondition(bear != bear[1] and bear, 'Bearish Direction', 'Zigzag on {{ticker}} bearish direction at {{time}}')
// ]

Overview

ZigCycleBarCount 2024-2 can mark higher highs and lower lows and shade upswings and downswings. The Repaint Levels option is on by default, so the latest leg changes until it is confirmed. It is for measuring swing durations and has no trade signals.

Details

Published by

mikeyhu70 on GitHub

Code credit

Trader_Morry, as written in the script's header

Draws

On the price chart

Markets

Any symbol

Timeframes

Any timeframe

Risk Notes

  • Signals can change on the live bar or after it closes (repainting)

Settings

The inputs you can change from the gear icon on the chart. Defaults are the author's.

SettingTypeDefaultVariable
Depthint17Depth
Deviationint5Deviation
Backstepint3Backstep
Line Thicknessint1line_thick
Bull Colorcolor#84e5f2upcolor
Bear Colorcolor#ff52dfdncolor
Repaint Levelsbooltruerepaint
Show HH/LLboolfalseshowHHLL
show upswing and downswing (repaint only)boolfalseshowSwing
Price Valuesbooltrueprice
Label StylestringTEXTLabel_Style
Third-party code. ForexR did not write, test or endorse this script, and the summary above was generated automatically from its code and README. Indicators describe the past, and a strategy's backtest can look better than live trading, especially when a script repaints. Check it in the Strategy Tester and on a demo account before you rely on it.

Similar Pine Scripts

947 stars

Moving Average Channel plots separate simple moving averages for upper and lower bands on the price chart. It fills the space between bands with semi-transparent color and colors bars green above the upper band, red below the lower band, or gray in between. Us

Indicator v4 Moving averagesSupport & resistance
Updated 11 days ago · GPL-3.0 GitHub repository of Moving Average Channel

ICT Equal Highs and Lows

by ArunKBhaskar
575 stars

This overlay indicator finds pivot highs and lows on the price chart and compares the last two highs and the last two lows. When the percentage difference between a pair is below the Equal HL threshold, it treats them as equal levels and draws a box. Left and

Indicator v5 SMC / ICT / price actionSupport & resistance
Updated 1 year ago · MPL-2.0 GitHub repository of ICT Equal Highs and Lows
330 stars

This indicator monitors multiple cryptocurrency symbols for trading signals. It calculates and plots entry prices, take profit, and stop loss levels for each symbol including BTCUSDT, ETHUSDT, BNBUSDT and others. Price crossovers trigger buy, sell or close ale

Indicator v5 Support & resistanceScreeners & dashboards
Updated 2 months ago · None stated GitHub repository of Multi Alert Long/Short [Alorse]

This overlay indicator draws a fixed-range volume profile on the price chart, splitting traded activity into up and down volume at each price level. It also plots a sentiment profile, a developing point of control, and value-area high and low around a configur

Indicator v5 VolumeSupport & resistance
Updated 2 months ago · MIT GitHub repository of Volume Profile and Indicator by DGT

BZ-tracker

by Allen1212
303 stars

The BZ-tracker indicator marks ARK Invest buy and sell transactions on stock charts with labels. It plots green labels for purchases and red labels for sales, each annotated with a multiplier such as X1 or X2 to show the number of ARK ETFs trading the stock on

Indicator v4 Support & resistanceScreeners & dashboards
Updated 2 years ago · None stated GitHub repository of BZ-tracker

Function - Linear Regression

by ricardosantos79
261 stars

This indicator fits a linear regression through stored pivot highs and lows and draws the resulting channel on the price chart. A function returns predicted values, maximum and minimum deviations, and the average absolute deviation. Confirmed two-bar pivots up

Indicator v5 TrendSupport & resistance
Updated 4 years ago · None stated GitHub repository of Function - Linear Regression

More Support & resistance scripts

Related on ForexR

Trade Your Charts With a Regulated Broker

Compare brokers that connect to TradingView, with spreads, minimum deposits and leverage side by side.

Compare brokers