Route RTT texture updates through GL backend

This commit is contained in:
2026-06-04 23:44:25 +02:00
parent c9fb91ab48
commit 111cc8c892
11 changed files with 115 additions and 44 deletions

View File

@@ -34,16 +34,6 @@ GLint rgba8_internal_format()
return static_cast<GLint>(pp::renderer::gl::rgba8_internal_format());
}
GLenum texture_2d_target()
{
return static_cast<GLenum>(pp::renderer::gl::texture_2d_target());
}
GLenum rgba_pixel_format()
{
return static_cast<GLenum>(pp::renderer::gl::rgba_pixel_format());
}
pp::renderer::RenderDeviceFeatures canvas_render_device_features() noexcept
{
return ShaderManager::render_device_features();
@@ -107,11 +97,6 @@ pp::paint_renderer::CanvasBlendGatePlan draw_merge_blend_gate_plan(
return fallback;
}
GLenum unsigned_byte_component_type()
{
return static_cast<GLenum>(pp::renderer::gl::unsigned_byte_component_type());
}
GLenum depth_test_state()
{
return static_cast<GLenum>(pp::renderer::gl::depth_test_state());
@@ -1961,10 +1946,7 @@ void Canvas::FloodData::apply()
auto& rtt = layer->rtt(plane);
App::I->render_task([&]
{
rtt.bindTexture();
glTexSubImage2D(texture_2d_target(), 0, 0, 0, rtt.getWidth(), rtt.getHeight(),
rgba_pixel_format(), unsigned_byte_component_type(), rgb[plane].get());
rtt.unbindTexture();
rtt.updateRgba8(0, 0, rtt.getWidth(), rtt.getHeight(), rgb[plane].get());
});
layer->face(plane) = true;
layer->box(plane) = box_union(layer->box(plane), bb[plane]);

View File

@@ -4,7 +4,6 @@
#include "canvas.h"
#include "canvas_actions.h"
#include "node_panel_layer.h"
#include "renderer_gl/opengl_capabilities.h"
void ActionStroke::undo()
{
@@ -37,22 +36,12 @@ void ActionStroke::undo()
{
App::I->render_task([&]
{
const auto texture_target = pp::renderer::gl::texture_2d_target();
const auto pixel_format = pp::renderer::gl::rgba_pixel_format();
const auto component_type = pp::renderer::gl::unsigned_byte_component_type();
m_canvas->m_layers[m_layer_idx]->rtt(i, m_frame_idx).bindTexture();
glTexSubImage2D(
texture_target,
0,
m_canvas->m_layers[m_layer_idx]->rtt(i, m_frame_idx).updateRgba8(
(int)m_box[i].x,
(int)m_box[i].y,
(int)box_sz.x,
(int)box_sz.y,
pixel_format,
component_type,
m_image[i].get());
m_canvas->m_layers[m_layer_idx]->rtt(i, m_frame_idx).unbindTexture();
});
}
else

View File

@@ -695,15 +695,11 @@ void LayerFrame::restore(const Snapshot& snap)
// it's just a quick fix DON'T SHIP!!
//m_rtt[i].recreate();
m_rtt[i].bindTexture();
glm::vec2 box_sz = zw(m_dirty_box[i]) - xy(m_dirty_box[i]);
glTexSubImage2D(pp::renderer::gl::texture_2d_target(), 0,
m_rtt[i].updateRgba8(
static_cast<int>(m_dirty_box[i].x), static_cast<int>(m_dirty_box[i].y),
static_cast<int>(box_sz.x), static_cast<int>(box_sz.y),
pp::renderer::gl::rgba_pixel_format(),
pp::renderer::gl::unsigned_byte_component_type(),
snap.image[i].get());
m_rtt[i].unbindTexture();
LOG("restore face %d - %d bytes (%dx%d)", i,
(int)box_sz.x * (int)box_sz.y * 4, (int)box_sz.x, (int)box_sz.y);
}

View File

@@ -832,6 +832,8 @@ pp::foundation::Status update_opengl_texture_2d(
}
if (update.texture_id == 0U
|| update.x < 0
|| update.y < 0
|| update.width <= 0
|| update.height <= 0
|| update.pixel_format == 0U
@@ -844,8 +846,8 @@ pp::foundation::Status update_opengl_texture_2d(
dispatch.tex_sub_image_2d(
texture_2d_target(),
0,
0,
0,
update.x,
update.y,
update.width,
update.height,
update.pixel_format,

View File

@@ -142,6 +142,8 @@ struct OpenGlTextureCubeAllocation {
struct OpenGlTexture2DUpdate {
std::uint32_t texture_id = 0;
std::int32_t x = 0;
std::int32_t y = 0;
std::int32_t width = 0;
std::int32_t height = 0;
std::uint32_t pixel_format = 0;

View File

@@ -92,6 +92,29 @@ void set_opengl_texture_2d_image(
data);
}
void set_opengl_texture_2d_sub_image(
std::uint32_t target,
std::int32_t level,
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,
const void* data) noexcept
{
glTexSubImage2D(
static_cast<GLenum>(target),
static_cast<GLint>(level),
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),
data);
}
void set_opengl_texture_parameter_f(std::uint32_t target, std::uint32_t parameter, float value) noexcept
{
glTexParameterf(static_cast<GLenum>(target), static_cast<GLenum>(parameter), static_cast<GLfloat>(value));
@@ -760,6 +783,34 @@ bool RTT::readPixelsRgba8(int x, int y, int width, int height, void* buffer) con
return ret;
}
bool RTT::updateRgba8(int x, int y, int width, int height, const void* data) noexcept
{
if (!valid() || data == nullptr)
return false;
const auto status = pp::renderer::gl::update_opengl_texture_2d(
pp::renderer::gl::OpenGlTexture2DUpdate {
.texture_id = texID,
.x = x,
.y = y,
.width = width,
.height = height,
.pixel_format = pp::renderer::gl::rgba_pixel_format(),
.component_type = pp::renderer::gl::unsigned_byte_component_type(),
.data = data,
},
pp::renderer::gl::OpenGlTexture2DUpdateDispatch {
.bind_texture = bind_opengl_texture,
.tex_sub_image_2d = set_opengl_texture_2d_sub_image,
});
if (!status.ok()) {
LOG("RTT::updateRgba8() failed because: %s", status.message);
return false;
}
unbindTexture();
return true;
}
uint8_t* RTT::readTextureData(uint8_t* buffer) const noexcept
{
if (!valid())

View File

@@ -68,6 +68,7 @@ public:
void clear(glm::vec4 color = glm::vec4(0));
void clear_mask(glm::bool4 mask, glm::vec4 color = glm::vec4(0));
glm::ivec4 calc_bounds() const noexcept;
bool updateRgba8(int x, int y, int width, int height, const void* data) noexcept;
bool readPixelsRgba8(int x, int y, int width, int height, void* buffer) const noexcept;
uint8_t* readTextureData(uint8_t* buffer = nullptr) const noexcept;
float* readTextureDataFloat(float* buffer = nullptr) const noexcept;