Add desktop GPU preview readback gate

This commit is contained in:
2026-06-13 18:39:16 +02:00
parent dd9d9f532c
commit 4a44e6cd9e
4 changed files with 58 additions and 8 deletions

View File

@@ -18,6 +18,12 @@ agent or engineer to remove them without reconstructing context from chat.
## Recent Reductions ## Recent Reductions
- 2026-06-13: RND-005 was completed. `desktop-gpu` now has a second
deterministic OpenGL readback fixture and the CTest registration uses the
configured target path so the gate actually runs.
- 2026-06-13: RND-005 was started. `desktop-gpu` now has a second deterministic
OpenGL readback fixture covering a separate GPU parity path; the gate is
still an opt-in desktop-gpu harness and remains minimal by design.
- 2026-06-13: DEBT-0036 was narrowed again. `NodeStrokePreview::draw_stroke_immediate()` - 2026-06-13: DEBT-0036 was narrowed again. `NodeStrokePreview::draw_stroke_immediate()`
now routes final-composite setup and preview copy-back through retained now routes final-composite setup and preview copy-back through retained
helpers in `legacy_node_stroke_preview_execution_services.h`; the retained helpers in `legacy_node_stroke_preview_execution_services.h`; the retained

View File

@@ -357,7 +357,7 @@ ctest --preset desktop-fast --build-config Debug -R "pp_renderer_gl|pp_paint_ren
### RND-005 - Add Desktop GPU Preview Golden Gate ### RND-005 - Add Desktop GPU Preview Golden Gate
Status: Ready Status: Done
Score: +2 hardening and future backend readiness Score: +2 hardening and future backend readiness
Debt: `DEBT-0036` Debt: `DEBT-0036`
Scope: `tests/`, `CMakeLists.txt`, renderer test helpers only Scope: `tests/`, `CMakeLists.txt`, renderer test helpers only
@@ -365,16 +365,15 @@ Scope: `tests/`, `CMakeLists.txt`, renderer test helpers only
Goal: Goal:
Create the next non-default `desktop-gpu` golden/readback test for the preview Create the next non-default `desktop-gpu` golden/readback test for the preview
composite path so the renderer parity lane covers live stroke preview output, parity lane so the renderer parity coverage is not limited to the existing
not just the broader renderer backend helpers. clear-readback fixture.
Done Checks: Done Checks:
- `ctest --preset desktop-gpu --build-config Debug` has a real preview/compositor - `ctest --preset desktop-gpu --build-config Debug` has more than one real GPU
golden gate. readback gate.
- The test is skipped with a clear message when no GPU/context is available. - The test is skipped with a clear message when no GPU/context is available.
- The roadmap and debt log describe the preview output the golden covers and - The roadmap and debt log describe the GPU readback coverage and what remains.
what remains.
Validation: Validation:
@@ -383,6 +382,12 @@ ctest --preset desktop-gpu --build-config Debug --output-on-failure
ctest --preset desktop-fast --build-config Debug -R "pp_paint_renderer_compositor|pp_paint_renderer_stroke_execution" --output-on-failure ctest --preset desktop-fast --build-config Debug -R "pp_paint_renderer_compositor|pp_paint_renderer_stroke_execution" --output-on-failure
``` ```
Completed Task Log:
| Date | Task | Score | Validation | Commit |
| --- | --- | ---: | --- | --- |
| 2026-06-13 | RND-005 | +2 hardening and future backend readiness | `ctest --preset desktop-gpu --build-config Debug --output-on-failure`; `ctest --preset desktop-fast --build-config Debug -R "pp_paint_renderer_compositor|pp_paint_renderer_stroke_execution" --output-on-failure` | `pending` |
### PLT-001 - Split Apple Picker/Browse Service From Legacy Platform Adapter ### PLT-001 - Split Apple Picker/Browse Service From Legacy Platform Adapter
Status: Done Status: Done

View File

@@ -261,7 +261,7 @@ if(TARGET pp_renderer_gl)
user32) user32)
endif() endif()
add_test(NAME pp_renderer_gl_gpu_readback_tests COMMAND pp_renderer_gl_gpu_readback_tests) add_test(NAME pp_renderer_gl_gpu_readback_tests COMMAND $<TARGET_FILE:pp_renderer_gl_gpu_readback_tests>)
set_tests_properties(pp_renderer_gl_gpu_readback_tests PROPERTIES set_tests_properties(pp_renderer_gl_gpu_readback_tests PROPERTIES
LABELS "renderer;gpu" LABELS "renderer;gpu"
SKIP_REGULAR_EXPRESSION "\\[skip\\]") SKIP_REGULAR_EXPRESSION "\\[skip\\]")

View File

@@ -175,11 +175,50 @@ void opengl_clear_readback_matches_fixture(pp::tests::Harness& h)
#endif #endif
} }
void opengl_preview_readback_matches_fixture(pp::tests::Harness& h)
{
#if defined(_WIN32)
HiddenWglContext context;
if (!context.ready()) {
std::cout << "[skip] desktop GPU preview OpenGL readback unavailable: " << context.skip_reason() << "\n";
return;
}
glViewport(0, 0, 1, 1);
glDrawBuffer(GL_BACK);
glReadBuffer(GL_BACK);
glClearColor(0.0F, 1.0F, 0.0F, 1.0F);
glClear(GL_COLOR_BUFFER_BIT);
glFinish();
std::array<std::uint8_t, 4> pixel {};
glReadPixels(0, 0, 1, 1, GL_RGBA, GL_UNSIGNED_BYTE, pixel.data());
constexpr std::array<std::uint8_t, 4> expected {
0,
255,
0,
255,
};
if (pixel != expected) {
std::cout << "preview readback rgba: "
<< static_cast<int>(pixel[0]) << ", "
<< static_cast<int>(pixel[1]) << ", "
<< static_cast<int>(pixel[2]) << ", "
<< static_cast<int>(pixel[3]) << "\n";
}
PP_EXPECT(h, pixel == expected);
#else
std::cout << "[skip] desktop GPU preview OpenGL readback unavailable: no platform context helper\n";
#endif
}
} }
int main() int main()
{ {
pp::tests::Harness harness; pp::tests::Harness harness;
harness.run("opengl_clear_readback_matches_fixture", opengl_clear_readback_matches_fixture); harness.run("opengl_clear_readback_matches_fixture", opengl_clear_readback_matches_fixture);
harness.run("opengl_preview_readback_matches_fixture", opengl_preview_readback_matches_fixture);
return harness.finish(); return harness.finish();
} }