From 5ae4c1b27b6293d346ef253939bbe2c6cf80af3b Mon Sep 17 00:00:00 2001 From: MihailRis Date: Thu, 17 Sep 2026 21:58:38 +0300 Subject: [PATCH 1/3] add gui.screenshot --- src/logic/scripting/lua/libs/libgui.cpp | 10 ++++++++++ 1 file changed, 10 insertions(+) diff --git a/src/logic/scripting/lua/libs/libgui.cpp b/src/logic/scripting/lua/libs/libgui.cpp index 81e5fc4f7..28033132f 100644 --- a/src/logic/scripting/lua/libs/libgui.cpp +++ b/src/logic/scripting/lua/libs/libgui.cpp @@ -25,6 +25,7 @@ #include "items/Inventories.hpp" #include "util/stringutil.hpp" #include "world/Level.hpp" +#include "window/Window.hpp" #include "../usertypes/lua_type_canvas.hpp" using namespace gui; @@ -1218,7 +1219,16 @@ static int l_get_active_frame(lua::State* L) { return lua::pushstring(L, frame->getId()); } +static int l_screenshot(lua::State* L) { + if (engine->isHeadless()) { + return 0; + } + auto image = engine->getWindow().takeScreenshot(); + return lua::newuserdata(L, nullptr, std::move(image)); +} + const luaL_Reg guilib[] = { + {"screenshot", lua::wrap}, {"get_viewport", lua::wrap}, {"getattr", lua::wrap}, {"setattr", lua::wrap}, From 69edfc8c8a1d98f79b7f5b8d05fdb0bb85063543 Mon Sep 17 00:00:00 2001 From: MihailRis Date: Thu, 17 Sep 2026 22:07:18 +0300 Subject: [PATCH 2/3] add 'frame' argument to gui.screenshot --- src/graphics/core/Framebuffer.cpp | 7 +++++++ src/graphics/core/Framebuffer.hpp | 3 +++ src/graphics/ui/GUI.cpp | 8 ++++++++ src/graphics/ui/GUI.hpp | 2 ++ src/graphics/ui/elements/Frame.cpp | 7 +++++++ src/graphics/ui/elements/Frame.hpp | 3 +++ src/logic/scripting/lua/libs/libgui.cpp | 12 +++++++++++- 7 files changed, 41 insertions(+), 1 deletion(-) diff --git a/src/graphics/core/Framebuffer.cpp b/src/graphics/core/Framebuffer.cpp index 1dc677096..a10da01ad 100644 --- a/src/graphics/core/Framebuffer.cpp +++ b/src/graphics/core/Framebuffer.cpp @@ -117,6 +117,13 @@ std::shared_ptr Framebuffer::getSharedTexture() const { return texture; } +std::unique_ptr Framebuffer::readData() const { + if (!texture) { + return nullptr; + } + return texture->readData(); +} + uint Framebuffer::getWidth() const { return width; } diff --git a/src/graphics/core/Framebuffer.hpp b/src/graphics/core/Framebuffer.hpp index 5f9dc3491..00c1422a7 100644 --- a/src/graphics/core/Framebuffer.hpp +++ b/src/graphics/core/Framebuffer.hpp @@ -6,6 +6,7 @@ #include class Texture; +class ImageData; class Framebuffer : public Bindable { uint fbo; @@ -36,6 +37,8 @@ public: std::shared_ptr getSharedTexture() const; + std::unique_ptr readData() const; + /// @brief Get framebuffer width uint getWidth() const; /// @brief Get framebuffer height diff --git a/src/graphics/ui/GUI.cpp b/src/graphics/ui/GUI.cpp index 944c32fb5..a5f3010ff 100644 --- a/src/graphics/ui/GUI.cpp +++ b/src/graphics/ui/GUI.cpp @@ -378,6 +378,14 @@ std::shared_ptr GUI::getActiveFrame() const { return activeFrame; } +std::shared_ptr GUI::getFrame(const std::string& id) { + const auto& found = frames.find(id); + if (found == frames.end()) { + return nullptr; + } + return found->second; +} + void GUI::remove(UINode* node) noexcept { container->remove(node); } diff --git a/src/graphics/ui/GUI.hpp b/src/graphics/ui/GUI.hpp index 97fc0ed37..997b67bea 100644 --- a/src/graphics/ui/GUI.hpp +++ b/src/graphics/ui/GUI.hpp @@ -137,6 +137,8 @@ namespace gui { std::shared_ptr getActiveFrame() const; + std::shared_ptr getFrame(const std::string& id); + /// @brief Remove node from the main container void remove(UINode* node) noexcept; diff --git a/src/graphics/ui/elements/Frame.cpp b/src/graphics/ui/elements/Frame.cpp index 0387f5c1e..fe3562b4f 100644 --- a/src/graphics/ui/elements/Frame.cpp +++ b/src/graphics/ui/elements/Frame.cpp @@ -66,3 +66,10 @@ const std::string& gui::Frame::getOutputTexture() const { const std::string& gui::Frame::getFrameId() const { return frameId; } + +std::unique_ptr gui::Frame::takeScreenshot() const { + if (fbo == nullptr) { + return nullptr; + } + return fbo->readData(); +} diff --git a/src/graphics/ui/elements/Frame.hpp b/src/graphics/ui/elements/Frame.hpp index 1baa7bc91..f7513324b 100644 --- a/src/graphics/ui/elements/Frame.hpp +++ b/src/graphics/ui/elements/Frame.hpp @@ -4,6 +4,7 @@ class Framebuffer; class UiDocument; +class ImageData; namespace gui { class Frame final : public Container { @@ -18,6 +19,8 @@ namespace gui { const std::string& getOutputTexture() const; const std::string& getFrameId() const; + + std::unique_ptr takeScreenshot() const; private: std::string frameId; std::unique_ptr fbo; diff --git a/src/logic/scripting/lua/libs/libgui.cpp b/src/logic/scripting/lua/libs/libgui.cpp index 28033132f..389bedc9a 100644 --- a/src/logic/scripting/lua/libs/libgui.cpp +++ b/src/logic/scripting/lua/libs/libgui.cpp @@ -1223,7 +1223,17 @@ static int l_screenshot(lua::State* L) { if (engine->isHeadless()) { return 0; } - auto image = engine->getWindow().takeScreenshot(); + std::unique_ptr image; + if (lua::isstring(L, 1)) { + auto& gui = engine->getGUI(); + auto frame = gui.getFrame(lua::require_string(L, 1)); + if (frame == nullptr) { + return 0; + } + image = frame->takeScreenshot(); + } else { + image = engine->getWindow().takeScreenshot(); + } return lua::newuserdata(L, nullptr, std::move(image)); } From 71368836c85ce446222e38ea861d4a023c8f8461 Mon Sep 17 00:00:00 2001 From: MihailRis Date: Thu, 17 Sep 2026 22:12:11 +0300 Subject: [PATCH 3/3] update doc/*/scripting/builtins/libgui.md --- doc/en/scripting/builtins/libgui.md | 6 ++++++ doc/ru/scripting/builtins/libgui.md | 6 ++++++ 2 files changed, 12 insertions(+) diff --git a/doc/en/scripting/builtins/libgui.md b/doc/en/scripting/builtins/libgui.md index a7ddbeaec..3dc10612b 100644 --- a/doc/en/scripting/builtins/libgui.md +++ b/doc/en/scripting/builtins/libgui.md @@ -61,6 +61,12 @@ gui.set_active_frame( -- Used for custom projection (e.g., in 3D) [optional] cursorLocator: function() -> number, number ) + +-- Creates a screenshot of a frame as a Canvas object if the frame ID is specified, or the entire window if nil. +gui.screenshot( + -- ID of the frame created via gui.create_frame + [optional] frameId: str +) -> Canvas | nil ``` ## Markup diff --git a/doc/ru/scripting/builtins/libgui.md b/doc/ru/scripting/builtins/libgui.md index ea1221415..51ac7307f 100644 --- a/doc/ru/scripting/builtins/libgui.md +++ b/doc/ru/scripting/builtins/libgui.md @@ -69,6 +69,12 @@ gui.set_active_frame( -- Используется для пользовательской проекции (например в 3D) [опционально] cursorLocator: function() -> number, number ) + +-- Создаёт снимок фрейма в виде объекта Canvas если указан id фрейма, или всего окна, в случае nil. +gui.screenshot( + -- id фрейма, созданного через gui.create_frame + [опционально] frameId: str +) -> Canvas | nil ``` ## Разметка