Files
Renderive/web_server/app/Web_Plot_Session.cpp
T
2026-08-17 15:24:28 +08:00

51 lines
1.9 KiB
C++

#include "Web_Plot_Session.h"
#include "Pixel_Frame.h"
#include "render_2D/scene/Render_Scene_2D.h"
#include <memory>
#include <type_traits>
namespace renderive::web {
struct Web_Plot_Session::Impl {
Size viewport{960, 600};
std::uint64_t sequence{};
std::unique_ptr<Render_Scene_2D> scene;
Impl() { rebuild(); }
void rebuild() {
Render_Scene_2D::State state;
state.viewport = viewport;
scene = Render_Scene_2D::Builder{state}.build(
std::make_shared<Low_Latency_Render_Scene_2D_Strategy>());
scene->activate_view();
}
std::optional<Web_Response> handle(const Web_Event& event) {
return std::visit([this](const auto& value) -> std::optional<Web_Response> {
using T = std::decay_t<decltype(value)>;
if constexpr (std::same_as<T, Frame_Request>) {
const auto result = scene->render_frame(true);
if (!result || scene->wait_for_render() != Scene_Render_Result::none)
return std::nullopt;
std::string pixels;
scene->with_frame([&](Image_View image) {
pixels = encode_pixel_frame(image, ++sequence);
});
if (pixels.empty()) return std::nullopt;
return Web_Response{Web_Response_Type::Pixels,
std::move(pixels)};
} else if constexpr (std::same_as<T, Viewport_Resize>) {
viewport = value.size;
rebuild();
} else if constexpr (std::derived_from<T, Event>) {
scene->dispatch_event(value);
}
return std::nullopt;
}, event);
}
};
Web_Plot_Session::Web_Plot_Session() : impl_(std::make_unique<Impl>()) {}
Web_Plot_Session::~Web_Plot_Session() = default;
std::optional<Web_Response> Web_Plot_Session::handle(const Web_Event& event) {
return impl_->handle(event);
}
} // namespace renderive::web