使用定时器需要用到如下几个函数:
1.设置定时器函数
//如果第四个参数为NULL则系统发送一个WM_TIMER消息到应用程序队列
//如果第一个参数为0 则第二个参数忽略 一般为0
//返回定时器ID,返回0表示失败
UINT SetTimer(
HWND hWnd, //窗口句柄
UINT nIDEvent, //定时器ID
UINT uElapse, //定时时间
TIMERPROC lpTimerFunc //时间过程函数
);
2.时间过程函数
void CALLBACK TimerProc(
HWND hwnd, //窗口句柄
UINT uMsg, //指定的WM_TIMER消息
UINT idEvent, //定时器ID
DWORD dwTime //从GetTickCount函数返回的值
);
3.关掉定时器
//非0表示成功 0表示失败
BOOL KillTimer(
HWND hWnd,
UINT uIDEvent //定时器ID
);
注意:WM_TIMER消息并不是异步的,而是正常的队列消息,也需要排队,所以当消息队列拥挤的时候,比如你
设置定时器为1秒发送一次WM_TIMER消息,但是当队列中还有消息在排队的时候,程序是收不到WM_TIMER消息的。
使用定时器的三种方法:
-
将WM_TIMER发送到对应的程序窗口过程
//当前程序的窗口句柄
//定时器ID为1
//时间间隔为1秒
//无时间过程函数
SetTimer(hwnd,1,1000,NULL);//你可以在任何地方关掉定时器,如果想使用一次性定时器就
//在WM_TIMER消息中关掉定时器,否则在WM_DESTROY消息中关掉
//第二个参数是要关掉的定时器ID
KillTimer(hwnd,1);在WM_TIMER消息中,wParam等于定时器的ID,lParam是0
例如:
#define TIMER_1 1
#define TIMER_2 2
[其它代码]
case WM_CREATE:
//定时器1
SetTimer(hwnd, TIMER_1, 7000, nullptr);
//定时器2
SetTimer(hwnd, TIMER_2, 3000, nullptr);
return 0;
[其他代码]
case WM_TIMER:
switch (wParam)
{
case TIMER_1:
MessageBox(hwnd, L"定时器1被触发了", L"", 0);
break;
case TIMER_2:
MessageBox(hwnd, L"定时器2被触发了", L"", 0);
break;
default:
break;
}
return 0;
[其他代码]
case WM_DESTROY:
//关掉定时器1、2
KillTimer(hwnd, TIMER_1);
KillTimer(hwnd, TIMER_2);
PostQuitMessage(0);
return 0;
[其他代码]
2.设置一个回调函数来处理WM_TIMER消息
SetTimer(hwnd,1,1000,TimerProc);
KillTimer(hwnd,1);
例如:
case WM_CREATE:
//定时器1
SetTimer(hwnd, TIMER_1, 7000, TimerProc);
//定时器2
SetTimer(hwnd, TIMER_2, 3000, TimerProc);
return 0;
[其他代码]
case WM_DESTROY:
//关掉定时器1、2
KillTimer(hwnd, TIMER_1);
KillTimer(hwnd, TIMER_2);
PostQuitMessage(0);
return 0;
[其他代码]
.
.
.
//时间过程函数
//这个函数只处理WM_TIMER消息
void CALLBACK TimerProc(
HWND hwnd, //窗口句柄
UINT uMsg, //指定的WM_TIMER消息
UINT idEvent, //定时器ID
DWORD dwTime //定时时间
)
{
switch (idEvent)
{
case TIMER_1:
MessageBox(hwnd, L"定时器1被触发了", L"", 0);
break;
case TIMER_2:
MessageBox(hwnd, L"定时器2被触发了", L"", 0);
break;
default:
break;
}
}
3.把第一个参数设置为NULL,第二个设置为0,返回值为定时器ID
//如果函数返回0表示没有可用的定时器,这个可能性非常低
iTimerID=SetTimer(NULL,0,1000,TimerProc);
//定时器必须这样关掉
KillTimer(NULL,iTimerID);
获取时间:
//获取当前时间
void GetLocalTime(
LPSYSTEMTIME lpSystemTime
);
void GetSystemTime(
LPSYSTEMTIME lpSystemTime
);
//一个是本地时间,一个是协调世界时(UTC)
//系统时间信息结构
typedef struct _SYSTEMTIME {
WORD wYear; //当前年份
WORD wMonth; //当前月份
WORD wDayOfWeek;//当前星期 Sunday=0
WORD wDay; //当前月的第几天
WORD wHour; //当前的时间
WORD wMinute;
WORD wSecond;
WORD wMilliseconds;
} SYSTEMTIME;
例如:
//时间过程函数
//这个函数只处理WM_TIMER消息
void CALLBACK TimerProc(
HWND hwnd, //窗口句柄
UINT uMsg, //指定的WM_TIMER消息
UINT idEvent, //定时器ID
DWORD dwTime //定时时间
)
{
//时间信息结构
SYSTEMTIME st = { 0 };
//获取时间信息
GetLocalTime(&st);
//打印时间信息
MessageBoxPrintf(L"", L"现在是%d-%d-%d-%d-%d-%d-%d-%d", st.wYear,st.wMonth,st.wDay,st.wDayOfWeek,
st.wHour,st.wMinute,st.wSecond,st.wMilliseconds);
}
如图: