Bind Win32 tablet state in runtime shell

This commit is contained in:
2026-06-17 08:52:02 +02:00
parent 3930e70817
commit e9723276be
6 changed files with 107 additions and 80 deletions

View File

@@ -20,6 +20,7 @@ namespace {
struct RetainedWindowsRuntimeState final {
App* app = nullptr;
AppRuntime* runtime = nullptr;
WacomTablet* tablet = nullptr;
};
[[nodiscard]] RetainedWindowsRuntimeState& retained_runtime_state()
@@ -56,10 +57,12 @@ void install_debug_gl_callbacks()
void initialize_wintab(HWND hWnd, bool sandboxed)
{
auto* tablet = bound_wacom_tablet();
assert(tablet);
if (!sandboxed)
{
LOG("init WinTab");
WacomTablet::I.init(hWnd);
tablet->init(hWnd);
}
else
{
@@ -110,7 +113,8 @@ void run_main_message_loop()
void shutdown_main_window_runtime(const MainWindowStartupState& startup, HINSTANCE hInst)
{
WacomTablet::I.terminate();
if (auto* tablet = retained_runtime_state().tablet)
tablet->terminate();
UnregisterClass(startup.window_class.lpszClassName, hInst);
LogRemote::I.stop();
}
@@ -137,6 +141,16 @@ AppRuntime* bound_runtime() noexcept
return retained_runtime_state().runtime;
}
void bind_wacom_tablet(WacomTablet* tablet) noexcept
{
retained_runtime_state().tablet = tablet;
}
WacomTablet* bound_wacom_tablet() noexcept
{
return retained_runtime_state().tablet;
}
int run_main_application(int argc, char** argv)
{
auto& state = retained_state();
@@ -146,6 +160,7 @@ int run_main_application(int argc, char** argv)
App::I = app;
bind_app(app);
bind_runtime(&app->runtime());
bind_wacom_tablet(&WacomTablet::I);
app->set_platform_services(&pp::platform::windows::platform_services());
app->initLog();
@@ -176,10 +191,12 @@ int run_main_application(int argc, char** argv)
case pp::platform::windows::MainStartupResult::GladLoadFailure:
bind_app(nullptr);
bind_runtime(nullptr);
bind_wacom_tablet(nullptr);
return 0;
case pp::platform::windows::MainStartupResult::MissingCoreContextSupport:
bind_app(nullptr);
bind_runtime(nullptr);
bind_wacom_tablet(nullptr);
return -1;
}
@@ -195,6 +212,7 @@ int run_main_application(int argc, char** argv)
app->cmd_convert(argv[2], argv[3]);
bind_app(nullptr);
bind_runtime(nullptr);
bind_wacom_tablet(nullptr);
return 0;
case const_hash("-vrmode"):
start_in_vr = true;
@@ -205,6 +223,7 @@ int run_main_application(int argc, char** argv)
}
pp::platform::windows::run_main_window_runtime(startup, start_in_vr, splash);
bind_wacom_tablet(nullptr);
return 0;
}

View File

@@ -5,6 +5,7 @@
class App;
class AppRuntime;
class WacomTablet;
namespace pp::platform::windows {
@@ -14,5 +15,7 @@ void bind_app(App* app) noexcept;
[[nodiscard]] App* bound_app() noexcept;
void bind_runtime(AppRuntime* runtime) noexcept;
[[nodiscard]] AppRuntime* bound_runtime() noexcept;
void bind_wacom_tablet(WacomTablet* tablet) noexcept;
[[nodiscard]] WacomTablet* bound_wacom_tablet() noexcept;
}

View File

@@ -8,6 +8,7 @@
#include "wacom.h"
namespace pp::platform::windows {
namespace {
struct StylusInputState final
@@ -28,6 +29,13 @@ StylusInputState& stylus_input_state()
return state;
}
[[nodiscard]] WacomTablet& active_wacom_tablet()
{
auto* tablet = bound_wacom_tablet();
assert(tablet);
return *tablet;
}
}
void initialize_stylus_input()
@@ -55,24 +63,25 @@ void update_stylus_state(float dt)
{
auto& state = stylus_input_state();
auto* app = bound_app();
auto& tablet = active_wacom_tablet();
state.timer_stylus += dt;
state.timer_ink_touch += dt;
state.timer_ink_pen += dt;
if (state.timer_stylus > 0.1f && (WacomTablet::I.m_stylus || WacomTablet::I.m_eraser))
if (state.timer_stylus > 0.1f && (tablet.m_stylus || tablet.m_eraser))
{
WacomTablet::I.m_stylus = false;
WacomTablet::I.m_eraser = false;
tablet.m_stylus = false;
tablet.m_eraser = false;
app->redraw = true;
}
if (state.timer_ink_pen > 0.1f && WacomTablet::I.m_ink_pen)
if (state.timer_ink_pen > 0.1f && tablet.m_ink_pen)
{
WacomTablet::I.m_ink_pen = false;
tablet.m_ink_pen = false;
app->redraw = true;
}
if (state.timer_ink_touch > 0.1f && WacomTablet::I.m_ink_touch)
if (state.timer_ink_touch > 0.1f && tablet.m_ink_touch)
{
WacomTablet::I.m_ink_touch = false;
tablet.m_ink_touch = false;
app->redraw = true;
}
}
@@ -87,6 +96,7 @@ void note_wintab_packet()
void handle_pointer_update_message(WPARAM wp)
{
auto& state = stylus_input_state();
auto& tablet = active_wacom_tablet();
if (!state.get_pointer_info)
return;
@@ -109,8 +119,8 @@ void handle_pointer_update_message(WPARAM wp)
return;
state.timer_ink_touch = 0.0f;
WacomTablet::I.m_ink_touch = true;
WacomTablet::I.m_pen_pres = 1.0f;
tablet.m_ink_touch = true;
tablet.m_pen_pres = 1.0f;
return;
case PT_PEN:
@@ -118,8 +128,8 @@ void handle_pointer_update_message(WPARAM wp)
return;
state.timer_ink_pen = 0.0f;
WacomTablet::I.m_ink_pen = true;
WacomTablet::I.m_pen_pres = static_cast<float>(pen_info.pressure) / 1024.0f;
tablet.m_ink_pen = true;
tablet.m_pen_pres = static_cast<float>(pen_info.pressure) / 1024.0f;
bound_app()->set_stylus();
return;

View File

@@ -14,6 +14,28 @@ void destroy_window();
namespace pp::platform::windows {
namespace {
[[nodiscard]] WacomTablet& active_wacom_tablet()
{
auto* tablet = bound_wacom_tablet();
assert(tablet);
return *tablet;
}
[[nodiscard]] kEventSource resolve_pointer_source(const WacomTablet& tablet, LPARAM extra)
{
if (tablet.m_ink_pen || tablet.m_ink_touch)
return tablet.m_ink_pen ? kEventSource::Stylus : kEventSource::Touch;
auto pointer_source = tablet.m_stylus ? kEventSource::Stylus : kEventSource::Mouse;
if ((extra & 0xFFFFFF00) == 0xFF515700)
pointer_source = kEventSource::Touch;
return pointer_source;
}
}
void initialize_retained_input_state()
{
auto& state = retained_state();
@@ -94,7 +116,7 @@ LRESULT CALLBACK main_window_proc(HWND hWnd, UINT msg, WPARAM wp, LPARAM lp)
platform_services().set_cursor_visible(true);
app->ui_task_async([app, &state, wp, lp] {
int active = GET_WM_ACTIVATE_STATE(wp, lp);
WacomTablet::I.set_focus(active);
active_wacom_tablet().set_focus(active);
static BYTE keys[256];
if (GetKeyboardState(keys))
{
@@ -117,7 +139,7 @@ LRESULT CALLBACK main_window_proc(HWND hWnd, UINT msg, WPARAM wp, LPARAM lp)
{
note_wintab_packet();
app->ui_task_async([=] {
WacomTablet::I.handle_message(hWnd, msg, wp, lp);
active_wacom_tablet().handle_message(hWnd, msg, wp, lp);
});
break;
}
@@ -149,19 +171,11 @@ LRESULT CALLBACK main_window_proc(HWND hWnd, UINT msg, WPARAM wp, LPARAM lp)
lastPoint = { GET_X_LPARAM(lp), GET_Y_LPARAM(lp) };
{
auto pt = lastPoint;
app->ui_task_async([app, 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->mouse_move((float)pt.x, (float)pt.y, p, pointer_source, WacomTablet::I.m_eraser);
auto& tablet = active_wacom_tablet();
app->ui_task_async([app, pt, extra, p = tablet.get_pressure()] {
auto& ui_tablet = active_wacom_tablet();
app->mouse_move((float)pt.x, (float)pt.y, p,
resolve_pointer_source(ui_tablet, extra), ui_tablet.m_eraser);
});
}
break;
@@ -169,19 +183,11 @@ LRESULT CALLBACK main_window_proc(HWND hWnd, UINT msg, WPARAM wp, LPARAM lp)
{
SetCapture(hWnd);
auto pt = lastPoint;
app->ui_task_async([app, 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->mouse_down(0, (float)pt.x, (float)pt.y, p, pointer_source, WacomTablet::I.m_eraser);
auto& tablet = active_wacom_tablet();
app->ui_task_async([app, pt, extra, p = tablet.get_pressure()] {
auto& ui_tablet = active_wacom_tablet();
app->mouse_down(0, (float)pt.x, (float)pt.y, p,
resolve_pointer_source(ui_tablet, extra), ui_tablet.m_eraser);
});
}
break;
@@ -190,19 +196,10 @@ LRESULT CALLBACK main_window_proc(HWND hWnd, UINT msg, WPARAM wp, LPARAM lp)
ReleaseCapture();
auto pt = lastPoint;
app->ui_task_async([app, 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->mouse_up(0, (float)pt.x, (float)pt.y, pointer_source, WacomTablet::I.m_eraser);
auto& tablet = active_wacom_tablet();
tablet.reset_pressure();
app->mouse_up(0, (float)pt.x, (float)pt.y,
resolve_pointer_source(tablet, extra), tablet.m_eraser);
});
}
break;
@@ -211,18 +208,8 @@ LRESULT CALLBACK main_window_proc(HWND hWnd, UINT msg, WPARAM wp, LPARAM lp)
SetCapture(hWnd);
auto pt = lastPoint;
app->ui_task_async([app, 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->mouse_down(1, (float)pt.x, (float)pt.y, 1.f, pointer_source, 0);
const auto& tablet = active_wacom_tablet();
app->mouse_down(1, (float)pt.x, (float)pt.y, 1.f, resolve_pointer_source(tablet, extra), 0);
});
}
break;
@@ -231,18 +218,8 @@ LRESULT CALLBACK main_window_proc(HWND hWnd, UINT msg, WPARAM wp, LPARAM lp)
ReleaseCapture();
auto pt = lastPoint;
app->ui_task_async([app, 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->mouse_up(1, (float)pt.x, (float)pt.y, pointer_source, 0);
const auto& tablet = active_wacom_tablet();
app->mouse_up(1, (float)pt.x, (float)pt.y, resolve_pointer_source(tablet, extra), 0);
});
}
break;