198 lines
6.7 KiB
C++
198 lines
6.7 KiB
C++
#include "Plot_Scene.h"
|
|
#include "detail/Plot_Scene_Model.hpp"
|
|
#include "../plottable/Performance_Overlay.h"
|
|
#include "../renderable/Renderable.h"
|
|
#include <renderive/scene/base/Scene_Base.hpp>
|
|
|
|
#include <stdexcept>
|
|
#include <variant>
|
|
|
|
namespace renderive::detail {
|
|
void record_performance_frame(Performance_Overlay& overlay, double duration_ms, const Low_Latency_Diagnostics& diagnostics, std::size_t renderable_count, Size viewport) {
|
|
overlay.record_frame(duration_ms, diagnostics, renderable_count, viewport);
|
|
}
|
|
}
|
|
|
|
namespace renderive {
|
|
namespace {
|
|
using Manual_Plot_Scene = Plot_Scene_Model<detail::Manual_Frame_Control>;
|
|
using Low_Latency_Plot_Scene = Plot_Scene_Model<detail::Low_Latency_Frame_Control>;
|
|
using Playback_Plot_Scene = Plot_Scene_Model<detail::Playback_Frame_Control>;
|
|
}
|
|
|
|
struct Plot_Scene::Impl {
|
|
using Model = std::variant<std::unique_ptr<Manual_Plot_Scene>,
|
|
std::unique_ptr<Low_Latency_Plot_Scene>,
|
|
std::unique_ptr<Playback_Plot_Scene>>;
|
|
|
|
explicit Impl(Plot_Frame_Mode mode) : mode(mode), model(create(mode)) {}
|
|
|
|
template <class Operation>
|
|
decltype(auto) apply(Operation&& operation) {
|
|
return std::visit(
|
|
[&operation](auto& scene) -> decltype(auto) {
|
|
return operation(*scene);
|
|
},
|
|
model);
|
|
}
|
|
|
|
template <class Operation>
|
|
decltype(auto) apply(Operation&& operation) const {
|
|
return std::visit(
|
|
[&operation](const auto& scene) -> decltype(auto) {
|
|
return operation(*scene);
|
|
},
|
|
model);
|
|
}
|
|
|
|
static Model create(Plot_Frame_Mode mode) {
|
|
switch (mode) {
|
|
case Plot_Frame_Mode::Manual:
|
|
return std::make_unique<Manual_Plot_Scene>();
|
|
case Plot_Frame_Mode::Low_Latency:
|
|
return std::make_unique<Low_Latency_Plot_Scene>();
|
|
case Plot_Frame_Mode::Playback:
|
|
return std::make_unique<Playback_Plot_Scene>();
|
|
}
|
|
throw std::invalid_argument("unknown Plot_Scene frame mode");
|
|
}
|
|
|
|
Plot_Frame_Mode mode;
|
|
Model model;
|
|
};
|
|
|
|
Plot_Scene::Plot_Scene(Plot_Scene_Options options)
|
|
: impl_(std::make_unique<Impl>(options.frame_mode)) {}
|
|
|
|
Plot_Scene::~Plot_Scene() = default;
|
|
|
|
void Plot_Scene::init() { impl_->apply([](auto& scene) { scene.init(); }); }
|
|
|
|
renderive_Owner<Renderable> Plot_Scene::root_renderable() const {
|
|
return impl_->apply([](const auto& scene) { return scene.root_renderable(); });
|
|
}
|
|
|
|
Scene_2D_Base::Attach_Builder Plot_Scene::attach_builder() {
|
|
return static_cast<Scene_2D_Base&>(render_scene()).attach_builder();
|
|
}
|
|
|
|
Scene_Base::Edit_Operation Plot_Scene::edit_renderables(Scene_2D_Base::Renderable_Edit edit) {
|
|
return static_cast<Scene_2D_Base&>(render_scene()).edit_renderables(std::move(edit));
|
|
}
|
|
|
|
Scene_Base& Plot_Scene::render_scene() noexcept {
|
|
return impl_->apply([](auto& scene) -> Scene_Base& { return scene; });
|
|
}
|
|
|
|
const Scene_Base& Plot_Scene::render_scene() const noexcept {
|
|
return impl_->apply([](const auto& scene) -> const Scene_Base& { return scene; });
|
|
}
|
|
|
|
void Plot_Scene::set_background_color(Color color) {
|
|
impl_->apply([color](auto& scene) { scene.set_background_color(color); });
|
|
}
|
|
|
|
Color Plot_Scene::background_color() const noexcept {
|
|
return impl_->apply([](const auto& scene) { return scene.background_color(); });
|
|
}
|
|
|
|
void Plot_Scene::set_viewport_size(Size size) {
|
|
impl_->apply([size](auto& scene) { scene.set_viewport_size(size); });
|
|
}
|
|
|
|
Size Plot_Scene::viewport_size() const noexcept {
|
|
return impl_->apply([](const auto& scene) { return scene.viewport_size(); });
|
|
}
|
|
|
|
void Plot_Scene::dispatch_event(const Event& event) {
|
|
impl_->apply([&event](auto& scene) { scene.dispatch_event(event); });
|
|
}
|
|
|
|
bool Plot_Scene::prepare_frame() {
|
|
return impl_->apply([](auto& scene) { return scene.prepare_frame(); });
|
|
}
|
|
|
|
bool Plot_Scene::refresh_manual_frame() {
|
|
return impl_->apply([](auto& scene) { return scene.refresh_manual_frame(); });
|
|
}
|
|
|
|
bool Plot_Scene::render_prepared_frame() {
|
|
return impl_->apply([](auto& scene) { return scene.render_prepared_frame(); });
|
|
}
|
|
|
|
bool Plot_Scene::discard_pending_frame() {
|
|
return impl_->apply([](auto& scene) { return scene.discard_pending_frame(); });
|
|
}
|
|
|
|
bool Plot_Scene::render_frame(bool force) {
|
|
return impl_->apply([force](auto& scene) { return scene.render_frame(force); });
|
|
}
|
|
|
|
void Plot_Scene::with_frame(const std::function<void(Image_View)>& consumer) {
|
|
impl_->apply([&consumer](auto& scene) { scene.with_frame(consumer); });
|
|
}
|
|
|
|
void Plot_Scene::activate_view() noexcept {
|
|
impl_->apply([](auto& scene) { scene.activate_view(); });
|
|
}
|
|
|
|
void Plot_Scene::deactivate_view() noexcept {
|
|
impl_->apply([](auto& scene) { scene.deactivate_view(); });
|
|
}
|
|
|
|
bool Plot_Scene::view_active() const noexcept {
|
|
return impl_->apply([](const auto& scene) { return scene.view_active(); });
|
|
}
|
|
|
|
void Plot_Scene::request_redraw() noexcept { render_scene().notify_model_dirty(); }
|
|
|
|
Plot_Control_Error Plot_Scene::set_max_render_fps(double fps) {
|
|
return impl_->apply([fps](auto& scene) { return scene.set_max_render_fps(fps); });
|
|
}
|
|
Plot_Control_Error Plot_Scene::clear_max_render_fps() {
|
|
return impl_->apply([](auto& scene) { return scene.clear_max_render_fps(); });
|
|
}
|
|
|
|
double Plot_Scene::max_render_fps() const noexcept {
|
|
return impl_->apply([](const auto& scene) { return scene.max_render_fps(); });
|
|
}
|
|
|
|
Plot_Control_Error Plot_Scene::set_consumer_feedback(Frame_Consumer_Feedback feedback) {
|
|
return impl_->apply([feedback](auto& scene) { return scene.set_consumer_feedback(feedback); });
|
|
}
|
|
Plot_Control_Error Plot_Scene::clear_consumer_feedback() {
|
|
return impl_->apply([](auto& scene) { return scene.clear_consumer_feedback(); });
|
|
}
|
|
|
|
Plot_Frame_Mode Plot_Scene::frame_mode() const noexcept { return impl_->mode; }
|
|
|
|
Plot_Frame_Status Plot_Scene::frame_status() const {
|
|
return impl_->apply([](const auto& scene) { return scene.frame_status(); });
|
|
}
|
|
|
|
Low_Latency_Diagnostics Plot_Scene::diagnostics() const {
|
|
return impl_->apply([](const auto& scene) { return scene.diagnostics(); });
|
|
}
|
|
|
|
Refresh_Control_Snapshot Plot_Scene::refresh_feedback_snapshot() const {
|
|
return impl_->apply(
|
|
[](const auto& scene) { return scene.refresh_feedback_snapshot(); });
|
|
}
|
|
|
|
void Plot_Scene::set_presentation_sink(std::weak_ptr<Presentation_Sink> sink) {
|
|
impl_->apply([&sink](auto& scene) { scene.set_presentation_sink(std::move(sink)); });
|
|
}
|
|
|
|
std::shared_ptr<Performance_Overlay> Plot_Scene::performance_overlay() const {
|
|
return impl_->apply([](const auto& scene) { return scene.performance_overlay(); });
|
|
}
|
|
|
|
void Plot_Scene::set_performance_overlay(
|
|
std::shared_ptr<Performance_Overlay> overlay) {
|
|
impl_->apply([&overlay](auto& scene) {
|
|
scene.set_performance_overlay(std::move(overlay));
|
|
});
|
|
}
|
|
|
|
} // namespace renderive
|