// MotorBase.h: interface for the CMotorBase class. // ////////////////////////////////////////////////////////////////////// #if !defined(AFX_MOTORBASE_H__04B8BC9A_5FF9_4E00_BA08_FDEC856015F1__INCLUDED_) #define AFX_MOTORBASE_H__04B8BC9A_5FF9_4E00_BA08_FDEC856015F1__INCLUDED_ #if _MSC_VER > 1000 #pragma once #endif // _MSC_VER > 1000 #include "Motor.h" #include #ifdef BUILD_IODLL #define IODLLCLASS __declspec(dllexport) #else #define IODLLCLASS __declspec(dllimport) #endif class CMotionControllerBase; class IODLLCLASS CMotionLogger { public: CMotionLogger(const char *formatString, ...); CMotionLogger(const char *loggerName); ~CMotionLogger(); void Log(const char *formatString, ...); void Log(const char *filename, int linenr, const char *formatString, ...); private: CHighResPerformanceCounter m_time; CString m_loggerName; }; class IODLLCLASS CMotorBase : public CMtrPos, public CCard, public CMtrOnOff, public CMyWait { protected: enum HOME_SEQ { HOME_NORMAL, HOME_SENSOR_BLOCKED, HOME_LIMIT_BLOCKED, }; enum HOME_DIR { HOME_FWD, HOME_REV, }; enum MOTION_SPEED { SPEED_LOW, SPEED_HIGH, }; enum LEAVE_HOME_CHECK_SENSOR { NO_CHECK, CHECK_HOME, CHECK_INDEX, CHECK_POS_LIMIT, CHECK_NEG_LIMIT, }; enum PROFILE_CURVE { T_CURVE, S_CURVE, }; // these profile parameters are in motor pulses/values instead of real world values struct motion_profile { enum PROFILE_TYPE { ACC, DEC, SACC, SDEC, START_SPEED, MAX_SPEED, CONSTANT_SPEED, HOME_SLOW_ACC, HOME_SLOW_DEC, HOME_SLOW_SACC, HOME_SLOW_SDEC, HOME_SLOW_START_SPEED, HOME_SLOW_MAX_SPEED, HOME_SLOW_CONSTANT_SPEED, POSITIVE_SOFT_LIMIT, NEGATIVE_SOFT_LIMIT, MAX_PROFILE_TPYE, }; protected: std::map profile; public: motion_profile() { if (profile.empty()) { for (int i = 0; i < MAX_PROFILE_TPYE; i++) { profile[static_cast(i)] = 0; } } } double Get(PROFILE_TYPE type) { return (profile.find(type) != profile.end()) ? profile[type] : 0; } void Set(PROFILE_TYPE type, double dValue) { profile[type] = dValue; } } m_profile; struct multiple_trigger { double dStartPosition; double dStopPosition; double dIntervalDistance; int nNoOfTrigger; int nCmpSource; multiple_trigger() { dStartPosition = 0; dStopPosition = 0; dIntervalDistance = 0; nNoOfTrigger = 0; nCmpSource = 0; } }; public: CMotorBase(); CMotorBase(const char* cpMutexName, const CMtrProfile &mtrProfile, double *dpPos, CMotionControllerBase *pBaseController); virtual ~CMotorBase(); // ************************************************************** // Virtual Methods declaration // ************************************************************** // method to close the axis virtual void CloseAxis(); // method to initialize and configure the axis virtual void ConstructAxis() = 0; void StartThreads(); void KillThreads(); HANDLE GetKillEventHandle() { return m_hKillThread; } virtual void MotorMoveIntThread(); virtual void MotorHomeThread(); // method to On/Off motor int OnMtr(bool bOn); virtual bool OnMotor() = 0; virtual bool OffMotor() = 0; virtual bool IsBenchDebug(); // method to stop motor with decceleration int DecStop(); virtual bool DecelStop() = 0; // method to trigger Emergency stop the motor virtual int EStop(); int EStop(); virtual bool EmergStop() = 0; // virtual method to get commanded position double GetCommandPosition(); virtual bool GetMotorCommandedPosition(int nMtrNo, double *pRaw) = 0; // virtual method to get the motor axis IO status virtual int GetMotionIOStatus(); // virtual method to get the Motor Ready Status virtual BOOL IsMotorReady(); // virtual method to get the Motor Alarm Status virtual BOOL IsMotorAlarm(); // virtual method to get the Motor Negative/CCW Limit Status virtual BOOL IsNegLmtHit(); // virtual method to get the Motor Positive/CW Limit Status virtual BOOL IsPosLmtHit(); // virtual method to get the Motor Home Sensor Status virtual BOOL IsHomed(); // virtual method to check if the Motor is TURN ON virtual bool IsMtrOn(); // virtual method Check other axis home sensor virtual BOOL IsHomed(const CMtrProfile &mtrProfile); // virtual method to get other motor axis IO status virtual int GetMotionIOStatus(const CMtrProfile &mtrProfile) = 0; // virtual method to get Other axis motor ready status virtual BOOL IsMotorReady(const CMtrProfile &mtrProfile); // virtual method to get Other axis Alarm status virtual BOOL IsMotorAlarm(const CMtrProfile &mtrProfile); // virtual method to get Other axis negative/ccw limit status virtual BOOL IsNegLmtHit(const CMtrProfile &mtrProfile); // virtual method to get Other axis positive/cw limit status virtual BOOL IsPosLmtHit(const CMtrProfile &mtrProfile); // virtual method to get Other axis home sensor status virtual bool IsMtrOn(const CMtrProfile &mtrProfile); // virtual method to get other motor axis current position double GetOtherAxisPosition(const CMtrProfile &mtrProfile); virtual bool GetMotorPosition(const CMtrProfile &mtrProfile, double *pRawPosition) = 0; // virtual method to get motor axis current position error double GetPosErr(); virtual bool GetMotorPositionError(double *pRawPositionError) = 0; virtual bool ResetMotorPositionError(); // virtual method to get the current motor position double GetPosition(); // virtual method to do homing by limit sensor virtual BOOL HomingByLimit(); // virtual method to do homing by sensor as well as index virtual BOOL HomeBySensorAndIndex(); // virtual method to do homing by index signal virtual BOOL HomeByIndex(); // virtual method to do homing by Home Sensor virtual BOOL HomeBySensor(); // virtual method by limit then index virtual BOOL HomeByLimitThenIndex(); // virtual method to move absolute int MoveAbs(double dPosition, int nPos = -1, int nMode = 0); virtual bool AbsoluteMove(double dPosition, int nMode, PROFILE_CURVE curve) = 0; // virtual method to move continuously virtual int MoveContinuously(bool bCW = true); // virtual method to move relative distance int MoveRel(double dDistance, int nPos = -1); virtual bool RelativeMove(double dDistance, PROFILE_CURVE curve) = 0; // virtual method to process interrupt to decode what happen to the motor virtual void ProcessInt(int nIntCode = 0) = 0; // virtual method to reset single trigger virtual int ResetSingleTrigger(double dPosition = 0.0); // virtual method to set the commanded position register int SetCommandPosition(double dPosition); virtual bool SetMotorCommandedPosition(double dPosition) = 0; // virtual method to set the mechanical coversion factor int SetConversionFactor(double dUPR, double dPPR, double dEPPR); virtual bool RefreshMotorConversionFactor() = 0; // virtual method to set homing modes virtual int SetHomeMode(int iHomeMode) = 0; // virtual method to set multiple trigger virtual int SetMultipleTrigger(double dStartPosition, double dStopPosition, double dIntervalDistance, int nNoOfTrigger, int nCmpSource = 1); virtual bool SetMotorMultipleTrigger(const multiple_trigger &trigger); // virtual method to force set the current position int SetPosition(double dPosition); virtual bool SetMotorPosition(double dPosition) = 0; // virtual method to arm controller axis for single trigger virtual int SetSingleTrigger(double dPosition, int nCmpSource = 1, int nPulseStretch = STRETCH_NON); // virtual method to arm multiaxis for simultaneous motion virtual int SimultaneousMove(int nNoOfAxis, CMtrProfile *mtrProfile, double *dPosition, double *dStartVel, double *dMaxVel, double *dAcc, int nMode = 0); // virtual method to move absolute with s-curve profile int SMoveAbs(double dPosition, int nPos = -1, int nMode = 0); // virtual method to move motor in s-curve continuously virtual int SMoveContinuously(bool bCW = true); // virtual method to move relative distance with s-curve profile int SMoveRel(double dDistance, int nPos = -1); // return: success = MOTION_END; error = MOTION_ERROR; Force Stop = MOTION_FORCE_STOP virtual DWORD WaitHomeDone(); // wait for motion stop based on pulse send out or in-position signal // call this function after calling a move operation // return: success = MOTION_END; error = MOTION_ERROR; Force Stop = MOTION_FORCE_STOP // positive limit = MOTION_LIMIT_POS_HIT; negative limit = MOTION_LIMIT_NEG_HIT virtual DWORD WaitMotionDone(DWORD dwTimeout = 1000); // virtual method to get the encoder index signal virtual BOOL IsIndex(); // method to get other axis encoder index signal virtual BOOL IsIndex(const CMtrProfile &mtrProfile); // ************************************************************** // virtual Methods declaration applicable to ACS ONLY - STARTS // ************************************************************** virtual int SegmentedMotion(int nAxis, const CMtrProfile *pMtrProfile, double *dPositions); virtual int SegmentedLine(double *dPositions); virtual int SegmentedEnd(); virtual int SegmentedArc(double *dCenter, double *dFinalPoint, int rotation); virtual int MasterSlaveEnable(const CMtrProfile slaveMtrProfile, double offset, double leftBoundary, double rightBoundary); virtual int MasterSlaveDisable(const CMtrProfile slaveMtrProfile); // ************************************************************** // virtual Methods declaration applicable to ACS ONLY - ENDS // ************************************************************** // ************************************************************** // virtual Methods declaration applicable to GALIL ONLY - STARTS // ************************************************************** // virtual method to get motion stop code virtual int GetStopCode(); // virtual method to get motion stop code virtual CString GetVariable(CString csVariableName); // virtual method to send direct command string to controller virtual int SendCommand(CString csCommand); // virtual method to stop any running script program and stop all motion virtual int StopProgramAndMotion(); // virtual method to update motion profile virtual int UpdateProfile(); // ************************************************************** // virtual Methods declaration applicable to GALIL ONLY - ENDS // ************************************************************** // ************************************************************** // Methods declaration // ************************************************************** // method to get the real world distance in pulse double ConvertToPulse(double dDistance); // method to check if Axis will check for interrupt bool IsEnableIntCheck(); // method to check disable interrupt void DisableIntCheck(); // method to check enable interrupt void EnableIntCheck(); // method to enable/disable auto reset motor position during home operation void EnableResetPositionDuringHoming(bool bResetPositionDuringHoming) { m_bResetPositionDuringHoming = bResetPositionDuringHoming; } // method to get the event for homimg complete HANDLE GetHomeMotionDoneTrigger(); // method to get the event for motion complete HANDLE GetMotionDoneTrigger(); // method to get the negative software limit in mm double GetNegativeSoftLimit(); // method to get the positive software limit in mm double GetPositiveSoftLimit(); // method to set positive software limit void SetPositiveSoftLimit(double dPosSoftLimit); // method to set negative software limit void SetNegativeSoftLimit(double dPosSoftLimit); // method to home motor, normal or use limit sensor as home. // Whether to reset position tracking int Home(DWORD dwTimeout, bool bResetPositionTrack = true, bool bByLimit = false); // method to do homing, by Sensor or by Index mode BOOL Homing(); // method to move motor based on position array int Move(int iPos, int nMode = 0); // method to reset necessary motion events before any motion void ResetRequiredMotionEvents(); virtual void SetMotorProfile(double dValue, motion_profile::PROFILE_TYPE type) = 0; // method to set normal, slow acceleration int SetAcce(double dAcce, bool bHomeSlow = false); // method to set normal, slow deceleration int SetDec(double dDec, bool bHomeSlow = false); // method to set normal acceleration int SetSAcce(double dSAcce); // method to set normal deceleration int SetSDec(double dSDec); // method to set constant speed int SetConst(double dConst); // method to set normal, slow start up speed int SetStartUp(double dStartUp, bool bHomeSlow = false); // method to set normal, slow max speed int SetCruise(double dCruise, bool bHomeSlow = false); // method to set virtual home position int SetVirtualHomePosition(double dVirtualHomePosition); // method to get virtual home position double GetVirtualHomePosition(); // method to move motor based on position array with s-curve profile int SMove(int iPos, int nMode = 0); // method to update the current motor position number for tracking purpose void UpdatePosition(int nPos); // method to update auto position number tracking after any motion done // call to manually update the motor position tracking if never use wait motion done command // normally by calling wait motion done, position tracking is automatically updated. void UpdatePosition(); // Gary 21Mar11, V1.28.01 // This method is used to reset alarm via MotionNet virtual int ResetAlarm(bool bReset); // These methods only applies to ETEL Gantry Mode // Gary 8Apr11, V1.29.00 virtual int GantryEnable(int /*nNoOfAxis*/, CMtrProfile* /*mtrProfile*/) { return MOTION_ERROR; } virtual int GantryDisable(int /*nNoOfAxis*/, CMtrProfile* /*mtrProfile*/) { return MOTION_ERROR; } // Method to force a compare output pulse // Gary 2Jul12, V1.29.07 virtual int TriggerCompareOutput() { return MOTION_ERROR; } BOOL TestIOStatus(const CMtrProfile &mtrProfile, unsigned short bitmask); virtual bool SetFixSpdRange(double dMaxVel){return MOTION_ERROR;}; virtual bool UnFixSpdRange(){return MOTION_ERROR;}; // ************************************************************** // variables declaration // ************************************************************** // event to trigger axis interrupt HANDLE m_hAxisInt; // event to start normal home operation HANDLE m_hStartHome; // event to start home by limit operation HANDLE m_hStartHomeByLimit; // event to inform motion is completed HANDLE m_hMotionDone; // event to inform homing is completed HANDLE m_hHomeMotionDone; // event to inform motion has stopped HANDLE m_hStop; // event to inform motor trigger positive/cw limit HANDLE m_hPosLmtHit; // event to inform motor trigger negative/cw limit HANDLE m_hNegLmtHit; // Gary 24Feb11, V1.28.01, new positive limit handle for MotionNet Only // event to inform motor trigger positive/cw limit HANDLE m_hMotionNetPosLmtHit; // Gary 24Feb11, V1.28.01, new negative limit handle for MotionNet Only // event to inform motor trigger negative/cw limit HANDLE m_hMotionNetNegLmtHit; // mutex for interlocking CMutex m_mutexMotion; // flag to indicate if axis should respond to any interrupts bool m_bEnableIntCheck; // variable to keep track of original Home Sensor Logic int m_nOrgLogic; // flag to indicate whether to reset position during homing bool m_bResetPositionDuringHoming; // thread to monitor axis motion CWinThread *m_pThread; // keep track of which motor no int m_iMtrNo; // keep track of no of pos int m_iNoOfPos; // pointer to position array double *m_dpPos; // motor profile const CMtrProfile m_MtrProfile; // variable to track what's the current position number of the axis int m_nCurrentPosNo; struct signal_mask { // home signal bit mask unsigned short m_usHomeBitMask; // index signal bit mask unsigned short m_usIndexBitMask; // CW Limit signal bit mask unsigned short m_usCWLimitBitMask; // CCW Limit signal bit mask unsigned short m_usCCWLimitBitMask; // Motor Ready signal bit mask unsigned short m_usReadyBitMask; // Motor On signal bit mask unsigned short m_usOnBitMask; // Alarm signal bit mask unsigned short m_usAlarmBitMask; // In Position signal bit mask unsigned short m_usInPositionBitMask; signal_mask() { m_usHomeBitMask = 0; m_usIndexBitMask = 0; m_usCWLimitBitMask = 0; m_usCCWLimitBitMask = 0; m_usReadyBitMask = 0; m_usOnBitMask = 0; m_usAlarmBitMask = 0; m_usInPositionBitMask = 0; } } m_structSignalMask; protected: // methods to reset related motion events before any motion void ResetMotionEvents(); // methods to log trace data void Log(CString csData); void Log(const char *filename, int linenr, const char *formatString, ...); void StartHomingTimeoutTimer(); void StopHomingTimeoutTimer(); void SetRemainingHomingTimeout(DWORD dwTimeout); DWORD GetRemainingHomingTimeout(); DWORD GetHomeTimeout(); DWORD GetHomingStatus(); void SetHomingStatus(DWORD dwStatus); DWORD WaitHomeComplete(DWORD dwTimeout); bool IsHomingComplete(DWORD dwStatus); bool IsHomingHitLimit(DWORD dwStatus); bool IsMotorAtHomeLimit(); bool IsHomingDirectionCorrect(DWORD dwMotionStopStatus); bool DoLeaveHomeOperation(int nHowManyTimes, double dDistance, LEAVE_HOME_CHECK_SENSOR check); bool IsWithinSoftLimit(double dPosition); void StartMotionTimer(); void StopMotionTimer(); long GetMotionTime(); double ConvertToMotorCoordinate(double dPosition); double ConvertToRealWorldCoordinate(double dPosition); double ConvertOutputPulseToPosition(double dPulse); double ConvertInputPulseToPosition(double dPulse); double ConvertInputPulseToPosition(const CMtrProfile &mtrProfile, double dPulse); double GetHomeLeaveSteps(); bool IsMotorNumberValid(int nNumber); double Convert_M_To_mm(double dValue); double Convert_mm_To_M(double dValue); bool UseHomeSlowSpeed(); CMotionControllerBase *m_pBaseController; private: // thread to monitor home operation CWinThread *m_pHomeThread; // event to kill any running thread HANDLE m_hKillThread; CHighResPerformanceCounter m_homingTimer; // High resolution timer object to track motion time CHighResPerformanceCounter m_timerMotion; DWORD m_dwHomingTimeout; DWORD m_dwHomingStatus; // variable to store home motion timeout setting DWORD m_dwHomeTimeout; // home leave steps with direction double m_dHomeLeaveSteps; // variable to store the no. of output pulse per mm double m_dPulsePerMM; // variable to store the no. of encoder input pulse per mm double m_dEncoderPulsePerMM; // virtual home position double m_dVirtualHomePosition; void SetHomeTimeout(DWORD dwTimeout); void SetHomeLeaveSteps(double dLeaveSteps); int BaseRelativeMove(double dDistance, int nPos, PROFILE_CURVE curve); int BaseAbsoluteMove(double dPosition, int nPos, int nMode, PROFILE_CURVE curve); }; #define LOG_TRACE(format, ...) if (m_bTraceData) m_logger.Log(__FILE__, __LINE__, format, __VA_ARGS__) #endif // !defined(AFX_MOTORBASE_H__04B8BC9A_5FF9_4E00_BA08_FDEC856015F1__INCLUDED_)