SetTimer 笔记

SetTimer

The SetTimer function creates a timer with the specified time-out value.

UINT_PTR SetTimer(
  HWND hWnd,              // handle to window 窗口句柄
  UINT_PTR nIDEvent,      // timer identifier 标识符
  UINT uElapse,           // time-out value 超时值
  TIMERPROC lpTimerFunc   // timer procedure 回调函数
);

Parameters

hWnd

[in] Handle to the window to be associated with the timer. This window must be owned by the calling thread. If this parameter is NULL, no window is associated with the timer and the nIDEvent parameter is ignored.

与定时器关联的窗口句柄,这个句柄必须为调用线程所有。如果参数为NULL,则没有窗口与这个定时器关联,同时参数nIDEvent将被忽略

nIDEvent

[in] Specifies a nonzero timer identifier. If the hWnd parameter is NULL, this parameter is ignored.

指定一个非零的定时器标识符,如果参数hWndNULL,则该参数被忽略

If the hWnd parameter is not NULL and the window specified by hWnd already has a timer with the value nIDEvent, then the existing timer is replaced by the new timer. When SetTimer replaces a timer, the timer is reset. Therefore, a message will be sent after the current time-out value elapses, but the previously set time-out value is ignored.

如果参数hWnd不为NULL,而且hWnd指定的窗口中存在了nIDEvent指定的定时器,这时已存在的定时器将由新的定时器取代。当SetTimer取代一个定时器的时候,定时器将被复位。因此,直到当前设定的定时值超时后才会有消息发送,先前设定的超时参数被忽略。

uElapse

[in] Specifies the time-out value, in milliseconds.

超时值,(毫秒)

lpTimerFunc

[in] Pointer to the function to be notified when the time-out value elapses. For more information about the function, see TimerProc.

指定的超时参数超时时得到通知的函数指针

If lpTimerFunc is NULL, the system posts a WM_TIMER message to the application queue. The hwnd member of the message's MSG structure contains the value of the hWnd parameter.

如果参数为lpTimerFunc 为NULL,则系统将在应用程序消息队列中投递一个WM_TIMER消息,该消息的MSG结构体中的hwnd成员包含了这里的hWnd参数.

Return Values

If the function succeeds and the hWnd parameter is NULL, the return value is an integer identifying the new timer. An application can pass this value to the KillTimer function to destroy the timer.

如果函数成功,且参数hWnd为NULL,返回值是整数,标识开启的新定时器。应用程序可以将这个数作为参数传给KillTimer,来销毁这个定时器

If the function succeeds and the hWnd parameter is not NULL, then the return value is a nonzero integer. An application can pass the value of the nIDTimer parameter to the KillTimer function to destroy the timer.

如果函数成功,且参数hWnd不为NULL,则返回值是一个非零的整数。应用程序可以将这个数作为参数传该KillTimer函数的nIDTimer,来销毁后这个定时器

If the function fails to create a timer, the return value is zero. To get extended error information, call GetLastError.

Remarks

An application can process WM_TIMER messages by including a WM_TIMER case statement in the window procedure or by specifying a TimerProc callback function when creating the timer. When you specify a TimerProc callback function, the default window procedure calls the callback function when it processes WM_TIMER. Therefore, you need to dispatch messages in the calling thread, even when you use TimerProc instead of processing WM_TIMER.

一个应用程序可以通过在窗口回调函数中处理WM_TIMER 或通过在创建定时器指定TimerProc回调函数。当您指定TimerProc回调函数,默认的窗口过程调用的回调函数处理WM_TIMER消息。因此,你需要在调用线程的调度信息,即使您使用的TimerProc代替处理WM_TIMER消息。

 

The wParam parameter of the WM_TIMER message contains the value of the nIDEvent parameter.

WM_TIMER 消息的wParam参数包含了nIDEvent参数的值

The timer identifier, nIDEvent, is specific to the associated window. Another window can have its own timer which has the same identifier as a timer owned by another window. The timers are distinct.

定时器的标识符nIDEvent是对该定时器所对应窗口指定的。其他窗口可以拥有同样标识的定时器,这是不同的定时器。

 


 


 

 

 

 

定时器采用回调函数时,该回调函数的执行仍然在主线程中。

试验:

.h/

static void CALLBACK EXPORT TimerProc(HWND hWnd,UINT nMsg,UINT nTimerid,DWORD dwTime);

 

.cpp///

 

BOOL CTimerTestDlg::OnInitDialog() { CDialog::OnInitDialog(); …… SetTimer(1122,2000,TimerProc); return TRUE; }   

void CALLBACK EXPORT CTimerTestDlg::TimerProc(HWND hWnd,UINT nMsg,UINT nTimerid,DWORD dwTime) { CTime tmCur = CTime::GetCurrentTime(); TRACE(_T("我是定时器%d,现在是 [%.2d:%.2d:%.2d]/r/n"),nTimerid,tmCur.GetHour(),tmCur.GetMinute(),tmCur.GetSecond()); if(g_unCnt<3) { g_unCnt ++; Sleep(5000); } }   

 

 

TRACE输出

我是定时器1122,现在是 [15:20:55]

我是定时器1122,现在是 [15:21:00]

我是定时器1122,现在是 [15:21:05]

我是定时器1122,现在是 [15:21:10]

我是定时器1122,现在是 [15:21:11]

我是定时器1122,现在是 [15:21:13]

我是定时器1122,现在是 [15:21:15]

我是定时器1122,现在是 [15:21:17]

我是定时器1122,现在是 [15:21:19]

1.    当回调函数中有Sleep时,主进程死掉,显然该回调函数仍然占用主线程的时间片。

2.    同时通过TRACE输出可以发现,主线程拥塞后,多个定时器消息将被整合成一个消息,不会出现多个定时器消息在主线程解除拥塞后爆发执行的情况。

 

 

 

void CALLBACK EXPORT CTimerTestDlg::TimerProc(HWND hWnd,UINT nMsg,UINT nTimerid,DWORD dwTime) { CTimerTestDlg *pDlg = (CTimerTestDlg*)CWnd::FromHandle(hWnd); CTime tmCur = CTime::GetCurrentTime(); TRACE(_T("我是定时器%d,现在是 [%.2d:%.2d:%.2d]/r/n"),nTimerid,tmCur.GetHour(),tmCur.GetMinute(),tmCur.GetSecond()); g_unCnt = (g_unCnt==0)?1:0; pDlg->SetTimer(1122,2000*(g_unCnt+1),TimerProc); }   

 

我是定时器1122,现在是 [15:39:06]

我是定时器1122,现在是 [15:39:10]

我是定时器1122,现在是 [15:39:12]

我是定时器1122,现在是 [15:39:16]

我是定时器1122,现在是 [15:39:18]

我是定时器1122,现在是 [15:39:22]

我是定时器1122,现在是 [15:39:24]

 

可见,当打开已经被打开的定时器时,将使先前设定的定时器复位,并且使用最新设定的

超时参数从新开始计时。

 

 

 

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值