From 6df6355ba79f704e0a6d8cf2335fbf9f17f68521 Mon Sep 17 00:00:00 2001 From: Jorijn van der Graaf Date: Wed, 26 Nov 2025 20:41:54 +0100 Subject: [PATCH] dirty rect --- implementations/Crafter.Graphics-Window.cpp | 13 ++---- .../Crafter.Graphics-Window_wayland.cpp | 43 ++++++++++++------- 2 files changed, 32 insertions(+), 24 deletions(-) diff --git a/implementations/Crafter.Graphics-Window.cpp b/implementations/Crafter.Graphics-Window.cpp index 701288f..35d0a32 100644 --- a/implementations/Crafter.Graphics-Window.cpp +++ b/implementations/Crafter.Graphics-Window.cpp @@ -111,15 +111,10 @@ void Window::AddDirtyRect(ScaleData scale) { return; } - for (ClipRect& existingRect : dirtyRects) { - if (rect.left <= existingRect.right && rect.right >= existingRect.left && rect.top <= existingRect.bottom && rect.bottom >= existingRect.top) { - existingRect.left = std::min(existingRect.left, rect.left); - existingRect.right = std::max(existingRect.right, rect.right); - existingRect.top = std::min(existingRect.top, rect.top); - existingRect.bottom = std::max(existingRect.bottom, rect.bottom); - return; - } - } + //merging logic should work so that no pixel is drawn twice, and that no pixel not marked dirty is drawn. + //so lets say there is already an existing horizontal bar and the new rect is a vertical bar making a cross shape, the center of the cross will currently be drawn twice + //so we need to turn it into 3 rects, the top part of the vertical bar, the horizontal bar, and the bottom part of the vertical bar + //in this way no pixel is drawn twice and no area not marked dirty is included dirtyRects.push_back(rect); } \ No newline at end of file diff --git a/implementations/Crafter.Graphics-Window_wayland.cpp b/implementations/Crafter.Graphics-Window_wayland.cpp index c79f5b2..d321e1a 100644 --- a/implementations/Crafter.Graphics-Window_wayland.cpp +++ b/implementations/Crafter.Graphics-Window_wayland.cpp @@ -212,25 +212,38 @@ void WindowWayland::Render() { elements.erase(std::remove(elements.begin(), elements.end(), static_cast(nullptr)), elements.end()); std::sort(elements.begin(), elements.end(), [](Transform* a, Transform* b){ return a->z < b->z; }); - if (!dirtyRects.empty()) { - for (ClipRect rect : dirtyRects) { - for (std::int_fast32_t y = rect.top; y < rect.bottom; y++) { - for (std::int_fast32_t x = rect.left; x < rect.right; x++) { - framebuffer[y * width + x] = {0, 0, 0, 0}; - } + for(uint_fast32_t i = 0; i < width*height; i++) { + framebuffer[i] = {0, 0, 0, 255}; + } + + for (ClipRect rect : dirtyRects) { + //std::cout << std::format("{}, {}, {}, {}", rect.left, rect.top, rect.right, rect.bottom) << std::endl; + for (std::int_fast32_t y = rect.top; y < rect.bottom; y++) { + for (std::int_fast32_t x = rect.left; x < rect.right; x++) { + framebuffer[y * width + x].r += 30; } } - - for(Transform* child : elements) { - RenderElement(child); - } - - for (ClipRect rect : dirtyRects) { - wl_surface_damage(surface, rect.left, rect.top, rect.right-rect.left, rect.bottom-rect.top); - } - dirtyRects.clear(); } + // if (!dirtyRects.empty()) { + // for (ClipRect rect : dirtyRects) { + // for (std::int_fast32_t y = rect.top; y < rect.bottom; y++) { + // for (std::int_fast32_t x = rect.left; x < rect.right; x++) { + // framebuffer[y * width + x] = {0, 0, 0, 0}; + // } + // } + // } + + // for(Transform* child : elements) { + // RenderElement(child); + // } + + // for (ClipRect rect : dirtyRects) { + // wl_surface_damage(surface, rect.left, rect.top, rect.right-rect.left, rect.bottom-rect.top); + // } + // dirtyRects.clear(); + // } + dirtyRects.clear(); wl_surface_damage(surface, 0, 0, width, height);