转载:http://blog.youkuaiyun.com/qq_17749439/article/details/37903435
updata定时器,每一帧都被触发,使用scheduleUpdate方法来启用
schedule定时器,可以设置触发的
在CCNode中
- //启用update定时器
- voidCCNode::scheduleUpdate()
- {
- scheduleUpdateWithPriority(0);
- }
- //启用update定时器,并设定定时器的优先级
- voidCCNode::scheduleUpdateWithPriority(int priority)
- {
- m_pScheduler->scheduleUpdateForTarget(this, priority, !m_bRunning);
- }
- voidCCNode::scheduleUpdateWithPriorityLua(int nHandler,int priority)
- {
- unscheduleUpdate();
- m_nUpdateScriptHandler = nHandler;
- m_pScheduler->scheduleUpdateForTarget(this, priority, !m_bRunning);
- }
- //取消update定时器
- voidCCNode::unscheduleUpdate()
- {
- m_pScheduler->unscheduleUpdateForTarget(this);
- if (m_nUpdateScriptHandler)
- {
- CCScriptEngineManager::sharedManager()->getScriptEngine()->removeScriptHandler(m_nUpdateScriptHandler);
- m_nUpdateScriptHandler =0;
- }
- }
- //添加一个定时器
- //selector参数为定时器的事件函数
- //interval参数为定时器的时间间隔
- //repeat参数为定时时间触发一次后还会再次触发的次数(kCCRepeatForever表示触发无穷多次)
- //delay为第一次触发事件前的延时
- voidCCNode::schedule(SEL_SCHEDULE selector)
- {
- this->schedule(selector,0.0f,kCCRepeatForever,0.0f);
- }
- voidCCNode::schedule(SEL_SCHEDULE selector,float interval)
- {
- this->schedule(selector, interval,kCCRepeatForever,0.0f);
- }
- voidCCNode::schedule(SEL_SCHEDULE selector,float interval, unsignedint repeat,float delay)
- {
- CCAssert( selector,"Argument must be non-nil");
- CCAssert( interval >=0,"Argument must be positive");
- m_pScheduler->scheduleSelector(selector,this, interval , repeat, delay, !m_bRunning);
- }
- //添加一个定时器,只触发一次
- voidCCNode::scheduleOnce(SEL_SCHEDULE selector,float delay)
- {
- this->schedule(selector,0.0f,0, delay);
- }
- //取消selector所对应函数的定时器
- voidCCNode::unschedule(SEL_SCHEDULE selector)
- {
- // explicit nil handling
- if (selector ==0)
- return;
- m_pScheduler->unscheduleSelector(selector,this);
- }
- //取消此节点所关联的全部定时器
- voidCCNode::unscheduleAllSelectors()
- {
- m_pScheduler->unscheduleAllForTarget(this);
- }
- //继续此节点所关联的全部定时器
- voidCCNode::resumeSchedulerAndActions()
- {
- m_pScheduler->resumeTarget(this);
- m_pActionManager->resumeTarget(this);
- }
- //暂停此节点所关联的全部定时器
- voidCCNode::pauseSchedulerAndActions()
- {
- m_pScheduler->pauseTarget(this);
- m_pActionManager->pauseTarget(this);
- }
////////////////////////////////////////////////////////////////////////////////////////////////////////////////
而m_pScheduler的类型为CCScheduler,
所以控制游戏定时器的中CCScheduler中。
在游戏循环中调用了m_pScheduler->update(m_fDeltaTime);来控制定时器的调度。
- // main loop
- voidCCScheduler::update(float dt)
- {
- m_bUpdateHashLocked =true;
- //预处理
- if (m_fTimeScale !=1.0f)
- {
- dt *=m_fTimeScale;
- }
- //枚举所有的update定时器
- // Iterate over all the Updates' selectors
- tListEntry *pEntry, *pTmp;
- //优先级小于0的定时器
- // updates with priority < 0
- DL_FOREACH_SAFE(m_pUpdatesNegList, pEntry, pTmp)
- {
- if ((! pEntry->paused) && (! pEntry->markedForDeletion))
- {
- pEntry->target->update(dt);
- }
- }
- //优先级等于0的定时器
- // updates with priority == 0
- DL_FOREACH_SAFE(m_pUpdates0List, pEntry, pTmp)
- {
- if ((! pEntry->paused) && (! pEntry->markedForDeletion))
- {
- pEntry->target->update(dt);
- }
- }
- //优先级大于0的定时器
- // updates with priority > 0
- DL_FOREACH_SAFE(m_pUpdatesPosList, pEntry, pTmp)
- {
- if ((! pEntry->paused) && (! pEntry->markedForDeletion))
- {
- pEntry->target->update(dt);
- }
- }
- //枚举所有的普通定时器
- // Iterate over all the custom selectors
- for (tHashTimerEntry *elt =m_pHashForTimers; elt !=NULL; )
- {
- m_pCurrentTarget = elt;
- m_bCurrentTargetSalvaged =false;
- if (!m_pCurrentTarget->paused)
- {
- //枚举此节点大所有定时器
- //timers数组可能在循环中改变,因此中此处需要小心处理
- // The 'timers' array may change while inside this loop
- for (elt->timerIndex =0; elt->timerIndex < elt->timers->num; ++(elt->timerIndex))
- {
- elt->currentTimer = (CCTimer*)(elt->timers->arr[elt->timerIndex]);
- elt->currentTimerSalvaged =false;
- elt->currentTimer->update(dt);
- if (elt->currentTimerSalvaged)
- {
- // The currentTimer told the remove itself. To prevent the timer from
- // accidentally deallocating itself before finishing its step, we retained
- // it. Now that step is done, it's safe to release it.
- //该currenttimer告诉自行删除。阻止定时器意外释放本身之前完成的步骤,我们保留它。现在这一步完成之后,释放它的安全。
- elt->currentTimer->release();
- }
- elt->currentTimer =NULL;
- }
- }
- // elt, at this moment, is still valid
- // so it is safe to ask this here (issue #490)
- elt = (tHashTimerEntry *)elt->hh.next;
- // only delete currentTarget if no actions were scheduled during the cycle (issue #481)
- if (m_bCurrentTargetSalvaged &&m_pCurrentTarget->timers->num ==0)
- {
- removeHashElement(m_pCurrentTarget);
- }
- }
- //处理脚本引擎相关的事件
- // Iterate over all the script callbacks
- if (m_pScriptHandlerEntries)
- {
- for (int i =m_pScriptHandlerEntries->count() -1; i >= 0; i--)
- {
- CCSchedulerScriptHandlerEntry* pEntry =static_cast<CCSchedulerScriptHandlerEntry*>(m_pScriptHandlerEntries->objectAtIndex(i));
- if (pEntry->isMarkedForDeletion())
- {
- m_pScriptHandlerEntries->removeObjectAtIndex(i);
- }
- elseif (!pEntry->isPaused())
- {
- pEntry->getTimer()->update(dt);
- }
- }
- }
- //清理所有被标记来删除记号的update方法
- // delete all updates that are marked for deletion
- // updates with priority < 0
- //优先级小于0的定时器
- DL_FOREACH_SAFE(m_pUpdatesNegList, pEntry, pTmp)
- {
- if (pEntry->markedForDeletion)
- {
- this->removeUpdateFromHash(pEntry);
- }
- }
- // updates with priority == 0
- //优先级等于0的定时器
- DL_FOREACH_SAFE(m_pUpdates0List, pEntry, pTmp)
- {
- if (pEntry->markedForDeletion)
- {
- this->removeUpdateFromHash(pEntry);
- }
- }
- // updates with priority > 0
- //优先级大于0的定时器
- DL_FOREACH_SAFE(m_pUpdatesPosList, pEntry, pTmp)
- {
- if (pEntry->markedForDeletion)
- {
- this->removeUpdateFromHash(pEntry);
- }
- }
- m_bUpdateHashLocked =false;
- m_pCurrentTarget =NULL;
- }
例子:
- this->schedule(schedule_selector(GameScene::updateGame),1.0f);
- void GameScene::updateGame(ccTime dt)
- {
- }
本文详细解析了Cocos2d-x中的定时器机制,包括如何启用和取消定时器,以及不同类型的定时器如何工作。通过具体的代码示例,介绍了update定时器和schedule定时器的区别及用法。
977

被折叠的 条评论
为什么被折叠?



