[英]WinAPI create window in dll
I injected a dll into the game process, and then dll create hook which creates, a new thread to handle the windows event. 我向游戏进程中注入了一个dll,然后dll create hook创建了一个新线程来处理Windows事件。
Thread function: 线程功能:
void CFile::winThread(void *pData)
{
CFile *pThis = reinterpret_cast<CFile*>(pData);
// Common controls init
INITCOMMONCONTROLSEX iCC;
iCC.dwSize = sizeof(INITCOMMONCONTROLSEX);
iCC.dwICC = ICC_BAR_CLASSES;
InitCommonControlsEx(&iCC);
pThis->m_pConnect = new WinConnect(300, 180);
pThis->m_pConnect->setText("Connecting");
pThis->m_pConnect->show();
MSG message;
while (GetMessage(&message, 0, 0, 0))
{
TranslateMessage(&message);
DispatchMessage(&message);
}
tthread::mutex _mutex;
_mutex.lock();
pThis->m_bIsFinished = true;
_mutex.unlock();
}
WinConnect.cpp WinConnect.cpp
WinConnect::WinConnect(int width, int height)
{
if (registerWin())
{
int screenWidth = GetSystemMetrics(SM_CXSCREEN);
int screenHeight = GetSystemMetrics(SM_CYSCREEN);
int x = (screenWidth / 2) - (width / 2);
int y = (screenHeight / 2) - (height / 2);
m_hWin = CreateWindowExA(WS_EX_CLIENTEDGE, winNameConnect, "Test Window",
WS_POPUP | WS_BORDER | WS_CAPTION,
x, y + 200, width, height, NULL, NULL, GetModuleHandle(NULL), NULL);
printf("GetLastError %d\n", GetLastError());
if (m_hWin)
{
RECT size;
GetClientRect(m_hWin, &size);
int winH = size.bottom - size.top;
int winW = size.right - size.left;
int buttonW = winW / 2;
m_hLInfo = CreateWindowEx(0, "STATIC", "",
WS_VISIBLE | WS_CHILD | SS_CENTER | SS_CENTERIMAGE,
7, 7, winW - 14, winH - 41, m_hWin, NULL, GetModuleHandle(NULL), NULL);
printf("GetLastError %d\n", GetLastError());
// 9 pix odstep height
m_hBCancel = CreateWindowEx(0, "BUTTON", "Cancel",
WS_VISIBLE | WS_CHILD | SS_CENTER,
buttonW / 2, winH - 30, buttonW, 25, m_hWin, NULL, GetModuleHandle(NULL), NULL);
printf("GetLastError %d\n", GetLastError());
}
}
}
bool WinConnect::registerWin()
{
WNDCLASSEX winClass;
winClass.hInstance = GetModuleHandle(NULL);
winClass.lpszClassName = winNameConnect;
winClass.lpfnWndProc = wndProc;
winClass.style = CS_DBLCLKS;
winClass.cbSize = sizeof(WNDCLASSEX);
winClass.hIcon = LoadIcon(NULL, IDI_APPLICATION);
winClass.hIconSm = LoadIcon(NULL, IDI_APPLICATION);
winClass.hCursor = LoadCursor(NULL, IDC_ARROW);
winClass.lpszMenuName = NULL;
winClass.cbClsExtra = 0;
winClass.cbWndExtra = 0;
winClass.hbrBackground = (HBRUSH)COLOR_BACKGROUND;
if (!RegisterClassEx(&winClass))
return false;
return true;
}
The output of GetLastError is: GetLastError的输出是:
GetLastError 0
GetLastError 0
GetLastError 127
GetLastError 127
GetLastError 127
GetLastError 127
I can't figure out why this label and button are not created. 我不知道为什么不创建此标签和按钮。 Window always is created, witchout any problem.
窗口总是被创建,避免任何问题。 Any help?
有什么帮助吗?
Firstly, as stated in the comments, GetLastError
's result is meaningless unless the previous function actually failed. 首先,如注释中所述,除非先前的函数实际失败,否则
GetLastError
的结果是没有意义的。 So you would have to check for instance whether m_hLInfo == NULL
first (which I guess it is, though). 因此,您必须首先检查
m_hLInfo == NULL
是否为m_hLInfo == NULL
(不过我想是的)。
About the actual problem: It looks to me like your code is using the Unicode-version of the Windows API but feeding it ANSI strings. 关于实际问题:在我看来,您的代码正在使用Windows API的Unicode版本,但将其提供给ANSI字符串。
The reason why the window is created correctly is that you explicitely call CreateWindowExA
(notice the A
) which is the ANSI-version of the function. 正确创建窗口的原因是,您明确调用了函数的ANSI版本的
CreateWindowExA
(注意A
)。 For the button and the label you call CreateWindowEx
which your header files have #define
'd as CreateWindowExW
, the Unicode-version. 对于按钮和标签,您调用
CreateWindowEx
,其头文件已# #define
为CreateWindowExW
,即Unicode版本。 But your class names ( "STATIC"
and "BUTTON"
) are not Unicode, though! 但是,您的类名(
"STATIC"
和"BUTTON"
)却不是Unicode! (So Windows tries to create windows with mojibake classnames, which will of course fail horribly.) (因此Windows尝试使用mojibake类名创建窗口,这当然会严重失败。)
So you could either change CreateWindowEx
to CreateWindowExA
everywhere, or - better - use proper Unicode strings everywhere: Remove the A
from CreateWindowExA
and prepend all strings you feed WinAPI function with L
, eg L"BUTTON"
. 因此,您可以在任何地方都将
CreateWindowEx
更改为CreateWindowExA
,或者-更好地-在各处使用正确的Unicode字符串:从CreateWindowExA
删除A
,并在所有使用L
提供给WinAPI函数的字符串之前加上L
,例如L"BUTTON"
。 (Or, if you are not sure that you will always be in a Unicode compiler environment, you can use the _T
macro, eg _T("BUTTON")
.) (或者,如果不确定您将始终处于Unicode编译器环境中,则可以使用
_T
宏,例如_T("BUTTON")
。)
Further reading: 进一步阅读:
Wikibooks article Wikibooks文章
MSDN article MSDN文章
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.