Extract UI state and Win32 window shell

This commit is contained in:
2026-06-16 13:16:19 +02:00
parent cb9d06c6dc
commit 8ea56cbd30
12 changed files with 619 additions and 670 deletions

View File

@@ -12,6 +12,7 @@
#include "platform_windows/windows_lifecycle_shell.h"
#include "platform_windows/windows_splash.h"
#include "platform_windows/windows_stylus_input.h"
#include "platform_windows/windows_window_shell.h"
#include "platform_windows/windows_vr_shell.h"
#include "../resource.h"
@@ -30,24 +31,9 @@ namespace pp::platform::windows {
bool try_lock_async_render_context();
void unlock_async_render_context();
void swap_async_render_context();
RetainedState& retained_state();
}
struct RetainedState
{
HINSTANCE hInst{};
HWND hWnd{};
bool keys[256]{};
std::map<kKey, int> vkey_map;
wchar_t window_title[512]{};
bool sandboxed = false;
pp::platform::windows::VrShellState vr;
};
RetainedState& retained_state()
{
static RetainedState state;
return state;
}
using pp::platform::windows::retained_state;
namespace {
struct RetainedMainTaskQueue final
@@ -571,262 +557,6 @@ int main(int argc, char** argv)
LogRemote::I.stop();
}
LRESULT CALLBACK WndProc(HWND hWnd, UINT msg, WPARAM wp, LPARAM lp)
{
auto& state = retained_state();
static bool leftDown = false;
static DWORD lastTime;
static glm::vec2 lastPoint;
auto extra = GetMessageExtraInfo();
// if ((extra & 0xFFFFFF00) == 0xFF515700)
// LOG("source %s", extra & 0x80 ? "touch" : "pen");
switch (msg)
{
case pp::platform::windows::kUserCloseMessage:
pp::platform::windows::handle_window_close_message(state.vr);
return 0;
case WM_PAINT:
App::I->redraw = true;
break;
case WM_CREATE:
BT_SetTerminate();
break;
case WM_CLOSE:
{
App::I->ui_task_async([] {
if (App::I->request_close())
{
destroy_window();
}
});
return 1;
break;
}
case WM_SIZE:
{
auto w = (float)LOWORD(lp);
auto h = (float)HIWORD(lp);
if (h != 0 && pp::platform::windows::lifecycle_is_running())
{
App::I->ui_task_async([=]
{
App::I->resize(w, h);
App::I->redraw = true;
}, true);
}
break;
}
case WM_ACTIVATE:
{
pp::platform::windows::platform_services().set_cursor_visible(true);
App::I->ui_task_async([&state, wp, lp] {
int active = GET_WM_ACTIVATE_STATE(wp, lp);
WacomTablet::I.set_focus(active);
static BYTE keys[256];
if (GetKeyboardState(keys))
{
bool alt = keys[VK_MENU] & 0x80;
for (auto k : state.vkey_map)
{
// ignore alt + tab
if (alt && k.first == kKey::KeyTab)
continue;
bool down = keys[k.second] & 0x80;
if (App::I->keys[(int)k.first] && !down)
App::I->key_up(k.first);
else if(!App::I->keys[(int)k.first] && down)
App::I->key_down(k.first);
}
}
});
break;
}
// case WM_TOUCH:
// {
// App::I->ui_task_async([=] {
// //LOG("touch");
// });
// break;
// }
case WT_PACKET:
{
pp::platform::windows::note_wintab_packet();
App::I->ui_task_async([=] {
WacomTablet::I.handle_message(hWnd, msg, wp, lp);
});
break;
}
case WM_SYSKEYDOWN:
case WM_KEYDOWN:
if ((lp >> 30 & 1) == 0 && // ignore repeated
!(wp == VK_TAB && App::I->keys[(int)kKey::KeyAlt])) // ignore alt+tab
{
App::I->ui_task_async([wp] {
App::I->key_down(convert_key((int)wp));
});
}
break;
case WM_SYSKEYUP:
case WM_KEYUP:
if (!(wp == VK_TAB && App::I->keys[(int)kKey::KeyAlt])) // ignore alt+tab
{
App::I->ui_task_async([wp] {
App::I->key_up(convert_key((int)wp));
});
}
break;
case WM_CHAR:
{
App::I->ui_task_async([wp]{
App::I->key_char((int)wp);
});
}
break;
case WM_MOUSEMOVE:
{
/*
RECT r;
POINT curpos;
GetWindowRect(hWnd, &r);
glm::vec2 center = { r.left + (r.right - r.left) / 2, r.top + (r.bottom - r.top) / 2 };
GetCursorPos(&curpos);
SetCursorPos(center.x, center.y);
//glm::vec2 cur = { GET_X_LPARAM(lp), GET_Y_LPARAM(lp) };
glm::vec2 sz = { App::I->width, App::I->height };
glm::vec2 diff = { curpos.x - center.x, curpos.y - center.y };
lastPoint = glm::clamp(lastPoint + diff, { 0, 0 }, sz);
*/
lastPoint = { GET_X_LPARAM(lp), GET_Y_LPARAM(lp) };
auto pt = lastPoint;
App::I->ui_task_async([pt, extra, p = WacomTablet::I.get_pressure()]{
kEventSource pointer_source;
if (WacomTablet::I.m_ink_pen || WacomTablet::I.m_ink_touch)
{
pointer_source = WacomTablet::I.m_ink_pen ? kEventSource::Stylus : kEventSource::Touch;
}
else
{
pointer_source = WacomTablet::I.m_stylus ? kEventSource::Stylus : kEventSource::Mouse;
if ((extra & 0xFFFFFF00) == 0xFF515700)
pointer_source = kEventSource::Touch;
}
App::I->mouse_move((float)pt.x, (float)pt.y, p, pointer_source, WacomTablet::I.m_eraser);
});
}
break;
case WM_LBUTTONDOWN:
{
SetCapture(hWnd);
auto pt = lastPoint;
App::I->ui_task_async([pt, extra, hWnd, p = WacomTablet::I.get_pressure()]{
kEventSource pointer_source;
if (WacomTablet::I.m_ink_pen || WacomTablet::I.m_ink_touch)
{
pointer_source = WacomTablet::I.m_ink_pen ? kEventSource::Stylus : kEventSource::Touch;
}
else
{
pointer_source = WacomTablet::I.m_stylus ? kEventSource::Stylus : kEventSource::Mouse;
if ((extra & 0xFFFFFF00) == 0xFF515700)
pointer_source = kEventSource::Touch;
}
App::I->mouse_down(0, (float)pt.x, (float)pt.y, p, pointer_source, WacomTablet::I.m_eraser);
});
}
break;
case WM_LBUTTONUP:
{
ReleaseCapture();
auto pt = lastPoint;
App::I->ui_task_async([pt, extra] {
WacomTablet::I.reset_pressure();
kEventSource pointer_source;
if (WacomTablet::I.m_ink_pen || WacomTablet::I.m_ink_touch)
{
pointer_source = WacomTablet::I.m_ink_pen ? kEventSource::Stylus : kEventSource::Touch;
}
else
{
pointer_source = WacomTablet::I.m_stylus ? kEventSource::Stylus : kEventSource::Mouse;
if ((extra & 0xFFFFFF00) == 0xFF515700)
pointer_source = kEventSource::Touch;
}
App::I->mouse_up(0, (float)pt.x, (float)pt.y, pointer_source, WacomTablet::I.m_eraser);
});
}
break;
case WM_RBUTTONDOWN:
{
SetCapture(hWnd);
auto pt = lastPoint;
App::I->ui_task_async([pt, extra, hWnd] {
kEventSource pointer_source;
if (WacomTablet::I.m_ink_pen || WacomTablet::I.m_ink_touch)
{
pointer_source = WacomTablet::I.m_ink_pen ? kEventSource::Stylus : kEventSource::Touch;
}
else
{
pointer_source = WacomTablet::I.m_stylus ? kEventSource::Stylus : kEventSource::Mouse;
if ((extra & 0xFFFFFF00) == 0xFF515700)
pointer_source = kEventSource::Touch;
}
App::I->mouse_down(1, (float)pt.x, (float)pt.y, 1.f, pointer_source, 0);
});
}
break;
case WM_RBUTTONUP:
{
ReleaseCapture();
auto pt = lastPoint;
App::I->ui_task_async([pt, extra] {
kEventSource pointer_source;
if (WacomTablet::I.m_ink_pen || WacomTablet::I.m_ink_touch)
{
pointer_source = WacomTablet::I.m_ink_pen ? kEventSource::Stylus : kEventSource::Touch;
}
else
{
pointer_source = WacomTablet::I.m_stylus ? kEventSource::Stylus : kEventSource::Mouse;
if ((extra & 0xFFFFFF00) == 0xFF515700)
pointer_source = kEventSource::Touch;
}
App::I->mouse_up(1, (float)pt.x, (float)pt.y, pointer_source, 0);
});
}
break;
case WM_MOUSEWHEEL:
{
POINT pt;
pt.x = GET_X_LPARAM(lp);
pt.y = GET_Y_LPARAM(lp);
ScreenToClient(hWnd, &pt);
{
App::I->ui_task_async([pt, wp] {
App::I->mouse_scroll((float)pt.x, (float)pt.y,
(float)GET_WHEEL_DELTA_WPARAM(wp) / (float)WHEEL_DELTA);
});
}
break;
}
case WM_POINTERUPDATE:
{
pp::platform::windows::handle_pointer_update_message(wp);
break;
}
}
// avoid annoying alt system menu
if (wp == SC_KEYMENU && (lp >> 16) <= 0) return 0;
return DefWindowProc(hWnd, msg, wp, lp);
}
int WINAPI WinMain(HINSTANCE, HINSTANCE, LPSTR, int)
{
int argc = 0;