/////////////////////////////////////////////////////// // // SaherElm IT Center MQL5 Class Library // -------------------------------------- // Name: XPOI // Description: Provides Point of Interests ... // - Swing Highs; // - Swing Lows; // // Maintainer: // ------------ // Hadi Khazaee Asl (hadi_khazaee_asl@yahoo.com) // ////////////////////////////////////////////////////// // // Global Properties ... #property library #property copyright "Copyright 2023, SaherElm IT Center" #property link "https://www.saherelm.ir" #property version "1.00" #property strict // // Imports ... // #include "../Classes/x-saherelm.xalert.class.mq5" #include #include #include // // Definitions ... // // All Available POI(s) ... enum ENUM_XPOIS { // // Momentum Bar ... X_POI_MOMENTUM_BAR, // Momentum Bar ... // // Rejection Bar ... X_POI_REJECTION_BAR, // Rejection Bar ... // // Swings ... X_POI_SWING_HIGH, // Simple Swing High ... X_POI_SWING_LOW, // Simple Swing Low ... // // Support nad Resistance ... X_POI_SUPPORT, // Support Zone ... X_POI_RESISTANCE, // Resistance Zone ... }; // // Event Types ... enum ENUM_XPOI_EVENTS { // // Momentum Bar ... X_MOMENTUM_BAR_DETECTED, // Momentum Bar ... // // Rejection Bar ... X_REJECTION_BAR_DETECTED, // Rejection Bar ... // // Swings ... X_SWING_HIGH_DETECTED, X_SWING_LOW_DETECTED, // // Support nad Resistance ... X_SUPPORT_DETECTED, X_RESISTANCE_DETECTED, }; // // XOHCL Event Handler ... typedef void (*TXOHCLEventHandler)( XOHCL &bar // ); // // Extensions ... /** * Converts ENUM_XPOI value to String Representation ... * * @param value: ENUM_XPOI member ... * * @return ( string ) */ string ToString(ENUM_XPOIS value) { // string result = NULL; // switch (value) { // case X_POI_MOMENTUM_BAR: result = "XMNTMB"; break; // case X_POI_REJECTION_BAR: result = "XRJCTB"; break; // case X_POI_SWING_HIGH: result = "XSPH"; break; // case X_POI_SWING_LOW: result = "XSPL"; break; // case X_POI_SUPPORT: result = "XSUP"; break; // case X_POI_RESISTANCE: result = "XRES"; break; } // return result; } // // Implementation ... // class XCPOI : public XSCBaseAlert { // public: // // // Constructors ... /** * Create an Instance ... * * @param symbol: String ... * @param period: ENUM_TIMEFRAMES member ... */ void XCPOI( string symbol, ENUM_TIMEFRAMES period // ) { // // Attach Required Properties ... mSymbol = symbol; mPeriod = period; // // Initialize Bar Tracker ... mBarTracker.Init( mSymbol, mPeriod // ); // // Apply Default Configurations ... ApplyDefaultConfig(); } // // Deconstructor ... void ~XCPOI() { // DestroyPOIs(); DestroyObjects(); } // // Getter(s) / Setter(s) ... /** * Get Chart ID ... * * @return ( long ) */ long ChartID() { return mChartID; } /** * Set Chart ID ... * * @param value: Long */ void ChartID(long value) { // if (value < 0) { value = 0; } // mChartID = value; } /** * Get Sub Window Number ... * * @return ( int ) */ int Window() { return mWindow; } /** * Get Sub Window Number ... * * @param value: Integer ... */ void Window(int value) { // if (value < 0) { value = 0; } // mWindow = value; } /** * Get Max Number of POIs which holds ... * * @return ( int ) */ int MaxNumberOfPOIs() { return mMaxNumberOfPOIs; } /** * Set Max Number of POIs which holds ... * 0 => Infinity ... * * @param value: Integer ... */ void MaxNumberOfPOIs(int value) { // if (value < 0) { value = 0; } // mMaxNumberOfPOIs = value; } /** * Get Number of POI(s) which must Find at Initializations ... * * @return ( int ) */ int MaxNumberOfRequiredPOIs() { return mMaxNumberOfRequiredPOIs; } /** * Set Number of POI(s) which must Find at Initializations ... * 2 is Default ... * * @param value: Integer ... */ void MaxNumberOfRequiredPOIs(int value) { // if (value < 2) { value = 2; } // mMaxNumberOfRequiredPOIs = value; } /** * Check Is Locked or not ... * * @return ( bool ) */ bool IsLocked() { return mLock; } // // POI(s) Configs ... // // Swing High ... /** * Get Draw Swing Highs State ... * * @return ( bool ) */ bool AllowDrawSwingHighs() { return mAllowDrawSwingHighs; } /** * Set Draw Swing Highs State ... * * @param value: Boolean */ void AllowDrawSwingHighs(bool value) { mAllowDrawSwingHighs = value; } /** * Get Threshold Required for Swing High Detection ... * * @return ( double ) */ double SwingHighThreshold() { return mSwingHighThreshold; } /** * Set Threshold Required for Swing High Detection ... * * @param value: Double ... */ void SwingHighThreshold(double value) { // if (value < 0) { value = 0; } // mSwingHighThreshold = value; } /** * Get Swing High Arrow Code ... * * @return ( char ) */ char SwingHighArrowCode() { return mSwingHighArrowCode; } /** * Set Swing High Arrow Code ... * * @param value: Char ... */ void SwingHighArrowCode(char value) { mSwingHighArrowCode = value; } /** * Get Swing High Color ... * * @return ( color ) */ color SwingHighColor() { return mSwingHighColor; } /** * Get Swing High Color ... * * @param value: Color */ void SwingHighColor(color value) { mSwingHighColor = value; } /** * Get Swing High Width ... * * @return ( int ) */ int SwingHighWidth() { return mSwingHighWidth; } /** * Set Swing High Width ... * * @param value: Integer ... */ void SwingHighWidth(int value) { // if (value < 1) { value = 1; } // mSwingHighWidth = value; } // // Swing Low ... /** * Get Draw Swing Lows State ... * * @return ( bool ) */ bool AllowDrawSwingLows() { return mAllowDrawSwingLows; } /** * Set Draw Swing Lows State ... * * @param value: Boolean */ void AllowDrawSwingLows(bool value) { mAllowDrawSwingLows = value; } /** * Get Threshold Required for Swing Low Detection ... * * @return ( double ) */ double SwingLowThreshold() { return mSwingLowThreshold; } /** * Set Threshold Required for Swing Low Detection ... * * @param value: Double ... */ void SwingLowThreshold(double value) { // if (value < 0) { value = 0; } // mSwingLowThreshold = value; } /** * Get Swing Low Arrow Code ... * * @return ( char ) */ char SwingLowArrowCode() { return mSwingLowArrowCode; } /** * Set Swing Low Arrow Code ... * * @param value: Char ... */ void SwingLowArrowCode(char value) { mSwingLowArrowCode = value; } /** * Get Swing Low Color ... * * @return ( color ) */ color SwingLowColor() { return mSwingLowColor; } /** * Get Swing Low Color ... * * @param value: Color */ void SwingLowColor(color value) { mSwingLowColor = value; } /** * Get Swing Low Width ... * * @return ( int ) */ int SwingLowWidth() { return mSwingLowWidth; } /** * Set Swing Low Width ... * * @param value: Integer ... */ void SwingLowWidth(int value) { // if (value < 1) { value = 1; } // mSwingLowWidth = value; } // // Momentum Bars ... /** * Get Draw Momentum Bars State ... * * @return ( bool ) */ bool AllowDrawMomentumBars() { return mAllowDrawMomentumBars; } /** * Set Draw Momentum Bars State ... * * @param value: Boolean */ void AllowDrawMomentumBars(bool value) { mAllowDrawMomentumBars = value; } /** * Get Momentum Bar Percent ... * * @return ( int ) */ int MomentumBarPercent() { return mMomentumBarPercent; } /** * Set Momentum Bar Percent ... * * @param value: Integer */ void MomentumBarPercent(int value) { // if (value < 0) { value = 0; } // mMomentumBarPercent = value; } /** * Get Momentum Bar Sharp Ratio ... * * @return ( double ) */ double MomentumBarSharpRatio() { return mMomentumBarSharpRatio; } /** * Set Momentum Bar Sharp Ratio ... * * @param value: Double ... */ void MomentumBarSharpRatio(double value) { // if (value < 0) { value = 0; } // mMomentumBarSharpRatio = value; } /** * Get Momentum Bar Loopback ... * * @return ( int ) */ int MomentumBarLoopBack() { return mMomentumBarLoopBack; } /** * Set Momentum Bar Loopback ... * * @param value: Integer ... */ void MomentumBarLoopBack(int value) { // if (value < 0) { value = 0; } // mMomentumBarLoopBack = value; } /** * Get Momentum Bar Width ... * * @return ( int ) */ int MomentumBarWidth() { return mMomentumBarWidth; } /** * Set Momentum Bar Width ... * * @param value: Integer ... */ void MomentumBarWidth(int value) { mMomentumBarWidth = value; } /** * Get Bullish Momentum Bar Arrow Code ... * * @return ( char ) */ char MomentumBarBullishArrowCode() { return mMomentumBarBullishArrowCode; } /** * Set Bullish Momentum Bar Arrow Code ... * * @param value: Char ... */ void MomentumBarBullishArrowCode(char value) { mMomentumBarBullishArrowCode = value; } /** * Get Bullish Momentum Bar Color ... * * @return ( char ) */ char MomentumBarBearishArrowCode() { return mMomentumBarBearishArrowCode; } /** * Set Bullish Momentum Bar Color ... * * @param value: Color ... */ void MomentumBarBearishArrowCode(char value) { mMomentumBarBearishArrowCode = value; } /** * Get Bearish Momentum Bar Arrow Code ... * * @return ( color ) */ color MomentumBarBullishColor() { return mMomentumBarBullishColor; } /** * Set Bearish Momentum Bar Arrow Code ... * * @param value: Color ... */ void MomentumBarBullishColor(color value) { mMomentumBarBullishColor = value; } /** * Get Bearish Momentum Bar Color ... * * @return ( color ) */ color MomentumBarBearishColor() { return mMomentumBarBearishColor; } /** * Set Bearish Momentum Bar Color ... * * @param value: Color ... */ void MomentumBarBearishColor(color value) { mMomentumBarBearishColor = value; } // // Actions ... /** * Initialize POI Detector ... */ void Init() { // // Detect Previous POI(s) ... DetectRequiredPOIs(); } /** * Update POI(s) ... * * @param state: an Array Refrence of ENUM_XPOI_EVENTS members ... */ int Update( ENUM_XPOI_EVENTS &state[] // ) { // int result = 0; // Clean(state); // // Check Bar Tracker if Waits ... if (!mBarTracker.IsNewBar()) { return result; } // int cIndex = 1; int pIndex = cIndex + 1; // XOHCL cBar; bool isInited = cBar.Init( mSymbol, mPeriod, cIndex // ); if (!isInited) { return result; } // XOHCL pBar; isInited = pBar.Init( mSymbol, mPeriod, pIndex // ); if (!isInited) { return result; } // // Detect Swing High ... int swingHighsCount = ArraySize(mSwingHighs); bool isSingHigh = pBar.IsSimpleSwingHigh(SwingHighThreshold()); if (isSingHigh) { // AddRef( pBar, mSwingHighs // ); swingHighsCount = ArraySize(mSwingHighs); // DrawSwingHighs(); // Add( X_SWING_HIGH_DETECTED, state // ); OnSwingHighDetected(pBar); NotifySwingHighEventListeners(pBar); } // // Detect Swing Low ... int swingLowsCount = ArraySize(mSwingLows); bool isSingLow = pBar.IsSimpleSwingLow(SwingLowThreshold()); if (isSingLow) { // AddRef( pBar, mSwingLows // ); swingLowsCount = ArraySize(mSwingLows); // DrawSwingLows(); // Add( X_SWING_LOW_DETECTED, state // ); OnSwingLowDetected(pBar); NotifySwingLowEventListeners(pBar); } // // Detect Momentum Bar ... int momentumBarsCount = ArraySize(mMomentumBars); bool isStrongBar = cBar.IsStrong(MomentumBarPercent()); bool isSharpBullish = cBar.IsSharpBullish( MomentumBarLoopBack(), MomentumBarSharpRatio() // ); bool isSharpBearish = cBar.IsSharpBearish( MomentumBarLoopBack(), MomentumBarSharpRatio() // ); bool isMomentumBar = isStrongBar && (isSharpBearish || isSharpBullish); if (isMomentumBar) { // AddRef( cBar, mMomentumBars // ); momentumBarsCount = ArraySize(mMomentumBars); // DrawMomentumBars(); // Add( X_MOMENTUM_BAR_DETECTED, state // ); OnMomentumBarDetected(pBar); NotifyMomentumBarEventListeners(pBar); } // mBarTracker.Waits(); // result = ArraySize(state); // return result; } /** * Enable Draw All POI(s) ... */ void EnableDrawPOIs() { // bool state = true; // AllowDrawSwingHighs(state); AllowDrawSwingLows(state); AllowDrawMomentumBars(state); } /** * Disable Draw All POI(s) ... */ void DisableDrawPOIs() { // bool state = false; // AllowDrawSwingHighs(state); AllowDrawSwingLows(state); AllowDrawMomentumBars(state); } // // Virtual Actions ... /** * Apply Default Configurations ... */ virtual void ApplyDefaultConfig() { // ChartID(0); Window(0); // MaxNumberOfPOIs(10); MaxNumberOfRequiredPOIs(2); // SwingHighWidth(5); SwingHighThreshold(3); SwingHighArrowCode(108); SwingHighColor(clrMagenta); // SwingLowWidth(5); SwingLowThreshold(3); SwingLowArrowCode(108); SwingLowColor(clrAqua); // MomentumBarPercent(55); MomentumBarLoopBack(3); MomentumBarSharpRatio(1.2); MomentumBarWidth(5); MomentumBarBullishArrowCode((char)225); MomentumBarBearishArrowCode((char)226); MomentumBarBullishColor(clrAqua); MomentumBarBearishColor(clrMagenta); } // // Event Listeners ... /** * Calls When new Swing High Detected ... * * @param bar: XOHCL instance ... */ virtual void OnSwingHighDetected(XOHCL &bar) { } /** * Register an Event Listener for New Swing High Detected ... * * @param listener: TXOHCLEventHandler instance ... */ void AddSwingHighEventListener(TXOHCLEventHandler listener) { // Add( listener, mSwingHighEventListeners // ); } /** * Calls When new Swing Low Detected ... * * @param bar: XOHCL instance ... */ virtual void OnSwingLowDetected(XOHCL &bar) { } /** * Register an Event Listener for New Swing Low Detected ... * * @param listener: TXOHCLEventHandler instance ... */ void AddSwingLowEventListener(TXOHCLEventHandler listener) { // Add( listener, mSwingLowEventListeners // ); } /** * Calls When new Momentum Bar Detected ... * * @param bar: XOHCL instance ... */ virtual void OnMomentumBarDetected(XOHCL &bar) { } /** * Register an Event Listener for New Momentum Bar Detected ... * * @param listener: TXOHCLEventHandler instance ... */ void AddMomentumBarEventListener(TXOHCLEventHandler listener) { // Add( listener, mMomentumBarEventListeners // ); } // protected: // // // Actions ... /** * Lock ... */ void Lock() { mLock = true; } /** * Unlock ... */ void Unlock() { mLock = false; } /** * Detect Required POI(s) ... * * @param barIndex: Integer Start bar index ... * 0 is Default ... */ void DetectRequiredPOIs(int barIndex = 0) { // // Validate Reuired POI(s) ... int requiredPOIs = MaxNumberOfRequiredPOIs(); if (requiredPOIs <= 0) { return; } // Lock(); // // Normalize Bar Index ... if (barIndex < 0) { barIndex = 0; } // // Define Index of Bars ... int zIndex = barIndex; int cIndex = zIndex + 1; // XOHCL cBar; bool isRetrieved = mBarTracker.GetBar(cBar, cIndex); if (!isRetrieved) { return; } // // Detect POI(s) based On Current Bar ... // // Swing Highs ... int swingHighsCount = ArraySize(mSwingHighs); if (swingHighsCount < requiredPOIs) { // bool isSwingHigh = cBar.IsSimpleSwingHigh(SwingHighThreshold()); if (isSwingHigh) { // AddRef( cBar, mSwingHighs // ); // swingHighsCount = ArraySize(mSwingHighs); } } // // Swing Low ... int swingLowsCount = ArraySize(mSwingLows); if (swingLowsCount < requiredPOIs) { // bool isSwingLow = cBar.IsSimpleSwingLow(SwingLowThreshold()); if (isSwingLow) { // AddRef( cBar, mSwingLows // ); // swingLowsCount = ArraySize(mSwingLows); } } // // Momentum Bars ... int momentumBarsCount = ArraySize(mMomentumBars); if (momentumBarsCount < requiredPOIs) { // bool isStrongBar = cBar.IsStrong(MomentumBarPercent()); // // Bullish ... bool isSharpBullish = cBar.IsSharpBullish( MomentumBarLoopBack(), MomentumBarSharpRatio() // ); // // Bearish ... bool isSharpBearish = cBar.IsSharpBearish( MomentumBarLoopBack(), MomentumBarSharpRatio() // ); // bool isMomentumBar = isStrongBar && (isSharpBearish || isSharpBullish); if (isMomentumBar) { // AddRef( cBar, mMomentumBars // ); // momentumBarsCount = ArraySize(mMomentumBars); } } // bool canContinue = // swingHighsCount < requiredPOIs || swingLowsCount < requiredPOIs || momentumBarsCount < requiredPOIs // ; if (canContinue) { DetectRequiredPOIs(barIndex + 1); } else { // // Complete Calculations ... // XOHCL tmpBars[]; // // Reverse Swing Highs ... Copy( mSwingHighs, tmpBars // ); Clean(mSwingHighs); ArrayReverse(tmpBars); Copy( tmpBars, mSwingHighs // ); Clean(tmpBars); // // Reverse Swing Lows ... Copy( mSwingLows, tmpBars // ); Clean(mSwingLows); ArrayReverse(tmpBars); Copy( tmpBars, mSwingLows // ); Clean(tmpBars); // // Reverse Momentum Bars ... Copy( mMomentumBars, tmpBars // ); Clean(mMomentumBars); ArrayReverse(tmpBars); Copy( tmpBars, mMomentumBars // ); Clean(tmpBars); // Unlock(); DrawPOIs(); } } // // Destroy POIs ... /** * Destroy All POI(s) ... */ void DestroyPOIs() { // DestroySwingHighs(); DestroySwingLows(); // DestroyMomentumBars(); } /** * Destroy Swing Highs ... */ void DestroySwingHighs() { Clean(mSwingHighs); } /** * Destroy Swing Lows ... */ void DestroySwingLows() { Clean(mSwingLows); } /** * Destroy Momentum Bars ... */ void DestroyMomentumBars() { Clean(mMomentumBars); } // // Draw Actions ... /** * Draw All POI(s) ... */ void DrawPOIs() { // DrawSwingHighs(); DrawSwingLows(); // DrawMomentumBars(); } /** * Draw Swing Highs ... */ void DrawSwingHighs() { // bool allow = AllowDrawSwingHighs(); if (!allow) { return; } // int count = ArraySize(mSwingHighs); if (!IsValidSize(count)) { return; } // for (int i = 0; i < count; i++) { // XOHCL iSwing = mSwingHighs[i]; // string iName = iSwing.GetTag(ToString(X_POI_SWING_HIGH)); int iIDX = HasObject( iName, mSwingHighObjects // ); if (IsValidIndex(iIDX)) { continue; } // CreateSwingHighObject(iSwing, iName); } } /** * Draw Swing Lows ... */ void DrawSwingLows() { // bool allow = AllowDrawSwingLows(); if (!allow) { return; } // int count = ArraySize(mSwingLows); if (!IsValidSize(count)) { return; } // for (int i = 0; i < count; i++) { // XOHCL iSwing = mSwingLows[i]; // string iName = iSwing.GetTag(ToString(X_POI_SWING_LOW)); int iIDX = HasObject( iName, mSwingLowObjects // ); if (IsValidIndex(iIDX)) { continue; } // CreateSwingLowObject(iSwing, iName); } } /** * Draw Momentum Bars ... */ void DrawMomentumBars() { // bool allow = AllowDrawMomentumBars(); if (!allow) { return; } // int count = ArraySize(mMomentumBars); if (!IsValidSize(count)) { return; } // for (int i = 0; i < count; i++) { // XOHCL iBar = mMomentumBars[i]; // string iName = iBar.GetTag(ToString(X_POI_MOMENTUM_BAR)); int iIDX = HasObject( iName, mMomentumBarObjects // ); if (IsValidIndex(iIDX)) { continue; } // CreateMomentumBarObject(iBar, iName); } } /** * Clean All Drawn Objects ... */ void DestroyObjects() { // DestroySwingHighObjects(); DestroySwingLowObjects(); DestroyMomentumBarObjects(); } /** * Clean Swing Highs Drawn Objects ... */ void DestroySwingHighObjects() { mSwingHighObjects.Clear(); } /** * Clean Swing Lows Drawn Objects ... */ void DestroySwingLowObjects() { mSwingLowObjects.Clear(); } /** * Clean Momentum Bars Drawn Objects ... */ void DestroyMomentumBarObjects() { mMomentumBarObjects.Clear(); } /** * Detect an Object Exists in Array or not ... * * @param name: String ... * @param array: CArrayObj instance ... * * @return ( int ): index of Object ... */ int HasObject( string name, CArrayObj &array // ) { // int result = -1; // if (!IsValid(name)) { return result; } // int count = array.Total(); if (!IsValidSize(count)) { return result; } // for (int i = 0; i < count; i++) { // CChartObject iObj = array.At(i); // if (iObj.Name() == name) { // result = i; break; } } // return result; } // // Event Handler Notifiers ... /** * Notify New Swing High Point Event Handlers ... * * @param bar: XOHCL instance ... */ void NotifySwingHighEventListeners(XOHCL &bar) { // if (!bar.IsValid()) { return; } // int count = ArraySize(mSwingHighEventListeners); if (!IsValidSize(count)) { return; } // for (int i = 0; i < count; i++) { // TXOHCLEventHandler iListener = mSwingHighEventListeners[i]; iListener(bar); } } /** * Notify New Swing Low Point Event Handlers ... * * @param bar: XOHCL instance ... */ void NotifySwingLowEventListeners(XOHCL &bar) { // if (!bar.IsValid()) { return; } // int count = ArraySize(mSwingLowEventListeners); if (!IsValidSize(count)) { return; } // for (int i = 0; i < count; i++) { // TXOHCLEventHandler iListener = mSwingLowEventListeners[i]; iListener(bar); } } /** * Notify New Momentum Bar Event Handlers ... * * @param bar: XOHCL instance ... */ void NotifyMomentumBarEventListeners(XOHCL &bar) { // if (!bar.IsValid()) { return; } // int count = ArraySize(mMomentumBarEventListeners); if (!IsValidSize(count)) { return; } // for (int i = 0; i < count; i++) { // TXOHCLEventHandler iListener = mMomentumBarEventListeners[i]; iListener(bar); } } // private: // // // Props ... // bool mLock; // Lock State ... string mSymbol; // Market Symbol ... ENUM_TIMEFRAMES mPeriod; // Market Period ... long mChartID; // Chart ID ... int mWindow; // Window ID ... int mMaxNumberOfPOIs; // Max Allowed Number of POI(s) which Can Holds ... int mMaxNumberOfRequiredPOIs; // Max Allowed Number of POI(s) which Must Find at Initializion Time ... // XBarTracker mBarTracker; // Market Bar Tracker ... // // POI Holders ... // // Swing Highs ... bool mAllowDrawSwingHighs; // Draw Swing Highs ... char mSwingHighArrowCode; // Swing High Arrow Code ... color mSwingHighColor; // Swing High Color ... int mSwingHighWidth; // Swing High Width ... double mSwingHighThreshold; // Threshold Required for Swing High Detection ... XOHCL mSwingHighs[]; // Swing Highs ... CArrayObj mSwingHighObjects; // Swing High Chart Objects ... TXOHCLEventHandler mSwingHighEventListeners[]; // Swing High Event Listeners ... /** * Create an Object to Represent Swing High on Chart ... * * @param bar: XOHCL instance ... * @param name: String ... */ void CreateSwingHighObject( XOHCL &bar, string name // ) { // if (!bar.IsValid() || !IsValid(name)) { return; } // CChartObjectArrow *iObj; iObj = new CChartObjectArrow(); bool isCreated = iObj.Create( ChartID(), name, Window(), bar.time, bar.high, SwingHighArrowCode() // ); if (!isCreated) { return; } // // Configure Object ... iObj.Width(SwingHighWidth()); iObj.Color(SwingHighColor()); iObj.Anchor(ANCHOR_BOTTOM); // mSwingHighObjects.Add(iObj); } // // Swing Lows ... bool mAllowDrawSwingLows; // Draw Swing Lows ... char mSwingLowArrowCode; // Swing Low Arrow Code ... color mSwingLowColor; // Swing Low Color ... int mSwingLowWidth; // Swing Low Width ... double mSwingLowThreshold; // Threshold Required for Swing Low Detection ... XOHCL mSwingLows[]; // Swing Lows ... CArrayObj mSwingLowObjects; // Swing Low Chart Objects ... TXOHCLEventHandler mSwingLowEventListeners[]; // Swing Low Event Listeners ... /** * Create an Object to Represent Swing Low on Chart ... * * @param bar: XOHCL instance ... * @param name: String ... */ void CreateSwingLowObject( XOHCL &bar, string name // ) { // if (!bar.IsValid() || !IsValid(name)) { return; } // CChartObjectArrow *iObj; iObj = new CChartObjectArrow(); bool isCreated = iObj.Create( ChartID(), name, Window(), bar.time, bar.low, SwingLowArrowCode() // ); if (!isCreated) { return; } // // Configure Object ... iObj.Width(SwingLowWidth()); iObj.Color(SwingLowColor()); iObj.Anchor(ANCHOR_TOP); // mSwingLowObjects.Add(iObj); } // // Momentum Bar ... bool mAllowDrawMomentumBars; // Draw Momentum Bars ... int mMomentumBarPercent; // Momentum Bar Percent ... double mMomentumBarSharpRatio; // Momentum Bar Sharp Ratio ... int mMomentumBarLoopBack; // Momentum Bar Loopback ... int mMomentumBarWidth; // Momentum Bar Width ... char mMomentumBarBullishArrowCode; // Bullish Momentum Bar Arrow Code ... char mMomentumBarBearishArrowCode; // Bullish Momentum Bar Color ... color mMomentumBarBullishColor; // Bearish Momentum Bar Arrow Code ... color mMomentumBarBearishColor; // Bearish Momentum Bar Color ... XOHCL mMomentumBars[]; // Momentum Bars ... CArrayObj mMomentumBarObjects; // Momentm Bar Chart Objects ... TXOHCLEventHandler mMomentumBarEventListeners[]; // Momentum Bars Event Listeners ... /** * Create an Object to Represent Momentum Bar on Chart ... * * @param bar: XOHCL instance ... * @param name: String ... */ void CreateMomentumBarObject( XOHCL &bar, string name // ) { // if (!bar.IsValid() || !IsValid(name)) { return; } // bool isBullish = bar.IsBullish(); double price = isBullish ? bar.low : bar.high; char arrowCode = isBullish ? MomentumBarBullishArrowCode() : MomentumBarBearishArrowCode(); color clr = isBullish ? MomentumBarBullishColor() : MomentumBarBearishColor(); ENUM_ARROW_ANCHOR anchor = isBullish ? ANCHOR_TOP : ANCHOR_BOTTOM; // CChartObjectArrow *iObj; iObj = new CChartObjectArrow(); bool isCreated = iObj.Create( ChartID(), name, Window(), bar.time, price, arrowCode // ); if (!isCreated) { return; } // // Configure Object ... iObj.Width(MomentumBarWidth()); iObj.Color(clr); iObj.Anchor(anchor); // mMomentumBarObjects.Add(iObj); } // }; //