From 511aa1b666a88bc3fb3ba331452acffde076b98b Mon Sep 17 00:00:00 2001 From: Jan Niklas Hasse Date: Wed, 27 Nov 2024 20:45:10 +0100 Subject: [PATCH] Add jngl::UpdateModelview effect --- src/jngl/Widget.cpp | 6 +++++- src/jngl/effects.cpp | 22 ++++++++++++++++++++++ src/jngl/effects.hpp | 29 +++++++++++++++++++++++++++++ 3 files changed, 56 insertions(+), 1 deletion(-) diff --git a/src/jngl/Widget.cpp b/src/jngl/Widget.cpp index 6d585283..a9e9cd97 100644 --- a/src/jngl/Widget.cpp +++ b/src/jngl/Widget.cpp @@ -46,7 +46,11 @@ void Widget::draw() const { for (const auto& effect : effects) { effect->beginDraw(); } - drawSelf(jngl::modelview()); + auto mv = jngl::modelview(); + for (const auto& effect : effects) { + effect->updateModelview(mv); + } + drawSelf(mv); for (const auto& effect : effects) { effect->endDraw(); } diff --git a/src/jngl/effects.cpp b/src/jngl/effects.cpp index 28a57c35..e972a90f 100644 --- a/src/jngl/effects.cpp +++ b/src/jngl/effects.cpp @@ -13,6 +13,28 @@ namespace jngl { Effect::~Effect() = default; +void Effect::updateModelview(Mat3& modelview) const { +} + +UpdateModelview::UpdateModelview(std::function function) +: function(std::move(function)) { +} + +auto UpdateModelview::step() -> Action { + time += 1.f / static_cast(getStepsPerSecond()); + return Action::NONE; +} + +void UpdateModelview::beginDraw() const { +} + +void UpdateModelview::endDraw() const { +} + +void UpdateModelview::updateModelview(Mat3& modelview) const { + function(time, modelview); +} + Zoom::Zoom(std::function function) : function(std::move(function)) { } diff --git a/src/jngl/effects.hpp b/src/jngl/effects.hpp index 38ed1601..11d71b0f 100644 --- a/src/jngl/effects.hpp +++ b/src/jngl/effects.hpp @@ -10,6 +10,8 @@ namespace jngl { +class Mat3; + /// Base class for effects that can be applied to jngl::Widget class Effect { public: @@ -23,6 +25,33 @@ class Effect { [[nodiscard]] virtual Action step() = 0; virtual void beginDraw() const = 0; virtual void endDraw() const = 0; + + /// Called before drawing the widget + virtual void updateModelview(Mat3& modelview) const; +}; + +class UpdateModelview : public Effect { +public: + /// Pass a function that gets the time the effect is in use and a reference to the Modelview so + /// that it can update it + /// + /// Wiggle effect example: + /// \code + /// widget->addEffect([](float t, jngl::Mat3& modelview) { + /// float effectIntensity = std::max(std::sin(t * 3), 0.f); + /// modelview.rotate(std::sin(t * 50) * 0.08 * effectIntensity) + /// .scale(1 + effectIntensity * 0.1); + /// }); + /// \endcode + explicit UpdateModelview(std::function); + Action step() override; + void beginDraw() const override; + void endDraw() const override; + void updateModelview(Mat3& modelview) const override; + +private: + std::function function; + float time = 0; }; /// Scales the ModelView matrix