// Downloaded From https://www.WiseStockTrader.com /* HARMONIC PATTERN DETECTION using ATR type Peaks and Troughs Automatic Detection of Harmonic Patterns - Gartley, Bat, Butterfly and Crab. Original code by joy.edakad@gmail.com, see: http://www.inditraders.com/amibroker/1934-afl-harmonic-patterns.html file: Harmonic1.1.afl (2009) Modernized by E.M.Pottasch - Using ATR based pivots instead of fractal based - Improved visualisation of the patterns. - Nomenclature of variables, constants and arrays, adjusted following code from David Keleher. - uncompleted pivots given white color - multiple issues of the original code corrected for - added potential reversal zones The original code was based on "fractal type pivots", this code uses "ATR type pivots". This code also includes a timeframe factor. To fully understand how to interpret a pattern use the Amibroker playback utility and see how the patterns develop. The potential reversal zones are based on the parameter constraints for each pattern. 1 pattern may transform into another pattern. Only the last pattern is shown, however the reversal zones for subsequent patterns are shown. E.M.Pottasch (Jan 2017). */ Version( 6.0 ); GfxSetZOrder( -5 ); GfxSetCoordsMode( 1 ); BullBat4 = BullButterfly4 = BullCrab4 = BullGartley4 = 0; BullBat = BullButterfly = BullCrab = BullGartley = 0; BearBat4 = BearButterfly4 = BearCrab4 = BearGartley4 = 0; BearBat = BearButterfly = BearCrab = BearGartley = 0; pk = tr = pkn = trn = 0; bi = BarIndex(); fvb = FirstVisibleValue( bi ); lvb = LastVisibleValue( bi ); GraphXSpace = 5; SetChartBkColor( colorBlack ); SetChartOptions( 1, chartShowDates, chartGridMiddle, 0, 0, 0 ); SetBarFillColor( IIf( C > O, ColorRGB( 0, 75, 0 ), IIf( C <= O, ColorRGB( 75, 0, 0 ), colorLightGrey ) ) ); Plot( C, "", IIf( C > O, ColorRGB( 0, 255, 0 ), IIf( C <= O, ColorRGB( 255, 0, 0 ), colorLightGrey ) ), 64, Null, Null, 0, 0, 1 ); _SECTION_BEGIN( "Patterns" ); perBull = Param( "Bullish ATR Period", 20, 1, 150, 1 ); perBear = Param( "Bearish ATR Period", 20, 1, 150, 1 ); multBull = Param( "Bullish ATR Multiple", 2, 1, 4, 0.05 ); multBear = Param( "Bearish ATR Multiple", 2, 1, 4, 0.05 ); trailValueClose = ParamToggle( "Trail value", "High/Low|Close", 1 ); //tfrm = in1Minute * Param( "Time Frame (min)", 5, 1, 1440 * 10, 1 ); // 1440 minutes is 1 day tfrm = in1Minute * Interval() / 60 * Param( "Chart Time Frame Factor", 1, 1, 10, 1 ); // factor 1 uses timeframe of chart showATRPivots = ParamToggle( "Show ATR Pivots", "Off|On", 0 ); showLabels = ParamToggle( "Show ATR Pivot Labels", "Off|On", 0 ); bu = ParamToggle( "Show Bullish Pattern", "Off|On", 1 ); be = ParamToggle( "Show Bearish Pattern", "Off|On", 1 ); nBull = Param( "Max Number of Bullish Patterns", 10, 0, 100, 1 ); nBear = Param( "Max Number of Bearish Patterns", 10, 0, 100, 1 ); dBat = ParamToggle( "Draw Bat", "Off|On", 1 ); dBut = ParamToggle( "Draw Buterfly", "Off|On", 1 ); dCrab = ParamToggle( "Draw Crab", "Off|On", 1 ); dGart = ParamToggle( "Draw Gartley", "Off|On", 1 ); showPatternDevelopmentPoints = ParamToggle( "Show Points of Pattern Development", "Off|On", 1 ); showPatternLabels = ParamToggle( "Show Pattern Labels", "Off|On", 1 ); showPatternName = ParamToggle( "Show Pattern Name", "Off|On", 1 ); showReversalZone = ParamToggle( "Show Reversal Zone", "Off|On", 1 ); colorContrastFactor = Param( "Color Contrast Factor", 10, 2, 100, 2 ); _SECTION_END(); _SECTION_BEGIN( "Gartley" ); GarABXAmin = Param( "Swing B Min.(XA)", 0.55, 0.3, 1, 0.01 ); GarABXAmax = Param( "Swing B Max.(XA)", 0.72, 0.4, 1, 0.01 ); GarBCABmin = Param( "Swing C Min.(AB)", 0.38, 0.3, 1.27, 0.01 ); GarBCABmax = Param( "Swing C Max.(AB)", 1.0, 0.4, 1.27, 0.01 ); GarCDXAmin = Param( "Swing D Min.(XA)", 0.55, 0.3, 1, 0.01 ); GarCDXAmax = Param( "Swing D Max.(XA)", 1.0, 0.4, 1.0, 0.01 ); _SECTION_END(); _SECTION_BEGIN( "Bat" ); BatABXAmin = Param( "Swing AB Min.(XA)", 0.38, 0.3, 1, 0.01 ); BatABXAmax = Param( "Swing AB Max.(XA)", 0.55, 0.4, 1, 0.01 ); BatBCABmin = Param( "Swing BC Min.(AB)", 0.38, 0.3, 1.62, 0.01 ); BatBCABmax = Param( "Swing BC Max.(AB)", 1.27, 0.4, 1.62, 0.01 ); BatCDXAmin = Param( "Swing CD Min.(XA)", 0.5, 0.3, 1, 0.01 ); BatCDXAmax = Param( "Swing CD Max.(XA)", 1.0, 0.4, 1.0, 0.01 ); _SECTION_END(); _SECTION_BEGIN( "Butterfly" ); ButABXAmin = Param( "Swing B Min.(XA)", 0.55, 0.3, 1, 0.01 ); ButABXAmax = Param( "Swing B Max.(XA)", 0.9, 0.4, 1, 0.01 ); ButBCABmin = Param( "Swing C Min.(AB)", 0.38, 0.3, 1.62, 0.01 ); ButBCABmax = Param( "Swing C Max.(AB)", 1.27, 0.4, 1.62, 0.01 ); ButCDXAmin = Param( "Swing D Min.(XA)", 1, 1, 1.8, 0.01 ); ButCDXAmax = Param( "Swing D Max.(XA)", 1.38, 1, 1.8, 0.01 ); _SECTION_END(); _SECTION_BEGIN( "Crab" ); CraABXAmin = Param( "Swing B Min.(XA)", 0.38, 0.3, 1, 0.01 ); CraABXAmax = Param( "Swing B Max.(XA)", 0.65, 0.4, 1, 0.01 ); CraBCABmin = Param( "Swing C Min.(AB", 0.38, 0.3, 1.62, 0.01 ); CraBCABmax = Param( "Swing C Max.(AB)", 1.270, 0.4, 1.62, 0.01 ); CraCDXAmin = Param( "Swing D Min.(XA)", 1.25, 1, 1.8, 0.01 ); CraCDXAmax = Param( "Swing D Max.(XA)", 1.8, 1, 2, 0.01 ); _SECTION_END(); function ATRtrail_func() { // Trail code largely from: // http://traders.com/Documentation/FEEDbk_docs/2009/06/TradersTips.html if( trailValueClose ) { tvHigh = C; tvLow = C; } else { tvHigh = H; tvLow = L; } sup = tvHigh - multBull * ATR( perBull ); res = tvLow + multBear * ATR( perBear ); trailARRAY = Null; trailstop = 0; for( i = 1; i < BarCount; i++ ) { if( C[ i ] > trailstop AND C[ i - 1 ] > trailstop ) trailstop = Max( trailstop, sup[ i ] ); else if( C[ i ] < trailstop AND C[ i - 1 ] < trailstop ) trailstop = Min( trailstop, res[ i ] ); else trailstop = IIf( C[ i ] > trailstop, sup[ i ], res[ i ] ); trailARRAY[ i ] = trailstop; } return trailARRAY; } TimeFrameSet( tfrm ); trBull = multBull * ATR( perBull ); trBear = multBear * ATR( perBear ); trailArray = ATRtrail_func(); ts = IIf( trailArray > C, trailArray, Null ); // dntrend tl = IIf( trailArray < C, trailArray, Null ); // uptrend TimeFrameRestore(); ts = TimeFrameExpand( ts, tfrm, expandlast ); tl = TimeFrameExpand( tl, tfrm, expandlast ); lll = LLV( L, BarsSince( !IsEmpty( tl ) ) ); lll = IIf( ts, lll, Null ); trn = ts AND L == lll; hhh = HHV( H, BarsSince( !IsEmpty( ts ) ) ); hhh = IIf( tl, hhh, Null ); pkn = tl AND H == hhh; tr = ExRem( Reverse( trn ), Reverse( pkn ) ); pk = ExRem( Reverse( pkn ), Reverse( trn ) ); tr = Reverse( tr ); pk = Reverse( pk ); for( i = 0; i < 3; i++ ) { VarSet( "px" + i, ValueWhen( pk, bi, i ) ); VarSet( "tx" + i, ValueWhen( tr, bi, i ) ); VarSet( "ph" + i, ValueWhen( pk, H, i ) ); VarSet( "tl" + i, ValueWhen( tr, L, i ) ); } ll = tr AND tl1 < tl2; hl = tr AND tl1 > tl2; hh = pk AND ph1 > ph2; lh = pk AND ph1 < ph2; dt = pk AND ph1 == ph2; db = tr AND tl1 == tl2; if( showATRPivots ) { PlotShapes( shapeSmallCircle * tr, IIf( tx1 < px0, ColorRGB( 0, 0, 255 ), colorWhite ), 0, L, -10 ); PlotShapes( shapeSmallCircle * pk, IIf( px1 < tx0, ColorRGB( 255, 0, 0 ), colorWhite ), 0, H, 10 ); } // +++ Bullish Patterns PTvalid = ( px1 > tx1 AND tx1 > px2 AND px2 > tx2 ) AND pk; if( dGart AND bu ) { BullGartley4 = PTvalid AND( ph2 - tl1 ) / ( ph2 - tl2 ) > GarABXAmin AND( ph2 - tl1 ) / ( ph2 - tl2 ) < GarABXAmax AND( ph1 - tl1 ) / ( ph2 - tl1 ) > GarBCABMin AND( ph1 - tl1 ) / ( ph2 - tl1 ) < GarBCABMax; BullGartley = IIf( Nz( LowestSince( BullGartley4, L ) ) < Nz( ValueWhen( BullGartley4, ph2 ) ) - ( Nz( ValueWhen( BullGartley4, ph2 ) ) - Nz( ValueWhen( BullGartley4, tl2 ) ) ) * GarCDXAmin AND Nz( LowestSince( bullGartley4, L ) ) > Nz( ValueWhen( BullGartley4, ph2 ) ) - ( Nz( ValueWhen( BullGartley4, ph2 ) ) - Nz( ValueWhen( BullGartley4, tl2 ) ) ) * GarCDXAmax AND Nz( HighestSince( BullGartley4, H ) ) <= Nz( ValueWhen( BullGartley4, ph1 ) ) AND Nz( LowestSince( BullGartley4, L ) ) < Nz( ValueWhen( BullGartley4, tl1 ) ) AND Nz( trn ) AND Nz( LowestSince( bullGartley4, L ) ) == L, True, False ); } if( dBat AND bu ) { BullBat4 = PTvalid AND( ph2 - tl1 ) / ( ph2 - tl2 ) > BatABXAmin AND( ph2 - tl1 ) / ( ph2 - tl2 ) < BatABXAmax AND( ph1 - tl1 ) / ( ph2 - tl1 ) > BatBCABMin AND( ph1 - tl1 ) / ( ph2 - tl1 ) < BatBCABMax; BullBat = IIf( Nz( LowestSince( BullBat4, L ) ) < Nz( ValueWhen( BullBat4, ph2 ) ) - ( Nz( ValueWhen( BullBat4, ph2 ) ) - Nz( ValueWhen( BullBat4, tl2 ) ) ) * BatCDXAmin AND Nz( LowestSince( BullBat4, L ) ) > Nz( ValueWhen( BullBat4, ph2 ) ) - ( Nz( ValueWhen( BullBat4, ph2 ) ) - Nz( ValueWhen( BullBat4, tl2 ) ) ) * BatCDXAmax AND Nz( HighestSince( BullBat4, H ) ) <= Nz( ValueWhen( BullBat4, ph1 ) ) AND Nz( LowestSince( BullBat4, L ) ) < Nz( ValueWhen( BullBat4, tl1 ) ) AND Nz( trn ) AND Nz( LowestSince( BullBat4, L ) ) == L, True, False ); } if( dBut AND bu ) { BullButterfly4 = PTvalid AND( ph2 - tl1 ) / ( ph2 - tl2 ) > ButABXAmin AND( ph2 - tl1 ) / ( ph2 - tl2 ) < ButABXAMax AND( ph1 - tl1 ) / ( ph2 - tl1 ) > ButBCABmin AND( ph1 - tl1 ) / ( ph2 - tl1 ) < ButBCABmax; BullButterfly = IIf( Nz( LowestSince( BullButterfly4, L ) ) < Nz( ValueWhen( BullButterfly4, ph2 ) ) - ( Nz( ValueWhen( BullButterfly4, ph2 ) ) - Nz( ValueWhen( BullButterfly4, tl2 ) ) ) * ButCDXAMin AND Nz( LowestSince( BullButterfly4, L ) ) > Nz( ValueWhen( BullButterfly4, ph2 ) ) - ( Nz( ValueWhen( BullButterfly4, ph2 ) ) - Nz( ValueWhen( BullButterfly4, tl2 ) ) ) * ButCDXAmax AND Nz( HighestSince( BullButterfly4, H ) ) <= Nz( ValueWhen( BullButterfly4, ph1 ) ) AND Nz( LowestSince( BullButterfly4, L ) ) < Nz( ValueWhen( BullButterfly4, tl2 ) ) AND Nz( trn ) AND Nz( LowestSince( bullButterfly4, L ) ) == L, True, False ); } if( dCrab AND bu ) { BullCrab4 = PTvalid AND( ph2 - tl1 ) / ( ph2 - tl2 ) > CraABXAmin AND( ph2 - tl1 ) / ( ph2 - tl2 ) < CraABXAmax AND( ph1 - tl1 ) / ( ph2 - tl1 ) > CraBCABmin AND( ph1 - tl1 ) / ( ph2 - tl1 ) < CraBCABmax; BullCrab = IIf( Nz( LowestSince( BullCrab4, L ) ) < Nz( ValueWhen( BullCrab4, ph2 ) ) - ( Nz( ValueWhen( BullCrab4, ph2 ) ) - Nz( ValueWhen( BullCrab4, tl2 ) ) ) * CraCDXAmin AND Nz( LowestSince( BullCrab4, L ) ) > Nz( ValueWhen( BullCrab4, ph2 ) ) - ( Nz( ValueWhen( BullCrab4, ph2 ) ) - Nz( ValueWhen( BullCrab4, tl2 ) ) ) * CraCDXAmax AND Nz( HighestSince( BullCrab4, H ) ) <= Nz( ValueWhen( BullCrab4, ph1 ) ) AND Nz( LowestSince( BullCrab4, L ) ) < Nz( ValueWhen( BullCrab4, tl2 ) ) AND Nz( trn ) AND Nz( LowestSince( bullCrab4, L ) ) == L, True, False ); } BullCrab = BullCrab AND IIf( Nz( ValueWhen( BullCrab4, bi ) ) >= Nz( ValueWhen( BullGartley4, bi ) ) AND Nz( ValueWhen( BullCrab4, bi ) ) >= Nz( ValueWhen( BullBat4, bi ) ) AND Nz( ValueWhen( BullCrab4, bi ) ) >= Nz( ValueWhen( BullButterfly4, bi ) ), 1, 0 ); BullBat = BullBat AND IIf( Nz( ValueWhen( BullBat4, bi ) ) >= Nz( ValueWhen( BullGartley4, bi ) ) AND Nz( ValueWhen( BullBat4, bi ) ) >= Nz( ValueWhen( BullCrab4, bi ) ) AND Nz( ValueWhen( BullBat4, bi ) ) >= Nz( ValueWhen( BullButterfly4, bi ) ), 1, 0 ); BullButterfly = BullButterfly AND IIf( Nz( ValueWhen( BullButterfly4, bi ) ) >= Nz( ValueWhen( BullGartley4, bi ) ) AND Nz( ValueWhen( BullButterfly4, bi ) ) >= Nz( ValueWhen( BullCrab4, bi ) ) AND Nz( ValueWhen( BullButterfly4, bi ) ) >= Nz( ValueWhen( BullBat4, bi ) ), 1, 0 ); BullGartley = BullGartley AND IIf( Nz( ValueWhen( BullGartley4, bi ) ) >= Nz( ValueWhen( BullBat4, bi ) ) AND Nz( ValueWhen( BullGartley4, bi ) ) >= Nz( ValueWhen( BullCrab4, bi ) ) AND Nz( ValueWhen( BullGartley4, bi ) ) >= Nz( ValueWhen( BullButterfly4, bi ) ), 1, 0 ); // remove overlapping patterns BullGartley = IIf( ( BullGartley == BullBat OR BullGartley == BullCrab OR BullGartley == BullButterfly ), 0, BullGartley ); BullBat = IIf( ( BullBat == BullGartley OR BullBat == BullCrab OR BullBat == BullButterfly ), 0, BullBat ); BullButterfly = IIf( ( BullButterfly == BullGartley OR BullButterfly == BullCrab OR BullButterfly == BullBat ), 0, BullButterfly ); BullCrab = IIf( ( BullCrab == BullGartley OR BullCrab == BullBat OR BullCrab == BullButterfly ), 0, BullCrab ); BullHar4 = BullGartley4 OR BullButterfly4 OR BullBat4 OR BullCrab4 ; BullHar = BullGartley OR BullButterfly OR BullBat OR BullCrab ; buXy = ValueWhen( BullHar4, tl2 ); buXx = ValueWhen( BullHar4, tx2 ); buAy = ValueWhen( BullHar4, ph2 ); buAx = ValueWhen( BullHar4, px2 ); buBy = ValueWhen( BullHar4, tl1 ); buBx = ValueWhen( BullHar4, tx1 ); buCy = ValueWhen( BullHar4, ph1 ); buCx = ValueWhen( BullHar4, px1 ); buDy = ValueWhen( BullHar, L ); buDx = ValueWhen( BullHar, bi ); buABdXA = ( buAy - buBy ) / ( buAy - buXy ); buBCdAB = ( buCy - buBy ) / ( buAy - buBy ); buADdXA = ( buAy - buDy ) / ( buAy - buXy ); buBCdCD = ( buCy - buDy ) / ( buCy - buBy ); function drawBullishPattern( i, patternName ) { GfxSetZOrder( -1 ); GfxSelectPen( ColorRGB( 0, 0, 255 ), 1, 5 ); GfxSelectSolidBrush( ColorRGB( 0, 0, 50 ) ); GfxPolygon( buXx[i], buXy[i], buAx[i], buAy[i], buBx[i], buBy[i], buCx[i], buCy[i], buDx[i], buDy[i], buBx[i], buBy[i], buXx[i], buXy[i] ); GfxSelectPen( ColorRGB( 0, 0, 255 ), 2, 0 ); GfxMoveTo( buXx[i], buXy[i] ); GfxLineTo( buAx[i], buAy[i] ); GfxMoveTo( buAx[i], buAy[i] ); GfxLineTo( buBx[i], buBy[i] ); GfxMoveTo( buBx[i], buBy[i] ); GfxLineTo( buCx[i], buCy[i] ); GfxMoveTo( buCx[i], buCy[i] ); GfxLineTo( buDx[i], buDy[i] ); GfxMoveTo( buXx[i], buXy[i] ); GfxLineTo( buAx[i], buAy[i] ); GfxSelectPen( ColorRGB( 0, 0, 255 ), 1, 2 ); GfxMoveTo( buXx[i], buXy[i] ); GfxLineTo( buBx[i], buBy[i] ); GfxMoveTo( buAx[i], buAy[i] ); GfxLineTo( buCx[i], buCy[i] ); GfxMoveTo( buBx[i], buBy[i] ); GfxLineTo( buDx[i], buDy[i] ); GfxMoveTo( buXx[i], buXy[i] ); GfxLineTo( buDx[i], buDy[i] ); if( showPatternName ) { GfxSetZOrder( 1 ); GfxSetCoordsMode( 1 ); GfxSetTextColor( ColorRGB( 0, 100, 255 ) ); GfxSelectFont( "Helvetica", 10, 700 ); GfxSetTextAlign( 0 | 8 ); GfxTextOut( patternName, buCx[i] + 4, buCy[i] ); } GfxSetZOrder( 1 ); GfxSetTextAlign( 0 | 0 ); GfxSetTextColor( ColorRGB( 0, 150, 255 ) ); GfxSelectFont( "Helvetica", 8, 700 ); GfxTextOut( "" + Prec( buABdXA[i], 2 ), ( buBx[i] + buXx[i] ) / 2, ( buBy[i] + buXy[i] ) / 2 ); GfxTextOut( "" + Prec( buBCdAB[i], 2 ), ( buCx[i] + buAx[i] ) / 2, ( buCy[i] + buAy[i] ) / 2 ); GfxTextOut( "" + Prec( buADdXA[i], 2 ), ( buDx[i] + buXx[i] ) / 2, ( buDy[i] + buXy[i] ) / 2 ); GfxTextOut( "" + Prec( buBCdCD[i], 2 ), ( buBx[i] + buDx[i] ) / 2, ( buBy[i] + buDy[i] ) / 2 ); if( showPatternLabels ) { GfxSetZOrder( 1 ); GfxSetTextColor( ColorRGB( 0, 150, 255 ) ); GfxSelectFont( "Helvetica", 11, 700 ); GfxSetTextAlign( 0 | 24 ); GfxTextOut( "X", buXx[i] - 2, buXy[i] ); GfxTextOut( "A", buAx[i] - 2, buAy[i] ); GfxTextOut( "B", buBx[i] - 2, buBy[i] ); GfxTextOut( "C", buCx[i] + 1, buCy[i] ); GfxTextOut( "D", buDx[i] + 1, buDy[i] ); } } function drawBullishReversalZone( i, CDXAmin, CDXAmax, cntzones, pname ) { clr1 = ColorRGB( 0, 80 + cntzones * colorContrastFactor, 140 + cntzones * colorContrastFactor ); clr2 = ColorRGB( 0, 20 + cntzones * colorContrastFactor, 35 + cntzones * colorContrastFactor ); GfxSetZOrder( 1 ); GfxSelectPen( clr1, 1, 1 ); GfxMoveTo( buCx[i], buAy[i] - ( buAy[i] - buXy[i] )*CDXAmin ); GfxLineTo( Max( i, buDx[i] ), buAy[i] - ( buAy[i] - buXy[i] )*CDXAmin ); GfxMoveTo( buCx[i], buAy[i] - ( buAy[i] - buXy[i] )*CDXAmin ); GfxLineTo( buCx[i], buAy[i] - ( buAy[i] - buXy[i] )*CDXAmax ); GfxMoveTo( buCx[i], buAy[i] - ( buAy[i] - buXy[i] )*CDXAmax ); GfxLineTo( Max( i, buDx[i] ), buAy[i] - ( buAy[i] - buXy[i] )*CDXAmax ); GfxMoveTo( Max( i, buDx[i] ), buAy[i] - ( buAy[i] - buXy[i] )*CDXAmin ); GfxLineTo( Max( i, buDx[i] ), buAy[i] - ( buAy[i] - buXy[i] )*CDXAmax ); GfxSetZOrder( -2 ); GfxSelectSolidBrush( clr2 ); GfxPolygon( buCx[i], buAy[i] - ( buAy[i] - buXy[i] )*CDXAmin, Max( i, buDx[i] ), buAy[i] - ( buAy[i] - buXy[i] )*CDXAmin, Max( i, buDx[i] ), buAy[i] - ( buAy[i] - buXy[i] )*CDXAmax, buCx[i], buAy[i] - ( buAy[i] - buXy[i] )*CDXAmax, buCx[i], buAy[i] - ( buAy[i] - buXy[i] )*CDXAmin ); GfxSetZOrder( 1 ); GfxSetTextColor( ColorRGB( 0, 100, 255 ) ); GfxSelectFont( "Helvetica", 7, 700 ); GfxSetTextAlign( 0 | 8 ); GfxTextOut( pname, buCx[i] + 0, buAy[i] - ( buAy[i] - buXy[i] )*CDXAmin ); } function drawBullishPatterns() { flag1 = 1; flag2 = 0; cnt = 0; for( i = lvb; i > fvb; i-- ) { if( BullHar[i] AND flag1 AND cnt < nBull ) { flag1 = 0; flag2 = 1; cnt = cnt + 1; if( BullButterfly[i] AND bu AND dBut ) { drawBullishPattern( i, "Bullish Butterfly" ); } else if( BullCrab[i] AND bu AND dCrab ) { drawBullishPattern( i, "Bullish Crab" ); } else if( BullBat[i] AND bu AND dBat ) { drawBullishPattern( i, "Bullish Bat" ); } else if( BullGartley[i] AND bu AND dGart ) { drawBullishPattern( i, "Bullish Gartley" ); } } if( BullHar4[i] AND flag2 ) { flag1 = 1; flag2 = 0; } } } function manageBullishReversalZones() { cnt = 0; cntzones = 0; ButFlag1 = 1; CraFlag1 = 1; BatFlag1 = 1; GarFlag1 = 1; yMax = yMin = 0; for( i = lvb; i > fvb; i-- ) { if( BullButterfly[i] AND bu AND dBut AND ButFlag1 AND( L[i] < yMin OR L[i] > yMax[i] ) ) { ButFlag1 = 0; CraFlag1 = 1; BatFlag1 = 1; GarFlag1 = 1; drawBullishReversalZone( i, ButCDXAmin, ButCDXAmax, cntzones, "Butterfly" ); yMax = buAy[i] - ( buAy[i] - buXy[i] ) * ButCDXAmax; yMin = buAy[i] - ( buAy[i] - buXy[i] ) * ButCDXAmin; cntzones = cntzones + 1; } if( BullCrab[i] AND bu AND dCrab AND CraFlag1 AND( L[i] < yMin OR L[i] > yMax[i] ) ) { ButFlag1 = 1; CraFlag1 = 0; BatFlag1 = 1; GarFlag1 = 1; drawBullishReversalZone( i, CraCDXAmin, CraCDXAmax, cntzones, "Crab" ); yMax = buAy[i] - ( buAy[i] - buXy[i] ) * CraCDXAmax; yMin = buAy[i] - ( buAy[i] - buXy[i] ) * CraCDXAmin; cntzones = cntzones + 1; } if( BullBat[i] AND bu AND dBat AND BatFlag1 AND( L[i] < yMin OR L[i] > yMax[i] ) ) { ButFlag1 = 1; CraFlag1 = 1; BatFlag1 = 0; GarFlag1 = 1; drawBullishReversalZone( i, BatCDXAmin, BatCDXAmax, cntzones, "Bat" ); yMax = buAy[i] - ( buAy[i] - buXy[i] ) * BatCDXAmax; yMin = buAy[i] - ( buAy[i] - buXy[i] ) * BatCDXAmin; cntzones = cntzones + 1; } if( BullGartley[i] AND bu AND dGart AND GarFlag1 AND( L[i] < yMin OR L[i] > yMax[i] ) ) { ButFlag1 = 1; CraFlag1 = 1; BatFlag1 = 1; GarFlag1 = 0; drawBullishReversalZone( i, GarCDXAmin, GarCDXAmax, cntzones, "Gartley" ); yMax = buAy[i] - ( buAy[i] - buXy[i] ) * GarCDXAmax; yMin = buAy[i] - ( buAy[i] - buXy[i] ) * GarCDXAmin; cntzones = cntzones + 1; } if( BullHar4[i] ) { ButFlag1 = 1; CraFlag1 = 1; BatFlag1 = 1; GarFlag1 = 1; cnt = cnt + 1; yMax = 0; yMin = 0; cntzones = 0; } if( cnt >= nBull ) break; } } drawBullishPatterns(); if( showReversalZone ) manageBullishReversalZones(); // +++ Bearish Patterns PTvalid = ( tx1 > px1 AND px1 > tx2 AND tx2 > px2 ) AND tr; if( dGart AND be ) { BearGartley4 = PTvalid AND( ph1 - tl2 ) / ( ph2 - tl2 ) > GarABXAmin AND( ph1 - tl2 ) / ( ph2 - tl2 ) < GarABXAmax AND ( ph1 - tl1 ) / ( ph1 - tl2 ) > GarBCABmin AND( ph1 - tl1 ) / ( ph1 - tl2 ) < GarBCABmax; BearGartley = IIf( Nz( HighestSince( bearGartley4, H ) ) > Nz( ValueWhen( BearGartley4, tl2 ) ) + ( Nz( ValueWhen( BearGartley4, ph2 ) ) - Nz( ValueWhen( BearGartley4, tl2 ) ) ) * GarCDXAmin AND Nz( HighestSince( bearGartley4, H ) ) < Nz( ValueWhen( BearGartley4, tl2 ) ) + ( Nz( ValueWhen( BearGartley4, ph2 ) ) - Nz( ValueWhen( BearGartley4, tl2 ) ) ) * GarCDXAMax AND Nz( LowestSince( BearGartley4, L ) ) >= Nz( ValueWhen( BearGartley4, tl1 ) ) AND Nz( HighestSince( BearGartley4, H ) ) > Nz( ValueWhen( BearGartley4, ph1 ) ) AND Nz( pkn ) AND Nz( HighestSince( BearGartley4, H ) ) == H, True, False ); } if( dBat AND be ) { BearBat4 = PTvalid AND( ph1 - tl2 ) / ( ph2 - tl2 ) > BatABXAmin AND( ph1 - tl2 ) / ( ph2 - tl2 ) < BatABXAmax AND ( ph1 - tl1 ) / ( ph1 - tl2 ) > BatBCABmin AND( ph1 - tl1 ) / ( ph1 - tl2 ) < BatBCABmax; BearBat = IIf( Nz( HighestSince( BearBat4, H ) ) > Nz( ValueWhen( BearBat4, tl2 ) ) + ( Nz( ValueWhen( BearBat4, ph2 ) ) - Nz( ValueWhen( BearBat4, tl2 ) ) ) * BatCDXAmin AND Nz( HighestSince( BearBat4, H ) ) < Nz( ValueWhen( BearBat4, tl2 ) ) + ( Nz( ValueWhen( BearBat4, ph2 ) ) - Nz( ValueWhen( BearBat4, tl2 ) ) ) * BatCDXAMax AND Nz( LowestSince( BearBat4, L ) ) >= Nz( ValueWhen( BearBat4, tl1 ) ) AND Nz( HighestSince( BearBat4, H ) ) > Nz( ValueWhen( BearBat4, ph1 ) ) AND Nz( pkn ) AND Nz( HighestSince( BearBat4, H ) ) == H, True, False ); } if( dBut AND be ) { BearButterfly4 = PTvalid AND( ph1 - tl2 ) / ( ph2 - tl2 ) > ButABXAmin AND( ph1 - tl2 ) / ( ph2 - tl2 ) < ButABXAmax AND ( ph1 - tl1 ) / ( ph1 - tl2 ) > ButBCABmin AND( ph1 - tl1 ) / ( ph1 - tl2 ) < ButBCABmax; BearButterfly = IIf( Nz( HighestSince( BearButterfly4, H ) ) > Nz( ValueWhen( BearButterfly4, tl2 ) ) + ( Nz( ValueWhen( BearButterfly4, ph2 ) ) - Nz( ValueWhen( BearButterfly4, tl2 ) ) ) * ButCDXAmin AND Nz( HighestSince( BearButterfly4, H ) ) < Nz( ValueWhen( BearButterfly4, tl2 ) ) + ( Nz( ValueWhen( BearButterfly4, ph2 ) ) - Nz( ValueWhen( BearButterfly4, tl2 ) ) ) * ButCDXAMax AND Nz( LowestSince( BearButterfly4, L ) ) >= Nz( ValueWhen( BearButterfly4, tl1 ) ) AND Nz( HighestSince( BearButterfly4, H ) ) > Nz( ValueWhen( BearButterfly4, ph2 ) ) AND Nz( pkn ) AND Nz( HighestSince( BearButterfly4, H ) ) == H, True, False ); } if( dCrab AND be ) { BearCrab4 = PTvalid AND( ph1 - tl2 ) / ( ph2 - tl2 ) > CraABXAmin AND( ph1 - tl2 ) / ( ph2 - tl2 ) < CraABXAmax AND ( ph1 - tl1 ) / ( ph1 - tl2 ) > CraBCABmin AND( ph1 - tl1 ) / ( ph1 - tl2 ) < CraBCABmax; BearCrab = IIf( Nz( HighestSince( BearCrab4, H ) ) > Nz( ValueWhen( BearCrab4, tl2 ) ) + ( Nz( ValueWhen( BearCrab4, ph2 ) ) - Nz( ValueWhen( BearCrab4, tl2 ) ) ) * CraCDXAmin AND Nz( HighestSince( BearCrab4, H ) ) < Nz( ValueWhen( BearCrab4, tl2 ) ) + ( Nz( ValueWhen( BearCrab4, ph2 ) ) - Nz( ValueWhen( BearCrab4, tl2 ) ) ) * CraCDXAMax AND Nz( LowestSince( BearCrab4, L ) ) >= Nz( ValueWhen( BearCrab4, tl1 ) ) AND Nz( HighestSince( BearCrab4, H ) ) > Nz( ValueWhen( BearCrab4, ph2 ) ) AND Nz( pkn ) AND Nz( HighestSince( BearCrab4, H ) ) == H, True, False ); } BearCrab = BearCrab AND IIf( Nz( ValueWhen( BearCrab4, bi ) ) >= Nz( ValueWhen( BearGartley4, bi ) ) AND Nz( ValueWhen( BearCrab4, bi ) ) >= Nz( ValueWhen( BearBat4, bi ) ) AND Nz( ValueWhen( BearCrab4, bi ) ) >= Nz( ValueWhen( BearButterfly4, bi ) ), 1, 0 ); BearBat = BearBat AND IIf( Nz( ValueWhen( BearBat4, bi ) ) >= Nz( ValueWhen( BearGartley4, bi ) ) AND Nz( ValueWhen( BearBat4, bi ) ) >= Nz( ValueWhen( BearCrab4, bi ) ) AND Nz( ValueWhen( BearBat4, bi ) ) >= Nz( ValueWhen( BearButterfly4, bi ) ), 1, 0 ); BearButterfly = BearButterfly AND IIf( Nz( ValueWhen( BearButterfly4, bi ) ) >= Nz( ValueWhen( BearGartley4, bi ) ) AND Nz( ValueWhen( BearButterfly4, bi ) ) >= Nz( ValueWhen( BearCrab4, bi ) ) AND Nz( ValueWhen( BearButterfly4, bi ) ) >= Nz( ValueWhen( BearBat4, bi ) ), 1, 0 ); BearGartley = BearGartley AND IIf( Nz( ValueWhen( BearGartley4, bi ) ) >= Nz( ValueWhen( BearBat4, bi ) ) AND Nz( ValueWhen( BearGartley4, bi ) ) >= Nz( ValueWhen( BearCrab4, bi ) ) AND Nz( ValueWhen( BearGartley4, bi ) ) >= Nz( ValueWhen( BearButterfly4, bi ) ), 1, 0 ); // remove overlapping patterns BearGartley = IIf( ( BearGartley == BearBat OR BearGartley == BearCrab OR BearGartley == BearButterfly ), 0, BearGartley ); BearBat = IIf( ( BearBat == BearGartley OR BearBat == BearCrab OR BearBat == BearButterfly ), 0, BearBat ); BearButterfly = IIf( ( BearButterfly == BearGartley OR BearButterfly == BearCrab OR BearButterfly == BearBat ), 0, BearButterfly ); BearCrab = IIf( ( BearCrab == BearGartley OR BearCrab == BearBat OR BearCrab == BearButterfly ), 0, BearCrab ); BearHar4 = BearGartley4 OR BearButterfly4 OR BearBat4 OR BearCrab4 ; BearHar = BearGartley OR BearButterfly OR BearBat OR BearCrab ; beXy = ValueWhen( BearHar4, ph2 ); beXx = ValueWhen( BearHar4, px2 ); beAy = ValueWhen( BearHar4, tl2 ); beAx = ValueWhen( BearHar4, tx2 ); beBy = ValueWhen( BearHar4, ph1 ); beBx = ValueWhen( BearHar4, px1 ); beCy = ValueWhen( BearHar4, tl1 ); beCx = ValueWhen( BearHar4, tx1 ); beDy = ValueWhen( BearHar, H ); beDx = ValueWhen( BearHar, bi ); beABdXA = ( beBy - beAy ) / ( beXy - beAy ); beBCdAB = ( beBy - beCy ) / ( beBy - beAy ); beADdXA = ( beDy - beAy ) / ( beXy - beAy ); beBCdCD = ( beDy - beCy ) / ( beBy - beCy ); function drawBearishPattern( i, patternName ) { GfxSetZOrder( -1 ); GfxSelectPen( ColorRGB( 255, 0, 0 ), 1, 5 ); // invisible pen to remove blue hue GfxSelectSolidBrush( ColorRGB( 50, 0, 0 ) ); GfxPolygon( beXx[i], beXy[i], beAx[i], beAy[i], beBx[i], beBy[i], beCx[i], beCy[i], beDx[i], beDy[i], beBx[i], beBy[i], beXx[i], beXy[i] ); GfxSelectPen( ColorRGB( 255, 0, 0 ), 2, 0 ); GfxMoveTo( beXx[i], beXy[i] ); GfxLineTo( beAx[i], beAy[i] ); GfxMoveTo( beAx[i], beAy[i] ); GfxLineTo( beBx[i], beBy[i] ); GfxMoveTo( beBx[i], beBy[i] ); GfxLineTo( beCx[i], beCy[i] ); GfxMoveTo( beCx[i], beCy[i] ); GfxLineTo( beDx[i], beDy[i] ); GfxMoveTo( beXx[i], beXy[i] ); GfxLineTo( beAx[i], beAy[i] ); GfxSelectPen( ColorRGB( 255, 0, 0 ), 1, 2 ); GfxMoveTo( beXx[i], beXy[i] ); GfxLineTo( beBx[i], beBy[i] ); GfxMoveTo( beAx[i], beAy[i] ); GfxLineTo( beCx[i], beCy[i] ); GfxMoveTo( beBx[i], beBy[i] ); GfxLineTo( beDx[i], beDy[i] ); GfxMoveTo( beXx[i], beXy[i] ); GfxLineTo( beDx[i], beDy[i] ); if( showPatternName ) { GfxSetZOrder( 1 ); GfxSetTextColor( ColorRGB( 255, 100, 0 ) ); GfxSelectFont( "Helvetica", 10, 700 ); GfxSetTextAlign( 0 | 0 ); GfxTextOut( patternName, beCx[i] + 3, beCy[i] ); } GfxSetZOrder( 1 ); GfxSetTextAlign( 0 | 0 ); GfxSetTextColor( ColorRGB( 255, 150, 50 ) ); GfxSelectFont( "Helvetica", 8, 700 ); GfxTextOut( "" + Prec( beABdXA[i], 2 ), ( beBx[i] + beXx[i] ) / 2, ( beBy[i] + beXy[i] ) / 2 ); GfxTextOut( "" + Prec( beBCdAB[i], 2 ), ( beCx[i] + beAx[i] ) / 2, ( beCy[i] + beAy[i] ) / 2 ); GfxTextOut( "" + Prec( beADdXA[i], 2 ), ( beDx[i] + beXx[i] ) / 2, ( beDy[i] + beXy[i] ) / 2 ); GfxTextOut( "" + Prec( beBCdCD[i], 2 ), ( beBx[i] + beDx[i] ) / 2, ( beBy[i] + beDy[i] ) / 2 ); if( showPatternLabels ) { GfxSetZOrder( 1 ); GfxSetTextColor( ColorRGB( 255, 150, 0 ) ); GfxSelectFont( "Helvetica", 11, 700 ); GfxSetTextAlign( 0 | 24 ); GfxTextOut( "X", beXx[i] - 2, beXy[i] ); GfxTextOut( "A", beAx[i] - 2, beAy[i] ); GfxTextOut( "B", beBx[i] - 2, beBy[i] ); GfxTextOut( "C", beCx[i] + 1, beCy[i] ); GfxTextOut( "D", beDx[i] + 1, beDy[i] ); } } function drawBearishReversalZone( i, CDXAmin, CDXAmax, cntzones, pname ) { clr1 = ColorRGB( 160 + cntzones * colorContrastFactor, 80 + cntzones * colorContrastFactor, 0 ); clr2 = ColorRGB( 35 + cntzones * colorContrastFactor, 15 + cntzones * colorContrastFactor, 0 ); GfxSetZOrder( 1 ); GfxSelectPen( clr1, 1, 1 ); GfxMoveTo( beCx[i], beAy[i] - ( beAy[i] - beXy[i] )*CDXAmin ); GfxLineTo( Max( i, beDx[i] ), beAy[i] - ( beAy[i] - beXy[i] )*CDXAmin ); GfxMoveTo( beCx[i], beAy[i] - ( beAy[i] - beXy[i] )*CDXAmin ); GfxLineTo( beCx[i], beAy[i] - ( beAy[i] - beXy[i] )*CDXAmax ); GfxMoveTo( beCx[i], beAy[i] - ( beAy[i] - beXy[i] )*CDXAmax ); GfxLineTo( Max( i, beDx[i] ), beAy[i] - ( beAy[i] - beXy[i] )*CDXAmax ); GfxMoveTo( Max( i, beDx[i] ), beAy[i] - ( beAy[i] - beXy[i] )*CDXAmin ); GfxLineTo( Max( i, beDx[i] ), beAy[i] - ( beAy[i] - beXy[i] )*CDXAmax ); GfxSetZOrder( -2 ); GfxSelectSolidBrush( clr2 ); GfxPolygon( beCx[i], beAy[i] - ( beAy[i] - beXy[i] )*CDXAmin, Max( i, beDx[i] ), beAy[i] - ( beAy[i] - beXy[i] )*CDXAmin, Max( i, beDx[i] ), beAy[i] - ( beAy[i] - beXy[i] )*CDXAmax, beCx[i], beAy[i] - ( beAy[i] - beXy[i] )*CDXAmax, beCx[i], beAy[i] - ( beAy[i] - beXy[i] )*CDXAmin ); GfxSetZOrder( 1 ); GfxSetTextColor( ColorRGB( 255, 100, 0 ) ); GfxSelectFont( "Helvetica", 7, 700 ); GfxSetTextAlign( 0 | 0 ); GfxTextOut( pname, beCx[i] + 0, beAy[i] - ( beAy[i] - beXy[i] )*CDXAmin ); } function drawBearishPatterns() { flag1 = 1; flag2 = 0; cnt = 0; for( i = lvb; i > fvb; i-- ) { if( BearHar[i] AND flag1 AND cnt < nBear ) { flag1 = 0; flag2 = 1; cnt = cnt + 1; if( BearButterfly[i] AND be AND dBut ) { drawBearishPattern( i, "Bearish Butterfly" ); } else if( BearCrab[i] AND be AND dCrab ) { drawBearishPattern( i, "Bearish Crab" ); } else if( BearBat[i] AND be AND dBat ) { drawBearishPattern( i, "Bearish Bat" ); } else if( BearGartley[i] AND be AND dGart ) { drawBearishPattern( i, "Bearish Gartley" ); } } if( BearHar4[i] AND flag2 ) { flag1 = 1; flag2 = 0; } } } function manageBearishReversalZones() { cnt = 0; cntzones = 0; ButFlag1 = 1; CraFlag1 = 1; BatFlag1 = 1; GarFlag1 = 1; yMax = yMin = 0; for( i = lvb; i > fvb; i-- ) { if( BearButterfly[i] AND be AND dBut AND ButFlag1 AND( H[i] > yMax OR H[i] < yMin ) ) { ButFlag1 = 0; CraFlag1 = 1; BatFlag1 = 1; GarFlag1 = 1; drawBearishReversalZone( i, ButCDXAmin, ButCDXAmax, cntzones, "Butterfly" ); yMax = beAy[i] - ( beAy[i] - beXy[i] ) * ButCDXAmax; yMin = beAy[i] - ( beAy[i] - beXy[i] ) * ButCDXAmin; cntzones = cntzones + 1; } if( BearCrab[i] AND be AND dCrab AND CraFlag1 AND( H[i] > yMax OR H[i] < yMin ) ) { ButFlag1 = 1; CraFlag1 = 0; BatFlag1 = 1; GarFlag1 = 1; drawBearishReversalZone( i, CraCDXAmin, CraCDXAmax, cntzones, "Crab" ); yMax = beAy[i] - ( beAy[i] - beXy[i] ) * CraCDXAmax; yMin = beAy[i] - ( beAy[i] - beXy[i] ) * CraCDXAmin; cntzones = cntzones + 1; } if( BearBat[i] AND be AND dBat AND BatFlag1 AND( H[i] > yMax OR H[i] < yMin ) ) { ButFlag1 = 1; CraFlag1 = 1; BatFlag1 = 0; GarFlag1 = 1; drawBearishReversalZone( i, BatCDXAmin, BatCDXAmax, cntzones, "Bat" ); yMax = beAy[i] - ( beAy[i] - beXy[i] ) * BatCDXAmax; yMin = beAy[i] - ( beAy[i] - beXy[i] ) * BatCDXAmin; cntzones = cntzones + 1; } if( BearGartley[i] AND be AND dGart AND GarFlag1 AND( H[i] > yMax OR H[i] < yMin ) ) { ButFlag1 = 1; CraFlag1 = 1; BatFlag1 = 1; GarFlag1 = 0; drawBearishReversalZone( i, GarCDXAmin, GarCDXAmax, cntzones, "Gartley" ); yMax = beAy[i] - ( beAy[i] - beXy[i] ) * GarCDXAmax; yMin = beAy[i] - ( beAy[i] - beXy[i] ) * GarCDXAmin; cntzones = cntzones + 1; } if( BearHar4[i] ) { ButFlag1 = 1; CraFlag1 = 1; BatFlag1 = 1; GarFlag1 = 1; cnt = cnt + 1; yMax = 0; yMin = 0; cntzones = 0; } if( cnt >= nBear ) break; } } drawBearishPatterns(); if( showReversalZone ) manageBearishReversalZones(); function drawPivotLabels() { sz = 5; for( i = lvb; i > fvb; i-- ) { { if( ll[i] ) PlotTextSetFont( "LL", "Arial Black", sz, i, L[i], colorBlue, colorDefault, -25 ); if( hl[i] ) PlotTextSetFont( "HL", "Arial Black", sz, i, L[i], colorBlue, colorDefault, -25 ); if( db[i] ) PlotTextSetFont( "DB", "Arial Black", sz, i, L[i], colorLightBlue, colorDefault, -25 ); if( hh[i] ) PlotTextSetFont( "HH", "Arial Black", sz, i, H[i], colorRed, colorDefault, 20 ); if( lh[i] ) PlotTextSetFont( "LH", "Arial Black", sz, i, H[i], colorRed, colorDefault, 20 ); if( dt[i] ) PlotTextSetFont( "DT", "Arial Black", sz, i, H[i], colorOrange, colorDefault, 20 ); } } } if( showLabels ) drawPivotLabels(); if( showPatternDevelopmentPoints ) { if( bu ) { PlotShapes( shapeDigit4 * BullHar4, colorBlue, O, H, 35 ); PlotShapes( shapeSmallCircle * BullHar, ColorLightBlue, O, L, -10 ); } if( be ) { PlotShapes( shapeDigit4 * BearHar4, colorRed, O, L, -35 ); PlotShapes( shapeSmallCircle * BearHar, colorOrange, O, H, 10 ); } } Title = Name() + " | " + Now( 2 ) + " | " + "PIVOT TIMEFRAME: " + tfrm / 60 + " Minutes or " + tfrm / 3600 + " Hours or " + tfrm / ( 3600 * 24 ) + " Days ";