У меня проблемы с проектом WINAPI. Есть две проблемы, когда я запускаю окно с приведенным ниже кодом, параметр высоты ведет себя странно. Кажется, он закрывается на 1092, 18 пикселей ниже, где мне это нужно на моем компьютере. Вторая проблема заключается в том, что в окне нет краев или верхней панели меню, пока я не использую комбинацию клавиш Windows + Up/Down, чтобы минимизировать и максимизировать ее, тогда она ведет себя нормально. Я использую приведенный ниже код для инициализации окна (единственный код, который выполняется до этого, инициализирует options.pxXRes и другие переменные, используемые ниже):
//Set up the window class
WNDCLASSEX wndClass;
wndClass.cbSize = sizeof(WNDCLASSEX);
wndClass.style = CS_OWNDC | CS_HREDRAW | CS_VREDRAW;
wndClass.lpfnWndProc = &WndHandleInput;
wndClass.cbClsExtra = 0;
wndClass.cbWndExtra = 0;
wndClass.hInstance = GetModuleHandle(nullptr);
wndClass.hIcon = nullptr;
wndClass.hCursor = LoadCursor(nullptr, IDC_ARROW);
wndClass.hbrBackground = (HBRUSH)(COLOR_BACKGROUND + 1);
wndClass.lpszMenuName = nullptr;
wndClass.lpszClassName = "ToastCatClass";
wndClass.hIconSm = nullptr;
RegisterClassEx(&wndClass);
RECT wndRect;
if (options.fullscreen) {
wndRect.left = 0;
wndRect.right = options.pxXRes;
wndRect.top = 0;
wndRect.bottom = options.pxYRes;
AdjustWindowRect(&wndRect, WS_OVERLAPPEDWINDOW, false);
} else {
wndRect.left = (GetPXXRes() - options.pxXRes) / 2;
wndRect.right = options.pxXRes;
wndRect.top = (GetPXYRes() - options.pxYRes) / 2;
wndRect.bottom = options.pxYRes;
AdjustWindowRect(&wndRect, WS_OVERLAPPEDWINDOW, false);
}
hWnd = CreateWindowEx(
0,
wndClass.lpszClassName,
"ToastCat",
WS_OVERLAPPEDWINDOW,
wndRect.left,
wndRect.top,
wndRect.right - wndRect.left,
wndRect.bottom - wndRect.top,
nullptr,
nullptr,
wndClass.hInstance,
nullptr
);
assert(hWnd != nullptr, "Failure to launch window.");
ShowWindow(hWnd, SW_SHOWDEFAULT);
UpdateWindow(hWnd);
Процедура Window выглядит следующим образом:
LRESULT __stdcall WndHandleInput(HWND hWndParam, UINT msg, WPARAM wParam, LPARAM lParam) {
switch (msg) {
case WM_NCCREATE:
return true;
case WM_KEYDOWN:
switch (wParam) {
//TODO: Update controls
}
break;
case WM_KEYUP:
switch (wParam) {
//TODO: Update controls
}
break;
case WM_CLOSE:
case WM_QUIT:
Cleanup();
break;
default:
return DefWindowProc(hWnd, msg, wParam, lParam);
}
return 0;
}
Windows имеет два разных прямоугольника:
AdjustWindowRect
вы конвертируете прямоугольник клиента в прямоугольник окна. Поэтому границы и меню не могут быть видны, если вы настраиваете прямоугольник клиента размером с весь экран, преобразовывая его в прямоугольник окна и создавая окно с таким размером. Если вы посмотрите на wndRect
после вызова функции AdjustWindowRect(..)
с помощью отладчика, вы увидите, что top
и left
отрицательные.
То, что высота окна отключена на некоторые пиксели, - это поведение окон по умолчанию. Windows по умолчанию не позволяет окнам иметь высоту, большую, чем высота экрана, потому что это приведет к перемещению субтитров из области, к которой может добраться мышь. Чтобы изменить это, вам необходимо обработать сообщение WM_GETMINMAXINFO
:
case WM_GETMINMAXINFO:
DefWindowProc(hWnd, msg, wParam, lParam);
MINMAXINFO *pmmi = (MINMAXINFO*)lParam;
pmmi->ptMaxTrackSize.x *= 2; // just make it bigger...
pmmi->ptMaxTrackSize.y *= 2; //
return 0;
Если вы просто хотите запустить свое окно либо максимизировано (со всеми видимыми элементами управления и границей), либо в каком-либо другом определенном месте, выполните следующие действия: Создайте свое окно обычно с помощью wndRect
инициализированного внутри else-части if (options.fullscreen)
и измените вызов ShowWindow(..)
следующим образом:
if (options.fullscreen)
{
ShowWindow(hWnd, SW_MAXIMIZE);
}
else
{
ShowWindow(hWnd, SW_SHOWDEFAULT);
}
UpdateWindow(hWnd);
CS_OWNDC
? 2) Ваши вызовыassert()
не будут работать;assert()
принимает один параметр, так что,
становится (в сравнении) неясной функция C называется выражение запятой, которая отбрасывает левую сторону и возвращает правую сторону, что в вашем случае является строковым, что ненулевой указатель, что всегда верно.WM_NCCREATE
доDefWindowProc()
вместо того, чтобы обрабатывать его самостоятельно?