在游戏中定时器十分常见,主要有定时一段时间循环执行,延迟执行等等。
比如我要实现这样的功能,延迟2秒执行a,在每隔1秒执行b,持续10次。
auto a = [ this ] ( )
{
int k = 0 ;
Log ( to_string ( Width) + "----------" + to_string ( Height) ) ;
this -> Log ( "延迟2秒后" ) ;
auto b = [ & k , this ] ( )
{
this -> Log ( "延迟1秒输出" + to_string ( k) ) ;
k++ ;
} ;
TimesScheduleCommand* c = new TimesScheduleCommand ( b, 10 , 1 ) ;
auto m = [ this ] ( )
{
this -> Log ( "任务完成" ) ;
} ;
c-> onComplete = m;
Time :: PushCommand ( c) ;
} ;
DelayScheduleCommand* d = new DelayScheduleCommand ( a, 2.0 ) ;
Time :: PushCommand ( d) ;
结果如下
ScheduleCommand类,所有定时命令
# ifndef ScheduleCommand_H
# define ScheduleCommand_H
# include <functional>
# include <iostream>
using namespace std;
class ScheduleCommand
{
public :
float curTime;
bool isDispose;
bool isExecutedEnd;
std:: function< void ( void ) > action;
std:: function< void ( void ) > onComplete;
ScheduleCommand ( std:: function< void ( void ) > fun)
{
isDispose = false ;
isExecutedEnd = false ;
curTime = 0 ;
action = fun;
}
~ ScheduleCommand ( )
{
}
virtual void Execute ( float deltaTime) {
curTime += deltaTime;
} ;
} ;
class LoopInSecondScheduleCommand : public ScheduleCommand
{
public :
float timePerLoop;
float timeInLoop;
LoopInSecondScheduleCommand ( std:: function< void ( void ) > fun, float time) : ScheduleCommand ( fun)
{
timePerLoop = time;
timeInLoop = 0 ;
}
void Execute ( float deltaTime) override
{
__super:: Execute ( deltaTime) ;
timeInLoop += deltaTime;
if ( timeInLoop > timePerLoop)
{
action ( ) ;
timeInLoop -= timePerLoop;
}
}
} ;
class LoopPerFrameScheduleCommand : public ScheduleCommand
{
public :
LoopPerFrameScheduleCommand ( std:: function< void ( void ) > fun) : ScheduleCommand ( fun)
{
}
void Execute ( float deltaTime) override
{
__super:: Execute ( deltaTime) ;
action ( ) ;
}
} ;
class TimesScheduleCommand : public ScheduleCommand
{
public :
unsigned int times;
float timePerFrequency;
float timeInFrequency;
TimesScheduleCommand ( std:: function< void ( void ) > fun, int times , float timePerFrequency) : ScheduleCommand ( fun) , times ( times) , timePerFrequency ( timePerFrequency)
{
timeInFrequency = 0 ;
}
void Execute ( float deltaTime) override
{
__super:: Execute ( deltaTime) ;
timeInFrequency += deltaTime;
if ( timeInFrequency > timePerFrequency)
{
action ( ) ;
timeInFrequency -= timePerFrequency;
times-- ;
if ( times <= 0 )
isExecutedEnd = true ;
}
}
} ;
class PerFrameScheduleCommand : public ScheduleCommand
{
public :
float totalTime;
PerFrameScheduleCommand ( std:: function< void ( void ) > fun, int totalTime) : ScheduleCommand ( fun) , totalTime ( totalTime)
{
}
void Execute ( float deltaTime) override
{
__super:: Execute ( deltaTime) ;
action ( ) ;
if ( curTime > totalTime)
isExecutedEnd = true ;
}
} ;
class DelayScheduleCommand : public ScheduleCommand
{
public :
float DelayTime;
DelayScheduleCommand ( std:: function< void ( void ) > fun, int DelayTime) : ScheduleCommand ( fun) , DelayTime ( DelayTime)
{
}
void Execute ( float deltaTime) override
{
__super:: Execute ( deltaTime) ;
if ( curTime > DelayTime)
{
action ( ) ;
isExecutedEnd = true ;
}
}
} ;
# endif
在Time类中循环执行
# ifndef Time_H
# define Time_H
# include "Window.h"
# include <boost/function.hpp>
# include "ScheduleCommand.h"
class Time
{
private :
static float _deltaTime;
static float _startTime;
static float _curTime;
friend void Window :: SetDeltaTime ( float time) ;
friend void Window :: SetCurTime ( float time) ;
friend void Window :: SetStartTime ( float time) ;
static void PullCommand ( ScheduleCommand* schedules) ;
static void MoveToBack ( ScheduleCommand* schedules) ;
static void Execute ( ) ;
public :
static const unsigned int MAX_COMMANDNUM = 1999 ;
static ScheduleCommand* commands[ ] ;
static int commandStartIndex;
static int commandCount;
static float GetDeltaTime ( ) ;
static float GetCurTime ( ) ;
static float GetStartTimee ( ) ;
static void Update ( ) ;
static void PushCommand ( ScheduleCommand* schedules) ;
} ;
# endif
# include "Time.h"
# include
float Time:: _deltaTime = 0.0f ;
float Time:: _curTime = 0.0f ;
float Time:: _startTime = 0.0f ;
int Time:: commandStartIndex = 0 ;
int Time:: commandCount = 0 ;
ScheduleCommand* Time:: commands[ MAX_COMMANDNUM] ;
float Time :: GetDeltaTime ( )
{
return _deltaTime;
}
float Time :: GetCurTime ( )
{
return _curTime;
}
float Time :: GetStartTimee ( )
{
return _startTime;
}
void Time :: Update ( )
{
Execute ( ) ;
}
void Time :: PushCommand ( ScheduleCommand* schedules)
{
assert ( commandCount < MAX_COMMANDNUM) ;
int insertIndex = ( commandStartIndex + commandCount) % MAX_COMMANDNUM;
commands[ insertIndex] = schedules;
commandCount++ ;
}
void Time :: PullCommand ( ScheduleCommand* schedules)
{
delete schedules;
commandCount-- ;
}
void Time :: MoveToBack ( ScheduleCommand* schedules)
{
int moveIndex = ( commandStartIndex + commandCount) % MAX_COMMANDNUM;
commands[ moveIndex] = schedules;
}
void Time :: Execute ( )
{
unsigned int start = commandStartIndex;
unsigned int end = start + commandCount;
while ( start < end)
{
int index = start % MAX_COMMANDNUM;
start++ ;
if ( commands[ index] -> isDispose)
{
PullCommand ( commands[ index] ) ;
commandStartIndex++ ;
continue ;
}
commands[ index] -> Execute ( _deltaTime) ;
if ( commands[ index] -> isExecutedEnd)
{
if ( commands[ index] -> onComplete)
commands[ index] -> onComplete ( ) ;
PullCommand ( commands[ index] ) ;
}
else
{
MoveToBack ( commands[ index] ) ;
}
commandStartIndex++ ;
}
}