Skip to content

Instantly share code, notes, and snippets.

@voidproc
Last active June 26, 2024 09:03
Show Gist options
  • Save voidproc/f47f19b79bdd53cf45d6c116b04e5603 to your computer and use it in GitHub Desktop.
Save voidproc/f47f19b79bdd53cf45d6c116b04e5603 to your computer and use it in GitHub Desktop.
#include <Siv3D.hpp> // Siv3D v0.6.14
#include <CoTaskLib.hpp> // CoTaskLib v0.2.0
class Twinkle : public Co::SequenceBase<>
{
public:
Twinkle(const Vec2& pos)
: pos_{ pos }
{
tweener_.setPivot(pos);
tweener_.setRotation(Random(Math::TwoPi));
scale_ = Random(0.1, 1.0);
}
private:
Co::Task<> start() override
{
const double moveDist = Random(16.0, 200.0);
const double moveAngle = Random(Math::TwoPi);
const auto _ = tweener_
.tweenPosition(0.4s)
.fromTo(Circular{ moveDist * Random(0.3, 1.0), moveAngle}, Circular{ moveDist, moveAngle })
.setEase(EaseOutSine)
.playScoped();
co_await Co::All(
tweener_.fadeInAlpha(0.07s).play(),
tweener_.tweenScale(0.1s).from(0.2 * scale_).to(1.0 * scale_).play()
);
co_await Co::All(
tweener_.fadeOutAlpha(0.3s).play(),
tweener_.tweenRotation(0.3s).to(tweener_.rotation() + Math::Pi / 16.0).play(),
tweener_.tweenScale(0.3s).from(1.0 * scale_).to(0.98 * scale_).play()
);
}
void draw() const override
{
{
const auto _ = tweener_.applyScoped();
Shape2D::Astroid(pos_, 48, 48).draw();
}
}
Vec2 pos_;
double scale_;
Co::Tweener tweener_;
};
class Ripple : public Co::SequenceBase<>
{
public:
Ripple(const Vec2& pos)
: pos_{ pos }
{
tweener_.setPivot(pos);
}
private:
Co::Task<> start() override
{
co_await Co::All(
tweener_.tweenScale(0.3s).from(0.3).to(1.0).setEase(EaseOutCirc).play(),
tweener_.fadeOutAlpha(0.3s).play()
);
}
void draw() const override
{
{
const auto _ = tweener_.applyScoped();
Circle{ pos_, 170 }.drawFrame(5.0);
}
}
Vec2 pos_;
Co::Tweener tweener_;
};
// ※ タスク開始時、内部的に中断する仕様のため `const Vec2& pos` などとして
// 一時オブジェクトの参照を渡すとダングリング参照となることに注意
Co::Task<> GenerateClickEffect(Co::MultiRunner& mr, const Vec2 pos)
{
Co::Play<Ripple>(pos).runAddTo(mr);
for (int i = 0; i < 16; ++i)
{
Co::Play<Twinkle>(pos).runAddTo(mr);
co_await Co::Delay(1s * Random(0.0, 0.025));
}
co_return;
}
void Main()
{
Scene::SetBackground(Palette::Slateblue);
Co::Init();
Co::MultiRunner twinkleRunner;
twinkleRunner.reserve(128);
while (System::Update())
{
if (MouseL.down())
{
GenerateClickEffect(twinkleRunner, Cursor::PosF()).runAddTo(twinkleRunner);
}
twinkleRunner.removeDone();
}
}
@voidproc
Copy link
Author

screenshot

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment