mirror of
https://github.com/ultimatepp/ultimatepp.git
synced 2026-05-16 06:05:58 -06:00
156 lines
No EOL
3.6 KiB
C++
156 lines
No EOL
3.6 KiB
C++
#include "Timer.h"
|
|
|
|
//Timer
|
|
|
|
Timer::Timer()
|
|
{
|
|
granularity = 10;
|
|
run = true;
|
|
t.Run(THISBACK(TimerThread));
|
|
}
|
|
|
|
Timer::~Timer()
|
|
{
|
|
run = false;
|
|
t.Wait();
|
|
|
|
Mutex::Lock __(sTimerLock);
|
|
while(elist.GetNext() != elist.GetPtr())
|
|
delete elist.GetNext();
|
|
}
|
|
|
|
void Timer::sTimeCallback(dword time, int delay, Callback cb, void *id) {
|
|
TimeEvent *list = elist.GetPtr();
|
|
TimeEvent *e;
|
|
for(e = list->GetNext(); e != list && time >= e->time; e = e->GetNext());
|
|
TimeEvent *ne = e->InsertPrev();
|
|
ne->time = time;
|
|
ne->cb = cb;
|
|
ne->delay = delay;
|
|
ne->id = id;
|
|
}
|
|
|
|
void Timer::SetTimeCallback(int delay_ms, Callback cb, void *id) {
|
|
Mutex::Lock __(sTimerLock);
|
|
ASSERT(abs(delay_ms) < 0x40000000);
|
|
sTimeCallback(GetTickCount() + abs(delay_ms), delay_ms, cb, id);
|
|
}
|
|
|
|
void Timer::KillTimeCallbacks(void *id, void *idlim) {
|
|
Mutex::Lock __(sTimerLock);
|
|
TimeEvent *list = elist.GetPtr();
|
|
for(TimeEvent *e = list->GetNext(); e != list;)
|
|
if(e->id >= id && e->id < idlim) {
|
|
e = e->GetNext();
|
|
delete e->GetPrev();
|
|
}
|
|
else
|
|
e = e->GetNext();
|
|
}
|
|
void Timer::KillTimeCallbacks(void *id) {
|
|
Mutex::Lock __(sTimerLock);
|
|
TimeEvent *list = elist.GetPtr();
|
|
for(TimeEvent *e = list->GetNext(); e != list;)
|
|
if(e->id == id) {
|
|
e = e->GetNext();
|
|
delete e->GetPrev();
|
|
}
|
|
else
|
|
e = e->GetNext();
|
|
}
|
|
|
|
bool Timer::ExistsTimeCallback(void *id) {
|
|
Mutex::Lock __(sTimerLock);
|
|
TimeEvent *list = elist.GetPtr();
|
|
for(TimeEvent *e = list->GetNext(); e != list; e = e->GetNext())
|
|
if(e->id == id)
|
|
return true;
|
|
return false;
|
|
}
|
|
|
|
void Timer::KillTimeCallback(void *id) {
|
|
// KillTimeCallbacks(id, (byte *)id + 1);
|
|
KillTimeCallbacks(id);
|
|
}
|
|
|
|
void Timer::TimerProc(dword time, int & leftsleep)
|
|
{
|
|
if(IsPanicMode())
|
|
return;
|
|
sTimerLock.Enter();
|
|
TimeEvent *list = elist.GetPtr();
|
|
if(sTClick > time)
|
|
for(TimeEvent *e = list->GetNext(); e != list; e = e->GetNext())
|
|
if(e->time > 0x80000000)
|
|
e->time = 0;
|
|
sTClick = time;
|
|
// sTimerLock.Leave();
|
|
// //***
|
|
// sTimerLock.Enter();
|
|
while(list->GetNext() != list && ((leftsleep = (list->GetNext()->time - time)) <= 0)) {
|
|
TimeEvent *e = list->GetNext();
|
|
e->Unlink();
|
|
if(e->delay < 0)
|
|
sTimeCallback(time - e->delay, e->delay, e->cb, e->id);
|
|
sTimerLock.Leave();
|
|
e->cb();
|
|
sTimerLock.Enter();
|
|
delete e;
|
|
}
|
|
sTimerLock.Leave();
|
|
if(leftsleep < 0) leftsleep = granularity; //if last done has been processed and no more in queue, ensure good sleep
|
|
}
|
|
|
|
//SAME API AS IN Ctrl
|
|
void Timer::SetTimeCallback(int delay_ms, Callback cb, int id) {
|
|
// ASSERT(id >= 0 && (size_t)id < (int)sizeof(Timer));
|
|
// SetTimeCallback(delay_ms, cb, (byte *)this + id);
|
|
SetTimeCallback(delay_ms, cb, (byte *)id);
|
|
}
|
|
|
|
void Timer::KillTimeCallback(int id) {
|
|
// ASSERT(id >= 0 && (size_t)id < sizeof(Timer));
|
|
// KillTimeCallback((byte *)this + id);
|
|
KillTimeCallback((byte *)id);
|
|
}
|
|
|
|
void Timer::KillSetTimeCallback(int delay_ms, Callback cb, int id)
|
|
{
|
|
KillTimeCallback(id);
|
|
SetTimeCallback(delay_ms, cb, id);
|
|
}
|
|
|
|
void Timer::PostCallback(Callback cb, int id)
|
|
{
|
|
SetTimeCallback(0, cb, id);
|
|
}
|
|
|
|
void Timer::KillPostCallback(Callback cb, int id)
|
|
{
|
|
KillSetTimeCallback(0, cb, id);
|
|
}
|
|
|
|
bool Timer::ExistsTimeCallback(int id) {
|
|
// ASSERT(id >= 0 && (size_t)id < sizeof(Timer));
|
|
// return ExistsTimeCallback((byte *)this + id);
|
|
return ExistsTimeCallback((byte *)id);
|
|
}
|
|
|
|
void Timer::SetTimerGranularity(int ms)
|
|
{
|
|
if(ms > 0)
|
|
granularity = ms;
|
|
}
|
|
|
|
///
|
|
|
|
void Timer::TimerThread()
|
|
{
|
|
int leftsleep;
|
|
while(run)
|
|
{
|
|
leftsleep = granularity;
|
|
TimerProc(GetTickCount(), leftsleep);
|
|
Sleep(min(granularity, leftsleep));
|
|
}
|
|
} |