// Generic "off-screen Android View rendered into its own OpenXR quad,
// hit-tested/touched via a laser pointer" module - each instance owns its
// own swapchain (via xr_swapchain.h), its own visible/position state, and
// the JNI glue to a backing Java class (menu launcher, keyboard, or any
// future such panel) that must expose these static methods, matching the
// pattern MenuOverlay.java already established:
//   static void nativeInit(Activity activity)
//   static byte[] nativeTakePixelsIfDirty()
//   static void nativeDispatchTouch(float u, float v, boolean down)
//   static void nativeUpdateCursor(float u, float v, boolean visible)
//
// xr_input.c drives touch/cursor dispatch and (for panels that support it,
// like the keyboard's title bar) dragging via xr_overlay_set_position();
// xr_session.c owns instance lifetime and calls
// xr_overlay_render_and_build_layer() once per frame per instance.
#ifndef QUESTSHOCK_XR_OVERLAY_H
#define QUESTSHOCK_XR_OVERLAY_H

#include <stdbool.h>
#include <stdint.h>

#define XR_USE_PLATFORM_ANDROID 1
#define XR_USE_GRAPHICS_API_OPENGL_ES 1
#include <openxr/openxr.h>

#ifdef __cplusplus
extern "C" {
#endif

typedef struct XrOverlay XrOverlay;

typedef struct {
    // Fully-qualified Java class name backing this overlay, e.g.
    // "de.ladkau.questshock.KeyboardOverlay" - resolved via the activity's
    // own ClassLoader (see xr_overlay_find_class() in xr_overlay.c).
    const char *java_class_name;
    // Pixel size of the overlay's own content/swapchain.
    int width;
    int height;
    // Initial local-space pose (meters, in front of the viewer along -Z) -
    // see xr_overlay_get_quad_extent(). width_m is the quad's physical
    // width; its height is derived to preserve width/height's aspect.
    float distance_m;
    float width_m;
    float default_center_x_m;
    float default_center_y_m;
} XrOverlayConfig;

// instance/session are used to create this overlay's own swapchain
// (format shared with every other quad this app submits - see
// xr_session.c's chosenFormat). Returns NULL (logged) on failure - the
// caller just has no such panel.
XrOverlay *xr_overlay_create(XrInstance instance, XrSession session, int64_t swapchain_format,
                              const XrOverlayConfig *config);
void xr_overlay_destroy(XrOverlay *overlay);

void xr_overlay_toggle_visible(XrOverlay *overlay);
void xr_overlay_set_visible(XrOverlay *overlay, bool visible);
bool xr_overlay_is_visible(const XrOverlay *overlay);

// Local-space pose/size of the quad, valid regardless of visibility -
// shared with xr_input.c's ray/quad hit-testing.
void xr_overlay_get_quad_extent(const XrOverlay *overlay, float *center_x_m, float *center_y_m,
                                 float *distance_m, float *half_width_m, float *half_height_m);

// Repositions the quad (world-space X/Y offset, same units/space as
// xr_overlay_get_quad_extent()'s center_x_m/center_y_m) - e.g. driven by
// xr_input.c while the user drags a panel's title bar. Distance from the
// viewer isn't adjustable this way - only left/right/up/down
// repositioning, not push/pull.
void xr_overlay_set_position(XrOverlay *overlay, float center_x_m, float center_y_m);

// Forwards a hit on the quad (in the quad's own 0..1 u/v, top-left origin)
// to the backing Java view as a synthetic touch down/up.
void xr_overlay_touch(XrOverlay *overlay, float u, float v, bool down);

// Updates the on-quad cursor the Java view draws at the current aim hit
// point (same u/v convention as xr_overlay_touch()) - called once per
// frame regardless of click state, so the cursor tracks the ray
// continuously. visible=false hides it.
void xr_overlay_update_cursor(XrOverlay *overlay, float u, float v, bool visible);

// If visible: acquires this overlay's next swapchain image, blits the
// Java view's latest rendered pixels into it, releases the image, and
// fills *out_quad's subImage/pose/size. space/eyeVisibility/layerFlags are
// left for the caller to set (shared/policy choices across every layer
// this app submits, e.g. translucency - not this module's concern).
// Returns false (out_quad untouched) if not visible or something failed -
// the caller should skip submitting a layer for it this frame.
bool xr_overlay_render_and_build_layer(XrOverlay *overlay, XrCompositionLayerQuad *out_quad);

#ifdef __cplusplus
}
#endif

#endif
