c++ - 使用 C++ 类方法作为函数回调

标签 c++ function methods callback std

我使用的是相机 API,每次有新图像时都会调用回调函数。回调函数传递为:

BOOL WINAPI StTrg_SetTransferEndCallback(HANDLE hCamera, funcTransferEndCallback func, PVOID pvContext);

funcTransferEndCallback 是:

typedef void (WINAPI *funcTransferEndCallback)(HANDLE hCamera, DWORD dwFrameNo, DWORD dwWidth, DWORD dwHeight, WORD wColorArray, PBYTE pbyteRaw, PVOID pvContext);

我不想创建回调函数,而是实际使用类中的方法。我在类的构造函数中调用此 StTrg_SetTransferEndCallback(),因此我可以初始化相机并传递类的方法来捕获每个新帧并进行处理。

我的方法在我的类 .h 中定义为:

public class Camera
{
public:
.....
void TakePicture(string pictureFileName);
void StartRecording(string videoFileName);
void StopRecording(void);
 .....
private:
volatile bool takePictureFlag;
volatile bool startRecordingFlag;
volatile bool stoptRecordingFlag;
void __stdcall TransferEndCallback(HANDLE hCamera, DWORD dwFrameNo, DWORD dwWidth, DWORD dwHeight, WORD wColorArray, PBYTE pbyteRaw, PVOID pvContext);
};

如果我尝试这样做:

StTrg_SetTransferEndCallback(cameraHandle, TransferEndCallback, NULL);

或者这个:

StTrg_SetTransferEndCallback(cameraHandle, this->TransferEndCallback, NULL)

Visual Studio 2013 说:

error C3867: 'MyNamespace::MyClass::TransferEndCallback': function call missing argument list; use '&MyNamespace::MyClass::TransferEndCallback' to create a pointer to member

所以我按照建议使用它:

StTrg_SetTransferEndCallback(cameraHandle, &MyNamespace::MyClass::TransferEndCallback, NULL)

我收到了这个错误信息:

error C2664: 'BOOL StTrg_SetTransferEndCallback(HANDLE,funcTransferEndCallback,PVOID)' : cannot convert argument 2 from 'void (__stdcall MyNamespace::MyClass::* )(HANDLE,DWORD,DWORD,DWORD,WORD,PBYTE,PVOID)' to 'funcTransferEndCallback' There is no context in which this conversion is possible

那么,是否可以将成员方法作为函数传递呢?这是 std::bind 的情况吗?

最佳答案

通常的模式是将实例指针this传递给PVOID pvContext参数,然后在回调中使用它来调用成员函数。

public class Camera
{
// ...
void ThisTransferEndCallback(HANDLE hCamera, DWORD dwFrameNo, DWORD dwWidth, DWORD dwHeight, WORD wColorArray, PBYTE pbyteRaw);
static void __stdcall TransferEndCallback(HANDLE hCamera, DWORD dwFrameNo, DWORD dwWidth, DWORD dwHeight, WORD wColorArray, PBYTE pbyteRaw, PVOID pvContext);
};

设置回调为

StTrg_SetTransferEndCallback(cameraHandle, TransferEndCallback, this);

然后写静态回调派发给成员函数

void __stdcall Camera::TransferEndCallback(HANDLE hCamera, DWORD dwFrameNo, DWORD dwWidth, DWORD dwHeight, WORD wColorArray, PBYTE pbyteRaw, PVOID pvContext)
{
    ((Camera *)pvContext)->ThisTransferEndCallback(hCamera, dwFrameNo, dwWidth, dwHeight, wColorArray, pbyteRaw);
}

以上不包括错误检查等

关于c++ - 使用 C++ 类方法作为函数回调,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/34094496/

相关文章:

python - 如何编写一个将列表添加到字典的函数?

c# - 对 C# 中的计算器操作感到困惑

可以为 NULL 的 C++ 字符串

c++ - 如何将连接的定义转换为 RC 文件中的字符串?

c++ - 为什么这个函数不会超过值 2^31?

.net - Powershell:调用 .NET 函数总是需要括号吗?

python - 以运算符作为参数的函数

c++ - const 在一个方法的末尾给出错误

objective-c - 如何从 Objective-C 调用使用 class_getInstanceMethod 保存的方法?

c++ - 数字和字段宽度的格式化输出,C++ 标准在哪里说的?