1、Cocos2dx之touch事件Cocos2dx之touch事件今天看了下ccocos2dx touch事件部分的源码,从CCTouch、CCTouchHandler和CCTouchDispatcher简单的做了分析和总结,先直接看源码吧!1、CCTouchclass CC_DLL CCTouch : public CCObjectpublic: CCTouch() : m_nId(0), m_startPointCaptured(false) /* returns the current touch location in OpenGL coordinates */ CCPoint getL
2、ocation() const;/获取当前touch位置,该位置基于OpenGL坐标 /* returns the previous touch location in OpenGL coordinates */ CCPoint getPreviousLocation() const;/获取前一次touch位置,该位置基于OpenGL坐标 /* returns the start touch location in OpenGL coordinates */ CCPoint getStartLocation() const;/获取该touch的起始位置,该位置基于OpenGL坐标 /* ret
3、urns the delta of 2 current touches locations in screen coordinates */ CCPoint getDelta() const; /获取前后两次位置的偏移量,基于OpenGL坐标 /* returns the current touch location in screen coordinates */ CCPoint getLocationInView() const; /当前touch位置,该位置基于屏幕坐标位置 /* returns the previous touch location in screen coordina
4、tes */ CCPoint getPreviousLocationInView() const; /获取touch前一次的位置,基于屏幕坐标位置 /* returns the start touch location in screen coordinates */ CCPoint getStartLocationInView() const; /获取touch起始位置,基于屏幕坐标位置 void setTouchInfo(int id, float x, float y) m_nId = id; m_prevPoint = m_point; m_point.x = x; m_point.y
5、 = y; if (!m_startPointCaptured) m_startPoint = m_point; m_startPointCaptured = true; int getID() const return m_nId; private: int m_nId; bool m_startPointCaptured; CCPoint m_startPoint; CCPoint m_point; CCPoint m_prevPoint;CCTouch中有三个主要成员,m_startPoint、m_point、m_prevPoint,这三个点都是基于屏幕坐标。将这三个点转化为OpenGL
6、坐标可以用CCDirector:sharedDirector()-convertToGL(m_point)函数来转化。2、CCTouchHandler、CCStandardTouchHandler和CCTargetedTouchHandlerclass CC_DLL CCTouchHandler : public CCObjectpublic: virtual CCTouchHandler(void); /* delegate */ CCTouchDelegate* getDelegate(); /获取touch代理 void setDelegate(CCTouchDelegate *pDel
7、egate); /设置touch代理 /* priority */ int getPriority(void); /获取代理优先级 void setPriority(int nPriority); /获取代理优先级 /* enabled selectors */ int getEnabledSelectors(void); / void setEnalbedSelectors(int nValue); /* initializes a TouchHandler with a delegate and a priority */ virtual bool initWithDelegate(CCT
8、ouchDelegate *pDelegate, int nPriority);public: /* allocates a TouchHandler with a delegate and a priority */创建一个CCTouchHandlerstatic CCTouchHandler* handlerWithDelegate(CCTouchDelegate *pDelegate, int nPriority);protected: CCTouchDelegate *m_pDelegate; /touch代理 int m_nPriority; /优先级 int m_nEnabledS
9、electors; /该成员没看出来有什么作用;CCTouchHandler主要将touch代理和优先级封装起来,CCTouchHandler还有两个派生对象: CCStandardTouchHandler和CCTargetedTouchHandler。这两个派生类很简单不需多说,简单的贴上代码吧。class CC_DLL CCStandardTouchHandler : public CCTouchHandlerpublic: /* initializes a TouchHandler with a delegate and a priority */ virtual bool initWi
10、thDelegate(CCTouchDelegate *pDelegate, int nPriority);public: /* allocates a TouchHandler with a delegate and a priority */ static CCStandardTouchHandler* handlerWithDelegate(CCTouchDelegate *pDelegate, int nPriority);class CC_DLL CCTargetedTouchHandler : public CCTouchHandlerpublic: CCTargetedTouch
11、Handler(void); /* whether or not the touches are swallowed */ bool isSwallowsTouches(void); /是否吞掉CCTouch void setSwallowsTouches(bool bSwallowsTouches); /设置是否吞掉CCTouch /* MutableSet that contains the claimed touches */ CCSet* getClaimedTouches(void); /获取将要处理的CCTouch的集合 /* initializes a TargetedTouch
12、Handler with a delegate, a priority and whether or not it swallows touches or not */ bool initWithDelegate(CCTouchDelegate *pDelegate, int nPriority, bool bSwallow);public: /* allocates a TargetedTouchHandler with a delegate, a priority and whether or not it swallows touches or not */ static CCTarge
13、tedTouchHandler* handlerWithDelegate(CCTouchDelegate *pDelegate, int nPriority, bool bSwallow);protected: bool m_bSwallowsTouches; /处理CCTouch后是否吞掉该CCTouch CCSet *m_pClaimedTouches; /要处理的CCTouch集合;3、CCTouch事件分发器CCTouchDispatcherclass CC_DLL CCTouchDispatcher : public CCObject, public EGLTouchDelegate
14、public: CCTouchDispatcher(); bool init(void); CCTouchDispatcher() : m_pTargetedHandlers(NULL) , m_pStandardHandlers(NULL) , m_pHandlersToAdd(NULL) , m_pHandlersToRemove(NULL) public: /* Whether or not the events are going to be dispatched. Default: true */ bool isDispatchEvents(void); /事件是否要被分发 void
15、 setDispatchEvents(bool bDispatchEvents); /设置是否分发事件 /* Adds a standard touch delegate to the dispatchers list. See StandardTouchDelegate description. IMPORTANT: The delegate will be retained. */ void addStandardDelegate(CCTouchDelegate *pDelegate, int nPriority); /向标准代理容器添加代理 /* Adds a targeted touc
16、h delegate to the dispatchers list. See TargetedTouchDelegate description. IMPORTANT: The delegate will be retained. */ void addTargetedDelegate(CCTouchDelegate *pDelegate, int nPriority, bool bSwallowsTouches); /向目标代理容器添加代理 /* Removes a touch delegate. The delegate will be released */ void removeDe
17、legate(CCTouchDelegate *pDelegate);/移除特定代理 /* Removes all touch delegates, releasing all the delegates */ void removeAllDelegates(void);/移除所有代理 /* Changes the priority of a previously added delegate. The lower the number, the higher the priority */ void setPriority(int nPriority, CCTouchDelegate *pD
18、elegate);/设置特定代理的优先级 void touches(CCSet *pTouches, CCEvent *pEvent, unsigned int uIndex); /分发事件逻辑处理,主要看的函数 /以下是对四种事件的处理 virtual void touchesBegan(CCSet* touches, CCEvent* pEvent); virtual void touchesMoved(CCSet* touches, CCEvent* pEvent); virtual void touchesEnded(CCSet* touches, CCEvent* pEvent);
19、virtual void touchesCancelled(CCSet* touches, CCEvent* pEvent);public: CCTouchHandler* findHandler(CCTouchDelegate *pDelegate); /根据代理查找特定CCTouchHandlerprotected: void forceRemoveDelegate(CCTouchDelegate *pDelegate); void forceAddHandler(CCTouchHandler *pHandler, CCArray* pArray); void forceRemoveAll
20、Delegates(void); void rearrangeHandlers(CCArray* pArray); /重新根据优先级对代理排序 CCTouchHandler* findHandler(CCArray* pArray, CCTouchDelegate *pDelegate);protected: CCArray* m_pTargetedHandlers; /目标事件代理容器 CCArray* m_pStandardHandlers; /标准事件代理容器 bool m_bLocked; /是否被锁 bool m_bToAdd; /是否需要添加 bool m_bToRemove; /
21、是否需要删除 CCArray* m_pHandlersToAdd; /要添加的代理容器 struct _ccCArray *m_pHandlersToRemove; /要删除的代理容器 bool m_bToQuit; /是否要退出 bool m_bDispatchEvents; /是否要处理touch事件 / 4, 1 for each type of event struct ccTouchHandlerHelperData m_sHandlerHelperDataccTouchMax;我们主要看一看void touches(CCSet *pTouches, CCEvent *pEvent,
22、 unsigned int uIndex); 这个函数看看touch事件分发器是如何实现事件的分发。先贴上该函数源码void CCTouchDispatcher:touches(CCSet *pTouches, CCEvent *pEvent, unsigned int uIndex) CCAssert(uIndex = 0 & uIndex count(); /获取目标事件代理个数 unsigned int uStandardHandlersCount = m_pStandardHandlers-count(); /获取标准事件代理个数 bool bNeedsMutableSet = (uT
23、argetedHandlersCount & uStandardHandlersCount); /需不需要拷贝CCTouch容器 pMutableTouches = (bNeedsMutableSet ? pTouches-mutableCopy() : pTouches); /拷贝CCTouch容器用于向标准touch代理分发事件 struct ccTouchHandlerHelperData sHelper = m_sHandlerHelperDatauIndex; / / process the target handlers 1st / if (uTargetedHandlersCou
24、nt 0) CCTouch *pTouch; CCSetIterator setIter; for (setIter = pTouches-begin(); setIter != pTouches-end(); +setIter) /遍历CCTouch集合 pTouch = (CCTouch *)(*setIter); CCTargetedTouchHandler *pHandler = NULL; CCObject* pObj = NULL; CCARRAY_FOREACH(m_pTargetedHandlers, pObj) /对于每一个CCTouch,遍历每一个目标事件代理处理器 pHa
25、ndler = (CCTargetedTouchHandler *)(pObj); if (! pHandler) break; bool bClaimed = false; /是否要得到处理 if (uIndex = CCTOUCHBEGAN) bClaimed=pHandler-getDelegate()-ccTouchBegan(pTouch, pEvent);/调用代理的ccTouchBegan函数 if (bClaimed) /如果ccTouchBegan函数返回true,说明事件要被处理 pHandler-getClaimedTouches()-addObject(pTouch);
26、 /将该touch事件加入到该touch事件处理器的待处理事件容器中 else if (pHandler-getClaimedTouches()-containsObject(pTouch) /判断handler内是否有该CCTouch / moved ended canceled bClaimed = true; /标记要被处理 switch (sHelper.m_type) case CCTOUCHMOVED: pHandler-getDelegate()-ccTouchMoved(pTouch, pEvent); /注意处理CCTouchMoved 不会移除相应CCTouch break
27、; case CCTOUCHENDED: pHandler-getDelegate()-ccTouchEnded(pTouch, pEvent); pHandler-getClaimedTouches()-removeObject(pTouch); /从代理handler中的要处理的CCTouch容器中移除该CCTouch break; case CCTOUCHCANCELLED: pHandler-getDelegate()-ccTouchCancelled(pTouch, pEvent); pHandler-getClaimedTouches()-removeObject(pTouch);
28、 /从代理handler中的要处理的CCTouch容器中移除该CCTouch break; if (bClaimed & pHandler-isSwallowsTouches() /已经被处理并且要吞掉 if (bNeedsMutableSet) / pMutableTouches-removeObject(pTouch); /从用于向标准代理分发事件的容器中移除该CCTouch break; / / process standard handlers 2nd /处理标准事件的分发,比目标事件简单 if (uStandardHandlersCount 0 & pMutableTouches-c
29、ount() 0) CCStandardTouchHandler *pHandler = NULL; CCObject* pObj = NULL; CCARRAY_FOREACH(m_pStandardHandlers, pObj) pHandler = (CCStandardTouchHandler*)(pObj); if (! pHandler) break; switch (sHelper.m_type) case CCTOUCHBEGAN: pHandler-getDelegate()-ccTouchesBegan(pMutableTouches, pEvent); break; case CCTOUCHMOVED: pHandler-getDelegate()-ccTouchesMoved(pMutableTouches, pEvent); break; case CCTOUCHENDED: pHandler-getDelegate()-ccTouchesEnded(pMutableTouches, pEvent); break; case CCTOUCHCANCELLED: pHandler-getDelegate()-ccTouchesCancelled(pMutableTouches, pEvent); break; if (bNeedsMutableSet)
copyright@ 2008-2022 冰豆网网站版权所有
经营许可证编号:鄂ICP备2022015515号-1