Periodic Cycle
// This source code is subject to the terms of the Mozilla Public License 2.0 at https://mozilla.org/MPL/2.0/
// © estyles_tvr1

//@version=5
indicator("Periodic Cycles", overlay=true)

period = input(defval=7*12, title="Cycle Lenght", inline="1")
period_res = input.timeframe('M', "", options=['1', '60', 'D', 'W', 'M'], inline="1")

periodBound = input(defval=12, title="Cycle up/down boundary")

i_date = input.time(timestamp("9 Sep 2021 00:00 +0300"), "Start Date")
l = label.new(i_date, na, "Start Date", xloc=xloc.bar_time, yloc=yloc.abovebar)
label.delete(l[1])

fillBackground = input(true, "Fill Background?")
newMoonBackgroundColor = input(#44444488, "Cycle Start Background Color")
fullMoonBackgroundColor = input(#22222288, "Cycle End Background Color")

print(string txt) => 
	var table t = table.new(position.middle_right, 1, 1)
	table.cell(t, 0, 0, txt, bgcolor = color.yellow)

calcPhase2(_year, _month, _day, _hour, _minute) =>
    current = timestamp(_year, _month, _day, _hour, _minute)
    start = i_date
    period_secs = period * timeframe.in_seconds(period_res) * 1000
    mod = ((current - start) / period_secs) % 1
    (mod < 0  and mod > ((periodBound-period)/period)) or (mod > 0 and mod > (periodBound/period)) ? 1 : -1

moon = calcPhase2(year, month, dayofmonth, hour, minute)
if(moon!=moon[1])
    line2 = line.new(time, 1, time, 2, xloc=xloc.bar_time, style=line.style_dashed, extend=extend.both)
    line.set_color(line2, color.red)

var color col = na
if moon == 1 and fillBackground
    col := fullMoonBackgroundColor
if moon == -1 and fillBackground
    col := newMoonBackgroundColor

bgcolor(col, title="Cycle")