make transitions work properly

This commit is contained in:
Konstantin Käfer
2014-07-01 12:21:53 +02:00
parent a6f7696feb
commit 97fc5d9f74
8 changed files with 65 additions and 24 deletions

View File

@@ -27,17 +27,10 @@ public:
public:
// Returns thie ID of the most recent
ClassID mostRecent() const {
return properties.size() ? properties.back().name : ClassID::Fallback;
}
void add(ClassID class_id, timestamp begin, timestamp end, const PropertyValue &value) {
properties.emplace_back(class_id, begin, end, value);
}
bool hasTransitions() const {
return properties.size() > 1;
}
ClassID mostRecent() const;
void add(ClassID class_id, timestamp begin, timestamp end, const PropertyValue &value);
bool hasTransitions() const;
void cleanup(timestamp now);
};
}

View File

@@ -24,14 +24,7 @@ public:
transitions.emplace(::std::forward<Args>(args)...);
}
inline const PropertyTransition &getTransition(PropertyKey key, const PropertyTransition &defaultTransition) const {
auto it = transitions.find(key);
if (it == transitions.end()) {
return defaultTransition;
} else {
return it->second;
}
}
const PropertyTransition &getTransition(PropertyKey key, const PropertyTransition &defaultTransition) const;
// Route-through iterable interface so that you can iterate on the object as is.
inline std::map<PropertyKey, PropertyValue>::const_iterator begin() const {

View File

@@ -54,6 +54,9 @@ private:
template <typename T> void applyStyleProperties(float z, timestamp t);
template <typename T> void applyStyleProperty(PropertyKey key, T &, float z, timestamp t);
// Removes all expired style transitions.
void cleanupAppliedStyleProperties(timestamp t);
public:
// The name of this layer.
const std::string id;

View File

@@ -381,6 +381,9 @@ bool Map::getDebug() const {
void Map::toggleClass(const std::string &name) {
style->toggleClass(name);
if (style->hasTransitions()) {
update();
}
}
const std::vector<std::string> &Map::getAppliedClasses() const {

View File

@@ -8,4 +8,29 @@ AppliedClassProperty::AppliedClassProperty(ClassID class_id, timestamp begin, ti
end(end),
value(value) {}
// Returns thie ID of the most recent
ClassID AppliedClassProperties::mostRecent() const {
return properties.size() ? properties.back().name : ClassID::Fallback;
}
void AppliedClassProperties::add(ClassID class_id, timestamp begin, timestamp end, const PropertyValue &value) {
properties.emplace_back(class_id, begin, end, value);
}
bool AppliedClassProperties::hasTransitions() const {
return properties.size() > 1;
}
// Erase all items in the property list that are before a completed transition.
// Then, if the only remaining property is a Fallback value, remove it too.
void AppliedClassProperties::cleanup(timestamp now) {
for (auto it = properties.end(), begin = properties.begin(); it != begin;) {
// If the property is finished, break iteration and delete all remaining items.
if ((--it)->end <= now) {
properties.erase(begin, it);
break;
}
}
}
}

View File

@@ -0,0 +1,15 @@
#include <llmr/style/class_properties.hpp>
namespace llmr {
const PropertyTransition &ClassProperties::getTransition(PropertyKey key, const PropertyTransition &defaultTransition) const {
auto it = transitions.find(key);
if (it == transitions.end()) {
fprintf(stderr, "using default transition: %d/%d\n", defaultTransition.duration, defaultTransition.delay);
return defaultTransition;
} else {
return it->second;
}
}
}

View File

@@ -56,7 +56,7 @@ void Style::updateProperties(float z, timestamp t) {
}
void Style::setDefaultTransitionDuration(uint16_t duration_milliseconds) {
defaultTransition.duration = duration_milliseconds * 1_millisecond;
defaultTransition.duration = duration_milliseconds;
}
const std::vector<std::string> &Style::getAppliedClasses() const {

View File

@@ -45,8 +45,8 @@ void StyleLayer::setClasses(const std::vector<std::string> &class_names, const t
if (appliedProperties.mostRecent() != ClassID::Fallback) {
// This property key hasn't been set by a previous class, so we need to add a transition
// to the fallback value for that key.
const timestamp begin = now + defaultTransition.delay;
const timestamp end = begin + defaultTransition.duration;
const timestamp begin = now + defaultTransition.delay * 1_millisecond;
const timestamp end = begin + defaultTransition.duration * 1_millisecond;
const PropertyValue &value = PropertyFallbackValue::Get(key);
appliedProperties.add(ClassID::Fallback, begin, end, value);
}
@@ -88,8 +88,8 @@ void StyleLayer::applyClassProperties(const ClassID class_id,
if (appliedProperties.mostRecent() != class_id) {
const PropertyTransition &transition =
properties.getTransition(key, defaultTransition);
const timestamp begin = now + transition.delay;
const timestamp end = begin + transition.duration;
const timestamp begin = now + transition.delay * 1_millisecond;
const timestamp end = begin + transition.duration * 1_millisecond;
const PropertyValue &value = property_pair.second;
appliedProperties.add(class_id, begin, end, value);
}
@@ -271,6 +271,8 @@ void StyleLayer::updateProperties(float z, const timestamp t) {
z += std::log(bucket->source->tile_size / 256.0f) / M_LN2;
}
cleanupAppliedStyleProperties(t);
if (layers) {
applyStyleProperties<CompositeProperties>(z, t);
} else if (bucket) {
@@ -296,4 +298,11 @@ bool StyleLayer::hasTransitions() const {
return false;
}
void StyleLayer::cleanupAppliedStyleProperties(timestamp now) {
for (std::pair<const PropertyKey, AppliedClassProperties> &pair : appliedStyle) {
pair.second.cleanup(now);
}
}
}