46 lines
1.7 KiB
C++
46 lines
1.7 KiB
C++
#pragma once
|
||
|
||
namespace Transitions {
|
||
|
||
// Fade-out estil "mosaic dissolve": al llarg del temps els píxels del
|
||
// canvas es reagrupen en blocs cada cop més grans (1×1 → max_block_size×
|
||
// max_block_size). Cada bloc es pinta amb el píxel central del què
|
||
// tenia abans, donant aquell aspecte chunky d'arcade. Al damunt
|
||
// s'aplica un fade-to-black quadràtic (alpha = p² × 255) perquè el
|
||
// resultat acabi en negre opac.
|
||
//
|
||
// La classe NO sap res del Screen abans de `render()`. El caller hi
|
||
// crida després de pintar la seva escena: l'efecte llegeix els
|
||
// píxels actuals del canvas, els rebina i escriu pixels modificats
|
||
// al mateix canvas. És, per tant, un post-procés in-place.
|
||
class Mosaic {
|
||
public:
|
||
struct Params {
|
||
int max_block_size;
|
||
};
|
||
|
||
explicit Mosaic(Params params);
|
||
|
||
// Arrenca un fade nou. Si ja n'hi havia un actiu, el reemplaça.
|
||
// `duration_ms <= 0` deixa l'efecte inactiu.
|
||
void begin(int duration_ms);
|
||
|
||
void tick(int delta_ms);
|
||
|
||
[[nodiscard]] auto isActive() const -> bool { return duration_ms_ > 0 && elapsed_ms_ < duration_ms_; }
|
||
[[nodiscard]] auto isFinished() const -> bool { return duration_ms_ > 0 && elapsed_ms_ >= duration_ms_; }
|
||
[[nodiscard]] auto progress() const -> float;
|
||
|
||
// Aplica el mosaic + alpha negre sobre el canvas actual de Screen.
|
||
// Cridar després del render normal de l'escena, abans de
|
||
// `Screen::present()`.
|
||
void render() const;
|
||
|
||
private:
|
||
Params params_;
|
||
int duration_ms_{0};
|
||
int elapsed_ms_{0};
|
||
};
|
||
|
||
} // namespace Transitions
|