mirror of
https://github.com/mihakralj/QuanTAlib.git
synced 2026-07-27 17:27:43 +00:00
51 lines
1.9 KiB
Plaintext
51 lines
1.9 KiB
Plaintext
// Licensed under the Apache License, Version 2.0
|
|
// © mihakralj
|
|
//@version=6
|
|
indicator("Arnaud Legoux Moving Average (ALMA)", "ALMA", overlay=true)
|
|
|
|
//@function Calculates ALMA using Gaussian distribution weights
|
|
//@param source Series to calculate ALMA from
|
|
//@param period Lookback period - window size
|
|
//@param offset Controls the Gaussian peak location (0 to 1)
|
|
//@param sigma Controls the Gaussian distribution width/curve shape
|
|
//@returns ALMA value, calculates from first bar using available data
|
|
//@optimized Uses Gaussian weighting with O(n) complexity per bar due to lookback loop
|
|
alma(series float source, simple int period, simple float offset=0.85, simple float sigma=6.0) =>
|
|
if period <= 0
|
|
runtime.error("Period must be greater than 0")
|
|
if offset < 0.0 or offset > 1.0
|
|
runtime.error("Offset must be between 0 and 1")
|
|
if sigma <= 0.0
|
|
runtime.error("Sigma must be greater than 0")
|
|
int p = math.min(bar_index + 1, period)
|
|
if p <= 1
|
|
source
|
|
else
|
|
float m = (1.0 - offset) * (p - 1)
|
|
float s = p / sigma
|
|
float s2 = 2.0 * (s * s)
|
|
float sum = 0.0
|
|
float weight_sum = 0.0
|
|
for i = 0 to p - 1
|
|
float price = source[i]
|
|
if not na(price)
|
|
float diff = i - m
|
|
float weight = math.exp(-(diff * diff) / s2)
|
|
sum += price * weight
|
|
weight_sum += weight
|
|
nz(sum / weight_sum, source)
|
|
|
|
// ---------- Main loop ----------
|
|
|
|
// Inputs
|
|
i_period = input.int(50, "Period", minval=1, tooltip="Number of bars used in the calculation")
|
|
i_offset = input.float(0.85, "Offset", minval=0.0, maxval=1.0, step=0.01)
|
|
i_sigma = input.float(6.0, "Sigma", minval=0.1, maxval=20.0, step=0.1)
|
|
i_source = input.source(close, "Source")
|
|
|
|
// Calculation
|
|
alma_value = alma(i_source, i_period, i_offset, i_sigma)
|
|
|
|
// Plot
|
|
plot(alma_value, "ALMA", color=color.yellow, linewidth=2)
|