From a33447dab9b9ebdc0bd636b6ec7721557d21feac Mon Sep 17 00:00:00 2001 From: Florin Malita Date: Tue, 29 May 2018 13:46:54 -0400 Subject: [skottie] Animation::animationTick() -> Animation::seek() Replace poorly defined animationTick() with a normalized seek() method. TBR= Change-Id: Id2ea17bb426fe86fede0d6c8a3d93236902f10af Reviewed-on: https://skia-review.googlesource.com/130508 Reviewed-by: Florin Malita Commit-Queue: Florin Malita --- dm/DMSrcSink.cpp | 8 +++----- modules/skottie/fuzz/FuzzSkottieJSON.cpp | 2 +- modules/skottie/include/Skottie.h | 24 +++++++++++++++++++++--- modules/skottie/src/Skottie.cpp | 15 ++++----------- tools/viewer/SkottieSlide.cpp | 7 +++++-- 5 files changed, 34 insertions(+), 22 deletions(-) diff --git a/dm/DMSrcSink.cpp b/dm/DMSrcSink.cpp index 6378fabd3a..9def615f2b 100644 --- a/dm/DMSrcSink.cpp +++ b/dm/DMSrcSink.cpp @@ -1234,9 +1234,7 @@ Error SkottieSrc::draw(SkCanvas* canvas) const { canvas->drawColor(SK_ColorWHITE); - const auto ip = fAnimation->inPoint() * 1000 / fAnimation->frameRate(), - op = fAnimation->outPoint() * 1000 / fAnimation->frameRate(), - fr = (op - ip) / (kTileCount * kTileCount - 1); + const auto t_rate = 1.0f / (kTileCount * kTileCount - 1); // Shuffled order to exercise non-linear frame progression. static constexpr int frames[] = { 4, 0, 3, 1, 2 }; @@ -1249,7 +1247,7 @@ Error SkottieSrc::draw(SkCanvas* canvas) const { const SkScalar x = frames[j] * fTileSize.width(); SkRect dest = SkRect::MakeXYWH(x, y, fTileSize.width(), fTileSize.height()); - const auto t = fr * (frames[i] * kTileCount + frames[j]); + const auto t = t_rate * (frames[i] * kTileCount + frames[j]); { SkAutoCanvasRestore acr(canvas, true); canvas->clipRect(dest, true); @@ -1257,7 +1255,7 @@ Error SkottieSrc::draw(SkCanvas* canvas) const { dest, SkMatrix::kCenter_ScaleToFit)); - fAnimation->animationTick(t); + fAnimation->seek(t); fAnimation->render(canvas); } } diff --git a/modules/skottie/fuzz/FuzzSkottieJSON.cpp b/modules/skottie/fuzz/FuzzSkottieJSON.cpp index e4f19ccad7..35135f133f 100644 --- a/modules/skottie/fuzz/FuzzSkottieJSON.cpp +++ b/modules/skottie/fuzz/FuzzSkottieJSON.cpp @@ -23,7 +23,7 @@ void FuzzSkottieJSON(sk_sp bytes) { if (!animation) { return; } - animation->animationTick(1337); // A "nothing up my sleeve" number + animation->seek(0.1337f); // A "nothing up my sleeve" number } #if defined(IS_FUZZING_WITH_LIBFUZZER) diff --git a/modules/skottie/include/Skottie.h b/modules/skottie/include/Skottie.h index 0a89ca0438..906ea82b68 100644 --- a/modules/skottie/include/Skottie.h +++ b/modules/skottie/include/Skottie.h @@ -48,9 +48,27 @@ public: ~Animation() override; - void render(SkCanvas*, const SkRect* dst = nullptr) const; - - void animationTick(SkMSec); + /** + * Draws the current animation frame. + * + * @param canvas destination canvas + * @param dst optional destination rect + */ + void render(SkCanvas* canvas, const SkRect* dst = nullptr) const; + + /** + * Updates the animation state for |t|. + * + * @param t normalized [0..1] frame selector, where 0 == inPoint and 1 == outPoint. + */ + void seek(SkScalar t); + + /** + * Returns the animation duration in seconds. + */ + SkScalar duration() const { + return (fOutPoint - fInPoint) / fFrameRate; + } const SkString& version() const { return fVersion; } const SkSize& size() const { return fSize; } diff --git a/modules/skottie/src/Skottie.cpp b/modules/skottie/src/Skottie.cpp index 8396b5ba90..ddea1be18b 100644 --- a/modules/skottie/src/Skottie.cpp +++ b/modules/skottie/src/Skottie.cpp @@ -733,9 +733,7 @@ sk_sp AttachNestedAnimation(const char* path, AttachContext* c protected: void onTick(float t) { - // map back from frame # to ms. - const auto t_ms = t * 1000 / fFrameRate; - fAnimation->animationTick(t_ms); + fAnimation->seek(t * fFrameRate / fAnimation->frameRate()); } private: @@ -1288,7 +1286,7 @@ Animation::Animation(const ResourceProvider& resources, fScene = sksg::Scene::Make(std::move(root), std::move(animators)); // In case the client calls render before the first tick. - this->animationTick(0); + this->seek(0); } Animation::~Animation() = default; @@ -1312,16 +1310,11 @@ void Animation::render(SkCanvas* canvas, const SkRect* dstR) const { fScene->render(canvas); } -void Animation::animationTick(SkMSec ms) { +void Animation::seek(SkScalar t) { if (!fScene) return; - // 't' in the BM model really means 'frame #' - auto t = static_cast(ms) * fFrameRate / 1000; - - t = fInPoint + std::fmod(t, fOutPoint - fInPoint); - - fScene->animate(t); + fScene->animate(fInPoint + SkTPin(t, 0.0f, 1.0f) * (fOutPoint - fInPoint)); } } // namespace skottie diff --git a/tools/viewer/SkottieSlide.cpp b/tools/viewer/SkottieSlide.cpp index f009066182..8eecf43c98 100644 --- a/tools/viewer/SkottieSlide.cpp +++ b/tools/viewer/SkottieSlide.cpp @@ -13,6 +13,8 @@ #include "SkCanvas.h" #include "Skottie.h" +#include + static void draw_stats_box(SkCanvas* canvas, const skottie::Animation::Stats& stats) { static constexpr SkRect kR = { 10, 10, 280, 120 }; static constexpr SkScalar kTextSize = 20; @@ -101,8 +103,9 @@ bool SkottieSlide::animate(const SkAnimTimer& timer) { } if (fAnimation) { - auto t = timer.msec() - fTimeBase; - fAnimation->animationTick(t); + const auto t = timer.msec() - fTimeBase; + const auto d = fAnimation->duration() * 1000; + fAnimation->seek(std::fmod(t, d) / d); } return true; } -- cgit v1.2.3