如何将线程函数的地址作为回调传递给winapi? [英] How to pass the address of a thread function as a callback to winapi?
问题描述
我有一个简单的线程,在执行过程中,我尝试使用该线程中定义的函数之一的地址调用EnumWindows(). 因此,我正在尝试执行以下操作:EnumWindows(@cbEnumWindowsClickOK,0);其中cbEnumWindowsClickOK是在线程类内部定义的EnumWindowProc,如下所示:
I have a simple thread and inside the execute I try to call EnumWindows() with the address of one of the functions defined in the thread. So I'm trying to do this: EnumWindows(@cbEnumWindowsClickOK, 0); where cbEnumWindowsClickOK is an EnumWindowProc defined inside the thread class, like so:
TAutoClickOKThread = class(TThread)
private
fExitEvent : THandle;
function cbEnumWindowsClickOK(Wnd: HWND; Info: Pointer): BOOL;
public
constructor Create(ExitEvent : Thandle);
procedure Execute(); override;
end;
尝试此操作时,我不断收到错误:需要变量",暗示它没有将@cbEnumWindowsClickOK解释为地址.如果我将函数移到全局范围(从线程中移出),它将起作用.
When I try this I keep getting "Error: Variable required", hinting that it doesn't interpret @cbEnumWindowsClickOK as an address. If I move the function to a global scope (removing it from the thread) it does work.
关于如何解决此问题的任何想法?
Any thoughts on how I can fix this?
推荐答案
您必须传递EnumWindows
一个普通的旧函数,即未绑定到实例的函数.您必须单独传递实例.像这样:
You have to pass EnumWindows
a plain old function, i.e. one that is not bound to an instance. You must pass the instance in separately. Like this:
function EnumFunc(hwnd: HWND; lParam: LPARAM): BOOL; stdcall;
begin
Result := TAutoClickOKThread(lParam).cbEnumWindowsClickOK(hwnd);
//note that there is now no need for the Info parameter
end;
...
procedure TAutoClickOKThread.Execute;
begin
...
EnumWindows(EnumFunc, LPARAM(Self));
...
end;
必须这样做的原因是实例方法与EnumWindows
所需的签名不匹配.实例方法有一个额外的隐式参数,其中包含实例引用,即Self
.这样便可以引用实例成员.但是EnumFunc
的签名不能满足此要求.
The reason it must be done this way is that an instance method does not match the required signature for EnumWindows
. An instance method has an extra, implicit, parameter containing the instance reference, i.e. Self
. This is how you are able to refer to instance members. But the signature for EnumFunc
does not cater for this.
这篇关于如何将线程函数的地址作为回调传递给winapi?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!