/* Crafter®.Graphics Copyright (C) 2025 Catcrafts® Catcrafts.net This library is free software; you can redistribute it and/or modify it under the terms of the GNU Lesser General Public License as published by the Free Software Foundation; either version 3.0 of the License, or (at your option) any later version. This library is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details. You should have received a copy of the GNU Lesser General Public License along with this library; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA */ module; #include #include #include #include #include #include #include #include #include #include #include #include #include #include "xdg-shell-client-protocol.h" #include "wayland-xdg-decoration-unstable-v1-client-protocol.h" #define _POSIX_C_SOURCE 200809L #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include module Crafter.Graphics; import Crafter.Event; using namespace Crafter; void ScaleBitmapR8G8B8(Pixel_RU8_GU8_BU8_AU8* dst, const Pixel_RU8_GU8_BU8_AU8* src, std::uint32_t srcWidth, std::uint32_t srcHeight, std::uint32_t dstWidth, std::uint32_t dstHeight) { for (std::uint32_t y = 0; y < dstHeight; y++) { std::uint32_t srcY = y * srcHeight / dstHeight; for (std::uint32_t x = 0; x < dstWidth; x++) { std::uint32_t srcX = x * srcWidth / dstWidth; const Pixel_RU8_GU8_BU8_AU8* srcPixel = src + (srcY * srcWidth + srcX); Pixel_RU8_GU8_BU8_AU8* dstPixel = dst + (y * dstWidth + x); dstPixel[0] = srcPixel[0]; } } } WindowWaylandWayland::WindowWaylandWayland(std::string name, std::uint32_t width, std::uint32_t height) : WindowWayland(name, width, height) { } void WindowWaylandWayland::Start() { thread = std::thread([this](){ while (open && wl_display_dispatch(display) != -1) { wl_surface_attach(surface, buffer, 0, 0); for(UiElement* element : elements.components) { std::int32_t realX; std::int32_t realY; std::int32_t elementWidth; std::int32_t elementHeight; if(element->ignoreScaling) { if(element->useRelativeSize) { elementWidth = element->relativeWidth*width; elementHeight = element->relativeHeight*height; } else { elementWidth = element->absoluteWidth; elementHeight = element->absoluteHeight; } } else { if(element->useRelativeSize) { elementWidth = element->relativeWidth*width*scale; elementHeight = element->relativeHeight*height*scale; } else { elementWidth = element->absoluteWidth*scale; elementHeight = element->absoluteHeight*scale; } } realX = (element->anchorX*width)-(element->anchorOffsetX*elementWidth); realY = (element->anchorY*height)-(element->anchorOffsetY*elementHeight); std::vector scaled(elementWidth*elementHeight); ScaleBitmapR8G8B8(scaled.data(), element->buffer.data(), element->bufferWidth, element->bufferHeight, elementWidth, elementHeight); for(std::int32_t x = realX; x-realX < elementWidth; x++) { for(std::int32_t y = realY; y-realY < elementHeight; y++) { if(x > 0 && x < width && y > 0 && y < height) { shm_data[x*width+y] = scaled[(x-realX)*elementWidth+(y-realY)]; } } } wl_surface_damage(surface, realX, realY, elementWidth, elementHeight); } wl_surface_commit(surface); } }); }