Indicatore Awesome Oscillator: formula, impostazioni e lettura
L'Awesome Oscillator è l'istogramma di momentum di Bill Williams: la media mobile semplice a 5 periodi del prezzo mediano della barra meno quella a 34 periodi. Viene disegnato in un pannello separato ed è positivo quando il centro del range sull'orizzonte breve si trova sopra quello sull'orizzonte lungo.
Senzoukria · Indicatori · Updated September 2026
Awesome Oscillator — Momentum, in un pannello separato sotto il grafico.
Che cosa misura Awesome Oscillator
L'input è il prezzo mediano, (massimo + minimo) / 2, e non la chiusura: Williams voleva seguire lo spostamento del centro dell'asta su due orizzonti, mentre la chiusura è un'unica istantanea di fine barra, rumorosa sui futures intraday. Entrambi i termini sono semplici medie mobili aritmetiche: la definizione originale non prevede smussatura esponenziale o di Wilder, e nemmeno questa implementazione. I valori predefiniti 5/34 vengono dal lavoro di Williams su base giornaliera, all'incirca una settimana contro un mese, e sono mantenuti invariati per coerenza con le altre piattaforme. Nessun punto dell'istogramma viene emesso finché la media lenta non è completa, quindi le prime barre restano vuote anziché approssimate.
La formula, così come è implementata
Non è la definizione consueta altrove: è ciò che calcola il codice distribuito, documentato accanto alla sua implementazione:
Période entière ≥ `min` depuis les params (garde-fou UI, même helper que momentum.ts / stats.ts). */ function intParam( params: Record<string, unknown>, key: string, fallback: number, min = 1, ): number { return Math.max(min, Math.floor(numParam(params, key, fallback))); } function clamp(v: number, lo: number, hi: number): number { return Math.min(hi, Math.max(lo, v)); } function toPoints( bars: readonly FootprintBar[], values: ReadonlyArray<number | null>, ): SeriesPoint[] { return bars.map((b, i) => ({ time: b.bucketTsNs, value: values[i] ?? null })); } /** Histogramme : une barre sans valeur n'émet PAS de point (contrat `HistogramPoint`, pas de trou représentable). */ function histPoints( bars: readonly FootprintBar[], values: ReadonlyArray<number | null>, ): HistogramPoint[] { const out: HistogramPoint[] = []; for (let i = 0; i < bars.length; i++) { const v = values[i]; if (v !== null && v !== undefined) { out.push({ time: bars[i].bucketTsNs, value: v }); } } return out; } /** SMA N sur série À TROUS : null dès qu'UNE valeur de la fenêtre est null — moyenner autour d'un trou mentirait sur la période effective. */ function smaNullable( values: ReadonlyArray<number | null>, period: number, ): Array<number | null> { const n = Math.max(1, Math.floor(period)); const out: Array<number | null> = new Array<number | null>(values.length).fill(null); for (let i = n - 1; i < values.length; i++) { let sum = 0; let ok = true; for (let j = i - n + 1; j <= i; j++) { const v = values[j]; if (v === null) { ok = false; break; } sum += v; } if (ok) out[i] = sum / n; } return out; } /** WMA N (poids linéaires 1..N, le plus récent pèse N) tolérante aux trous : null dès qu'une valeur manque dans la fenêtre. Même formule que `helpers.wmaSeries`, qui n'accepte que des `number[]`. */ function wmaNullable( values: ReadonlyArray<number | null>, period: number, ): Array<number | null> { const n = Math.max(1, Math.floor(period)); const denom = (n * (n + 1)) / 2; const out: Array<number | null> = new Array<number | null>(values.length).fill(null); for (let i = n - 1; i < values.length; i++) { let acc = 0; let ok = true; for (let j = 0; j < n; j++) { const v = values[i - n + 1 + j]; if (v === null) { ok = false; break; } acc += v * (j + 1); } if (ok) out[i] = acc / denom; } return out; } /** EMA N (graine SMA) sur une série dont les valeurs définies forment un SUFFIXE contigu — sortie d'un lissage précédent. Le préfixe reste null ; série toute-null ou trou interne → tout-null (dégradation propre, on ne devine pas). Copie locale de la primitive de momentum.ts (non exportée). */ function suffixEma( values: ReadonlyArray<number | null>, period: number, ): Array<number | null> { const out: Array<number | null> = new Array<number | null>(values.length).fill(null); const start = values.findIndex((v) => v !== null); if (start < 0) return out; const defined: number[] = []; for (let i = start; i < values.length; i++) { const v = values[i]; if (v === null) return out; defined.push(v); } const ema = emaSeries(defined, period); for (let j = 0; j < ema.length; j++) out[start + j] = ema[j]; return out; } /** ROC en POURCENT : 100·(x[i] − x[i−N])/x[i−N]. Référence NULLE → null (pas de division par zéro déguisée) — même règle que `roc` (momentum.ts). */ function rocPercentSeries( values: readonly number[], period: number, ): Array<number | null> { const n = Math.max(1, Math.floor(period)); const out: Array<number | null> = new Array<number | null>(values.length).fill(null); for (let i = n; i < values.length; i++) { const ref = values[i - n]; if (ref !== 0) out[i] = (100 * (values[i] - ref)) / ref; } return out; } /** Prix médian de la barre — l'entrée de Bill Williams et d'Ehlers. */ function hl2(b: FootprintBar): number { return (b.high + b.low) / 2; } /** Égalités RSI, STRICTEMENT celles de `rsi` (momentum.ts) : marché PLAT (les deux moyennes nulles) → null (pas d'information directionnelle) ; que des gains → 100 ; que des pertes → 0. */ function rsiValue(avgGain: number, avgLoss: number): number | null { if (avgLoss === 0 && avgGain === 0) return null; if (avgLoss === 0) return 100; if (avgGain === 0) return 0; return 100 - 100 / (1 + avgGain / avgLoss); } /** RSI de WILDER sur une série quelconque (closes, ou série de streaks pour Connors). Graine = moyenne SIMPLE des N premières variations, puis lissage Wilder avg = (avg·(N−1) + x)/N ; premier point à l'indice N. Copie locale de la primitive de momentum.ts (non exportée) — même formule, mêmes égalités, donc `connors-rsi` et `rsi` restent cohérents à l'écran. */ function wilderRsiSeries( values: readonly number[], period: number, ): Array<number | null> { const n = Math.max(1, Math.floor(period)); const out: Array<number | null> = new Array<number | null>(values.length).fill(null); if (values.length < n + 1) return out; let avgGain = 0; let avgLoss = 0; for (let i = 1; i <= n; i++) { const ch = values[i] - values[i - 1]; if (ch > 0) avgGain += ch; else avgLoss -= ch; } avgGain /= n; avgLoss /= n; out[n] = rsiValue(avgGain, avgLoss); for (let i = n + 1; i < values.length; i++) { const ch = values[i] - values[i - 1]; avgGain = (avgGain * (n - 1) + Math.max(0, ch)) / n; avgLoss = (avgLoss * (n - 1) + Math.max(0, -ch)) / n; out[i] = rsiValue(avgGain, avgLoss); } return out; } /** AO de Bill Williams — factorisé parce que l'Accelerator le consomme : SMA_fast(hl2) − SMA_slow(hl2), null tant que la LENTE n'est pas amorcée. */ function awesomeSeries( bars: readonly FootprintBar[], fast: number, slow: number, ): Array<number | null> { const mid = bars.map(hl2); const f = smaSeries(mid, fast); const s = smaSeries(mid, slow); return mid.map((_, i) => { const a = f[i]; const b = s[i]; return a !== null && b !== null ? a - b : null; }); } /** Étage « stochastique + lissage exponentiel à facteur fixe » de Schaff — factorisé parce que STC l'applique DEUX FOIS (cf. sa déf) : %K = 100·(x − min(x, cycle))/(max(x, cycle) − min(x, cycle)) état ← (premier %K défini) puis état + f·(%K − état) Fenêtre PLATE (max == min) ou incomplète → sortie null ET ÉTAT FIGÉ : on ne nourrit pas la récurrence avec un %K inventé, et on ne reconduit pas la dernière valeur (le `nz(f1[1])` des portages Pine peindrait un plateau faux). Un trou ainsi créé se propage aux fenêtres suivantes qui le contiennent — c'est le comportement voulu. / function schaffStage( src: ReadonlyArray<number | null>, cycle: number, factor: number, ): Array<number | null> { const n = Math.max(2, Math.floor(cycle)); const out: Array<number | null> = new Array<number | null>(src.length).fill(null); let state: number | null = null; for (let i = n - 1; i < src.length; i++) { let lo = Number.POSITIVE_INFINITY; let hi = Number.NEGATIVE_INFINITY; let ok = true; for (let j = i - n + 1; j <= i; j++) { const v = src[j]; if (v === null) { ok = false; break; } if (v < lo) lo = v; if (v > hi) hi = v; } const cur = src[i]; if (!ok || cur === null) continue; // trou → état figé, sortie null const range = hi - lo; if (!(range > 0)) continue; // fenêtre plate → null, jamais 0 const k = (100 * (cur - lo)) / range; state = state === null ? k : state + factor * (k - state); out[i] = state; } return out; } // ── Défs — Bill Williams ──────────────────────────────────────────────────── /** Awesome Oscillator (Bill Williams) — lissage SMA SIMPLE (pas d'EMA, pas de Wilder ; c'est la définition originale) sur le PRIX MÉDIAN : hl2 = (high + low)/2 AO = SMA_fast(hl2) − SMA_slow(hl2) POURQUOI hl2 et pas le close : Williams mesure le déplacement du CENTRE de l'enchère sur deux horizons ; le close n'est qu'un instantané de fin de barre, très bruité en intraday futures. Défauts 5/34 (Williams) — la paire « une semaine / un mois » de son analyse quotidienne, gardée telle quelle pour la parité avec ATAS/TradingView. HISTOGRAMME : warm-up (< slow barres) → AUCUN point. Le renderer colore par SIGNE (contrat `SeriesOutput.histogram`) ; Bill Williams colore par SENS DE VARIATION barre à barre — écart assumé et documenté, le shape du moteur ne transporte pas de couleur par point.
Come leggerlo
- Sopra zero, il centro del range sull'orizzonte breve è sopra quello sull'orizzonte lungo; sotto zero, il contrario. La linea dello zero è l'unico livello definito dalla formula.
- La distanza dallo zero misura quanto i due orizzonti si sono separati: è l'ampiezza del momentum, non una convinzione.
- Barre che si accorciano mentre il prezzo continua ad avanzare indicano che le due medie stanno convergendo e che il movimento rallenta.
- Un massimo di prezzo più alto contro un massimo dell'AO più basso è una divergenza di momentum: la descrizione di ciò che è già accaduto, non una previsione.
- In un mercato in equilibrio le barre oscillano strette attorno allo zero e i cambi di segno hanno poco significato.
Parametri e valori predefiniti
La media veloce (5) e la lenta (34) definiscono i due orizzonti di calcolo; è lo scarto tra le due, più della loro dimensione assoluta, a determinare l'ampiezza. Avvicinarle dà un istogramma più calmo con frequenti cambi di segno, allontanarle dà oscillazioni più ampie e lente e un riscaldamento più lungo. I due colori riguardano solo la visualizzazione.
| Parametro | Tipo | Predefinito | Intervallo |
|---|---|---|---|
| Fast SMA | number | 5 | 1 – 200 |
| Slow SMA | number | 34 | 2 – 500 |
Ciò che non mostra
L'Awesome Oscillator si basa solo sul prezzo: nessuna informazione di volume, delta o book lo raggiunge, quindi non può distinguere un rialzo accolto da vendite aggressive da uno che non ha incontrato nulla. È in ritardo per costruzione, perché entrambi i termini sono medie che seguono il prezzo. Il prezzo mediano ignora inoltre dove la barra ha chiuso, quindi una barra che si è invertita bruscamente in chiusura si legge come una che ha tenuto i massimi. Una nota sulla visualizzazione: qui le barre sono colorate in base al segno del valore, mentre Williams colorava ogni barra in base alla variazione rispetto alla precedente, quindi gli stessi dati possono apparire diversi da una piattaforma all'altra.
Indicatori correlati
Questa pagina in altre lingue
Frequently asked questions
- Perché l'Awesome Oscillator usa il prezzo mediano invece della chiusura?
- Williams lo ha progettato per seguire il centro dell'asta su due orizzonti, e il prezzo mediano, (massimo + minimo) / 2, riassume dove la barra ha scambiato anziché dove si è fermata. La chiusura è un singolo istante alla fine della barra ed è rumorosa sulle barre intraday brevi. Di conseguenza l'oscillatore ignora una chiusura forte all'interno di un range per il resto invariato.
- Che cosa significa l'attraversamento della linea dello zero dell'Awesome Oscillator?
- Significa che la media a 5 periodi del prezzo mediano ha incrociato la media a 34 periodi, quindi l'orizzonte breve è passato da un lato all'altro dell'orizzonte lungo. È un'affermazione su due medie che seguono il prezzo, ed entrambe si sono già mosse prima che l'incrocio compaia. In fase laterale le due medie restano vicine e gli incroci avvengono su differenze minime.
- I periodi 5 e 34 devono restare quelli predefiniti?
- No: entrambi sono modificabili, da 1 a 200 per la media veloce e da 2 a 500 per la lenta. I valori predefiniti sono quelli di Williams e vengono mantenuti perché le letture coincidano con le altre piattaforme che usano la stessa coppia. Modificarli cambia l'ampiezza e il riscaldamento, quindi il confronto con grafici sulle impostazioni predefinite non è più valido.