Skip to content

Commit

Permalink
Browse files Browse the repository at this point in the history
UI: Ensure tweens always complete.
  • Loading branch information
unknownbrackets committed Dec 3, 2017
1 parent b4b850b commit e32545b
Show file tree
Hide file tree
Showing 2 changed files with 37 additions and 19 deletions.
23 changes: 15 additions & 8 deletions ext/native/ui/ui_tween.cpp
Expand Up @@ -4,23 +4,30 @@

namespace UI {

uint32_t ColorTween::Current() {
return colorBlend(to_, from_, Position());
void Tween::Apply(View *view) {
if (time_now() >= start_ + duration_)
finishApplied_ = true;

float pos = Position();
DoApply(view, pos);
}

uint32_t ColorTween::Current(float pos) {
return colorBlend(to_, from_, pos);
}

void TextColorTween::Apply(View *view) {
void TextColorTween::DoApply(View *view, float pos) {
// TODO: No validation without RTTI?
TextView *tv = (TextView *)view;
tv->SetTextColor(Current());
tv->SetTextColor(Current(pos));
}

void VisibilityTween::Apply(View *view) {
view->SetVisibility(Current());
void VisibilityTween::DoApply(View *view, float pos) {
view->SetVisibility(Current(pos));
}

Visibility VisibilityTween::Current() {
Visibility VisibilityTween::Current(float p) {
// Prefer V_VISIBLE over V_GONE/V_INVISIBLE.
float p = Position();
if (from_ == V_VISIBLE && p < 1.0f)
return from_;
if (to_ == V_VISIBLE && p > 0.0f)
Expand Down
33 changes: 22 additions & 11 deletions ext/native/ui/ui_tween.h
Expand Up @@ -17,10 +17,10 @@ class Tween {
}

// Actually apply the tween to a view.
virtual void Apply(View *view) = 0;
void Apply(View *view);

bool Finished() {
return time_now() >= start_ + duration_;
return finishApplied_ && time_now() >= start_ + duration_;
}

protected:
Expand All @@ -32,8 +32,11 @@ class Tween {
return curve_(std::min(1.0f, DurationOffset() / duration_));
}

virtual void DoApply(View *view, float pos) = 0;

float start_;
float duration_;
bool finishApplied_ = false;
float (*curve_)(float);
};

Expand All @@ -47,8 +50,8 @@ class TweenBase: public Tween {

// Use this to change the destination value.
// Useful when a state flips while the tween is half-way through.
void Divert(const Value &newTo) {
const Value newFrom = Current();
void Divert(const Value &newTo, float newDuration = -1.0f) {
const Value newFrom = Current(Position());

// Are we already part way through another transition?
if (!Finished()) {
Expand All @@ -57,6 +60,9 @@ class TweenBase: public Tween {
} else if (newTo == from_) {
// Reversing, adjust start_ to be smooth from the current value.
float newOffset = duration_ - DurationOffset();
if (newDuration >= 0.0f && duration_ > 0.0f) {
newOffset *= newDuration / duration_;
}
start_ = time_now() - newOffset;
} else {
// Otherwise, start over.
Expand All @@ -65,15 +71,19 @@ class TweenBase: public Tween {
} else {
// Already finished, so restart.
start_ = time_now();
finishApplied_ = false;
}

from_ = newFrom;
to_ = newTo;
if (newDuration >= 0.0f) {
duration_ = newDuration;
}
}

// Stop animating the value.
void Stop() {
Reset(Current());
Reset(Current(Position()));
}

// Use when the value is explicitly reset. Implicitly stops the tween.
Expand All @@ -83,7 +93,7 @@ class TweenBase: public Tween {
}

protected:
virtual Value Current() = 0;
virtual Value Current(float pos) = 0;

Value from_;
Value to_;
Expand All @@ -95,24 +105,25 @@ class ColorTween : public TweenBase<uint32_t> {
using TweenBase::TweenBase;

protected:
uint32_t Current() override;
uint32_t Current(float pos) override;
};

class TextColorTween : public ColorTween {
public:
using ColorTween::ColorTween;

void Apply(View *view) override;
protected:
void DoApply(View *view, float pos) override;
};

class VisibilityTween : public TweenBase<Visibility> {
public:
using TweenBase::TweenBase;

void Apply(View *view) override;

protected:
Visibility Current() override;
void DoApply(View *view, float pos) override;

Visibility Current(float pos) override;
};

} // namespace

0 comments on commit e32545b

Please sign in to comment.