MFC多媒体定时器与普通定时器的比较

一、多媒体定时器的使用

多媒体定时器不依赖消息机制,而是有TimeSetEvent()产生一个独立的线程,在一定的中断次数到达后,直接调用预先设置的回调函数进行处理,而不必等待应用程序的消息队列为空,保证的定时器的实时相应,是一种很理想的高精度定时器,可以实现精度为1ms的定时精度。

1.多媒体定时器的使用

首先要包含MMSystem.h头文件,还要添加以下代码
#pragma comment(lib,"winmm.lib")

启动多媒体定时器原型

MMRESULT timeSetEvent( UINT uDelay, UINT uResolution, LPTIMECALLBACK lpTimeProc, WORD dwUser, UINT fuEvent )

参数说明:
uDelay:以毫秒指定时的周期
Uresolution:以毫秒指定延时的精度,数值越小定时器事件分辨率越高。缺省值为1ms。
LpTimeProc:指向一个回调函数,该回调函数包含需要定时执行的代码。
DwUser:存放用户提供的回调数据。
FuEvent:指定定时器事件类型:
TIME_ONESHOT:uDelay毫秒后只产生一次事件。
TIME_PERIODIC :每隔uDelay毫秒周期性地产生事件。

例:
UINT TimerID = timeSetEvent(1,1(LPTIMECALLBACK)MMTimerProc,(DWORD)this,TIME_PERIODIC);

停止多媒体定时器
timeKillEvent(TimerID);

多媒体定时器回调函数

void CALLBACK CMMTimerDlg::MMTimerProc(UINT uID,UINT uMsg,DWORD dwUsers,DWORD dw1,DWORD dw2)
{
    CXXX *pDlg = (CMMTimerDlg*)(dwUsers);
    //添加你的代码
}

此函数一定要声明为静态函数

二.普通定时器

开启普通定时器原型
UINT SetTimer(UINT nIDEvent,UINT nElapse,void ( CALLBACK* lpfnTimer )(HWND, UINT,UINT,DWORD) = NULL )

参数说明:
nIDEvent:非0值标识Timer的id 。
nElapse:以毫秒为单位的定时间隔时间
lpfnTimer 指向定时事件到达时调用的函数的指针,如果为NULL,那么调用WM_TIMER响应函数OnTimer()。

例:
SetTimer(1,200,NULL); //设置并启动一个时间间隔为200ms的定时器。消息响应函数为OnTimer()
SetTimer(2,1000, TimerProc ); //设置并启动一个实间间隔为1s的定时器,该定时器的响应函数为TimerProc。

停止定时器
KillTimer(TimerID); //TimerID为要结束的定时器ID号

普通定时器回调函数

若SetTimer第三个参数为NULL则不需要自己写回调函数,定时器时间到将产生WM_TIMER消息

自己定义回调函数
例:
SetTimer(1,1,(TIMERPROC)WMTimerProc);

void CALLBACK CMMTimerDlg::WMTimerProc(HWND hwnd,UINT uMsg,UINT idEvent,DWORD dwTime)
{
    CMMTimerDlg *pDlg = (CMMTimerDlg*)(AfxGetApp()->m_pMainWnd);
   //添加你的代码
}

三、多媒体定时器与普通定时器比较

MFC多媒体定时器与普通定时器的比较_第1张图片
定时周期1ms

MFC多媒体定时器与普通定时器的比较_第2张图片
定时周期10ms

MFC多媒体定时器与普通定时器的比较_第3张图片
定时周期100ms

MFC多媒体定时器与普通定时器的比较_第4张图片
定时周期1000ms

我们可以看到普通定时器根本无法达到1ms的分辨率,12多秒过去了才产生700多个中断。
当定时周期大于100ms时,普通定时器才处于可用状态
当定时周期大于1秒时,普通定时器与多媒体定时器相差不大
所以当你需要定时的周期小于1秒时,还是建议使用多媒体定时器。定时精度相当高,官方称可以达到1ms的精度。实测基本属实。

你可能感兴趣的:(MFC)