Share CanvasMode GL dispatch adapters

This commit is contained in:
2026-06-05 13:44:57 +02:00
parent 92fa5b224a
commit 03b999e60f
5 changed files with 98 additions and 115 deletions

View File

@@ -555,6 +555,9 @@ powershell -ExecutionPolicy Bypass -File scripts\automation\apple-remote-build.p
same helpers. `NodeCanvas` and `NodeStrokePreview` now share
`legacy_ui_gl_dispatch` for active texture, texture unbind, viewport/scissor,
clear-color, color-buffer clear, and capability query/apply adapter endpoints.
`CanvasMode` overlay, mask, transform, and canvas-tip pick paths now also
share that bridge for active texture, capability query/apply, viewport,
read-framebuffer query, and RGBA8 pixel-readback adapter endpoints.
Retained desktop HMD eye rendering also routes viewport
execution through tested backend dispatch.
Legacy `Texture2D`, `TextureManager`, `Sampler`, and `RTT` public headers no
@@ -861,6 +864,8 @@ powershell -ExecutionPolicy Bypass -File scripts\automation\apple-remote-build.p
plus retained `NodeCanvas` and `NodeStrokePreview` active-texture, fallback
texture unbind, viewport/scissor, clear-color, color-buffer clear, and
capability query/apply draw-state adapter endpoints,
plus retained `CanvasMode` active-texture, capability query/apply, viewport,
read-framebuffer query, and RGBA8 pixel-readback adapter endpoints,
tested convert-command state dispatch consumed by
`App::cmd_convert`, tested render platform hint dispatch consumed by
`WindowsPlatformServices` and the retained macOS legacy fallback, tested

File diff suppressed because one or more lines are too long

View File

@@ -1267,6 +1267,10 @@ clear, and clear-color restore paths use the same helpers. `NodeCanvas` and
`NodeStrokePreview` now share that retained UI GL dispatch bridge for
active-texture, fallback texture unbind, viewport/scissor, clear-color,
color-buffer clear, and capability query/apply adapter endpoints.
Retained `CanvasMode` overlay, mask, transform, and canvas-tip pick paths now
also use the same bridge for active-texture, capability query/apply, viewport,
read-framebuffer query, and RGBA8 pixel readback adapter endpoints while their
mode logic remains in the legacy UI implementation.
Desktop HMD eye rendering now routes eye framebuffer viewport changes through
the tested `pp_renderer_gl` viewport dispatch while platform VR SDK bridges
remain isolated for later platform-shell extraction.
@@ -2549,7 +2553,11 @@ Results:
- Retained Canvas, NodeCanvas, NodeStrokePreview, and HMD viewport/scissor/
capability execution now compiles through the renderer GL backend dispatch
adapters with `pp_legacy_paint_document`, `pp_panopainter_ui`, and
`panopainter_app`.
`panopainter_app`. CanvasMode overlay, mask, transform, and canvas-tip pick
paths now also consume the shared retained UI GL dispatch for active-texture,
capability query/apply, viewport, read-framebuffer query, and RGBA8 pixel
readback adapter endpoints, removing another local raw-GL adapter cluster
from `src/canvas_modes.cpp`.
- Windows desktop OpenGL context creation now consumes a tested
`windows_wgl_core_context_3_3_config()` catalog from `pp_renderer_gl`, moving
the active WGL context/pixel-format attribute literals out of the platform

View File

@@ -8,6 +8,7 @@
#include "canvas.h"
#include "shader.h"
#include "node_canvas.h"
#include "legacy_ui_gl_dispatch.h"
#include "app.h"
#include "util.h"
#include "renderer_gl/opengl_capabilities.h"
@@ -16,141 +17,39 @@ NodeCanvas* CanvasMode::node;
namespace {
void set_opengl_active_texture(std::uint32_t texture_unit) noexcept
{
glActiveTexture(static_cast<GLenum>(texture_unit));
}
void enable_opengl_state(std::uint32_t state) noexcept
{
glEnable(static_cast<GLenum>(state));
}
void disable_opengl_state(std::uint32_t state) noexcept
{
glDisable(static_cast<GLenum>(state));
}
std::uint8_t is_opengl_state_enabled(std::uint32_t state) noexcept
{
return static_cast<std::uint8_t>(glIsEnabled(static_cast<GLenum>(state)));
}
void set_opengl_viewport(std::int32_t x, std::int32_t y, std::int32_t width, std::int32_t height) noexcept
{
glViewport(static_cast<GLint>(x), static_cast<GLint>(y), static_cast<GLsizei>(width), static_cast<GLsizei>(height));
}
void get_opengl_integer(std::uint32_t name, std::int32_t* values) noexcept
{
static_assert(sizeof(GLint) == sizeof(std::int32_t));
glGetIntegerv(static_cast<GLenum>(name), reinterpret_cast<GLint*>(values));
}
void read_opengl_pixels(
std::int32_t x,
std::int32_t y,
std::int32_t width,
std::int32_t height,
std::uint32_t pixel_format,
std::uint32_t component_type,
void* pixels) noexcept
{
glReadPixels(
static_cast<GLint>(x),
static_cast<GLint>(y),
static_cast<GLsizei>(width),
static_cast<GLsizei>(height),
static_cast<GLenum>(pixel_format),
static_cast<GLenum>(component_type),
pixels);
}
void bind_opengl_framebuffer(std::uint32_t target, std::uint32_t framebuffer) noexcept
{
glBindFramebuffer(static_cast<GLenum>(target), static_cast<GLuint>(framebuffer));
}
void set_canvas_mode_active_texture_unit(std::uint32_t unit_index)
{
const auto status = pp::renderer::gl::activate_opengl_texture_unit(
unit_index,
pp::renderer::gl::OpenGlActiveTextureDispatch {
.active_texture = set_opengl_active_texture,
});
if (!status.ok())
LOG("Canvas mode active texture dispatch failed because: %s", status.message);
pp::legacy::ui_gl::activate_texture_unit(unit_index, "CanvasMode");
}
void apply_canvas_mode_capability(std::uint32_t state, bool enabled)
{
const auto status = pp::renderer::gl::apply_opengl_capability(
state,
enabled,
pp::renderer::gl::OpenGlCapabilityDispatch {
.enable = enable_opengl_state,
.disable = disable_opengl_state,
});
if (!status.ok())
LOG("Canvas mode capability dispatch failed because: %s", status.message);
pp::legacy::ui_gl::set_capability(state, enabled, "CanvasMode");
}
bool query_canvas_mode_capability(std::uint32_t state)
{
const auto result = pp::renderer::gl::query_opengl_capability_state(
state,
pp::renderer::gl::OpenGlCapabilityStateQueryDispatch {
.is_enabled = is_opengl_state_enabled,
});
if (!result.ok()) {
LOG("Canvas mode capability query failed because: %s", result.status().message);
return false;
}
return result.value();
return pp::legacy::ui_gl::query_capability(state, "CanvasMode");
}
void apply_canvas_mode_viewport(std::int32_t x, std::int32_t y, std::int32_t width, std::int32_t height)
{
const auto status = pp::renderer::gl::apply_opengl_viewport(
pp::renderer::gl::OpenGlViewportRect {
.x = x,
.y = y,
.width = width,
.height = height,
},
pp::renderer::gl::OpenGlViewportDispatch {
.viewport = set_opengl_viewport,
});
if (!status.ok())
LOG("Canvas mode viewport dispatch failed because: %s", status.message);
pp::legacy::ui_gl::apply_viewport(x, y, width, height, "CanvasMode");
}
std::uint32_t query_canvas_mode_read_framebuffer()
{
std::int32_t read_framebuffer = 0;
get_opengl_integer(pp::renderer::gl::read_framebuffer_binding_query(), &read_framebuffer);
return static_cast<std::uint32_t>(read_framebuffer);
return pp::legacy::ui_gl::query_read_framebuffer("CanvasMode");
}
void read_canvas_mode_pixel(std::int32_t x, std::int32_t y, glm::u8vec4& pixel)
{
const auto status = pp::renderer::gl::readback_opengl_framebuffer(
pp::renderer::gl::OpenGlFramebufferReadback {
.framebuffer = query_canvas_mode_read_framebuffer(),
.x = x,
.y = y,
.width = 1,
.height = 1,
.format = pp::renderer::gl::rgba8_readback_format(),
.pixels = &pixel,
},
pp::renderer::gl::OpenGlFramebufferReadbackDispatch {
.get_integer = get_opengl_integer,
.bind_framebuffer = bind_opengl_framebuffer,
.read_pixels = read_opengl_pixels,
});
if (!status.ok())
LOG("Canvas mode pixel readback dispatch failed because: %s", status.message);
pp::legacy::ui_gl::read_framebuffer_rgba8_pixel(
query_canvas_mode_read_framebuffer(),
x,
y,
&pixel,
"CanvasMode");
}
}

View File

@@ -53,6 +53,37 @@ inline void bind_opengl_texture(std::uint32_t target, std::uint32_t texture) noe
glBindTexture(static_cast<GLenum>(target), static_cast<GLuint>(texture));
}
inline void bind_opengl_framebuffer(std::uint32_t target, std::uint32_t framebuffer) noexcept
{
glBindFramebuffer(static_cast<GLenum>(target), static_cast<GLuint>(framebuffer));
}
inline void read_opengl_pixels(
std::int32_t x,
std::int32_t y,
std::int32_t width,
std::int32_t height,
std::uint32_t pixel_format,
std::uint32_t component_type,
void* pixels) noexcept
{
glReadPixels(
static_cast<GLint>(x),
static_cast<GLint>(y),
static_cast<GLsizei>(width),
static_cast<GLsizei>(height),
static_cast<GLenum>(pixel_format),
static_cast<GLenum>(component_type),
pixels);
}
inline void get_opengl_integer_scalar(std::uint32_t name, std::int32_t* value) noexcept
{
GLint raw_value = 0;
glGetIntegerv(static_cast<GLenum>(name), &raw_value);
*value = static_cast<std::int32_t>(raw_value);
}
inline void get_opengl_integer(std::uint32_t name, std::int32_t* values) noexcept
{
GLint raw_values[4] {};
@@ -109,6 +140,14 @@ inline bool query_capability(std::uint32_t state, const char* context)
return result.value();
}
inline std::uint32_t query_read_framebuffer(const char* context)
{
std::int32_t read_framebuffer = 0;
get_opengl_integer_scalar(pp::renderer::gl::read_framebuffer_binding_query(), &read_framebuffer);
(void)context;
return static_cast<std::uint32_t>(read_framebuffer);
}
inline void set_capability(std::uint32_t state, bool enabled, const char* context)
{
const auto status = pp::renderer::gl::apply_opengl_capability(
@@ -183,6 +222,32 @@ inline void apply_scissor_rect(
LOG("%s scissor dispatch failed because: %s", context, status.message);
}
inline void read_framebuffer_rgba8_pixel(
std::uint32_t framebuffer,
std::int32_t x,
std::int32_t y,
void* pixel,
const char* context)
{
const auto status = pp::renderer::gl::readback_opengl_framebuffer(
pp::renderer::gl::OpenGlFramebufferReadback {
.framebuffer = framebuffer,
.x = x,
.y = y,
.width = 1,
.height = 1,
.format = pp::renderer::gl::rgba8_readback_format(),
.pixels = pixel,
},
pp::renderer::gl::OpenGlFramebufferReadbackDispatch {
.get_integer = get_opengl_integer_scalar,
.bind_framebuffer = bind_opengl_framebuffer,
.read_pixels = read_opengl_pixels,
});
if (!status.ok())
LOG("%s pixel readback dispatch failed because: %s", context, status.message);
}
inline void clear_color_buffer(std::array<float, 4> color, const char* context)
{
const auto status = pp::renderer::gl::clear_opengl_render_target(