// Licensed under the Apache License, Version 2.0 // © mihakralj //@version=6 indicator("Zero-Lag EMA (ZLEMA)", "ZLEMA", overlay=true) //@function Calculates ZLEMA using zero-lag price and exponential smoothing with compensator //@param source Series to calculate ZLEMA from //@param period Smoothing period //@param alpha Optional smoothing factor (overrides period if provided) //@returns ZLEMA value with zero-lag effect applied //@optimized Uses lag compensation buffer and exponential warmup compensator for O(1) complexity zlema(series float source, simple int period=0, simple float alpha=0) => float a = alpha > 0 ? alpha : 2.0 / (period + 1) float beta = 1.0 - a simple int lag = math.max(1, math.round((period - 1) / 2)) var bool warmup = true var float e = 1.0 var float zlema = 0.0 var float result = source var priceBuffer = array.new(lag + 1, 0.0) if not na(source) array.shift(priceBuffer) array.push(priceBuffer, source) float laggedPrice = array.get(priceBuffer, 0) float signal = 2 * source - laggedPrice zlema := a * (signal - zlema) + zlema if warmup e *= beta float c = 1.0 / (1.0 - e) result := c * zlema warmup := e > 1e-10 else result := zlema result // ---------- Main loop ---------- // Inputs i_period = input.int(10, "Period", minval=1) i_source = input.source(close, "Source") // Calculation zlema_value = zlema(i_source, i_period) // Plot plot(zlema_value, "ZLEMA", color=color.yellow, linewidth=2)