X-Git-Url: http://git.localhorst.tv/?a=blobdiff_plain;f=src%2Fgraphics%2FAnimation.h;h=ee62493b18f54c623c729d52c450ec046b027993;hb=679b9e39c7680fd46482589f37f0a225032103b7;hp=55a16d99034fb70a30323ed6506514c67cebdfe0;hpb=ebeefe8b81fbb2e69939d67972453c01b023ec22;p=l2e.git diff --git a/src/graphics/Animation.h b/src/graphics/Animation.h index 55a16d9..ee62493 100644 --- a/src/graphics/Animation.h +++ b/src/graphics/Animation.h @@ -12,12 +12,15 @@ #include "../app/Application.h" #include "../app/State.h" #include "../app/Timer.h" -#include "../geometry/operators.h" -#include "../geometry/Point.h" #include "../geometry/Vector.h" +#include #include +namespace loader { + class TypeDescription; +} + namespace graphics { class Animation { @@ -30,45 +33,97 @@ public: virtual ~Animation() { }; public: + const Sprite *GetSprite() const { return sprite; } + int FrameTime() const { return frameTime; } + bool Repeat() const { return repeat; } + +public: + void SetSprite(const Sprite *s) { sprite = s; } + void SetFrameTime(int t) { frameTime = t; } + void SetRepeat(bool r) { repeat = r; } + +public: + virtual int NumFrames() const = 0; + virtual int Col(int frame) const = 0; + virtual int Row(int frame) const = 0; + virtual geometry::Vector Offset(int frame) const { return geometry::Vector(); } + +protected: + static void AddFields(loader::TypeDescription &, const Animation &, std::ptrdiff_t offset); + +private: + const Sprite *sprite; + int frameTime; + bool repeat; + +}; + + +class AnimationRunner { + +public: + explicit AnimationRunner(const Animation *a = 0, int colOffset = 0, int rowOffset = 0) + : animation(a), sprite(a ? a->GetSprite() : 0), colOffset(colOffset), rowOffset(rowOffset) { } + +public: + bool Valid() const { return animation; } + void Clear() { animation = 0; timer = app::Timer(); } + void Start(app::State &ctrl) { - timer = ctrl.GraphicsTimers().StartInterval(frameTime); + timer = ctrl.GraphicsTimers().StartInterval(animation->FrameTime()); } void Start(app::Application &ctrl) { - timer = ctrl.GlobalTimers().StartInterval(frameTime); + timer = ctrl.GlobalTimers().StartInterval(animation->FrameTime()); } void Stop() { timer = app::Timer(); } + bool Started() const { + return timer.Started(); + } bool Running() const { - return timer.Running() && (repeat || timer.Iteration() < NumFrames()); + return timer.Running() && (animation->Repeat() || timer.Iteration() < animation->NumFrames()); + } + bool Finished() const { + return Started() && !Running(); } - virtual void Draw(SDL_Surface *dest, geometry::Point position) const { - sprite->Draw(dest, position, Col(), Row()); + bool JustFinished() const { + return timer.JustHit() && timer.Iteration() == animation->NumFrames(); + } + + const app::Timer &GetTimer() { return timer; } + + void SetColOffset(int offset) { colOffset = offset; } + int ColOffset() const { return colOffset; } + void SetRowOffset(int offset) { rowOffset = offset; } + int RowOffset() const { return rowOffset; } + + void ChangeSprite(const Sprite *s) { sprite = s; } + const Sprite *GetSprite() const { return sprite; } + + void Draw(SDL_Surface *dest, geometry::Vector position) const { + sprite->Draw(dest, position + animation->Offset(Frame()), animation->Col(Frame()) + ColOffset(), animation->Row(Frame()) + RowOffset()); } - void DrawTopRight(SDL_Surface *dest, geometry::Point position) const { + void DrawTopRight(SDL_Surface *dest, geometry::Vector position) const { geometry::Vector offset(-sprite->Width(), 0); Draw(dest, position + offset); } - void DrawCenter(SDL_Surface *dest, geometry::Point position) const { - geometry::Vector offset(-sprite->Width() / 2, -sprite->Height() / 2); - Draw(dest, position + offset); + void DrawCenter(SDL_Surface *dest, geometry::Vector position) const { + Draw(dest, position - (sprite->Size() / 2)); } - void DrawCenterBottom(SDL_Surface *dest, geometry::Point position) const { + void DrawCenterBottom(SDL_Surface *dest, geometry::Vector position) const { geometry::Vector offset(-sprite->Width() / 2, -sprite->Height()); Draw(dest, position + offset); } -protected: - int Frame() const { return Running() ? (timer.Iteration() % NumFrames()) : 0; } - virtual int Col() const = 0; - virtual int Row() const = 0; - virtual int NumFrames() const = 0; + int Frame() const { return Running() ? (timer.Iteration() % animation->NumFrames()) : 0; } private: - const Sprite *sprite; + const Animation *animation; + const graphics::Sprite *sprite; app::Timer timer; - int frameTime; - bool repeat; + int colOffset; + int rowOffset; };