PINE LIBRARY
Pattern Atlas : Geometric [AxeAlgo]

Pattern Atlas : Geometric Patterns [AxeAlgo]
WHAT THIS LIBRARY IS
This is a Pine Script v6 library of 17 classical chart pattern detectors — Head and Shoulders, Double/Triple Tops and Bottoms, triangles, wedges, flags, and the rest of the standard technical-analysis catalog built from swing highs and lows rather than single-candle shape. Unlike candlestick patterns, which read one to a handful of fixed bars, chart patterns span a variable, often large number of bars, so this library carries one small piece of state — a rolling history of confirmed swing pivots — that every pattern function reads from. Beyond that, the same philosophy as Library #1 applies: no plotting, no alerts, and no inputs in this script by design, since a library's job is to hand other scripts a clean, reusable, well-documented API, not to draw on a chart itself (Pine doesn't allow a library to plot anything anyway). If you're looking for a ready-to-use indicator built on top of this library, see the companion "Pattern Atlas : Geometric Indicator [AxeAlgo]" script, which imports every function here and turns it into on-chart signals, measured-move price targets, a live scanner table, and alerts.
Chart pattern analysis is one of the foundational tools of classical technical analysis, going back to Edwards and Magee's original work and refined since by researchers like Thomas Bulkowski, whose statistical studies of pattern behavior are the closest thing this field has to an industry-standard reference. The patterns in this library follow that standard catalog, so anyone who already knows what a Head and Shoulders top or an Ascending Triangle looks like will recognize exactly what each function is checking for.
WHY A LIBRARY INSTEAD OF ONE MONOLITHIC INDICATOR
Splitting detection logic out as an importable library means:
- Any Pine coder building their own strategy, indicator, or screener can pull in exactly the pattern checks they need without copy-pasting swing-pivot and trendline math into every new script.
- The detection logic is tested and maintained in one place. When a threshold gets refined, everything importing this library benefits from the update by bumping one version number.
- It keeps the math separate from presentation — how a pattern gets drawn, colored, or alerted on is a completely separate decision from whether the pattern is actually present, and different users want different presentations.
HOW TO IMPORT AND USE IT
Add this line near the top of your script (adjust the version number to whatever the current published version is):
import AxeAlgo/Pattern_Atlas_Geometric/1 as geo
Unlike Library #1, most of the functions here need a shared pivot history to work from. Call trackPivots() exactly once per bar, then pass its result into every detect*() function that needs it:
pivots = geo.trackPivots()
match = geo.detectDoubleTopBottom(pivots)
if match.found
label.new(bar_index, high, match.patternName)
Four functions — detectSpike(), detectFlag(), detectPennant(), and detectIslandReversal() — read directly off recent price action instead of the shared pivot history, so they're called without a pivots argument: geo.detectSpike().
trackPivots() takes three optional parameters: leftBars and rightBars (how many less-extreme bars must surround a candidate swing point before it confirms as a pivot — higher values mean fewer, more significant pivots, at the cost of a longer confirmation lag), and maxPivots (how much pivot history to retain). All three have sensible defaults.
Every detect*() function returns the same structure, called ChartPatternMatch, so the calling pattern is identical no matter which of the 17 you use. It has nine fields:
- found — true if the pattern matched at the evaluated bar, false otherwise.
- patternName — the specific name of what matched (e.g. "Ascending Triangle"), na when not found.
- direction — "bullish" or "bearish".
- pivotBars — bar_index of each pivot the match was built from, in chronological order.
- pivotPrices — price of each pivot, in the same order as pivotBars.
- breakoutLevel — the support, resistance, or neckline level price broke through to confirm the pattern.
- necklineSlope — slope (price per bar) of the breakout line, na when the pattern's breakout level isn't a sloped line.
- barIndex — the bar_index the pattern completes (breaks out) on.
- description — a full sentence naming the pattern and the actual measured price levels that triggered it — genuinely useful for a tooltip or an alert message, not just a repeat of the pattern name.
Two additional exported functions turn that raw match into something more actionable, and both work on any ChartPatternMatch regardless of which detect*() function produced it:
- patternStrength(match) — a 0-100 score for how decisively the confirmation close broke through breakoutLevel, relative to the pattern's own price range. A breakout that clears the level by a meaningful fraction of the pattern's own size scores higher than a one-tick poke through it.
- patternTarget(match) — a classical measured-move price target, projecting the pattern's own height from the breakout point. Returns na for patterns without a reliable height to project from (V-Top/V-Bottom Spike, Island Reversal, Bump-and-Run Reversal).
Every detect*() function also exposes its own set of tunable threshold parameters — how flat a "flat top" has to be, how much two shoulders can differ and still count as equal, and so on — all with sensible defaults so you don't have to touch them unless you want to tighten or loosen a specific pattern's sensitivity for a particular instrument or timeframe.
THE 17 PATTERNS
Reversal patterns (7) — signal a potential change in the prevailing trend:
- Head and Shoulders / Inverse Head and Shoulders — detectHeadAndShoulders(). Three swing extremes with the middle one more extreme than the two roughly-equal outer ones, confirmed when price breaks the neckline connecting the two points between them.
- Double Top / Double Bottom — detectDoubleTopBottom(). Two roughly equal peaks (or troughs) with a retracement between them, confirmed when price breaks back through that retracement level.
- Triple Top / Triple Bottom — detectTripleTopBottom(). The same idea as a Double Top/Bottom with a third roughly-equal touch, confirmed on the break of the support or resistance formed between the touches.
- Rounding Top / Rounding Bottom — detectRoundingTopBottom(). A gradual, curved advance-and-rollover (or decline-and-recovery) between two similar edge levels. Approximate: read from three swing pivots rather than fitting a true curve.
- Diamond Top / Diamond Bottom — detectDiamondTopBottom(). Swing range that widens and then narrows again, confirmed on a break of the resulting support or resistance. Rare and approximate: read from three pivot pairs rather than a clean diamond outline.
- Broadening Formation — detectBroadeningTopBottom(). Diverging highs and lows forming an increasingly volatile range, confirmed on a break of either edge. Approximate: read from two pivot pairs rather than a hand-fitted diverging channel.
- V-Top / V-Bottom (Spike) — detectSpike(). A single sharp extreme with no rounding — a large move into the pivot and an equally large move away from it, both measured against the recent average bar range, within a handful of bars. Self-contained, no pivots argument needed.
Continuation patterns (8) — typically resolve in the direction of the move that preceded them:
- Ascending Triangle — detectTriangleAscending(). Flat resistance with rising support, confirmed on a break above resistance.
- Descending Triangle — detectTriangleDescending(). Flat support with falling resistance, confirmed on a break below support.
- Symmetrical Triangle — detectTriangleSymmetrical(). Converging highs and rising lows, confirmed (bullish or bearish) whichever side the price actually breaks.
- Rising Wedge / Falling Wedge — detectWedge(). Both trendlines slope the same direction and converge; breaks the opposite way from the slope, since the shared-direction move was already losing momentum.
- Bull Flag / Bear Flag — detectFlag(). A strong directional move (the pole), followed by a tight, roughly parallel pullback, confirmed on a break back out in the pole's direction. Self-contained, no pivots argument needed.
- Bull Pennant / Bear Pennant — detectPennant(). The same pole-and-consolidation structure as a Flag, but the consolidation narrows and converges rather than staying parallel. Self-contained, no pivots argument needed.
- Rectangle — detectRectangle(). Price boxed between flat support and flat resistance, confirmed on a break of either edge.
- Cup and Handle / Inverted Cup and Handle — detectCupAndHandle(). A rounded recovery (or decline) back to its starting rim, then a shallow pullback (the handle), confirmed on a break through the rim.
Structural / gap-based patterns (2):
- Bullish / Bearish Island Reversal — detectIslandReversal(). A bar (or small cluster) isolated by a gap on both sides, then abandoned by a gap the other way — an abrupt reversal. Self-contained, pure gap logic, no pivots argument needed.
- Bump-and-Run Reversal — detectBumpAndRun(). A lead-in trendline, then a "bump" phase accelerating well beyond it, then a "run" breaking back through the lead-in line. Approximate: the lead-in line is read from just two pivots rather than a hand-drawn trendline.
WHAT THIS LIBRARY DELIBERATELY DOES NOT DO
No plotting, no drawing, no alertcondition() calls, and no inputs — Pine doesn't allow any of those inside a library in the first place, since a library can never be added to a chart on its own. If you want signals, price targets, a scanner table, or alerts, import this library into your own script (or use the companion "Pattern Atlas : Chart Pattern Scanner [AxeAlgo]" indicator, which does exactly that) rather than expecting this script to render anything by itself.
This library also does not evaluate multi-timeframe data, volume, or broader market structure — it's swing-pivot and trendline geometry only, on purpose, so its behavior is easy to reason about and easy to reuse as one building block among several.
Four of the seventeen patterns are explicitly noted above as approximate: Rounding Top/Bottom, Diamond Top/Bottom, Broadening Formation, and Bump-and-Run Reversal are read from a small, fixed number of swing pivots rather than fitting a true curve or hand-drawn trendline to the data. They will not catch every textbook-perfect example of these shapes, and they may occasionally flag a looser approximation of one. Treat them as a starting point for further chart review, not a final word.
PART OF A LARGER SERIES
This is Library #2 in the AxeAlgo Pattern Atlas — a planned set of Pine libraries splitting pattern detection by the method actually used to find each kind of pattern: candlestick shape (Library #1, already published), classical chart/geometric patterns (this library), harmonic patterns (Fibonacci-ratio XABCD structures), and market-structure concepts (order blocks, liquidity, Wyckoff-style events). Each library is independent and useful on its own; together they're meant to cover technical pattern analysis without forcing unrelated detection methods into the same function.
A NOTE ON REPAINTING
trackPivots() only confirms a swing pivot once rightBars bars have passed since it happened — the same confirmation lag ta.pivothigh()/ta.pivotlow() use, just written out as plain comparisons so it works safely inside a library's exported functions. That means a pivot never moves or disappears once confirmed; it just takes rightBars bars to become known, which is a normal and unavoidable part of swing-pivot detection, not a defect in this library. On the currently-forming bar, a pattern's found status can still change tick to tick as that bar's own high, low, and close move — that's inherent to reading live price action. If you're building persisted signals, drawings, alerts, or price targets on top of these functions (rather than a live "what's happening right now" readout), gate your usage on barstate.isconfirmed so a signal only fires once the bar it describes has actually closed, exactly like the companion scanner indicator does.
DISCLAIMER
This library is a technical analysis tool for identifying classical chart pattern shapes in historical and live price data. It does not predict future price movement, and a detected pattern — including any projected price target — is a description of past price action, not a signal guaranteed to repeat. Nothing in this script constitutes financial advice. Always combine pattern recognition with your own risk management and broader analysis before making any trading decision.
WHAT THIS LIBRARY IS
This is a Pine Script v6 library of 17 classical chart pattern detectors — Head and Shoulders, Double/Triple Tops and Bottoms, triangles, wedges, flags, and the rest of the standard technical-analysis catalog built from swing highs and lows rather than single-candle shape. Unlike candlestick patterns, which read one to a handful of fixed bars, chart patterns span a variable, often large number of bars, so this library carries one small piece of state — a rolling history of confirmed swing pivots — that every pattern function reads from. Beyond that, the same philosophy as Library #1 applies: no plotting, no alerts, and no inputs in this script by design, since a library's job is to hand other scripts a clean, reusable, well-documented API, not to draw on a chart itself (Pine doesn't allow a library to plot anything anyway). If you're looking for a ready-to-use indicator built on top of this library, see the companion "Pattern Atlas : Geometric Indicator [AxeAlgo]" script, which imports every function here and turns it into on-chart signals, measured-move price targets, a live scanner table, and alerts.
Chart pattern analysis is one of the foundational tools of classical technical analysis, going back to Edwards and Magee's original work and refined since by researchers like Thomas Bulkowski, whose statistical studies of pattern behavior are the closest thing this field has to an industry-standard reference. The patterns in this library follow that standard catalog, so anyone who already knows what a Head and Shoulders top or an Ascending Triangle looks like will recognize exactly what each function is checking for.
WHY A LIBRARY INSTEAD OF ONE MONOLITHIC INDICATOR
Splitting detection logic out as an importable library means:
- Any Pine coder building their own strategy, indicator, or screener can pull in exactly the pattern checks they need without copy-pasting swing-pivot and trendline math into every new script.
- The detection logic is tested and maintained in one place. When a threshold gets refined, everything importing this library benefits from the update by bumping one version number.
- It keeps the math separate from presentation — how a pattern gets drawn, colored, or alerted on is a completely separate decision from whether the pattern is actually present, and different users want different presentations.
HOW TO IMPORT AND USE IT
Add this line near the top of your script (adjust the version number to whatever the current published version is):
import AxeAlgo/Pattern_Atlas_Geometric/1 as geo
Unlike Library #1, most of the functions here need a shared pivot history to work from. Call trackPivots() exactly once per bar, then pass its result into every detect*() function that needs it:
pivots = geo.trackPivots()
match = geo.detectDoubleTopBottom(pivots)
if match.found
label.new(bar_index, high, match.patternName)
Four functions — detectSpike(), detectFlag(), detectPennant(), and detectIslandReversal() — read directly off recent price action instead of the shared pivot history, so they're called without a pivots argument: geo.detectSpike().
trackPivots() takes three optional parameters: leftBars and rightBars (how many less-extreme bars must surround a candidate swing point before it confirms as a pivot — higher values mean fewer, more significant pivots, at the cost of a longer confirmation lag), and maxPivots (how much pivot history to retain). All three have sensible defaults.
Every detect*() function returns the same structure, called ChartPatternMatch, so the calling pattern is identical no matter which of the 17 you use. It has nine fields:
- found — true if the pattern matched at the evaluated bar, false otherwise.
- patternName — the specific name of what matched (e.g. "Ascending Triangle"), na when not found.
- direction — "bullish" or "bearish".
- pivotBars — bar_index of each pivot the match was built from, in chronological order.
- pivotPrices — price of each pivot, in the same order as pivotBars.
- breakoutLevel — the support, resistance, or neckline level price broke through to confirm the pattern.
- necklineSlope — slope (price per bar) of the breakout line, na when the pattern's breakout level isn't a sloped line.
- barIndex — the bar_index the pattern completes (breaks out) on.
- description — a full sentence naming the pattern and the actual measured price levels that triggered it — genuinely useful for a tooltip or an alert message, not just a repeat of the pattern name.
Two additional exported functions turn that raw match into something more actionable, and both work on any ChartPatternMatch regardless of which detect*() function produced it:
- patternStrength(match) — a 0-100 score for how decisively the confirmation close broke through breakoutLevel, relative to the pattern's own price range. A breakout that clears the level by a meaningful fraction of the pattern's own size scores higher than a one-tick poke through it.
- patternTarget(match) — a classical measured-move price target, projecting the pattern's own height from the breakout point. Returns na for patterns without a reliable height to project from (V-Top/V-Bottom Spike, Island Reversal, Bump-and-Run Reversal).
Every detect*() function also exposes its own set of tunable threshold parameters — how flat a "flat top" has to be, how much two shoulders can differ and still count as equal, and so on — all with sensible defaults so you don't have to touch them unless you want to tighten or loosen a specific pattern's sensitivity for a particular instrument or timeframe.
THE 17 PATTERNS
Reversal patterns (7) — signal a potential change in the prevailing trend:
- Head and Shoulders / Inverse Head and Shoulders — detectHeadAndShoulders(). Three swing extremes with the middle one more extreme than the two roughly-equal outer ones, confirmed when price breaks the neckline connecting the two points between them.
- Double Top / Double Bottom — detectDoubleTopBottom(). Two roughly equal peaks (or troughs) with a retracement between them, confirmed when price breaks back through that retracement level.
- Triple Top / Triple Bottom — detectTripleTopBottom(). The same idea as a Double Top/Bottom with a third roughly-equal touch, confirmed on the break of the support or resistance formed between the touches.
- Rounding Top / Rounding Bottom — detectRoundingTopBottom(). A gradual, curved advance-and-rollover (or decline-and-recovery) between two similar edge levels. Approximate: read from three swing pivots rather than fitting a true curve.
- Diamond Top / Diamond Bottom — detectDiamondTopBottom(). Swing range that widens and then narrows again, confirmed on a break of the resulting support or resistance. Rare and approximate: read from three pivot pairs rather than a clean diamond outline.
- Broadening Formation — detectBroadeningTopBottom(). Diverging highs and lows forming an increasingly volatile range, confirmed on a break of either edge. Approximate: read from two pivot pairs rather than a hand-fitted diverging channel.
- V-Top / V-Bottom (Spike) — detectSpike(). A single sharp extreme with no rounding — a large move into the pivot and an equally large move away from it, both measured against the recent average bar range, within a handful of bars. Self-contained, no pivots argument needed.
Continuation patterns (8) — typically resolve in the direction of the move that preceded them:
- Ascending Triangle — detectTriangleAscending(). Flat resistance with rising support, confirmed on a break above resistance.
- Descending Triangle — detectTriangleDescending(). Flat support with falling resistance, confirmed on a break below support.
- Symmetrical Triangle — detectTriangleSymmetrical(). Converging highs and rising lows, confirmed (bullish or bearish) whichever side the price actually breaks.
- Rising Wedge / Falling Wedge — detectWedge(). Both trendlines slope the same direction and converge; breaks the opposite way from the slope, since the shared-direction move was already losing momentum.
- Bull Flag / Bear Flag — detectFlag(). A strong directional move (the pole), followed by a tight, roughly parallel pullback, confirmed on a break back out in the pole's direction. Self-contained, no pivots argument needed.
- Bull Pennant / Bear Pennant — detectPennant(). The same pole-and-consolidation structure as a Flag, but the consolidation narrows and converges rather than staying parallel. Self-contained, no pivots argument needed.
- Rectangle — detectRectangle(). Price boxed between flat support and flat resistance, confirmed on a break of either edge.
- Cup and Handle / Inverted Cup and Handle — detectCupAndHandle(). A rounded recovery (or decline) back to its starting rim, then a shallow pullback (the handle), confirmed on a break through the rim.
Structural / gap-based patterns (2):
- Bullish / Bearish Island Reversal — detectIslandReversal(). A bar (or small cluster) isolated by a gap on both sides, then abandoned by a gap the other way — an abrupt reversal. Self-contained, pure gap logic, no pivots argument needed.
- Bump-and-Run Reversal — detectBumpAndRun(). A lead-in trendline, then a "bump" phase accelerating well beyond it, then a "run" breaking back through the lead-in line. Approximate: the lead-in line is read from just two pivots rather than a hand-drawn trendline.
WHAT THIS LIBRARY DELIBERATELY DOES NOT DO
No plotting, no drawing, no alertcondition() calls, and no inputs — Pine doesn't allow any of those inside a library in the first place, since a library can never be added to a chart on its own. If you want signals, price targets, a scanner table, or alerts, import this library into your own script (or use the companion "Pattern Atlas : Chart Pattern Scanner [AxeAlgo]" indicator, which does exactly that) rather than expecting this script to render anything by itself.
This library also does not evaluate multi-timeframe data, volume, or broader market structure — it's swing-pivot and trendline geometry only, on purpose, so its behavior is easy to reason about and easy to reuse as one building block among several.
Four of the seventeen patterns are explicitly noted above as approximate: Rounding Top/Bottom, Diamond Top/Bottom, Broadening Formation, and Bump-and-Run Reversal are read from a small, fixed number of swing pivots rather than fitting a true curve or hand-drawn trendline to the data. They will not catch every textbook-perfect example of these shapes, and they may occasionally flag a looser approximation of one. Treat them as a starting point for further chart review, not a final word.
PART OF A LARGER SERIES
This is Library #2 in the AxeAlgo Pattern Atlas — a planned set of Pine libraries splitting pattern detection by the method actually used to find each kind of pattern: candlestick shape (Library #1, already published), classical chart/geometric patterns (this library), harmonic patterns (Fibonacci-ratio XABCD structures), and market-structure concepts (order blocks, liquidity, Wyckoff-style events). Each library is independent and useful on its own; together they're meant to cover technical pattern analysis without forcing unrelated detection methods into the same function.
A NOTE ON REPAINTING
trackPivots() only confirms a swing pivot once rightBars bars have passed since it happened — the same confirmation lag ta.pivothigh()/ta.pivotlow() use, just written out as plain comparisons so it works safely inside a library's exported functions. That means a pivot never moves or disappears once confirmed; it just takes rightBars bars to become known, which is a normal and unavoidable part of swing-pivot detection, not a defect in this library. On the currently-forming bar, a pattern's found status can still change tick to tick as that bar's own high, low, and close move — that's inherent to reading live price action. If you're building persisted signals, drawings, alerts, or price targets on top of these functions (rather than a live "what's happening right now" readout), gate your usage on barstate.isconfirmed so a signal only fires once the bar it describes has actually closed, exactly like the companion scanner indicator does.
DISCLAIMER
This library is a technical analysis tool for identifying classical chart pattern shapes in historical and live price data. It does not predict future price movement, and a detected pattern — including any projected price target — is a description of past price action, not a signal guaranteed to repeat. Nothing in this script constitutes financial advice. Always combine pattern recognition with your own risk management and broader analysis before making any trading decision.
Bibliothèque Pine
Dans l'esprit TradingView, l'auteur a publié ce code Pine sous forme de bibliothèque open source afin que d'autres programmeurs Pine de notre communauté puissent le réutiliser. Bravo à l'auteur! Vous pouvez utiliser cette bibliothèque à titre privé ou dans d'autres publications open source, mais la réutilisation de ce code dans des publications est régie par nos Règles.
◆ AxeAlgo | axealgo.com
6 years building Pine Script indicators & strategies
6 years building Pine Script indicators & strategies
Clause de non-responsabilité
Les informations et publications ne sont pas destinées à être, et ne constituent pas, des conseils ou recommandations financiers, d'investissement, de trading ou autres fournis ou approuvés par TradingView. Pour en savoir plus, consultez les Conditions d'utilisation.
Bibliothèque Pine
Dans l'esprit TradingView, l'auteur a publié ce code Pine sous forme de bibliothèque open source afin que d'autres programmeurs Pine de notre communauté puissent le réutiliser. Bravo à l'auteur! Vous pouvez utiliser cette bibliothèque à titre privé ou dans d'autres publications open source, mais la réutilisation de ce code dans des publications est régie par nos Règles.
◆ AxeAlgo | axealgo.com
6 years building Pine Script indicators & strategies
6 years building Pine Script indicators & strategies
Clause de non-responsabilité
Les informations et publications ne sont pas destinées à être, et ne constituent pas, des conseils ou recommandations financiers, d'investissement, de trading ou autres fournis ou approuvés par TradingView. Pour en savoir plus, consultez les Conditions d'utilisation.