c++ - 运行 NI-IMAQ 和 WINAPI 需要 2 个不同的子系统
问题描述
我正在尝试将 WINAPI 实现为 NI-IMAQ 的功能。但是,NI-IMAQ 要求我在 Visual Studio 中的子系统是控制台,如下所示。
而 WINAPI 要求子系统是 Windows。
有没有办法解决这个问题?
以下是我的代码:
int main()
{
INTERFACE_ID interfaceID;
SESSION_ID sessionID;
unsigned int bitsPerPixel, plotFlag;
if (imgInterfaceOpen("img0", &interfaceID) == IMG_ERR_GOOD) // "img0" is interfacename, opens an interface named img0
{
std::cout << "Interface is open" << std::endl;
if (imgSessionOpen(interfaceID, &sessionID) == IMG_ERR_GOOD)
{
std::cout << "Session is open" << std::endl;
// 30 sept 2021: try GRAB
// 1. imgInterfaceOpen (DONE)
// 2. imgSessionOpen (DONE)
// 3. imgGrabSetup (DONE)
// 4. imgSessionStartAcquisition (DONE)
// 5. imgGrab (DONE)
// 6. User specific functions
// 7. imgSessionStop Acquisition (DONE)
// 8. imgClose (DONE)
//3. imgGrabSetup
imgGrabSetup(sessionID, TRUE); //manually start acquisition with imgSessionStartAcquisition
//4. imgSessionStartAcquisition
imgSessionStartAcquisition(sessionID);
//5. imgGrab (sessionID, buffer address, uint32 waitForNext)
imgGrab(sessionID, NULL, TRUE);
// imgSessionSaveBufferEx to save a buffer of a session to PNG
imgSessionSaveBufferEx(sessionID, NULL, reinterpret_cast<Int8*>(const_cast<char*>("test.png")));
std::cout << "Image saved" << std::endl;
// get attributes to get pixel depth of camera
imgGetAttribute(sessionID, IMG_ATTR_BITSPERPIXEL, &bitsPerPixel); // obtain pixel depth, then store in bitsPerPixel
std::cout << "Get Attribute" << std::endl;
// declare plotFlag according to pixel depth, bitsPerPixel
switch (bitsPerPixel)
{
case 10:
plotFlag = IMGPLOT_MONO_10;
break;
case 12:
plotFlag = IMGPLOT_MONO_12;
break;
case 14:
plotFlag = IMGPLOT_MONO_14;
break;
case 16:
plotFlag = IMGPLOT_MONO_16;
break;
case 24:
case 32:
// assumes that a 24 bits camera is a color camera.
// in this mode, even if the camera is 24 bits the board returns 32 bits values
plotFlag = IMGPLOT_COLOR_RGB32;
break;
default:
plotFlag = IMGPLOT_MONO_8;
break;
}
std::cout << "plotFlag obtained" << std::endl;
//6. functions or display using imgPlot (1. GUIHNDL window, 2. void* buffer, 3. uInt32 leftBufOffset, 4. uInt32 topBufOffset, 5. uInt32 xsize, 6. uInt32 ysize,
// 7. uInt32 xpos, 8. uInt32 ypos, 9. uInt32 flags)
// 1 2 3 4 5 6 7 8 9
imgPlot2(ImaqSmplHwnd, NULL, 0, 0, AcqWinWidth, AcqWinHeight, CanvasLeft, CanvasTop, plotFlag);
std::cout << "imgPlot2 done" << std::endl;
//7. imgSessionStop Acquisition
imgSessionStopAcquisition(sessionID);
std::cout << "Stop acquisition" << std::endl;
imgClose(sessionID, FALSE); // closes the session using the imgClose function
std::cout << "Session is closed" << std::endl;
}
imgClose(interfaceID, FALSE); // closes the interface using the imgClose function
std::cout << "Interface is closed" << std::endl;
}
}
////////////////////////////////////////////////////////
// 2. this is the window event callback function from line 15 , first parameter is window handler
LRESULT CALLBACK WindowProcessMessages(HWND hwnd, UINT msg, WPARAM param, LPARAM lparam);
// this is the main function
int WINAPI WinMain(HINSTANCE currentInstance, HINSTANCE previousInstance, LPSTR cmdLine, INT cmdCount)
{
// 1. Register the window class
const char* CLASS_NAME = "myWin32WindowClass";
WNDCLASS wc{};
wc.hInstance = currentInstance;
wc.lpszClassName = CLASS_NAME;
wc.hCursor = LoadCursor(nullptr, IDC_ARROW);
wc.hbrBackground = (HBRUSH)COLOR_WINDOW;
wc.lpfnWndProc = WindowProcessMessages; // every window requires a programmer defined callback function that is called by the OS when an event happens ie. close window, click inside window
RegisterClass(&wc);
// 3. Create the window
CreateWindow(CLASS_NAME, "Win32 Tutorial",
WS_OVERLAPPEDWINDOW | WS_VISIBLE, // Window style
CW_USEDEFAULT, CW_USEDEFAULT, // Window initial position
800, 600, // Window size
nullptr, nullptr, nullptr, nullptr);
// 4. Lastly, Window loop - all graphical applications need a loop that runs until application is closed
MSG msg{}; // empty window message, while loop runs as long as GetMessage returns TRUE
while (GetMessage(&msg, nullptr, 0, 0))
{
TranslateMessage(&msg);
//return MessageBox(NULL, "hello, world", "caption", 0);
DispatchMessage(&msg);
}
return 0;
}
// 2.
LRESULT CALLBACK WindowProcessMessages(HWND hwnd, UINT msg, WPARAM param, LPARAM lparam)
{
switch (msg) {
case WM_DESTROY: //user pressed cross button at top right corner
PostQuitMessage(0);
return 0;
default:
return DefWindowProc(hwnd, msg, param, lparam);
}
}
有 int main() 和 int WINAPI WinMain(),分别运行正常。
但是 int main() 中的代码只能在 Subsystem 为 Console 时运行,而 int WINAPI WinMain() 中的代码只能在 Subsystem 为 Windows 时运行。有没有办法将 2 整合为 1 或者它们是否相互冲突?
解决方案
只能有一个子系统。由于要显示一个窗口,因此请使用 Windows 子系统。
在 int main() 和 int WINAPI WinMain() 之间,使用 int WINAPI WinMain() 作为主函数,并包含来自 int main() 的函数调用。
推荐阅读
- ios - Flutter 构建 iOS 失败
- json - 使用 NewtonSoft 将 json 字符串转换并解析为键值对
- xml - 带有 & 符号 ( ) 的 xpath 属性引发错误“XPST0003: 没有关闭 ';' 为实体或字符参考找到'
- css - 使用css-grid时Div获得溢出滚动
- sql-server - PowerShell - 将多个查询结果存储在一个变量中
- python - 用xpath确认是否写注释
- c# - Azure Function v1 作为 SOAP 端点
- solr - Solr 7.x 带引号的短语搜索忽略标点符号
- python - LAMBDA 函数可以在进行聚合时从 python 中的另一列获取条件吗?
- unit-testing - 如何在 Junit 5 中模拟 FileWriter