Split the keyboard onto its own translucent OpenXR quad
build / build (push) Successful in 1m52s

Expand the on-screen keyboard to a full US layout (letters, digits,
punctuation, Shift layer, Tab, arrows, F1-F12, one-shot Ctrl/Alt
modifiers), make it a persistent, movable, closeable panel via a
title-bar drag handle, and lower its opacity.

Previously the keyboard was just a second panel swapped into the same
quad as the menu launcher, which made the launcher translucent too and
made the keyboard and menu mutually exclusive. Extract the shared
swapchain/JNI/touch-dispatch plumbing into two generic, reusable
modules - xr_swapchain.c (swapchain + per-image FBO setup) and
xr_overlay.c (an off-screen Android View rendered into its own OpenXR
quad, hit-tested via a laser pointer) - and make the menu launcher and
keyboard two independent XrOverlay instances instead of one. The
controller's menu button now only opens/closes the launcher; the
launcher's "Keyboard" button only opens the keyboard - so the keyboard
can stay up while picking something from the menu, and only the
keyboard's own Close button hides it.

xr_menu.c/.h are gone, fully absorbed into xr_overlay.c. On the Java
side, OverlayPanel.java carries the shared off-screen-render/touch/
cursor plumbing that MenuOverlay and the new KeyboardOverlay both
subclass.
This commit is contained in:
ml
2026-08-14 06:43:44 +02:00
parent 2d8fb49bf5
commit 3be310ade6
16 changed files with 1897 additions and 1102 deletions
+25 -9
View File
@@ -9,6 +9,8 @@
#include <stdbool.h>
#include "xr_overlay.h"
#ifdef __cplusplus
extern "C" {
#endif
@@ -17,13 +19,25 @@ extern "C" {
// current the GL context SDL/gl4es already use - creates the OpenXR
// instance/session sharing that same EGL display/context, plus the game
// quad's own swapchain, sized to the game's logical resolution
// (game_width/height, i.e. grd_cap->w/h - see Shock.c's InitSDL()). The
// menu quad's own, independently-sized swapchain (see xr_menu.h) is created
// alongside it. Returns false if OpenXR bring-up failed (e.g. no runtime
// installed) - callers should fall back to the existing window-present path
// in that case.
// (game_width/height, i.e. grd_cap->w/h - see Shock.c's InitSDL()). Also
// creates the menu launcher and keyboard overlay quads (see xr_overlay.h) -
// two independent XrOverlay instances, each with their own swapchain,
// visibility, and position, retrievable via xr_session_get_menu_overlay()/
// xr_session_get_keyboard_overlay() below. Returns false if OpenXR
// bring-up failed (e.g. no runtime installed) - callers should fall back
// to the existing window-present path in that case.
bool xr_init(int game_width, int game_height);
// The menu launcher (small "Keyboard" button panel, toggled by the
// controller's menu button) and keyboard (the on-screen key grid, shown/
// hidden independently via MenuOverlay's "Keyboard" button and
// KeyboardOverlay's own Close button) overlay quads - used by xr_input.c
// for ray/quad hit-testing and touch/cursor dispatch, and by
// questshock_native.c's JNI glue (nativeShowKeyboard()/
// nativeRequestClose()). NULL if xr_init() failed before creating them.
XrOverlay *xr_session_get_menu_overlay(void);
XrOverlay *xr_session_get_keyboard_overlay(void);
// Pumps XR session-state events. Call once per frame, before
// xr_frame_begin(). Must still be called even when xr_init() returned
// false (no-op in that case).
@@ -44,10 +58,12 @@ bool xr_is_session_running(void);
bool xr_frame_begin(void);
// Releases the game quad's swapchain image (if one was acquired this
// frame), acquires/renders/releases the menu quad's own swapchain image if
// it's currently visible (see xr_menu.h), submits whichever of the two
// quads actually rendered this frame as composition layers positioned in
// front of the local reference space's origin, then ends the XR frame.
// frame), then does the same acquire/render/release cycle for the menu
// launcher and keyboard overlay quads via xr_overlay_render_and_build_layer()
// for whichever of them is currently visible, and submits whichever of the
// three quads actually rendered this frame as composition layers
// positioned in front of the local reference space's origin, then ends the
// XR frame.
void xr_frame_end(void);
void xr_shutdown(void);