CreateWaitableTimer( lpTimerAttributes: PSecurityAttributes; bManualReset: BOOL; lpTimerName: PWideChar ): THandle; ; SetWaitableTimer( hTimer: THandle; lpDueTime: TLargeInteger; lPeriod: Longint; pfnCompletionRoutine: TFNTimerAPCRoutine; lpArgToCompletionRoutine: Pointer; fResume: BOOL ): BOOL; ;
WaitableTimer 对象较复杂, 其基本的理念是让等候的线程在指定的时间运行.
像其他同类对象一样, 先要建立(CreateWaitableTimer), 建立函数的第二个参数决定是调度一个线程还是所有等候的线程; 这一点和信号对象(Semaphore) 有些类似, 不过 Semaphore 可以指定可驱动线程的具体数目.
和其他同类对象不同的是: 在 CreateWaitableTimer 以后, WaitableTimer 对象并没有马上开始工作;
再调用 SetWaitableTimer 函数后才能让它发挥作用. 这又有点像 Event 对象.
SetWaitableTimer 函数比较麻烦, 得慢慢来, 譬如这样使用:
hWaitableTimer: THandle; TForm1.Button1Click(Sender: TObject); DueTime: Int64; hWaitableTimer := CreateWaitableTimer(, True, ); DueTime := ; SetWaitableTimer(hWaitableTimer, DueTime, , , , False ); ;
第一个例子我们将尽量简单的使用它(但这样体现不出它的优势):
CreateWaitableTimer 时我们就决定让它可控制多个线程;
SetWaitableTimer 时先让它立即参与控制, 只执行一次, 也不使用回调函数.
本例效果图:
代码文件:
Unit1; Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms, Dialogs, StdCtrls; TForm1 = (TForm) Button1: TButton; Button1Click(Sender: TObject); FormDestroy(Sender: TObject); ; Form1: TForm1; f: Integer; hWaitableTimer: THandle; MyThreadFun(p: Pointer): DWORD; ; i,y: Integer; Inc(f); y := * f; WaitForSingleObject(hWaitableTimer, INFINITE) = WAIT_OBJECT_0 i := Form1.Canvas.Lock; Form1.Canvas.TextOut(, y, IntToStr(i)); Form1.Canvas.Unlock; Sleep(); ; ; Result := ; ; TForm1.Button1Click(Sender: TObject); ThreadID: DWORD; DueTime: Int64; hWaitableTimer := CreateWaitableTimer(, True, ); DueTime := ; SetWaitableTimer(hWaitableTimer, DueTime, , , , False); Repaint; f := ; CreateThread(, , @MyThreadFun, , , ThreadID); CreateThread(, , @MyThreadFun, , , ThreadID); CreateThread(, , @MyThreadFun, , , ThreadID); ; TForm1.FormDestroy(Sender: TObject); CloseHandle(hWaitableTimer); ; .
窗体文件:
Form1: TForm1 Left = Top = Caption = ClientHeight = ClientWidth = Color = clBtnFace Font.Charset = DEFAULT_CHARSET Font.Color = clWindowText Font.Height = - Font.Name = Font.Style = [] OldCreateOrder = False OnDestroy = FormDestroy PixelsPerInch = TextHeight = Button1: TButton Left = Top = Width = Height = Caption = TabOrder = OnClick = Button1Click
下面是一个每隔半秒钟(500ms)执行一次的例子(窗体文件同上):
本例效果图:
代码文件:
Unit1; Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms, Dialogs, StdCtrls; TForm1 = (TForm) Button1: TButton; Button1Click(Sender: TObject); FormDestroy(Sender: TObject); ; Form1: TForm1; f: Integer; hWaitableTimer: THandle; MyThreadFun(p: Pointer): DWORD; ; i,y: Integer; Inc(f); y := * f; i := WaitForSingleObject(hWaitableTimer, INFINITE) = WAIT_OBJECT_0 Form1.Canvas.Lock; Form1.Canvas.TextOut(, y, IntToStr(i)); Form1.Canvas.Unlock; ; ; Result := ; ; TForm1.Button1Click(Sender: TObject); ThreadID: DWORD; DueTime: Int64; hWaitableTimer := CreateWaitableTimer(, False, ); DueTime := ; SetWaitableTimer(hWaitableTimer, DueTime, , , , False); Repaint; f := ; CreateThread(, , @MyThreadFun, , , ThreadID); CreateThread(, , @MyThreadFun, , , ThreadID); CreateThread(, , @MyThreadFun, , , ThreadID); ; TForm1.FormDestroy(Sender: TObject); CloseHandle(hWaitableTimer); ; .
转载于:https://blog.51cto.com/rosehacker/450123