@@ -19,7 +19,7 @@ public:
|
||||
|
||||
// Animations
|
||||
bool needsAnimation() const;
|
||||
void updateAnimations();
|
||||
void updateAnimations(double time);
|
||||
void cancelAnimations();
|
||||
|
||||
// Map view changes.
|
||||
|
||||
@@ -2,7 +2,6 @@
|
||||
#define LLMR_UTIL_ANIMATION
|
||||
|
||||
#include <llmr/util/noncopyable.hpp>
|
||||
#include <llmr/platform/platform.hpp>
|
||||
|
||||
namespace llmr {
|
||||
namespace util {
|
||||
@@ -13,15 +12,15 @@ public:
|
||||
running,
|
||||
complete
|
||||
};
|
||||
animation(double duration)
|
||||
: start(platform::elapsed()),
|
||||
animation(double start, double duration)
|
||||
: start(start),
|
||||
duration(duration) {}
|
||||
|
||||
double progress() const {
|
||||
return (platform::elapsed() - start) / duration;
|
||||
double progress(double time) const {
|
||||
return (time - start) / duration;
|
||||
}
|
||||
|
||||
virtual state update() const = 0;
|
||||
virtual state update(double time) const = 0;
|
||||
virtual ~animation();
|
||||
|
||||
protected:
|
||||
@@ -30,8 +29,8 @@ protected:
|
||||
|
||||
class ease_animation : public animation {
|
||||
public:
|
||||
ease_animation(double from, double to, double& value, double duration);
|
||||
state update() const;
|
||||
ease_animation(double from, double to, double& value, double start, double duration);
|
||||
state update(double time) const;
|
||||
|
||||
private:
|
||||
const double from, to;
|
||||
@@ -41,13 +40,13 @@ private:
|
||||
template <typename T>
|
||||
class timeout : public animation {
|
||||
public:
|
||||
timeout(T final_value, T& value, double duration)
|
||||
: animation(duration),
|
||||
timeout(T final_value, T& value, double start, double duration)
|
||||
: animation(start, duration),
|
||||
final_value(final_value),
|
||||
value(value) {}
|
||||
|
||||
state update() const {
|
||||
if (progress() >= 1) {
|
||||
state update(double time) const {
|
||||
if (progress(time) >= 1) {
|
||||
value = final_value;
|
||||
return complete;
|
||||
} else {
|
||||
|
||||
@@ -29,7 +29,7 @@ public:
|
||||
// animations
|
||||
void beginFadeInAnimation();
|
||||
bool needsAnimation() const;
|
||||
void updateAnimations();
|
||||
void updateAnimations(double time);
|
||||
|
||||
public:
|
||||
// loaded image dimensions
|
||||
|
||||
@@ -21,7 +21,6 @@
|
||||
@property (nonatomic) CGFloat quickZoomStart;
|
||||
@property (nonatomic) BOOL debug;
|
||||
@property (nonatomic) UIView *palette;
|
||||
@property (nonatomic) NSTimeInterval elapsed;
|
||||
|
||||
@end
|
||||
|
||||
@@ -183,8 +182,6 @@ MBXViewController *view = nullptr;
|
||||
|
||||
- (void)glkView:(GLKView *)view drawInRect:(CGRect)rect
|
||||
{
|
||||
self.elapsed = CACurrentMediaTime();
|
||||
|
||||
// Render the map
|
||||
map->resize(rect.size.width, rect.size.height, view.contentScaleFactor, view.drawableWidth, view.drawableHeight);
|
||||
|
||||
@@ -220,7 +217,6 @@ MBXViewController *view = nullptr;
|
||||
|
||||
- (void)unrotate
|
||||
{
|
||||
self.elapsed = CACurrentMediaTime();
|
||||
map->resetNorth();
|
||||
}
|
||||
|
||||
@@ -300,8 +296,6 @@ MBXViewController *view = nullptr;
|
||||
|
||||
- (void)handlePinchGesture:(UIPinchGestureRecognizer *)pinch
|
||||
{
|
||||
self.elapsed = CACurrentMediaTime();
|
||||
|
||||
map->cancelAnimations();
|
||||
|
||||
if (pinch.state == UIGestureRecognizerStateBegan)
|
||||
@@ -357,8 +351,6 @@ MBXViewController *view = nullptr;
|
||||
|
||||
- (void)handleRotateGesture:(UIRotationGestureRecognizer *)rotate
|
||||
{
|
||||
self.elapsed = CACurrentMediaTime();
|
||||
|
||||
map->cancelAnimations();
|
||||
|
||||
if (rotate.state == UIGestureRecognizerStateBegan)
|
||||
@@ -382,15 +374,11 @@ MBXViewController *view = nullptr;
|
||||
|
||||
- (void)handleSingleTapGesture:(UITapGestureRecognizer *)singleTap
|
||||
{
|
||||
self.elapsed = CACurrentMediaTime();
|
||||
|
||||
[self togglePalette];
|
||||
}
|
||||
|
||||
- (void)handleDoubleTapGesture:(UITapGestureRecognizer *)doubleTap
|
||||
{
|
||||
self.elapsed = CACurrentMediaTime();
|
||||
|
||||
map->cancelAnimations();
|
||||
|
||||
if (doubleTap.state == UIGestureRecognizerStateEnded) {
|
||||
@@ -403,8 +391,6 @@ MBXViewController *view = nullptr;
|
||||
|
||||
- (void)handleTwoFingerTapGesture:(UITapGestureRecognizer *)twoFingerTap
|
||||
{
|
||||
self.elapsed = CACurrentMediaTime();
|
||||
|
||||
map->cancelAnimations();
|
||||
|
||||
if (twoFingerTap.state == UIGestureRecognizerStateEnded) {
|
||||
@@ -417,8 +403,6 @@ MBXViewController *view = nullptr;
|
||||
|
||||
- (void)handleQuickZoomGesture:(UILongPressGestureRecognizer *)quickZoom
|
||||
{
|
||||
self.elapsed = CACurrentMediaTime();
|
||||
|
||||
map->cancelAnimations();
|
||||
|
||||
if (quickZoom.state == UIGestureRecognizerStateBegan)
|
||||
@@ -446,6 +430,8 @@ MBXViewController *view = nullptr;
|
||||
return ([validSimultaneousGestures containsObject:[gestureRecognizer class]] && [validSimultaneousGestures containsObject:[otherGestureRecognizer class]]);
|
||||
}
|
||||
|
||||
@end
|
||||
|
||||
|
||||
namespace llmr {
|
||||
namespace platform {
|
||||
@@ -465,10 +451,7 @@ namespace llmr {
|
||||
}
|
||||
|
||||
double elapsed() {
|
||||
return view.elapsed;
|
||||
return CACurrentMediaTime();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@end
|
||||
|
||||
|
||||
@@ -433,8 +433,10 @@ bool Map::updateTiles() {
|
||||
}
|
||||
|
||||
bool Map::render() {
|
||||
double animationTime = platform::elapsed();
|
||||
|
||||
if (transform.needsAnimation()) {
|
||||
transform.updateAnimations();
|
||||
transform.updateAnimations(animationTime);
|
||||
}
|
||||
|
||||
if (*style.sprite->raster && !style.sprite->raster->textured) {
|
||||
@@ -469,7 +471,7 @@ bool Map::render() {
|
||||
tile.data->raster->beginFadeInAnimation();
|
||||
}
|
||||
if (tile.data->use_raster && tile.data->raster->needsAnimation()) {
|
||||
tile.data->raster->updateAnimations();
|
||||
tile.data->raster->updateAnimations(animationTime);
|
||||
}
|
||||
painter.render(tile);
|
||||
}
|
||||
|
||||
@@ -3,6 +3,7 @@
|
||||
#include <llmr/util/mat4.hpp>
|
||||
#include <llmr/util/std.hpp>
|
||||
#include <llmr/util/math.hpp>
|
||||
#include <llmr/platform/platform.hpp>
|
||||
#include <cstdio>
|
||||
|
||||
using namespace llmr;
|
||||
@@ -24,9 +25,9 @@ bool Transform::needsAnimation() const {
|
||||
return !animations.empty();
|
||||
}
|
||||
|
||||
void Transform::updateAnimations() {
|
||||
animations.remove_if([](const std::shared_ptr<util::animation>& animation) {
|
||||
return animation->update() == util::animation::complete;
|
||||
void Transform::updateAnimations(double time) {
|
||||
animations.remove_if([time](const std::shared_ptr<util::animation>& animation) {
|
||||
return animation->update(time) == util::animation::complete;
|
||||
});
|
||||
}
|
||||
|
||||
@@ -49,8 +50,10 @@ void Transform::moveBy(double dx, double dy, double duration) {
|
||||
x = xn;
|
||||
y = yn;
|
||||
} else {
|
||||
animations.emplace_front(std::make_shared<util::ease_animation>(x, xn, x, duration));
|
||||
animations.emplace_front(std::make_shared<util::ease_animation>(y, yn, y, duration));
|
||||
// Use a common start time for all of the animations to avoid divergent animations.
|
||||
double start = platform::elapsed();
|
||||
animations.emplace_front(std::make_shared<util::ease_animation>(x, xn, x, start, duration));
|
||||
animations.emplace_front(std::make_shared<util::ease_animation>(y, yn, y, start, duration));
|
||||
}
|
||||
}
|
||||
|
||||
@@ -59,7 +62,8 @@ void Transform::startPanning() {
|
||||
|
||||
// Add a 200ms timeout for resetting this to false
|
||||
panning = true;
|
||||
pan_timeout = std::make_shared<util::timeout<bool>>(false, panning, 0.2);
|
||||
double start = platform::elapsed();
|
||||
pan_timeout = std::make_shared<util::timeout<bool>>(false, panning, start, 0.2);
|
||||
animations.emplace_front(pan_timeout);
|
||||
}
|
||||
|
||||
@@ -90,7 +94,8 @@ void Transform::startScaling() {
|
||||
|
||||
// Add a 200ms timeout for resetting this to false
|
||||
scaling = true;
|
||||
scale_timeout = std::make_shared<util::timeout<bool>>(false, scaling, 0.2);
|
||||
double start = platform::elapsed();
|
||||
scale_timeout = std::make_shared<util::timeout<bool>>(false, scaling, start, 0.2);
|
||||
animations.emplace_front(scale_timeout);
|
||||
}
|
||||
|
||||
@@ -136,7 +141,8 @@ void Transform::setAngle(double new_angle, double duration) {
|
||||
if (duration == 0) {
|
||||
angle = new_angle;
|
||||
} else {
|
||||
animations.emplace_front(std::make_shared<util::ease_animation>(angle, new_angle, angle, duration));
|
||||
double start = platform::elapsed();
|
||||
animations.emplace_front(std::make_shared<util::ease_animation>(angle, new_angle, angle, start, duration));
|
||||
}
|
||||
}
|
||||
|
||||
@@ -145,7 +151,8 @@ void Transform::startRotating() {
|
||||
|
||||
// Add a 200ms timeout for resetting this to false
|
||||
rotating = true;
|
||||
rotate_timeout = std::make_shared<util::timeout<bool>>(false, rotating, 0.2);
|
||||
double start = platform::elapsed();
|
||||
rotate_timeout = std::make_shared<util::timeout<bool>>(false, rotating, start, 0.2);
|
||||
animations.emplace_front(rotate_timeout);
|
||||
}
|
||||
|
||||
@@ -163,9 +170,11 @@ void Transform::setScaleXY(double new_scale, double xn, double yn, double durati
|
||||
x = xn;
|
||||
y = yn;
|
||||
} else {
|
||||
animations.emplace_front(std::make_shared<util::ease_animation>(scale, new_scale, scale, duration));
|
||||
animations.emplace_front(std::make_shared<util::ease_animation>(x, xn, x, duration));
|
||||
animations.emplace_front(std::make_shared<util::ease_animation>(y, yn, y, duration));
|
||||
// Use a common start time for all of the animations to avoid divergent animations.
|
||||
double start = platform::elapsed();
|
||||
animations.emplace_front(std::make_shared<util::ease_animation>(scale, new_scale, scale, start, duration));
|
||||
animations.emplace_front(std::make_shared<util::ease_animation>(x, xn, x, start, duration));
|
||||
animations.emplace_front(std::make_shared<util::ease_animation>(y, yn, y, start, duration));
|
||||
}
|
||||
|
||||
const double s = scale * util::tileSize;
|
||||
|
||||
@@ -8,15 +8,15 @@ UnitBezier ease(0.25, 0.1, 0.25, 1);
|
||||
|
||||
animation::~animation() {}
|
||||
|
||||
ease_animation::ease_animation(double from, double to, double &value, double duration)
|
||||
: animation(duration),
|
||||
ease_animation::ease_animation(double from, double to, double &value, double start, double duration)
|
||||
: animation(start, duration),
|
||||
from(from),
|
||||
to(to),
|
||||
value(value) {
|
||||
}
|
||||
|
||||
animation::state ease_animation::update() const {
|
||||
double t = progress();
|
||||
animation::state ease_animation::update(double time) const {
|
||||
double t = progress(time);
|
||||
if (t >= 1) {
|
||||
value = to;
|
||||
return complete;
|
||||
|
||||
@@ -3,6 +3,7 @@
|
||||
#include <memory>
|
||||
#include <cassert>
|
||||
|
||||
#include <llmr/platform/platform.hpp>
|
||||
#include <llmr/platform/gl.hpp>
|
||||
|
||||
#include <png.h>
|
||||
@@ -176,15 +177,16 @@ void Raster::bind(bool linear) {
|
||||
}
|
||||
|
||||
void Raster::beginFadeInAnimation() {
|
||||
fade_animation = std::make_shared<util::ease_animation>(opacity, 1.0, opacity, 0.25);
|
||||
double start = platform::elapsed();
|
||||
fade_animation = std::make_shared<util::ease_animation>(opacity, 1.0, opacity, start, 0.25);
|
||||
}
|
||||
|
||||
bool Raster::needsAnimation() const {
|
||||
return fade_animation != nullptr;
|
||||
}
|
||||
|
||||
void Raster::updateAnimations() {
|
||||
if (fade_animation->update() == util::animation::complete) {
|
||||
void Raster::updateAnimations(double time) {
|
||||
if (fade_animation->update(time) == util::animation::complete) {
|
||||
fade_animation = nullptr;
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user