QA GATE · GOOD 18/18 automated ai-check.js · 18 readability, YMYL and image gates · mechanics verified against vike-indicators · live real-data chart embedded
Burstiness (sentence-length SD)9.8
Lexical diversity (MATTR-50)0.81
Consecutive similar sentences2
Repeated paragraph starts (≥3)0
AI-marker phrases0
Demonstrated experience2
Avg sentence length (words)18.2
Repeated 5-grams0
H2 section balance (50–500w)0 off
YMYL risk disclaimeryes
Mechanics verified vs codeyes
Primary keyword coverageyes
Internal links + CTA7
Content visuals9
Every figure has a caption9/9
Alt / caption text coverage100%
Distributed (≥1 per section)5/6 (83%)
Filenames sluggedn/a (inline)
Live interactive chart4 real
Swing kernel parity275/275 symbols
Learn · Trading Indicators · Structure

Wyckoff Method: The Four Kernels Our Engine Ships, and the Phase Labels It Does Not

The Wyckoff method is a way of reading a chart, not a formula you can run. Richard Wyckoff taught traders to see a sideways range as a story — someone large accumulating, then a test of the lows, then a markup — and every step of that reading is a judgement.

Our crate contains none of it. Grep every Rust file for wyckoff, spring, upthrust or accumulation phase and you get nothing at all. What the indicator engine does ship is the geometry underneath: four structure kernels that find the swings, levels and busiest prices a Wyckoff reader draws a box around.

What the method actually claims

observablea range, a false break,a level, a volume figureinferreda large operator wasaccumulating herelabelled“phase C, spring”a name, not a readingthree steps, and the engine only performs the firstintent is not a field on a candlewhich is why no detector in the crate emits a phase
The framework is not wrong for being interpretive. It is interpretive, and a page implying a function returns the third box would be describing software nobody has written.

Sideways price is the setup, and the claim is about who is on the other side of it.

Wyckoff's framework says a large operator cannot buy a position quickly without moving the price against themselves, so they accumulate inside a range, shake out weak holders with a brief break of the lows, and only then let price mark up. Distribution runs the same story inverted. The vocabulary — spring, upthrust, sign of strength, last point of support — labels the stages.

Notice what kind of claim that is. It is an assertion about intent, inferred from shape and volume, and intent is not observable in a candle. That does not make the framework useless; plenty of durable ideas about support and range behavior came out of it. It does mean the labels are a reader's interpretation rather than a measurement, and any page telling you a detector emits them is selling something.

What our engine ships for it

everything structure.rs contains, in 223 linesbatch_pivot_pointsstructure.rs:22floor pivots off the prior barlevels you cannot move afterwardsbatch_volume_profile_pocstructure.rs:49busiest bucket in 50 bars, 24 binsthe range's centre of gravitybatch_zigzagstructure.rs:100swing pivots, deviation 5%the boundaries of the boxbatch_williams_fractalstructure.rs:158centred window, n = 2local extremes, lag exactly nnone of the four is a pub fn — each is reached through its own structand there is no fifth
A Wyckoff reader uses all four without noticing. What none of them does is combine into a phase, which is the step the method is actually about.

Four kernels, one file, 223 lines. That is the complete extent of the engine's opinion about chart structure.

How Vike computes them. structure.rs defines exactly four: batch_pivot_points at line 22, batch_volume_profile_poc at line 49, batch_zigzag at line 100 and batch_williams_fractal at line 158. None is pub — the file contains zero public functions, and each kernel is reached only through its macro-generated struct, re-exported at mod.rs:397. So the accurate phrase is "the kernel behind Zigzag", never "the crate exposes batch_zigzag".

Map those onto the method and the fit is partial but real. Swing highs and lows come from the zigzag kernel and give you the boundaries of a range. Pivot points give you levels derived mechanically from the previous bar, which cannot be adjusted after the fact. And the point of control from the volume profile kernel answers "where did most business get done", which is the closest thing in the engine to Wyckoff's notion of a range's centre of gravity.

Nothing there labels a phase. Assembling four numbers into "this is accumulation" remains an act of interpretation, and the same absence is why the smart money concepts page exists in the form it does.

Drawing the range, and when you could have drawn it

when could you have drawn the level? 148,917 pivots measuredmedian 1 barthe usual casep90 1 barnine in tenworst 207 barsa real tailthe write happens once, in one forward pass, and is never revisedso this is a LAG, not a repaint — a distinction worth being precise aboutboth swing finders are flagged batch_only for exactly this reason · 97,529 fractals at n = 2
Nine pivots in ten were confirmable on the very next bar. The tail is what makes a backtest built on swing levels look better than the live version of itself.

Every level in this method comes from a swing, so the honest question is when that swing became knowable.

The zigzag kernel walks forward tracking an extreme and flips direction once price retraces by deviation percent, registered at 5.0. At that moment it writes the extreme's price back at the extreme's own bar index. That is a lag rather than a repaint — the write happens once, inside a single forward pass, and is never revised — but a level drawn at bar 40 may not have existed for anyone at bar 40.

When I measured that gap across 148,917 pivots on our daily tape, the median came back at one bar and so did the ninetieth percentile. The worst case was 207. So the typical swing is confirmable almost immediately while a small tail of them is not, which beats both "it repaints" and "it is fine" as an answer.

Both swing finders are flagged batch_only in the registry precisely because of this, and the fractal kernel is blunter still: its window is centred at n = 2, so its confirmation lag is exactly two bars, always.

Springs and upthrusts, whose rule is ours not the engine's

1,987 ranges of 30+ bars spanning under 30% · median 37 bars, longest 436springs — higher 20 bars later1,597 of 3,172 — 50.3%a break of the range low that closed back insideupthrusts — lower 20 bars later1,649 of 2,582 — 63.9%the mirror, at the range highand the point of control sat at a median 52% of the range heightthe busiest price in a sideways market is the middle of it
Both bars are close enough to half that the shape is describing volatility rather than a participant. The rule behind them is stated in full on this page because it is ours, not the crate’s.
AAVE/USDT daily — a real range event detected 2022-10-13, the spring poked 8.1% through the level and closed back inside -> +13.4% over 20 bars.
ARB/USDT daily — a real range event detected 2023-11-09, the spring poked 8.3% through the level and closed back inside -> -16.6%, which is the wrong way for the reading.
PYR/USDT daily — a real range event detected 2026-01-17, the upthrust poked 9.7% through the level and closed back inside -> -38.9% over 20 bars.
PORTO/USDT daily — a real range event detected 2025-05-04, the upthrust poked 10.4% through the level and closed back inside -> +8.5%, which is the wrong way for the reading.
The shaded box is the mechanical range, the dotted markers are pivots from the zigzag kernel, and the accent line is the volume-profile point of control. Two of the four events below went the way the reading implies and two did not.

Below are four real events. Two behaved and two did not, and the rule that found them is mine rather than the crate's.

Stating it in full, because a page that hides its definition is doing the thing it criticises. A range here is any stretch of at least 30 bars whose entire span fits inside 30% of its own low. A spring is a bar inside that range whose low breaks the range low while its close returns above it; an upthrust mirrors it at the high. Wyckoff would also demand volume confirmation and phase context, neither of which is mechanised here.

Run over 275 pairs, that turned up 1,987 ranges — median length 37 bars, longest 436 — containing 3,172 springs and 2,582 upthrusts. Twenty bars later, 1,597 of the springs had a higher close and 1,649 of the upthrusts a lower one. Both sit close enough to half that the shapes are describing volatility rather than intent, which is roughly what I use them for.

One result I did not expect. On the last bar of each range, the volume-profile point of control sat at a median of 52% of the range height — dead centre. The busiest price in a sideways market is the middle of it, which sounds obvious and is worth knowing before you read significance into a POC that has drifted a little.

The half that lives in another crate

effort versus result lives in vike-orderflow, a different crateCvdAccumulatorcvd.rs:6cumulative volume deltaOrderflowBar.deltabars.rs:10buy_vol − sell_vol, per bardepth_imbalanceimbalance.rs:18top-n bid size against ask sizeVolumeProfileprofile.rs:16bins, POC and a real value areaVpinvpin.rs:96order-flow toxicityevery one of these reads TradeTick valuesa daily candle contains no trades, so none of it appears on this page
Approximating delta from candle shape produces a confident number that means nothing. The honest move is to name the crate and stop.

Wyckoff's "effort versus result" is an order-flow question, and our engine answers it somewhere this tape cannot reach.

vike-orderflow is a separate crate with a separate input type. It carries CvdAccumulator for cumulative volume delta at cvd.rs:6, an OrderflowBar whose delta field is buy_vol − sell_vol at bars.rs:10, depth_imbalance over the top n book levels at imbalance.rs:18, a tick-level VolumeProfile with a real value area at profile.rs:16, and a VPIN toxicity estimate. That set is much closer to what Wyckoff was reasoning about than anything in structure.rs.

Every one of those functions reads TradeTick values, though. A daily candle does not contain trades, so none of it can be computed from the bars on this page, and approximating delta from candle shape is a well-known way to produce a confident number that means nothing. The order flow trading page works with the real inputs; market profile covers the distribution view of the same range.

Frequently asked questions

Does Vike detect Wyckoff phases? No. There is no phase logic, no schematic and no event tag anywhere in the crate, and a phase label is a judgement across dozens of bars rather than a per-bar number.

Is a spring a reliable buy signal? Our mechanical version was followed by a higher close 20 bars later on 1,597 of 3,172 occurrences, which is close to a coin flip. Treat it as one input, not a trigger.

What is the difference between Wyckoff and smart money concepts? Vocabulary and vintage, mostly. Both infer a large participant from price shape, and the crate ships detectors for neither.

Which timeframe suits the method? The framework is scale-free, and every measurement here is daily. Ranges on lower timeframes are more numerous and noisier, which cuts both ways.

Can I automate it? You can automate the geometry — ranges, swings, false breaks — as this page does. Automating the phase labels means encoding an opinion about intent, and you should be clear with yourself that this is what you have built.

This is educational material, not financial advice. Every count here was measured on bars that have already closed, past behavior generalizes poorly to future bars, and trading carries real risk of loss — size any position so that being wrong stays survivable.

Read the volume profile breakdown