diff options
Diffstat (limited to 'src/mbgl/style/layers')
33 files changed, 1651 insertions, 1156 deletions
diff --git a/src/mbgl/style/layers/background_layer.cpp b/src/mbgl/style/layers/background_layer.cpp index b4ffea138b..d4ead18816 100644 --- a/src/mbgl/style/layers/background_layer.cpp +++ b/src/mbgl/style/layers/background_layer.cpp @@ -2,39 +2,65 @@ #include <mbgl/style/layers/background_layer.hpp> #include <mbgl/style/layers/background_layer_impl.hpp> -#include <mbgl/style/conversion/stringify.hpp> +#include <mbgl/style/layer_observer.hpp> namespace mbgl { namespace style { BackgroundLayer::BackgroundLayer(const std::string& layerID) - : Layer(LayerType::Background, std::make_unique<Impl>()) - , impl(static_cast<Impl*>(baseImpl.get())) { - impl->id = layerID; + : Layer(makeMutable<Impl>(LayerType::Background, layerID, std::string())) { } -BackgroundLayer::BackgroundLayer(const Impl& other) - : Layer(LayerType::Background, std::make_unique<Impl>(other)) - , impl(static_cast<Impl*>(baseImpl.get())) { +BackgroundLayer::BackgroundLayer(Immutable<Impl> impl_) + : Layer(std::move(impl_)) { } BackgroundLayer::~BackgroundLayer() = default; -std::unique_ptr<Layer> BackgroundLayer::Impl::clone() const { - return std::make_unique<BackgroundLayer>(*this); +const BackgroundLayer::Impl& BackgroundLayer::impl() const { + return static_cast<const Impl&>(*baseImpl); } -std::unique_ptr<Layer> BackgroundLayer::Impl::cloneRef(const std::string& id_) const { - auto result = std::make_unique<BackgroundLayer>(*this); - result->impl->id = id_; - result->impl->cascading = BackgroundPaintProperties::Cascading(); - return std::move(result); +Mutable<BackgroundLayer::Impl> BackgroundLayer::mutableImpl() const { + return makeMutable<Impl>(impl()); +} + +std::unique_ptr<Layer> BackgroundLayer::cloneRef(const std::string& id_) const { + auto impl_ = mutableImpl(); + impl_->id = id_; + impl_->paint = BackgroundPaintProperties::Transitionable(); + return std::make_unique<BackgroundLayer>(std::move(impl_)); } void BackgroundLayer::Impl::stringifyLayout(rapidjson::Writer<rapidjson::StringBuffer>&) const { } +// Visibility + +void BackgroundLayer::setVisibility(VisibilityType value) { + if (value == getVisibility()) + return; + auto impl_ = mutableImpl(); + impl_->visibility = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); +} + +// Zoom range + +void BackgroundLayer::setMinZoom(float minZoom) { + auto impl_ = mutableImpl(); + impl_->minZoom = minZoom; + baseImpl = std::move(impl_); +} + +void BackgroundLayer::setMaxZoom(float maxZoom) { + auto impl_ = mutableImpl(); + impl_->maxZoom = maxZoom; + baseImpl = std::move(impl_); +} + // Layout properties @@ -44,69 +70,81 @@ PropertyValue<Color> BackgroundLayer::getDefaultBackgroundColor() { return { Color::black() }; } -PropertyValue<Color> BackgroundLayer::getBackgroundColor(const optional<std::string>& klass) const { - return impl->cascading.template get<BackgroundColor>().get(klass); +PropertyValue<Color> BackgroundLayer::getBackgroundColor() const { + return impl().paint.template get<BackgroundColor>().value; } -void BackgroundLayer::setBackgroundColor(PropertyValue<Color> value, const optional<std::string>& klass) { - if (value == getBackgroundColor(klass)) +void BackgroundLayer::setBackgroundColor(PropertyValue<Color> value) { + if (value == getBackgroundColor()) return; - impl->cascading.template get<BackgroundColor>().set(value, klass); - impl->observer->onLayerPaintPropertyChanged(*this); + auto impl_ = mutableImpl(); + impl_->paint.template get<BackgroundColor>().value = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } -void BackgroundLayer::setBackgroundColorTransition(const TransitionOptions& value, const optional<std::string>& klass) { - impl->cascading.template get<BackgroundColor>().setTransition(value, klass); +void BackgroundLayer::setBackgroundColorTransition(const TransitionOptions& options) { + auto impl_ = mutableImpl(); + impl_->paint.template get<BackgroundColor>().options = options; + baseImpl = std::move(impl_); } -TransitionOptions BackgroundLayer::getBackgroundColorTransition(const optional<std::string>& klass) const { - return impl->cascading.template get<BackgroundColor>().getTransition(klass); +TransitionOptions BackgroundLayer::getBackgroundColorTransition() const { + return impl().paint.template get<BackgroundColor>().options; } PropertyValue<std::string> BackgroundLayer::getDefaultBackgroundPattern() { return { "" }; } -PropertyValue<std::string> BackgroundLayer::getBackgroundPattern(const optional<std::string>& klass) const { - return impl->cascading.template get<BackgroundPattern>().get(klass); +PropertyValue<std::string> BackgroundLayer::getBackgroundPattern() const { + return impl().paint.template get<BackgroundPattern>().value; } -void BackgroundLayer::setBackgroundPattern(PropertyValue<std::string> value, const optional<std::string>& klass) { - if (value == getBackgroundPattern(klass)) +void BackgroundLayer::setBackgroundPattern(PropertyValue<std::string> value) { + if (value == getBackgroundPattern()) return; - impl->cascading.template get<BackgroundPattern>().set(value, klass); - impl->observer->onLayerPaintPropertyChanged(*this); + auto impl_ = mutableImpl(); + impl_->paint.template get<BackgroundPattern>().value = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } -void BackgroundLayer::setBackgroundPatternTransition(const TransitionOptions& value, const optional<std::string>& klass) { - impl->cascading.template get<BackgroundPattern>().setTransition(value, klass); +void BackgroundLayer::setBackgroundPatternTransition(const TransitionOptions& options) { + auto impl_ = mutableImpl(); + impl_->paint.template get<BackgroundPattern>().options = options; + baseImpl = std::move(impl_); } -TransitionOptions BackgroundLayer::getBackgroundPatternTransition(const optional<std::string>& klass) const { - return impl->cascading.template get<BackgroundPattern>().getTransition(klass); +TransitionOptions BackgroundLayer::getBackgroundPatternTransition() const { + return impl().paint.template get<BackgroundPattern>().options; } PropertyValue<float> BackgroundLayer::getDefaultBackgroundOpacity() { return { 1 }; } -PropertyValue<float> BackgroundLayer::getBackgroundOpacity(const optional<std::string>& klass) const { - return impl->cascading.template get<BackgroundOpacity>().get(klass); +PropertyValue<float> BackgroundLayer::getBackgroundOpacity() const { + return impl().paint.template get<BackgroundOpacity>().value; } -void BackgroundLayer::setBackgroundOpacity(PropertyValue<float> value, const optional<std::string>& klass) { - if (value == getBackgroundOpacity(klass)) +void BackgroundLayer::setBackgroundOpacity(PropertyValue<float> value) { + if (value == getBackgroundOpacity()) return; - impl->cascading.template get<BackgroundOpacity>().set(value, klass); - impl->observer->onLayerPaintPropertyChanged(*this); + auto impl_ = mutableImpl(); + impl_->paint.template get<BackgroundOpacity>().value = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } -void BackgroundLayer::setBackgroundOpacityTransition(const TransitionOptions& value, const optional<std::string>& klass) { - impl->cascading.template get<BackgroundOpacity>().setTransition(value, klass); +void BackgroundLayer::setBackgroundOpacityTransition(const TransitionOptions& options) { + auto impl_ = mutableImpl(); + impl_->paint.template get<BackgroundOpacity>().options = options; + baseImpl = std::move(impl_); } -TransitionOptions BackgroundLayer::getBackgroundOpacityTransition(const optional<std::string>& klass) const { - return impl->cascading.template get<BackgroundOpacity>().getTransition(klass); +TransitionOptions BackgroundLayer::getBackgroundOpacityTransition() const { + return impl().paint.template get<BackgroundOpacity>().options; } } // namespace style diff --git a/src/mbgl/style/layers/background_layer_impl.cpp b/src/mbgl/style/layers/background_layer_impl.cpp index 6c4a4c26d9..a59a84fbe9 100644 --- a/src/mbgl/style/layers/background_layer_impl.cpp +++ b/src/mbgl/style/layers/background_layer_impl.cpp @@ -1,11 +1,10 @@ #include <mbgl/style/layers/background_layer_impl.hpp> -#include <mbgl/renderer/render_background_layer.hpp> namespace mbgl { namespace style { -std::unique_ptr<RenderLayer> BackgroundLayer::Impl::createRenderLayer() const { - return std::make_unique<RenderBackgroundLayer>(*this); +bool BackgroundLayer::Impl::hasLayoutDifference(const Layer::Impl&) const { + return false; } } // namespace style diff --git a/src/mbgl/style/layers/background_layer_impl.hpp b/src/mbgl/style/layers/background_layer_impl.hpp index 85152da4ec..248a751027 100644 --- a/src/mbgl/style/layers/background_layer_impl.hpp +++ b/src/mbgl/style/layers/background_layer_impl.hpp @@ -9,13 +9,12 @@ namespace style { class BackgroundLayer::Impl : public Layer::Impl { public: - std::unique_ptr<Layer> clone() const override; - std::unique_ptr<Layer> cloneRef(const std::string& id) const override; - void stringifyLayout(rapidjson::Writer<rapidjson::StringBuffer>&) const override; + using Layer::Impl::Impl; - std::unique_ptr<RenderLayer> createRenderLayer() const override; + bool hasLayoutDifference(const Layer::Impl&) const override; + void stringifyLayout(rapidjson::Writer<rapidjson::StringBuffer>&) const override; - BackgroundPaintProperties::Cascading cascading; + BackgroundPaintProperties::Transitionable paint; }; } // namespace style diff --git a/src/mbgl/style/layers/background_layer_properties.hpp b/src/mbgl/style/layers/background_layer_properties.hpp index fae6c26a4b..3a61392fb4 100644 --- a/src/mbgl/style/layers/background_layer_properties.hpp +++ b/src/mbgl/style/layers/background_layer_properties.hpp @@ -5,7 +5,9 @@ #include <mbgl/style/types.hpp> #include <mbgl/style/layout_property.hpp> #include <mbgl/style/paint_property.hpp> +#include <mbgl/style/properties.hpp> #include <mbgl/programs/attributes.hpp> +#include <mbgl/programs/uniforms.hpp> namespace mbgl { namespace style { @@ -22,7 +24,7 @@ struct BackgroundOpacity : PaintProperty<float> { static float defaultValue() { return 1; } }; -class BackgroundPaintProperties : public PaintProperties< +class BackgroundPaintProperties : public Properties< BackgroundColor, BackgroundPattern, BackgroundOpacity diff --git a/src/mbgl/style/layers/circle_layer.cpp b/src/mbgl/style/layers/circle_layer.cpp index 8b3431a9a1..9854932699 100644 --- a/src/mbgl/style/layers/circle_layer.cpp +++ b/src/mbgl/style/layers/circle_layer.cpp @@ -2,34 +2,34 @@ #include <mbgl/style/layers/circle_layer.hpp> #include <mbgl/style/layers/circle_layer_impl.hpp> -#include <mbgl/style/conversion/stringify.hpp> +#include <mbgl/style/layer_observer.hpp> namespace mbgl { namespace style { CircleLayer::CircleLayer(const std::string& layerID, const std::string& sourceID) - : Layer(LayerType::Circle, std::make_unique<Impl>()) - , impl(static_cast<Impl*>(baseImpl.get())) { - impl->id = layerID; - impl->source = sourceID; + : Layer(makeMutable<Impl>(LayerType::Circle, layerID, sourceID)) { } -CircleLayer::CircleLayer(const Impl& other) - : Layer(LayerType::Circle, std::make_unique<Impl>(other)) - , impl(static_cast<Impl*>(baseImpl.get())) { +CircleLayer::CircleLayer(Immutable<Impl> impl_) + : Layer(std::move(impl_)) { } CircleLayer::~CircleLayer() = default; -std::unique_ptr<Layer> CircleLayer::Impl::clone() const { - return std::make_unique<CircleLayer>(*this); +const CircleLayer::Impl& CircleLayer::impl() const { + return static_cast<const Impl&>(*baseImpl); } -std::unique_ptr<Layer> CircleLayer::Impl::cloneRef(const std::string& id_) const { - auto result = std::make_unique<CircleLayer>(*this); - result->impl->id = id_; - result->impl->cascading = CirclePaintProperties::Cascading(); - return std::move(result); +Mutable<CircleLayer::Impl> CircleLayer::mutableImpl() const { + return makeMutable<Impl>(impl()); +} + +std::unique_ptr<Layer> CircleLayer::cloneRef(const std::string& id_) const { + auto impl_ = mutableImpl(); + impl_->id = id_; + impl_->paint = CirclePaintProperties::Transitionable(); + return std::make_unique<CircleLayer>(std::move(impl_)); } void CircleLayer::Impl::stringifyLayout(rapidjson::Writer<rapidjson::StringBuffer>&) const { @@ -38,26 +38,55 @@ void CircleLayer::Impl::stringifyLayout(rapidjson::Writer<rapidjson::StringBuffe // Source const std::string& CircleLayer::getSourceID() const { - return impl->source; + return impl().source; } void CircleLayer::setSourceLayer(const std::string& sourceLayer) { - impl->sourceLayer = sourceLayer; + auto impl_ = mutableImpl(); + impl_->sourceLayer = sourceLayer; + baseImpl = std::move(impl_); } const std::string& CircleLayer::getSourceLayer() const { - return impl->sourceLayer; + return impl().sourceLayer; } // Filter void CircleLayer::setFilter(const Filter& filter) { - impl->filter = filter; - impl->observer->onLayerFilterChanged(*this); + auto impl_ = mutableImpl(); + impl_->filter = filter; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } const Filter& CircleLayer::getFilter() const { - return impl->filter; + return impl().filter; +} + +// Visibility + +void CircleLayer::setVisibility(VisibilityType value) { + if (value == getVisibility()) + return; + auto impl_ = mutableImpl(); + impl_->visibility = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); +} + +// Zoom range + +void CircleLayer::setMinZoom(float minZoom) { + auto impl_ = mutableImpl(); + impl_->minZoom = minZoom; + baseImpl = std::move(impl_); +} + +void CircleLayer::setMaxZoom(float maxZoom) { + auto impl_ = mutableImpl(); + impl_->maxZoom = maxZoom; + baseImpl = std::move(impl_); } // Layout properties @@ -69,258 +98,297 @@ DataDrivenPropertyValue<float> CircleLayer::getDefaultCircleRadius() { return { 5 }; } -DataDrivenPropertyValue<float> CircleLayer::getCircleRadius(const optional<std::string>& klass) const { - return impl->cascading.template get<CircleRadius>().get(klass); +DataDrivenPropertyValue<float> CircleLayer::getCircleRadius() const { + return impl().paint.template get<CircleRadius>().value; } -void CircleLayer::setCircleRadius(DataDrivenPropertyValue<float> value, const optional<std::string>& klass) { - if (value == getCircleRadius(klass)) +void CircleLayer::setCircleRadius(DataDrivenPropertyValue<float> value) { + if (value == getCircleRadius()) return; - impl->cascading.template get<CircleRadius>().set(value, klass); - if (value.isDataDriven()) { - impl->observer->onLayerDataDrivenPaintPropertyChanged(*this); - } else { - impl->observer->onLayerPaintPropertyChanged(*this); - } + auto impl_ = mutableImpl(); + impl_->paint.template get<CircleRadius>().value = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } -void CircleLayer::setCircleRadiusTransition(const TransitionOptions& value, const optional<std::string>& klass) { - impl->cascading.template get<CircleRadius>().setTransition(value, klass); +void CircleLayer::setCircleRadiusTransition(const TransitionOptions& options) { + auto impl_ = mutableImpl(); + impl_->paint.template get<CircleRadius>().options = options; + baseImpl = std::move(impl_); } -TransitionOptions CircleLayer::getCircleRadiusTransition(const optional<std::string>& klass) const { - return impl->cascading.template get<CircleRadius>().getTransition(klass); +TransitionOptions CircleLayer::getCircleRadiusTransition() const { + return impl().paint.template get<CircleRadius>().options; } DataDrivenPropertyValue<Color> CircleLayer::getDefaultCircleColor() { return { Color::black() }; } -DataDrivenPropertyValue<Color> CircleLayer::getCircleColor(const optional<std::string>& klass) const { - return impl->cascading.template get<CircleColor>().get(klass); +DataDrivenPropertyValue<Color> CircleLayer::getCircleColor() const { + return impl().paint.template get<CircleColor>().value; } -void CircleLayer::setCircleColor(DataDrivenPropertyValue<Color> value, const optional<std::string>& klass) { - if (value == getCircleColor(klass)) +void CircleLayer::setCircleColor(DataDrivenPropertyValue<Color> value) { + if (value == getCircleColor()) return; - impl->cascading.template get<CircleColor>().set(value, klass); - if (value.isDataDriven()) { - impl->observer->onLayerDataDrivenPaintPropertyChanged(*this); - } else { - impl->observer->onLayerPaintPropertyChanged(*this); - } + auto impl_ = mutableImpl(); + impl_->paint.template get<CircleColor>().value = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } -void CircleLayer::setCircleColorTransition(const TransitionOptions& value, const optional<std::string>& klass) { - impl->cascading.template get<CircleColor>().setTransition(value, klass); +void CircleLayer::setCircleColorTransition(const TransitionOptions& options) { + auto impl_ = mutableImpl(); + impl_->paint.template get<CircleColor>().options = options; + baseImpl = std::move(impl_); } -TransitionOptions CircleLayer::getCircleColorTransition(const optional<std::string>& klass) const { - return impl->cascading.template get<CircleColor>().getTransition(klass); +TransitionOptions CircleLayer::getCircleColorTransition() const { + return impl().paint.template get<CircleColor>().options; } DataDrivenPropertyValue<float> CircleLayer::getDefaultCircleBlur() { return { 0 }; } -DataDrivenPropertyValue<float> CircleLayer::getCircleBlur(const optional<std::string>& klass) const { - return impl->cascading.template get<CircleBlur>().get(klass); +DataDrivenPropertyValue<float> CircleLayer::getCircleBlur() const { + return impl().paint.template get<CircleBlur>().value; } -void CircleLayer::setCircleBlur(DataDrivenPropertyValue<float> value, const optional<std::string>& klass) { - if (value == getCircleBlur(klass)) +void CircleLayer::setCircleBlur(DataDrivenPropertyValue<float> value) { + if (value == getCircleBlur()) return; - impl->cascading.template get<CircleBlur>().set(value, klass); - if (value.isDataDriven()) { - impl->observer->onLayerDataDrivenPaintPropertyChanged(*this); - } else { - impl->observer->onLayerPaintPropertyChanged(*this); - } + auto impl_ = mutableImpl(); + impl_->paint.template get<CircleBlur>().value = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } -void CircleLayer::setCircleBlurTransition(const TransitionOptions& value, const optional<std::string>& klass) { - impl->cascading.template get<CircleBlur>().setTransition(value, klass); +void CircleLayer::setCircleBlurTransition(const TransitionOptions& options) { + auto impl_ = mutableImpl(); + impl_->paint.template get<CircleBlur>().options = options; + baseImpl = std::move(impl_); } -TransitionOptions CircleLayer::getCircleBlurTransition(const optional<std::string>& klass) const { - return impl->cascading.template get<CircleBlur>().getTransition(klass); +TransitionOptions CircleLayer::getCircleBlurTransition() const { + return impl().paint.template get<CircleBlur>().options; } DataDrivenPropertyValue<float> CircleLayer::getDefaultCircleOpacity() { return { 1 }; } -DataDrivenPropertyValue<float> CircleLayer::getCircleOpacity(const optional<std::string>& klass) const { - return impl->cascading.template get<CircleOpacity>().get(klass); +DataDrivenPropertyValue<float> CircleLayer::getCircleOpacity() const { + return impl().paint.template get<CircleOpacity>().value; } -void CircleLayer::setCircleOpacity(DataDrivenPropertyValue<float> value, const optional<std::string>& klass) { - if (value == getCircleOpacity(klass)) +void CircleLayer::setCircleOpacity(DataDrivenPropertyValue<float> value) { + if (value == getCircleOpacity()) return; - impl->cascading.template get<CircleOpacity>().set(value, klass); - if (value.isDataDriven()) { - impl->observer->onLayerDataDrivenPaintPropertyChanged(*this); - } else { - impl->observer->onLayerPaintPropertyChanged(*this); - } + auto impl_ = mutableImpl(); + impl_->paint.template get<CircleOpacity>().value = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } -void CircleLayer::setCircleOpacityTransition(const TransitionOptions& value, const optional<std::string>& klass) { - impl->cascading.template get<CircleOpacity>().setTransition(value, klass); +void CircleLayer::setCircleOpacityTransition(const TransitionOptions& options) { + auto impl_ = mutableImpl(); + impl_->paint.template get<CircleOpacity>().options = options; + baseImpl = std::move(impl_); } -TransitionOptions CircleLayer::getCircleOpacityTransition(const optional<std::string>& klass) const { - return impl->cascading.template get<CircleOpacity>().getTransition(klass); +TransitionOptions CircleLayer::getCircleOpacityTransition() const { + return impl().paint.template get<CircleOpacity>().options; } PropertyValue<std::array<float, 2>> CircleLayer::getDefaultCircleTranslate() { return { {{ 0, 0 }} }; } -PropertyValue<std::array<float, 2>> CircleLayer::getCircleTranslate(const optional<std::string>& klass) const { - return impl->cascading.template get<CircleTranslate>().get(klass); +PropertyValue<std::array<float, 2>> CircleLayer::getCircleTranslate() const { + return impl().paint.template get<CircleTranslate>().value; } -void CircleLayer::setCircleTranslate(PropertyValue<std::array<float, 2>> value, const optional<std::string>& klass) { - if (value == getCircleTranslate(klass)) +void CircleLayer::setCircleTranslate(PropertyValue<std::array<float, 2>> value) { + if (value == getCircleTranslate()) return; - impl->cascading.template get<CircleTranslate>().set(value, klass); - impl->observer->onLayerPaintPropertyChanged(*this); + auto impl_ = mutableImpl(); + impl_->paint.template get<CircleTranslate>().value = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } -void CircleLayer::setCircleTranslateTransition(const TransitionOptions& value, const optional<std::string>& klass) { - impl->cascading.template get<CircleTranslate>().setTransition(value, klass); +void CircleLayer::setCircleTranslateTransition(const TransitionOptions& options) { + auto impl_ = mutableImpl(); + impl_->paint.template get<CircleTranslate>().options = options; + baseImpl = std::move(impl_); } -TransitionOptions CircleLayer::getCircleTranslateTransition(const optional<std::string>& klass) const { - return impl->cascading.template get<CircleTranslate>().getTransition(klass); +TransitionOptions CircleLayer::getCircleTranslateTransition() const { + return impl().paint.template get<CircleTranslate>().options; } PropertyValue<TranslateAnchorType> CircleLayer::getDefaultCircleTranslateAnchor() { return { TranslateAnchorType::Map }; } -PropertyValue<TranslateAnchorType> CircleLayer::getCircleTranslateAnchor(const optional<std::string>& klass) const { - return impl->cascading.template get<CircleTranslateAnchor>().get(klass); +PropertyValue<TranslateAnchorType> CircleLayer::getCircleTranslateAnchor() const { + return impl().paint.template get<CircleTranslateAnchor>().value; } -void CircleLayer::setCircleTranslateAnchor(PropertyValue<TranslateAnchorType> value, const optional<std::string>& klass) { - if (value == getCircleTranslateAnchor(klass)) +void CircleLayer::setCircleTranslateAnchor(PropertyValue<TranslateAnchorType> value) { + if (value == getCircleTranslateAnchor()) return; - impl->cascading.template get<CircleTranslateAnchor>().set(value, klass); - impl->observer->onLayerPaintPropertyChanged(*this); + auto impl_ = mutableImpl(); + impl_->paint.template get<CircleTranslateAnchor>().value = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } -void CircleLayer::setCircleTranslateAnchorTransition(const TransitionOptions& value, const optional<std::string>& klass) { - impl->cascading.template get<CircleTranslateAnchor>().setTransition(value, klass); +void CircleLayer::setCircleTranslateAnchorTransition(const TransitionOptions& options) { + auto impl_ = mutableImpl(); + impl_->paint.template get<CircleTranslateAnchor>().options = options; + baseImpl = std::move(impl_); } -TransitionOptions CircleLayer::getCircleTranslateAnchorTransition(const optional<std::string>& klass) const { - return impl->cascading.template get<CircleTranslateAnchor>().getTransition(klass); +TransitionOptions CircleLayer::getCircleTranslateAnchorTransition() const { + return impl().paint.template get<CircleTranslateAnchor>().options; } PropertyValue<CirclePitchScaleType> CircleLayer::getDefaultCirclePitchScale() { return { CirclePitchScaleType::Map }; } -PropertyValue<CirclePitchScaleType> CircleLayer::getCirclePitchScale(const optional<std::string>& klass) const { - return impl->cascading.template get<CirclePitchScale>().get(klass); +PropertyValue<CirclePitchScaleType> CircleLayer::getCirclePitchScale() const { + return impl().paint.template get<CirclePitchScale>().value; +} + +void CircleLayer::setCirclePitchScale(PropertyValue<CirclePitchScaleType> value) { + if (value == getCirclePitchScale()) + return; + auto impl_ = mutableImpl(); + impl_->paint.template get<CirclePitchScale>().value = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); +} + +void CircleLayer::setCirclePitchScaleTransition(const TransitionOptions& options) { + auto impl_ = mutableImpl(); + impl_->paint.template get<CirclePitchScale>().options = options; + baseImpl = std::move(impl_); +} + +TransitionOptions CircleLayer::getCirclePitchScaleTransition() const { + return impl().paint.template get<CirclePitchScale>().options; +} + +PropertyValue<AlignmentType> CircleLayer::getDefaultCirclePitchAlignment() { + return { AlignmentType::Viewport }; +} + +PropertyValue<AlignmentType> CircleLayer::getCirclePitchAlignment() const { + return impl().paint.template get<CirclePitchAlignment>().value; } -void CircleLayer::setCirclePitchScale(PropertyValue<CirclePitchScaleType> value, const optional<std::string>& klass) { - if (value == getCirclePitchScale(klass)) +void CircleLayer::setCirclePitchAlignment(PropertyValue<AlignmentType> value) { + if (value == getCirclePitchAlignment()) return; - impl->cascading.template get<CirclePitchScale>().set(value, klass); - impl->observer->onLayerPaintPropertyChanged(*this); + auto impl_ = mutableImpl(); + impl_->paint.template get<CirclePitchAlignment>().value = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } -void CircleLayer::setCirclePitchScaleTransition(const TransitionOptions& value, const optional<std::string>& klass) { - impl->cascading.template get<CirclePitchScale>().setTransition(value, klass); +void CircleLayer::setCirclePitchAlignmentTransition(const TransitionOptions& options) { + auto impl_ = mutableImpl(); + impl_->paint.template get<CirclePitchAlignment>().options = options; + baseImpl = std::move(impl_); } -TransitionOptions CircleLayer::getCirclePitchScaleTransition(const optional<std::string>& klass) const { - return impl->cascading.template get<CirclePitchScale>().getTransition(klass); +TransitionOptions CircleLayer::getCirclePitchAlignmentTransition() const { + return impl().paint.template get<CirclePitchAlignment>().options; } DataDrivenPropertyValue<float> CircleLayer::getDefaultCircleStrokeWidth() { return { 0 }; } -DataDrivenPropertyValue<float> CircleLayer::getCircleStrokeWidth(const optional<std::string>& klass) const { - return impl->cascading.template get<CircleStrokeWidth>().get(klass); +DataDrivenPropertyValue<float> CircleLayer::getCircleStrokeWidth() const { + return impl().paint.template get<CircleStrokeWidth>().value; } -void CircleLayer::setCircleStrokeWidth(DataDrivenPropertyValue<float> value, const optional<std::string>& klass) { - if (value == getCircleStrokeWidth(klass)) +void CircleLayer::setCircleStrokeWidth(DataDrivenPropertyValue<float> value) { + if (value == getCircleStrokeWidth()) return; - impl->cascading.template get<CircleStrokeWidth>().set(value, klass); - if (value.isDataDriven()) { - impl->observer->onLayerDataDrivenPaintPropertyChanged(*this); - } else { - impl->observer->onLayerPaintPropertyChanged(*this); - } + auto impl_ = mutableImpl(); + impl_->paint.template get<CircleStrokeWidth>().value = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } -void CircleLayer::setCircleStrokeWidthTransition(const TransitionOptions& value, const optional<std::string>& klass) { - impl->cascading.template get<CircleStrokeWidth>().setTransition(value, klass); +void CircleLayer::setCircleStrokeWidthTransition(const TransitionOptions& options) { + auto impl_ = mutableImpl(); + impl_->paint.template get<CircleStrokeWidth>().options = options; + baseImpl = std::move(impl_); } -TransitionOptions CircleLayer::getCircleStrokeWidthTransition(const optional<std::string>& klass) const { - return impl->cascading.template get<CircleStrokeWidth>().getTransition(klass); +TransitionOptions CircleLayer::getCircleStrokeWidthTransition() const { + return impl().paint.template get<CircleStrokeWidth>().options; } DataDrivenPropertyValue<Color> CircleLayer::getDefaultCircleStrokeColor() { return { Color::black() }; } -DataDrivenPropertyValue<Color> CircleLayer::getCircleStrokeColor(const optional<std::string>& klass) const { - return impl->cascading.template get<CircleStrokeColor>().get(klass); +DataDrivenPropertyValue<Color> CircleLayer::getCircleStrokeColor() const { + return impl().paint.template get<CircleStrokeColor>().value; } -void CircleLayer::setCircleStrokeColor(DataDrivenPropertyValue<Color> value, const optional<std::string>& klass) { - if (value == getCircleStrokeColor(klass)) +void CircleLayer::setCircleStrokeColor(DataDrivenPropertyValue<Color> value) { + if (value == getCircleStrokeColor()) return; - impl->cascading.template get<CircleStrokeColor>().set(value, klass); - if (value.isDataDriven()) { - impl->observer->onLayerDataDrivenPaintPropertyChanged(*this); - } else { - impl->observer->onLayerPaintPropertyChanged(*this); - } + auto impl_ = mutableImpl(); + impl_->paint.template get<CircleStrokeColor>().value = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } -void CircleLayer::setCircleStrokeColorTransition(const TransitionOptions& value, const optional<std::string>& klass) { - impl->cascading.template get<CircleStrokeColor>().setTransition(value, klass); +void CircleLayer::setCircleStrokeColorTransition(const TransitionOptions& options) { + auto impl_ = mutableImpl(); + impl_->paint.template get<CircleStrokeColor>().options = options; + baseImpl = std::move(impl_); } -TransitionOptions CircleLayer::getCircleStrokeColorTransition(const optional<std::string>& klass) const { - return impl->cascading.template get<CircleStrokeColor>().getTransition(klass); +TransitionOptions CircleLayer::getCircleStrokeColorTransition() const { + return impl().paint.template get<CircleStrokeColor>().options; } DataDrivenPropertyValue<float> CircleLayer::getDefaultCircleStrokeOpacity() { return { 1 }; } -DataDrivenPropertyValue<float> CircleLayer::getCircleStrokeOpacity(const optional<std::string>& klass) const { - return impl->cascading.template get<CircleStrokeOpacity>().get(klass); +DataDrivenPropertyValue<float> CircleLayer::getCircleStrokeOpacity() const { + return impl().paint.template get<CircleStrokeOpacity>().value; } -void CircleLayer::setCircleStrokeOpacity(DataDrivenPropertyValue<float> value, const optional<std::string>& klass) { - if (value == getCircleStrokeOpacity(klass)) +void CircleLayer::setCircleStrokeOpacity(DataDrivenPropertyValue<float> value) { + if (value == getCircleStrokeOpacity()) return; - impl->cascading.template get<CircleStrokeOpacity>().set(value, klass); - if (value.isDataDriven()) { - impl->observer->onLayerDataDrivenPaintPropertyChanged(*this); - } else { - impl->observer->onLayerPaintPropertyChanged(*this); - } + auto impl_ = mutableImpl(); + impl_->paint.template get<CircleStrokeOpacity>().value = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } -void CircleLayer::setCircleStrokeOpacityTransition(const TransitionOptions& value, const optional<std::string>& klass) { - impl->cascading.template get<CircleStrokeOpacity>().setTransition(value, klass); +void CircleLayer::setCircleStrokeOpacityTransition(const TransitionOptions& options) { + auto impl_ = mutableImpl(); + impl_->paint.template get<CircleStrokeOpacity>().options = options; + baseImpl = std::move(impl_); } -TransitionOptions CircleLayer::getCircleStrokeOpacityTransition(const optional<std::string>& klass) const { - return impl->cascading.template get<CircleStrokeOpacity>().getTransition(klass); +TransitionOptions CircleLayer::getCircleStrokeOpacityTransition() const { + return impl().paint.template get<CircleStrokeOpacity>().options; } } // namespace style diff --git a/src/mbgl/style/layers/circle_layer_impl.cpp b/src/mbgl/style/layers/circle_layer_impl.cpp index 31b286f273..69f574cd6b 100644 --- a/src/mbgl/style/layers/circle_layer_impl.cpp +++ b/src/mbgl/style/layers/circle_layer_impl.cpp @@ -1,11 +1,14 @@ #include <mbgl/style/layers/circle_layer_impl.hpp> -#include <mbgl/renderer/render_circle_layer.hpp> namespace mbgl { namespace style { -std::unique_ptr<RenderLayer> CircleLayer::Impl::createRenderLayer() const { - return std::make_unique<RenderCircleLayer>(*this); +bool CircleLayer::Impl::hasLayoutDifference(const Layer::Impl& other) const { + assert(dynamic_cast<const CircleLayer::Impl*>(&other)); + const auto& impl = static_cast<const style::CircleLayer::Impl&>(other); + return filter != impl.filter || + visibility != impl.visibility || + paint.hasDataDrivenPropertyDifference(impl.paint); } } // namespace style diff --git a/src/mbgl/style/layers/circle_layer_impl.hpp b/src/mbgl/style/layers/circle_layer_impl.hpp index 886815f0d1..4b148cdc42 100644 --- a/src/mbgl/style/layers/circle_layer_impl.hpp +++ b/src/mbgl/style/layers/circle_layer_impl.hpp @@ -9,13 +9,12 @@ namespace style { class CircleLayer::Impl : public Layer::Impl { public: - std::unique_ptr<Layer> clone() const override; - std::unique_ptr<Layer> cloneRef(const std::string& id) const override; - void stringifyLayout(rapidjson::Writer<rapidjson::StringBuffer>&) const override; + using Layer::Impl::Impl; - std::unique_ptr<RenderLayer> createRenderLayer() const override; + bool hasLayoutDifference(const Layer::Impl&) const override; + void stringifyLayout(rapidjson::Writer<rapidjson::StringBuffer>&) const override; - CirclePaintProperties::Cascading cascading; + CirclePaintProperties::Transitionable paint; }; } // namespace style diff --git a/src/mbgl/style/layers/circle_layer_properties.hpp b/src/mbgl/style/layers/circle_layer_properties.hpp index 58206c61da..bc0c961e75 100644 --- a/src/mbgl/style/layers/circle_layer_properties.hpp +++ b/src/mbgl/style/layers/circle_layer_properties.hpp @@ -5,6 +5,7 @@ #include <mbgl/style/types.hpp> #include <mbgl/style/layout_property.hpp> #include <mbgl/style/paint_property.hpp> +#include <mbgl/style/properties.hpp> #include <mbgl/programs/attributes.hpp> #include <mbgl/programs/uniforms.hpp> @@ -39,6 +40,10 @@ struct CirclePitchScale : PaintProperty<CirclePitchScaleType> { static CirclePitchScaleType defaultValue() { return CirclePitchScaleType::Map; } }; +struct CirclePitchAlignment : PaintProperty<AlignmentType> { + static AlignmentType defaultValue() { return AlignmentType::Viewport; } +}; + struct CircleStrokeWidth : DataDrivenPaintProperty<float, attributes::a_stroke_width, uniforms::u_stroke_width> { static float defaultValue() { return 0; } }; @@ -51,7 +56,7 @@ struct CircleStrokeOpacity : DataDrivenPaintProperty<float, attributes::a_stroke static float defaultValue() { return 1; } }; -class CirclePaintProperties : public PaintProperties< +class CirclePaintProperties : public Properties< CircleRadius, CircleColor, CircleBlur, @@ -59,6 +64,7 @@ class CirclePaintProperties : public PaintProperties< CircleTranslate, CircleTranslateAnchor, CirclePitchScale, + CirclePitchAlignment, CircleStrokeWidth, CircleStrokeColor, CircleStrokeOpacity diff --git a/src/mbgl/style/layers/custom_layer.cpp b/src/mbgl/style/layers/custom_layer.cpp index cda8a157f0..854c771847 100644 --- a/src/mbgl/style/layers/custom_layer.cpp +++ b/src/mbgl/style/layers/custom_layer.cpp @@ -1,6 +1,6 @@ #include <mbgl/style/layers/custom_layer.hpp> #include <mbgl/style/layers/custom_layer_impl.hpp> -#include <mbgl/util/logging.hpp> +#include <mbgl/style/layer_observer.hpp> namespace mbgl { namespace style { @@ -8,23 +8,63 @@ namespace style { CustomLayer::CustomLayer(const std::string& layerID, CustomLayerInitializeFunction init, CustomLayerRenderFunction render, + CustomLayerContextLostFunction contextLost, CustomLayerDeinitializeFunction deinit, void* context) - : Layer(LayerType::Custom, std::make_unique<Impl>(layerID, init, render, deinit, context)) - , impl(static_cast<Impl*>(baseImpl.get())) { - Log::Info(Event::General, "New custom layer: %s", layerID.c_str()); + : Layer(makeMutable<Impl>(layerID, init, render, contextLost, deinit, context)) { } -CustomLayer::CustomLayer(const Impl& other) - : Layer(LayerType::Custom, std::make_unique<Impl>(other)) - , impl(static_cast<Impl*>(baseImpl.get())) { +CustomLayer::CustomLayer(const std::string& layerID, + CustomLayerInitializeFunction init, + CustomLayerRenderFunction render, + CustomLayerDeinitializeFunction deinit, + void* context) + : Layer(makeMutable<Impl>(layerID, init, render, nullptr, deinit, context)) { } CustomLayer::~CustomLayer() = default; +const CustomLayer::Impl& CustomLayer::impl() const { + return static_cast<const Impl&>(*baseImpl); +} + +Mutable<CustomLayer::Impl> CustomLayer::mutableImpl() const { + return makeMutable<Impl>(impl()); +} + +std::unique_ptr<Layer> CustomLayer::cloneRef(const std::string&) const { + assert(false); + return nullptr; +} + +// Visibility + +void CustomLayer::setVisibility(VisibilityType value) { + if (value == getVisibility()) + return; + auto impl_ = mutableImpl(); + impl_->visibility = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); +} + +// Zoom range + +void CustomLayer::setMinZoom(float minZoom) { + auto impl_ = mutableImpl(); + impl_->minZoom = minZoom; + baseImpl = std::move(impl_); +} + +void CustomLayer::setMaxZoom(float maxZoom) { + auto impl_ = mutableImpl(); + impl_->maxZoom = maxZoom; + baseImpl = std::move(impl_); +} + template <> bool Layer::is<CustomLayer>() const { - return type == LayerType::Custom; + return getType() == LayerType::Custom; } } // namespace style diff --git a/src/mbgl/style/layers/custom_layer_impl.cpp b/src/mbgl/style/layers/custom_layer_impl.cpp index 1d3e9af8d6..1de268d2e2 100644 --- a/src/mbgl/style/layers/custom_layer_impl.cpp +++ b/src/mbgl/style/layers/custom_layer_impl.cpp @@ -1,74 +1,28 @@ #include <mbgl/style/layers/custom_layer_impl.hpp> -#include <mbgl/renderer/render_custom_layer.hpp> -#include <mbgl/map/transform_state.hpp> -#include <mbgl/util/logging.hpp> + namespace mbgl { namespace style { -std::unique_ptr<RenderLayer> CustomLayer::Impl::createRenderLayer() const { - return std::make_unique<RenderCustomLayer>(*this); -} - CustomLayer::Impl::Impl(const std::string& id_, CustomLayerInitializeFunction initializeFn_, CustomLayerRenderFunction renderFn_, + CustomLayerContextLostFunction contextLostFn_, CustomLayerDeinitializeFunction deinitializeFn_, - void* context_) { - Log::Info(Event::General, "New custom layer Impl: %s", id_.c_str()); - id = id_; + void* context_) + : Layer::Impl(LayerType::Custom, id_, std::string()) { initializeFn = initializeFn_; renderFn = renderFn_; deinitializeFn = deinitializeFn_; + contextLostFn = contextLostFn_; context = context_; } -CustomLayer::Impl::Impl(const CustomLayer::Impl &other) - : Layer::Impl(other) { - id = other.id; - // Don't copy anything else. -} - -CustomLayer::Impl::~Impl() = default; - -std::unique_ptr<Layer> CustomLayer::Impl::clone() const { - return std::make_unique<CustomLayer>(*this); -} - -std::unique_ptr<Layer> CustomLayer::Impl::cloneRef(const std::string&) const { - assert(false); - return std::make_unique<CustomLayer>(*this); +bool CustomLayer::Impl::hasLayoutDifference(const Layer::Impl&) const { + return false; } void CustomLayer::Impl::stringifyLayout(rapidjson::Writer<rapidjson::StringBuffer>&) const { } -void CustomLayer::Impl::initialize() { - assert(initializeFn); - initializeFn(context); -} - -void CustomLayer::Impl::deinitialize() { - if (deinitializeFn) { - deinitializeFn(context); - } -} - -void CustomLayer::Impl::render(const TransformState& state) const { - assert(renderFn); - - CustomLayerRenderParameters parameters; - - parameters.width = state.getSize().width; - parameters.height = state.getSize().height; - parameters.latitude = state.getLatLng().latitude(); - parameters.longitude = state.getLatLng().longitude(); - parameters.zoom = state.getZoom(); - parameters.bearing = -state.getAngle() * util::RAD2DEG; - parameters.pitch = state.getPitch(); - parameters.fieldOfView = state.getFieldOfView(); - - renderFn(context, parameters); -} - } // namespace style } // namespace mbgl diff --git a/src/mbgl/style/layers/custom_layer_impl.hpp b/src/mbgl/style/layers/custom_layer_impl.hpp index e612d17f14..62efbbe15b 100644 --- a/src/mbgl/style/layers/custom_layer_impl.hpp +++ b/src/mbgl/style/layers/custom_layer_impl.hpp @@ -14,25 +14,16 @@ public: Impl(const std::string& id, CustomLayerInitializeFunction, CustomLayerRenderFunction, + CustomLayerContextLostFunction, CustomLayerDeinitializeFunction, void* context); - Impl(const Impl&); - ~Impl() final; - - void initialize(); - void deinitialize(); - void render(const TransformState&) const; - -private: - std::unique_ptr<Layer> clone() const override; - std::unique_ptr<Layer> cloneRef(const std::string& id) const override; + bool hasLayoutDifference(const Layer::Impl&) const override; void stringifyLayout(rapidjson::Writer<rapidjson::StringBuffer>&) const override; - std::unique_ptr<RenderLayer> createRenderLayer() const final; - CustomLayerInitializeFunction initializeFn = nullptr; CustomLayerRenderFunction renderFn = nullptr; + CustomLayerContextLostFunction contextLostFn = nullptr; CustomLayerDeinitializeFunction deinitializeFn = nullptr; void* context = nullptr; }; diff --git a/src/mbgl/style/layers/fill_extrusion_layer.cpp b/src/mbgl/style/layers/fill_extrusion_layer.cpp index 6f11d6052c..62f92cef75 100644 --- a/src/mbgl/style/layers/fill_extrusion_layer.cpp +++ b/src/mbgl/style/layers/fill_extrusion_layer.cpp @@ -2,34 +2,34 @@ #include <mbgl/style/layers/fill_extrusion_layer.hpp> #include <mbgl/style/layers/fill_extrusion_layer_impl.hpp> -#include <mbgl/style/conversion/stringify.hpp> +#include <mbgl/style/layer_observer.hpp> namespace mbgl { namespace style { FillExtrusionLayer::FillExtrusionLayer(const std::string& layerID, const std::string& sourceID) - : Layer(LayerType::FillExtrusion, std::make_unique<Impl>()) - , impl(static_cast<Impl*>(baseImpl.get())) { - impl->id = layerID; - impl->source = sourceID; + : Layer(makeMutable<Impl>(LayerType::FillExtrusion, layerID, sourceID)) { } -FillExtrusionLayer::FillExtrusionLayer(const Impl& other) - : Layer(LayerType::FillExtrusion, std::make_unique<Impl>(other)) - , impl(static_cast<Impl*>(baseImpl.get())) { +FillExtrusionLayer::FillExtrusionLayer(Immutable<Impl> impl_) + : Layer(std::move(impl_)) { } FillExtrusionLayer::~FillExtrusionLayer() = default; -std::unique_ptr<Layer> FillExtrusionLayer::Impl::clone() const { - return std::make_unique<FillExtrusionLayer>(*this); +const FillExtrusionLayer::Impl& FillExtrusionLayer::impl() const { + return static_cast<const Impl&>(*baseImpl); } -std::unique_ptr<Layer> FillExtrusionLayer::Impl::cloneRef(const std::string& id_) const { - auto result = std::make_unique<FillExtrusionLayer>(*this); - result->impl->id = id_; - result->impl->cascading = FillExtrusionPaintProperties::Cascading(); - return std::move(result); +Mutable<FillExtrusionLayer::Impl> FillExtrusionLayer::mutableImpl() const { + return makeMutable<Impl>(impl()); +} + +std::unique_ptr<Layer> FillExtrusionLayer::cloneRef(const std::string& id_) const { + auto impl_ = mutableImpl(); + impl_->id = id_; + impl_->paint = FillExtrusionPaintProperties::Transitionable(); + return std::make_unique<FillExtrusionLayer>(std::move(impl_)); } void FillExtrusionLayer::Impl::stringifyLayout(rapidjson::Writer<rapidjson::StringBuffer>&) const { @@ -38,26 +38,55 @@ void FillExtrusionLayer::Impl::stringifyLayout(rapidjson::Writer<rapidjson::Stri // Source const std::string& FillExtrusionLayer::getSourceID() const { - return impl->source; + return impl().source; } void FillExtrusionLayer::setSourceLayer(const std::string& sourceLayer) { - impl->sourceLayer = sourceLayer; + auto impl_ = mutableImpl(); + impl_->sourceLayer = sourceLayer; + baseImpl = std::move(impl_); } const std::string& FillExtrusionLayer::getSourceLayer() const { - return impl->sourceLayer; + return impl().sourceLayer; } // Filter void FillExtrusionLayer::setFilter(const Filter& filter) { - impl->filter = filter; - impl->observer->onLayerFilterChanged(*this); + auto impl_ = mutableImpl(); + impl_->filter = filter; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } const Filter& FillExtrusionLayer::getFilter() const { - return impl->filter; + return impl().filter; +} + +// Visibility + +void FillExtrusionLayer::setVisibility(VisibilityType value) { + if (value == getVisibility()) + return; + auto impl_ = mutableImpl(); + impl_->visibility = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); +} + +// Zoom range + +void FillExtrusionLayer::setMinZoom(float minZoom) { + auto impl_ = mutableImpl(); + impl_->minZoom = minZoom; + baseImpl = std::move(impl_); +} + +void FillExtrusionLayer::setMaxZoom(float maxZoom) { + auto impl_ = mutableImpl(); + impl_->maxZoom = maxZoom; + baseImpl = std::move(impl_); } // Layout properties @@ -69,173 +98,189 @@ PropertyValue<float> FillExtrusionLayer::getDefaultFillExtrusionOpacity() { return { 1 }; } -PropertyValue<float> FillExtrusionLayer::getFillExtrusionOpacity(const optional<std::string>& klass) const { - return impl->cascading.template get<FillExtrusionOpacity>().get(klass); +PropertyValue<float> FillExtrusionLayer::getFillExtrusionOpacity() const { + return impl().paint.template get<FillExtrusionOpacity>().value; } -void FillExtrusionLayer::setFillExtrusionOpacity(PropertyValue<float> value, const optional<std::string>& klass) { - if (value == getFillExtrusionOpacity(klass)) +void FillExtrusionLayer::setFillExtrusionOpacity(PropertyValue<float> value) { + if (value == getFillExtrusionOpacity()) return; - impl->cascading.template get<FillExtrusionOpacity>().set(value, klass); - impl->observer->onLayerPaintPropertyChanged(*this); + auto impl_ = mutableImpl(); + impl_->paint.template get<FillExtrusionOpacity>().value = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } -void FillExtrusionLayer::setFillExtrusionOpacityTransition(const TransitionOptions& value, const optional<std::string>& klass) { - impl->cascading.template get<FillExtrusionOpacity>().setTransition(value, klass); +void FillExtrusionLayer::setFillExtrusionOpacityTransition(const TransitionOptions& options) { + auto impl_ = mutableImpl(); + impl_->paint.template get<FillExtrusionOpacity>().options = options; + baseImpl = std::move(impl_); } -TransitionOptions FillExtrusionLayer::getFillExtrusionOpacityTransition(const optional<std::string>& klass) const { - return impl->cascading.template get<FillExtrusionOpacity>().getTransition(klass); +TransitionOptions FillExtrusionLayer::getFillExtrusionOpacityTransition() const { + return impl().paint.template get<FillExtrusionOpacity>().options; } DataDrivenPropertyValue<Color> FillExtrusionLayer::getDefaultFillExtrusionColor() { return { Color::black() }; } -DataDrivenPropertyValue<Color> FillExtrusionLayer::getFillExtrusionColor(const optional<std::string>& klass) const { - return impl->cascading.template get<FillExtrusionColor>().get(klass); +DataDrivenPropertyValue<Color> FillExtrusionLayer::getFillExtrusionColor() const { + return impl().paint.template get<FillExtrusionColor>().value; } -void FillExtrusionLayer::setFillExtrusionColor(DataDrivenPropertyValue<Color> value, const optional<std::string>& klass) { - if (value == getFillExtrusionColor(klass)) +void FillExtrusionLayer::setFillExtrusionColor(DataDrivenPropertyValue<Color> value) { + if (value == getFillExtrusionColor()) return; - impl->cascading.template get<FillExtrusionColor>().set(value, klass); - if (value.isDataDriven()) { - impl->observer->onLayerDataDrivenPaintPropertyChanged(*this); - } else { - impl->observer->onLayerPaintPropertyChanged(*this); - } + auto impl_ = mutableImpl(); + impl_->paint.template get<FillExtrusionColor>().value = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } -void FillExtrusionLayer::setFillExtrusionColorTransition(const TransitionOptions& value, const optional<std::string>& klass) { - impl->cascading.template get<FillExtrusionColor>().setTransition(value, klass); +void FillExtrusionLayer::setFillExtrusionColorTransition(const TransitionOptions& options) { + auto impl_ = mutableImpl(); + impl_->paint.template get<FillExtrusionColor>().options = options; + baseImpl = std::move(impl_); } -TransitionOptions FillExtrusionLayer::getFillExtrusionColorTransition(const optional<std::string>& klass) const { - return impl->cascading.template get<FillExtrusionColor>().getTransition(klass); +TransitionOptions FillExtrusionLayer::getFillExtrusionColorTransition() const { + return impl().paint.template get<FillExtrusionColor>().options; } PropertyValue<std::array<float, 2>> FillExtrusionLayer::getDefaultFillExtrusionTranslate() { return { {{ 0, 0 }} }; } -PropertyValue<std::array<float, 2>> FillExtrusionLayer::getFillExtrusionTranslate(const optional<std::string>& klass) const { - return impl->cascading.template get<FillExtrusionTranslate>().get(klass); +PropertyValue<std::array<float, 2>> FillExtrusionLayer::getFillExtrusionTranslate() const { + return impl().paint.template get<FillExtrusionTranslate>().value; } -void FillExtrusionLayer::setFillExtrusionTranslate(PropertyValue<std::array<float, 2>> value, const optional<std::string>& klass) { - if (value == getFillExtrusionTranslate(klass)) +void FillExtrusionLayer::setFillExtrusionTranslate(PropertyValue<std::array<float, 2>> value) { + if (value == getFillExtrusionTranslate()) return; - impl->cascading.template get<FillExtrusionTranslate>().set(value, klass); - impl->observer->onLayerPaintPropertyChanged(*this); + auto impl_ = mutableImpl(); + impl_->paint.template get<FillExtrusionTranslate>().value = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } -void FillExtrusionLayer::setFillExtrusionTranslateTransition(const TransitionOptions& value, const optional<std::string>& klass) { - impl->cascading.template get<FillExtrusionTranslate>().setTransition(value, klass); +void FillExtrusionLayer::setFillExtrusionTranslateTransition(const TransitionOptions& options) { + auto impl_ = mutableImpl(); + impl_->paint.template get<FillExtrusionTranslate>().options = options; + baseImpl = std::move(impl_); } -TransitionOptions FillExtrusionLayer::getFillExtrusionTranslateTransition(const optional<std::string>& klass) const { - return impl->cascading.template get<FillExtrusionTranslate>().getTransition(klass); +TransitionOptions FillExtrusionLayer::getFillExtrusionTranslateTransition() const { + return impl().paint.template get<FillExtrusionTranslate>().options; } PropertyValue<TranslateAnchorType> FillExtrusionLayer::getDefaultFillExtrusionTranslateAnchor() { return { TranslateAnchorType::Map }; } -PropertyValue<TranslateAnchorType> FillExtrusionLayer::getFillExtrusionTranslateAnchor(const optional<std::string>& klass) const { - return impl->cascading.template get<FillExtrusionTranslateAnchor>().get(klass); +PropertyValue<TranslateAnchorType> FillExtrusionLayer::getFillExtrusionTranslateAnchor() const { + return impl().paint.template get<FillExtrusionTranslateAnchor>().value; } -void FillExtrusionLayer::setFillExtrusionTranslateAnchor(PropertyValue<TranslateAnchorType> value, const optional<std::string>& klass) { - if (value == getFillExtrusionTranslateAnchor(klass)) +void FillExtrusionLayer::setFillExtrusionTranslateAnchor(PropertyValue<TranslateAnchorType> value) { + if (value == getFillExtrusionTranslateAnchor()) return; - impl->cascading.template get<FillExtrusionTranslateAnchor>().set(value, klass); - impl->observer->onLayerPaintPropertyChanged(*this); + auto impl_ = mutableImpl(); + impl_->paint.template get<FillExtrusionTranslateAnchor>().value = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } -void FillExtrusionLayer::setFillExtrusionTranslateAnchorTransition(const TransitionOptions& value, const optional<std::string>& klass) { - impl->cascading.template get<FillExtrusionTranslateAnchor>().setTransition(value, klass); +void FillExtrusionLayer::setFillExtrusionTranslateAnchorTransition(const TransitionOptions& options) { + auto impl_ = mutableImpl(); + impl_->paint.template get<FillExtrusionTranslateAnchor>().options = options; + baseImpl = std::move(impl_); } -TransitionOptions FillExtrusionLayer::getFillExtrusionTranslateAnchorTransition(const optional<std::string>& klass) const { - return impl->cascading.template get<FillExtrusionTranslateAnchor>().getTransition(klass); +TransitionOptions FillExtrusionLayer::getFillExtrusionTranslateAnchorTransition() const { + return impl().paint.template get<FillExtrusionTranslateAnchor>().options; } PropertyValue<std::string> FillExtrusionLayer::getDefaultFillExtrusionPattern() { return { "" }; } -PropertyValue<std::string> FillExtrusionLayer::getFillExtrusionPattern(const optional<std::string>& klass) const { - return impl->cascading.template get<FillExtrusionPattern>().get(klass); +PropertyValue<std::string> FillExtrusionLayer::getFillExtrusionPattern() const { + return impl().paint.template get<FillExtrusionPattern>().value; } -void FillExtrusionLayer::setFillExtrusionPattern(PropertyValue<std::string> value, const optional<std::string>& klass) { - if (value == getFillExtrusionPattern(klass)) +void FillExtrusionLayer::setFillExtrusionPattern(PropertyValue<std::string> value) { + if (value == getFillExtrusionPattern()) return; - impl->cascading.template get<FillExtrusionPattern>().set(value, klass); - impl->observer->onLayerPaintPropertyChanged(*this); + auto impl_ = mutableImpl(); + impl_->paint.template get<FillExtrusionPattern>().value = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } -void FillExtrusionLayer::setFillExtrusionPatternTransition(const TransitionOptions& value, const optional<std::string>& klass) { - impl->cascading.template get<FillExtrusionPattern>().setTransition(value, klass); +void FillExtrusionLayer::setFillExtrusionPatternTransition(const TransitionOptions& options) { + auto impl_ = mutableImpl(); + impl_->paint.template get<FillExtrusionPattern>().options = options; + baseImpl = std::move(impl_); } -TransitionOptions FillExtrusionLayer::getFillExtrusionPatternTransition(const optional<std::string>& klass) const { - return impl->cascading.template get<FillExtrusionPattern>().getTransition(klass); +TransitionOptions FillExtrusionLayer::getFillExtrusionPatternTransition() const { + return impl().paint.template get<FillExtrusionPattern>().options; } DataDrivenPropertyValue<float> FillExtrusionLayer::getDefaultFillExtrusionHeight() { return { 0 }; } -DataDrivenPropertyValue<float> FillExtrusionLayer::getFillExtrusionHeight(const optional<std::string>& klass) const { - return impl->cascading.template get<FillExtrusionHeight>().get(klass); +DataDrivenPropertyValue<float> FillExtrusionLayer::getFillExtrusionHeight() const { + return impl().paint.template get<FillExtrusionHeight>().value; } -void FillExtrusionLayer::setFillExtrusionHeight(DataDrivenPropertyValue<float> value, const optional<std::string>& klass) { - if (value == getFillExtrusionHeight(klass)) +void FillExtrusionLayer::setFillExtrusionHeight(DataDrivenPropertyValue<float> value) { + if (value == getFillExtrusionHeight()) return; - impl->cascading.template get<FillExtrusionHeight>().set(value, klass); - if (value.isDataDriven()) { - impl->observer->onLayerDataDrivenPaintPropertyChanged(*this); - } else { - impl->observer->onLayerPaintPropertyChanged(*this); - } + auto impl_ = mutableImpl(); + impl_->paint.template get<FillExtrusionHeight>().value = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } -void FillExtrusionLayer::setFillExtrusionHeightTransition(const TransitionOptions& value, const optional<std::string>& klass) { - impl->cascading.template get<FillExtrusionHeight>().setTransition(value, klass); +void FillExtrusionLayer::setFillExtrusionHeightTransition(const TransitionOptions& options) { + auto impl_ = mutableImpl(); + impl_->paint.template get<FillExtrusionHeight>().options = options; + baseImpl = std::move(impl_); } -TransitionOptions FillExtrusionLayer::getFillExtrusionHeightTransition(const optional<std::string>& klass) const { - return impl->cascading.template get<FillExtrusionHeight>().getTransition(klass); +TransitionOptions FillExtrusionLayer::getFillExtrusionHeightTransition() const { + return impl().paint.template get<FillExtrusionHeight>().options; } DataDrivenPropertyValue<float> FillExtrusionLayer::getDefaultFillExtrusionBase() { return { 0 }; } -DataDrivenPropertyValue<float> FillExtrusionLayer::getFillExtrusionBase(const optional<std::string>& klass) const { - return impl->cascading.template get<FillExtrusionBase>().get(klass); +DataDrivenPropertyValue<float> FillExtrusionLayer::getFillExtrusionBase() const { + return impl().paint.template get<FillExtrusionBase>().value; } -void FillExtrusionLayer::setFillExtrusionBase(DataDrivenPropertyValue<float> value, const optional<std::string>& klass) { - if (value == getFillExtrusionBase(klass)) +void FillExtrusionLayer::setFillExtrusionBase(DataDrivenPropertyValue<float> value) { + if (value == getFillExtrusionBase()) return; - impl->cascading.template get<FillExtrusionBase>().set(value, klass); - if (value.isDataDriven()) { - impl->observer->onLayerDataDrivenPaintPropertyChanged(*this); - } else { - impl->observer->onLayerPaintPropertyChanged(*this); - } + auto impl_ = mutableImpl(); + impl_->paint.template get<FillExtrusionBase>().value = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } -void FillExtrusionLayer::setFillExtrusionBaseTransition(const TransitionOptions& value, const optional<std::string>& klass) { - impl->cascading.template get<FillExtrusionBase>().setTransition(value, klass); +void FillExtrusionLayer::setFillExtrusionBaseTransition(const TransitionOptions& options) { + auto impl_ = mutableImpl(); + impl_->paint.template get<FillExtrusionBase>().options = options; + baseImpl = std::move(impl_); } -TransitionOptions FillExtrusionLayer::getFillExtrusionBaseTransition(const optional<std::string>& klass) const { - return impl->cascading.template get<FillExtrusionBase>().getTransition(klass); +TransitionOptions FillExtrusionLayer::getFillExtrusionBaseTransition() const { + return impl().paint.template get<FillExtrusionBase>().options; } } // namespace style diff --git a/src/mbgl/style/layers/fill_extrusion_layer_impl.cpp b/src/mbgl/style/layers/fill_extrusion_layer_impl.cpp index 5340541221..d37c2ad29b 100644 --- a/src/mbgl/style/layers/fill_extrusion_layer_impl.cpp +++ b/src/mbgl/style/layers/fill_extrusion_layer_impl.cpp @@ -1,11 +1,14 @@ #include <mbgl/style/layers/fill_extrusion_layer_impl.hpp> -#include <mbgl/renderer/render_fill_extrusion_layer.hpp> namespace mbgl { namespace style { -std::unique_ptr<RenderLayer> FillExtrusionLayer::Impl::createRenderLayer() const { - return std::make_unique<RenderFillExtrusionLayer>(*this); +bool FillExtrusionLayer::Impl::hasLayoutDifference(const Layer::Impl& other) const { + assert(dynamic_cast<const FillExtrusionLayer::Impl*>(&other)); + const auto& impl = static_cast<const style::FillExtrusionLayer::Impl&>(other); + return filter != impl.filter || + visibility != impl.visibility || + paint.hasDataDrivenPropertyDifference(impl.paint); } } // namespace style diff --git a/src/mbgl/style/layers/fill_extrusion_layer_impl.hpp b/src/mbgl/style/layers/fill_extrusion_layer_impl.hpp index 2353bd99fe..9abc6fc4b3 100644 --- a/src/mbgl/style/layers/fill_extrusion_layer_impl.hpp +++ b/src/mbgl/style/layers/fill_extrusion_layer_impl.hpp @@ -9,13 +9,12 @@ namespace style { class FillExtrusionLayer::Impl : public Layer::Impl { public: - std::unique_ptr<Layer> clone() const override; - std::unique_ptr<Layer> cloneRef(const std::string& id) const override; - void stringifyLayout(rapidjson::Writer<rapidjson::StringBuffer>&) const override; + using Layer::Impl::Impl; - std::unique_ptr<RenderLayer> createRenderLayer() const override; + bool hasLayoutDifference(const Layer::Impl&) const override; + void stringifyLayout(rapidjson::Writer<rapidjson::StringBuffer>&) const override; - FillExtrusionPaintProperties::Cascading cascading; + FillExtrusionPaintProperties::Transitionable paint; }; } // namespace style diff --git a/src/mbgl/style/layers/fill_extrusion_layer_properties.hpp b/src/mbgl/style/layers/fill_extrusion_layer_properties.hpp index f41ce68b94..19be59a2fe 100644 --- a/src/mbgl/style/layers/fill_extrusion_layer_properties.hpp +++ b/src/mbgl/style/layers/fill_extrusion_layer_properties.hpp @@ -5,6 +5,7 @@ #include <mbgl/style/types.hpp> #include <mbgl/style/layout_property.hpp> #include <mbgl/style/paint_property.hpp> +#include <mbgl/style/properties.hpp> #include <mbgl/programs/attributes.hpp> #include <mbgl/programs/uniforms.hpp> @@ -39,7 +40,7 @@ struct FillExtrusionBase : DataDrivenPaintProperty<float, attributes::a_base, un static float defaultValue() { return 0; } }; -class FillExtrusionPaintProperties : public PaintProperties< +class FillExtrusionPaintProperties : public Properties< FillExtrusionOpacity, FillExtrusionColor, FillExtrusionTranslate, diff --git a/src/mbgl/style/layers/fill_layer.cpp b/src/mbgl/style/layers/fill_layer.cpp index 9fd9d33af3..65975752db 100644 --- a/src/mbgl/style/layers/fill_layer.cpp +++ b/src/mbgl/style/layers/fill_layer.cpp @@ -2,34 +2,34 @@ #include <mbgl/style/layers/fill_layer.hpp> #include <mbgl/style/layers/fill_layer_impl.hpp> -#include <mbgl/style/conversion/stringify.hpp> +#include <mbgl/style/layer_observer.hpp> namespace mbgl { namespace style { FillLayer::FillLayer(const std::string& layerID, const std::string& sourceID) - : Layer(LayerType::Fill, std::make_unique<Impl>()) - , impl(static_cast<Impl*>(baseImpl.get())) { - impl->id = layerID; - impl->source = sourceID; + : Layer(makeMutable<Impl>(LayerType::Fill, layerID, sourceID)) { } -FillLayer::FillLayer(const Impl& other) - : Layer(LayerType::Fill, std::make_unique<Impl>(other)) - , impl(static_cast<Impl*>(baseImpl.get())) { +FillLayer::FillLayer(Immutable<Impl> impl_) + : Layer(std::move(impl_)) { } FillLayer::~FillLayer() = default; -std::unique_ptr<Layer> FillLayer::Impl::clone() const { - return std::make_unique<FillLayer>(*this); +const FillLayer::Impl& FillLayer::impl() const { + return static_cast<const Impl&>(*baseImpl); } -std::unique_ptr<Layer> FillLayer::Impl::cloneRef(const std::string& id_) const { - auto result = std::make_unique<FillLayer>(*this); - result->impl->id = id_; - result->impl->cascading = FillPaintProperties::Cascading(); - return std::move(result); +Mutable<FillLayer::Impl> FillLayer::mutableImpl() const { + return makeMutable<Impl>(impl()); +} + +std::unique_ptr<Layer> FillLayer::cloneRef(const std::string& id_) const { + auto impl_ = mutableImpl(); + impl_->id = id_; + impl_->paint = FillPaintProperties::Transitionable(); + return std::make_unique<FillLayer>(std::move(impl_)); } void FillLayer::Impl::stringifyLayout(rapidjson::Writer<rapidjson::StringBuffer>&) const { @@ -38,26 +38,55 @@ void FillLayer::Impl::stringifyLayout(rapidjson::Writer<rapidjson::StringBuffer> // Source const std::string& FillLayer::getSourceID() const { - return impl->source; + return impl().source; } void FillLayer::setSourceLayer(const std::string& sourceLayer) { - impl->sourceLayer = sourceLayer; + auto impl_ = mutableImpl(); + impl_->sourceLayer = sourceLayer; + baseImpl = std::move(impl_); } const std::string& FillLayer::getSourceLayer() const { - return impl->sourceLayer; + return impl().sourceLayer; } // Filter void FillLayer::setFilter(const Filter& filter) { - impl->filter = filter; - impl->observer->onLayerFilterChanged(*this); + auto impl_ = mutableImpl(); + impl_->filter = filter; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } const Filter& FillLayer::getFilter() const { - return impl->filter; + return impl().filter; +} + +// Visibility + +void FillLayer::setVisibility(VisibilityType value) { + if (value == getVisibility()) + return; + auto impl_ = mutableImpl(); + impl_->visibility = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); +} + +// Zoom range + +void FillLayer::setMinZoom(float minZoom) { + auto impl_ = mutableImpl(); + impl_->minZoom = minZoom; + baseImpl = std::move(impl_); +} + +void FillLayer::setMaxZoom(float maxZoom) { + auto impl_ = mutableImpl(); + impl_->maxZoom = maxZoom; + baseImpl = std::move(impl_); } // Layout properties @@ -69,173 +98,189 @@ PropertyValue<bool> FillLayer::getDefaultFillAntialias() { return { true }; } -PropertyValue<bool> FillLayer::getFillAntialias(const optional<std::string>& klass) const { - return impl->cascading.template get<FillAntialias>().get(klass); +PropertyValue<bool> FillLayer::getFillAntialias() const { + return impl().paint.template get<FillAntialias>().value; } -void FillLayer::setFillAntialias(PropertyValue<bool> value, const optional<std::string>& klass) { - if (value == getFillAntialias(klass)) +void FillLayer::setFillAntialias(PropertyValue<bool> value) { + if (value == getFillAntialias()) return; - impl->cascading.template get<FillAntialias>().set(value, klass); - impl->observer->onLayerPaintPropertyChanged(*this); + auto impl_ = mutableImpl(); + impl_->paint.template get<FillAntialias>().value = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } -void FillLayer::setFillAntialiasTransition(const TransitionOptions& value, const optional<std::string>& klass) { - impl->cascading.template get<FillAntialias>().setTransition(value, klass); +void FillLayer::setFillAntialiasTransition(const TransitionOptions& options) { + auto impl_ = mutableImpl(); + impl_->paint.template get<FillAntialias>().options = options; + baseImpl = std::move(impl_); } -TransitionOptions FillLayer::getFillAntialiasTransition(const optional<std::string>& klass) const { - return impl->cascading.template get<FillAntialias>().getTransition(klass); +TransitionOptions FillLayer::getFillAntialiasTransition() const { + return impl().paint.template get<FillAntialias>().options; } DataDrivenPropertyValue<float> FillLayer::getDefaultFillOpacity() { return { 1 }; } -DataDrivenPropertyValue<float> FillLayer::getFillOpacity(const optional<std::string>& klass) const { - return impl->cascading.template get<FillOpacity>().get(klass); +DataDrivenPropertyValue<float> FillLayer::getFillOpacity() const { + return impl().paint.template get<FillOpacity>().value; } -void FillLayer::setFillOpacity(DataDrivenPropertyValue<float> value, const optional<std::string>& klass) { - if (value == getFillOpacity(klass)) +void FillLayer::setFillOpacity(DataDrivenPropertyValue<float> value) { + if (value == getFillOpacity()) return; - impl->cascading.template get<FillOpacity>().set(value, klass); - if (value.isDataDriven()) { - impl->observer->onLayerDataDrivenPaintPropertyChanged(*this); - } else { - impl->observer->onLayerPaintPropertyChanged(*this); - } + auto impl_ = mutableImpl(); + impl_->paint.template get<FillOpacity>().value = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } -void FillLayer::setFillOpacityTransition(const TransitionOptions& value, const optional<std::string>& klass) { - impl->cascading.template get<FillOpacity>().setTransition(value, klass); +void FillLayer::setFillOpacityTransition(const TransitionOptions& options) { + auto impl_ = mutableImpl(); + impl_->paint.template get<FillOpacity>().options = options; + baseImpl = std::move(impl_); } -TransitionOptions FillLayer::getFillOpacityTransition(const optional<std::string>& klass) const { - return impl->cascading.template get<FillOpacity>().getTransition(klass); +TransitionOptions FillLayer::getFillOpacityTransition() const { + return impl().paint.template get<FillOpacity>().options; } DataDrivenPropertyValue<Color> FillLayer::getDefaultFillColor() { return { Color::black() }; } -DataDrivenPropertyValue<Color> FillLayer::getFillColor(const optional<std::string>& klass) const { - return impl->cascading.template get<FillColor>().get(klass); +DataDrivenPropertyValue<Color> FillLayer::getFillColor() const { + return impl().paint.template get<FillColor>().value; } -void FillLayer::setFillColor(DataDrivenPropertyValue<Color> value, const optional<std::string>& klass) { - if (value == getFillColor(klass)) +void FillLayer::setFillColor(DataDrivenPropertyValue<Color> value) { + if (value == getFillColor()) return; - impl->cascading.template get<FillColor>().set(value, klass); - if (value.isDataDriven()) { - impl->observer->onLayerDataDrivenPaintPropertyChanged(*this); - } else { - impl->observer->onLayerPaintPropertyChanged(*this); - } + auto impl_ = mutableImpl(); + impl_->paint.template get<FillColor>().value = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } -void FillLayer::setFillColorTransition(const TransitionOptions& value, const optional<std::string>& klass) { - impl->cascading.template get<FillColor>().setTransition(value, klass); +void FillLayer::setFillColorTransition(const TransitionOptions& options) { + auto impl_ = mutableImpl(); + impl_->paint.template get<FillColor>().options = options; + baseImpl = std::move(impl_); } -TransitionOptions FillLayer::getFillColorTransition(const optional<std::string>& klass) const { - return impl->cascading.template get<FillColor>().getTransition(klass); +TransitionOptions FillLayer::getFillColorTransition() const { + return impl().paint.template get<FillColor>().options; } DataDrivenPropertyValue<Color> FillLayer::getDefaultFillOutlineColor() { return { {} }; } -DataDrivenPropertyValue<Color> FillLayer::getFillOutlineColor(const optional<std::string>& klass) const { - return impl->cascading.template get<FillOutlineColor>().get(klass); +DataDrivenPropertyValue<Color> FillLayer::getFillOutlineColor() const { + return impl().paint.template get<FillOutlineColor>().value; } -void FillLayer::setFillOutlineColor(DataDrivenPropertyValue<Color> value, const optional<std::string>& klass) { - if (value == getFillOutlineColor(klass)) +void FillLayer::setFillOutlineColor(DataDrivenPropertyValue<Color> value) { + if (value == getFillOutlineColor()) return; - impl->cascading.template get<FillOutlineColor>().set(value, klass); - if (value.isDataDriven()) { - impl->observer->onLayerDataDrivenPaintPropertyChanged(*this); - } else { - impl->observer->onLayerPaintPropertyChanged(*this); - } + auto impl_ = mutableImpl(); + impl_->paint.template get<FillOutlineColor>().value = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } -void FillLayer::setFillOutlineColorTransition(const TransitionOptions& value, const optional<std::string>& klass) { - impl->cascading.template get<FillOutlineColor>().setTransition(value, klass); +void FillLayer::setFillOutlineColorTransition(const TransitionOptions& options) { + auto impl_ = mutableImpl(); + impl_->paint.template get<FillOutlineColor>().options = options; + baseImpl = std::move(impl_); } -TransitionOptions FillLayer::getFillOutlineColorTransition(const optional<std::string>& klass) const { - return impl->cascading.template get<FillOutlineColor>().getTransition(klass); +TransitionOptions FillLayer::getFillOutlineColorTransition() const { + return impl().paint.template get<FillOutlineColor>().options; } PropertyValue<std::array<float, 2>> FillLayer::getDefaultFillTranslate() { return { {{ 0, 0 }} }; } -PropertyValue<std::array<float, 2>> FillLayer::getFillTranslate(const optional<std::string>& klass) const { - return impl->cascading.template get<FillTranslate>().get(klass); +PropertyValue<std::array<float, 2>> FillLayer::getFillTranslate() const { + return impl().paint.template get<FillTranslate>().value; } -void FillLayer::setFillTranslate(PropertyValue<std::array<float, 2>> value, const optional<std::string>& klass) { - if (value == getFillTranslate(klass)) +void FillLayer::setFillTranslate(PropertyValue<std::array<float, 2>> value) { + if (value == getFillTranslate()) return; - impl->cascading.template get<FillTranslate>().set(value, klass); - impl->observer->onLayerPaintPropertyChanged(*this); + auto impl_ = mutableImpl(); + impl_->paint.template get<FillTranslate>().value = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } -void FillLayer::setFillTranslateTransition(const TransitionOptions& value, const optional<std::string>& klass) { - impl->cascading.template get<FillTranslate>().setTransition(value, klass); +void FillLayer::setFillTranslateTransition(const TransitionOptions& options) { + auto impl_ = mutableImpl(); + impl_->paint.template get<FillTranslate>().options = options; + baseImpl = std::move(impl_); } -TransitionOptions FillLayer::getFillTranslateTransition(const optional<std::string>& klass) const { - return impl->cascading.template get<FillTranslate>().getTransition(klass); +TransitionOptions FillLayer::getFillTranslateTransition() const { + return impl().paint.template get<FillTranslate>().options; } PropertyValue<TranslateAnchorType> FillLayer::getDefaultFillTranslateAnchor() { return { TranslateAnchorType::Map }; } -PropertyValue<TranslateAnchorType> FillLayer::getFillTranslateAnchor(const optional<std::string>& klass) const { - return impl->cascading.template get<FillTranslateAnchor>().get(klass); +PropertyValue<TranslateAnchorType> FillLayer::getFillTranslateAnchor() const { + return impl().paint.template get<FillTranslateAnchor>().value; } -void FillLayer::setFillTranslateAnchor(PropertyValue<TranslateAnchorType> value, const optional<std::string>& klass) { - if (value == getFillTranslateAnchor(klass)) +void FillLayer::setFillTranslateAnchor(PropertyValue<TranslateAnchorType> value) { + if (value == getFillTranslateAnchor()) return; - impl->cascading.template get<FillTranslateAnchor>().set(value, klass); - impl->observer->onLayerPaintPropertyChanged(*this); + auto impl_ = mutableImpl(); + impl_->paint.template get<FillTranslateAnchor>().value = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } -void FillLayer::setFillTranslateAnchorTransition(const TransitionOptions& value, const optional<std::string>& klass) { - impl->cascading.template get<FillTranslateAnchor>().setTransition(value, klass); +void FillLayer::setFillTranslateAnchorTransition(const TransitionOptions& options) { + auto impl_ = mutableImpl(); + impl_->paint.template get<FillTranslateAnchor>().options = options; + baseImpl = std::move(impl_); } -TransitionOptions FillLayer::getFillTranslateAnchorTransition(const optional<std::string>& klass) const { - return impl->cascading.template get<FillTranslateAnchor>().getTransition(klass); +TransitionOptions FillLayer::getFillTranslateAnchorTransition() const { + return impl().paint.template get<FillTranslateAnchor>().options; } PropertyValue<std::string> FillLayer::getDefaultFillPattern() { return { "" }; } -PropertyValue<std::string> FillLayer::getFillPattern(const optional<std::string>& klass) const { - return impl->cascading.template get<FillPattern>().get(klass); +PropertyValue<std::string> FillLayer::getFillPattern() const { + return impl().paint.template get<FillPattern>().value; } -void FillLayer::setFillPattern(PropertyValue<std::string> value, const optional<std::string>& klass) { - if (value == getFillPattern(klass)) +void FillLayer::setFillPattern(PropertyValue<std::string> value) { + if (value == getFillPattern()) return; - impl->cascading.template get<FillPattern>().set(value, klass); - impl->observer->onLayerPaintPropertyChanged(*this); + auto impl_ = mutableImpl(); + impl_->paint.template get<FillPattern>().value = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } -void FillLayer::setFillPatternTransition(const TransitionOptions& value, const optional<std::string>& klass) { - impl->cascading.template get<FillPattern>().setTransition(value, klass); +void FillLayer::setFillPatternTransition(const TransitionOptions& options) { + auto impl_ = mutableImpl(); + impl_->paint.template get<FillPattern>().options = options; + baseImpl = std::move(impl_); } -TransitionOptions FillLayer::getFillPatternTransition(const optional<std::string>& klass) const { - return impl->cascading.template get<FillPattern>().getTransition(klass); +TransitionOptions FillLayer::getFillPatternTransition() const { + return impl().paint.template get<FillPattern>().options; } } // namespace style diff --git a/src/mbgl/style/layers/fill_layer_impl.cpp b/src/mbgl/style/layers/fill_layer_impl.cpp index 6ec55a58e3..0dc7ed14d5 100644 --- a/src/mbgl/style/layers/fill_layer_impl.cpp +++ b/src/mbgl/style/layers/fill_layer_impl.cpp @@ -1,11 +1,14 @@ #include <mbgl/style/layers/fill_layer_impl.hpp> -#include <mbgl/renderer/render_fill_layer.hpp> namespace mbgl { namespace style { -std::unique_ptr<RenderLayer> FillLayer::Impl::createRenderLayer() const { - return std::make_unique<RenderFillLayer>(*this); +bool FillLayer::Impl::hasLayoutDifference(const Layer::Impl& other) const { + assert(dynamic_cast<const FillLayer::Impl*>(&other)); + const auto& impl = static_cast<const style::FillLayer::Impl&>(other); + return filter != impl.filter || + visibility != impl.visibility || + paint.hasDataDrivenPropertyDifference(impl.paint); } } // namespace style diff --git a/src/mbgl/style/layers/fill_layer_impl.hpp b/src/mbgl/style/layers/fill_layer_impl.hpp index 215558962e..2673cd7443 100644 --- a/src/mbgl/style/layers/fill_layer_impl.hpp +++ b/src/mbgl/style/layers/fill_layer_impl.hpp @@ -9,13 +9,12 @@ namespace style { class FillLayer::Impl : public Layer::Impl { public: - std::unique_ptr<Layer> clone() const override; - std::unique_ptr<Layer> cloneRef(const std::string& id) const override; - void stringifyLayout(rapidjson::Writer<rapidjson::StringBuffer>&) const override; + using Layer::Impl::Impl; - std::unique_ptr<RenderLayer> createRenderLayer() const override; + bool hasLayoutDifference(const Layer::Impl&) const override; + void stringifyLayout(rapidjson::Writer<rapidjson::StringBuffer>&) const override; - FillPaintProperties::Cascading cascading; + FillPaintProperties::Transitionable paint; }; } // namespace style diff --git a/src/mbgl/style/layers/fill_layer_properties.hpp b/src/mbgl/style/layers/fill_layer_properties.hpp index ee1e5158ce..cb01194515 100644 --- a/src/mbgl/style/layers/fill_layer_properties.hpp +++ b/src/mbgl/style/layers/fill_layer_properties.hpp @@ -5,6 +5,7 @@ #include <mbgl/style/types.hpp> #include <mbgl/style/layout_property.hpp> #include <mbgl/style/paint_property.hpp> +#include <mbgl/style/properties.hpp> #include <mbgl/programs/attributes.hpp> #include <mbgl/programs/uniforms.hpp> @@ -39,7 +40,7 @@ struct FillPattern : CrossFadedPaintProperty<std::string> { static std::string defaultValue() { return ""; } }; -class FillPaintProperties : public PaintProperties< +class FillPaintProperties : public Properties< FillAntialias, FillOpacity, FillColor, diff --git a/src/mbgl/style/layers/layer.cpp.ejs b/src/mbgl/style/layers/layer.cpp.ejs index 2f690c3158..573aabda8b 100644 --- a/src/mbgl/style/layers/layer.cpp.ejs +++ b/src/mbgl/style/layers/layer.cpp.ejs @@ -7,47 +7,45 @@ #include <mbgl/style/layers/<%- type.replace('-', '_') %>_layer.hpp> #include <mbgl/style/layers/<%- type.replace('-', '_') %>_layer_impl.hpp> -#include <mbgl/style/conversion/stringify.hpp> +#include <mbgl/style/layer_observer.hpp> namespace mbgl { namespace style { <% if (type === 'background') { -%> <%- camelize(type) %>Layer::<%- camelize(type) %>Layer(const std::string& layerID) - : Layer(LayerType::<%- camelize(type) %>, std::make_unique<Impl>()) - , impl(static_cast<Impl*>(baseImpl.get())) { - impl->id = layerID; + : Layer(makeMutable<Impl>(LayerType::<%- camelize(type) %>, layerID, std::string())) { } <% } else { -%> <%- camelize(type) %>Layer::<%- camelize(type) %>Layer(const std::string& layerID, const std::string& sourceID) - : Layer(LayerType::<%- camelize(type) %>, std::make_unique<Impl>()) - , impl(static_cast<Impl*>(baseImpl.get())) { - impl->id = layerID; - impl->source = sourceID; + : Layer(makeMutable<Impl>(LayerType::<%- camelize(type) %>, layerID, sourceID)) { } <% } -%> -<%- camelize(type) %>Layer::<%- camelize(type) %>Layer(const Impl& other) - : Layer(LayerType::<%- camelize(type) %>, std::make_unique<Impl>(other)) - , impl(static_cast<Impl*>(baseImpl.get())) { +<%- camelize(type) %>Layer::<%- camelize(type) %>Layer(Immutable<Impl> impl_) + : Layer(std::move(impl_)) { } <%- camelize(type) %>Layer::~<%- camelize(type) %>Layer() = default; -std::unique_ptr<Layer> <%- camelize(type) %>Layer::Impl::clone() const { - return std::make_unique<<%- camelize(type) %>Layer>(*this); +const <%- camelize(type) %>Layer::Impl& <%- camelize(type) %>Layer::impl() const { + return static_cast<const Impl&>(*baseImpl); } -std::unique_ptr<Layer> <%- camelize(type) %>Layer::Impl::cloneRef(const std::string& id_) const { - auto result = std::make_unique<<%- camelize(type) %>Layer>(*this); - result->impl->id = id_; - result->impl->cascading = <%- camelize(type) %>PaintProperties::Cascading(); - return std::move(result); +Mutable<<%- camelize(type) %>Layer::Impl> <%- camelize(type) %>Layer::mutableImpl() const { + return makeMutable<Impl>(impl()); +} + +std::unique_ptr<Layer> <%- camelize(type) %>Layer::cloneRef(const std::string& id_) const { + auto impl_ = mutableImpl(); + impl_->id = id_; + impl_->paint = <%- camelize(type) %>PaintProperties::Transitionable(); + return std::make_unique<<%- camelize(type) %>Layer>(std::move(impl_)); } <% if (layoutProperties.length) { -%> void <%- camelize(type) %>Layer::Impl::stringifyLayout(rapidjson::Writer<rapidjson::StringBuffer>& writer) const { - conversion::stringify(writer, layout); + layout.stringify(writer); } <% } else { -%> void <%- camelize(type) %>Layer::Impl::stringifyLayout(rapidjson::Writer<rapidjson::StringBuffer>&) const { @@ -58,31 +56,60 @@ void <%- camelize(type) %>Layer::Impl::stringifyLayout(rapidjson::Writer<rapidjs // Source const std::string& <%- camelize(type) %>Layer::getSourceID() const { - return impl->source; + return impl().source; } <% if (type !== 'raster') { -%> void <%- camelize(type) %>Layer::setSourceLayer(const std::string& sourceLayer) { - impl->sourceLayer = sourceLayer; + auto impl_ = mutableImpl(); + impl_->sourceLayer = sourceLayer; + baseImpl = std::move(impl_); } const std::string& <%- camelize(type) %>Layer::getSourceLayer() const { - return impl->sourceLayer; + return impl().sourceLayer; } // Filter void <%- camelize(type) %>Layer::setFilter(const Filter& filter) { - impl->filter = filter; - impl->observer->onLayerFilterChanged(*this); + auto impl_ = mutableImpl(); + impl_->filter = filter; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } const Filter& <%- camelize(type) %>Layer::getFilter() const { - return impl->filter; + return impl().filter; } <% } -%> <% } -%> +// Visibility + +void <%- camelize(type) %>Layer::setVisibility(VisibilityType value) { + if (value == getVisibility()) + return; + auto impl_ = mutableImpl(); + impl_->visibility = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); +} + +// Zoom range + +void <%- camelize(type) %>Layer::setMinZoom(float minZoom) { + auto impl_ = mutableImpl(); + impl_->minZoom = minZoom; + baseImpl = std::move(impl_); +} + +void <%- camelize(type) %>Layer::setMaxZoom(float maxZoom) { + auto impl_ = mutableImpl(); + impl_->maxZoom = maxZoom; + baseImpl = std::move(impl_); +} + // Layout properties <% for (const property of layoutProperties) { -%> @@ -91,14 +118,16 @@ const Filter& <%- camelize(type) %>Layer::getFilter() const { } <%- propertyValueType(property) %> <%- camelize(type) %>Layer::get<%- camelize(property.name) %>() const { - return impl->layout.unevaluated.get<<%- camelize(property.name) %>>(); + return impl().layout.get<<%- camelize(property.name) %>>(); } void <%- camelize(type) %>Layer::set<%- camelize(property.name) %>(<%- propertyValueType(property) %> value) { if (value == get<%- camelize(property.name) %>()) return; - impl->layout.unevaluated.get<<%- camelize(property.name) %>>() = value; - impl->observer->onLayerLayoutPropertyChanged(*this, "<%- property.name %>"); + auto impl_ = mutableImpl(); + impl_->layout.get<<%- camelize(property.name) %>>() = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } <% } -%> @@ -108,31 +137,27 @@ void <%- camelize(type) %>Layer::set<%- camelize(property.name) %>(<%- propertyV return { <%- defaultValue(property) %> }; } -<%- propertyValueType(property) %> <%- camelize(type) %>Layer::get<%- camelize(property.name) %>(const optional<std::string>& klass) const { - return impl->cascading.template get<<%- camelize(property.name) %>>().get(klass); +<%- propertyValueType(property) %> <%- camelize(type) %>Layer::get<%- camelize(property.name) %>() const { + return impl().paint.template get<<%- camelize(property.name) %>>().value; } -void <%- camelize(type) %>Layer::set<%- camelize(property.name) %>(<%- propertyValueType(property) %> value, const optional<std::string>& klass) { - if (value == get<%- camelize(property.name) %>(klass)) +void <%- camelize(type) %>Layer::set<%- camelize(property.name) %>(<%- propertyValueType(property) %> value) { + if (value == get<%- camelize(property.name) %>()) return; - impl->cascading.template get<<%- camelize(property.name) %>>().set(value, klass); -<% if (isDataDriven(property)) { -%> - if (value.isDataDriven()) { - impl->observer->onLayerDataDrivenPaintPropertyChanged(*this); - } else { - impl->observer->onLayerPaintPropertyChanged(*this); - } -<% } else { -%> - impl->observer->onLayerPaintPropertyChanged(*this); -<% } -%> + auto impl_ = mutableImpl(); + impl_->paint.template get<<%- camelize(property.name) %>>().value = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } -void <%- camelize(type) %>Layer::set<%- camelize(property.name) %>Transition(const TransitionOptions& value, const optional<std::string>& klass) { - impl->cascading.template get<<%- camelize(property.name) %>>().setTransition(value, klass); +void <%- camelize(type) %>Layer::set<%- camelize(property.name) %>Transition(const TransitionOptions& options) { + auto impl_ = mutableImpl(); + impl_->paint.template get<<%- camelize(property.name) %>>().options = options; + baseImpl = std::move(impl_); } -TransitionOptions <%- camelize(type) %>Layer::get<%- camelize(property.name) %>Transition(const optional<std::string>& klass) const { - return impl->cascading.template get<<%- camelize(property.name) %>>().getTransition(klass); +TransitionOptions <%- camelize(type) %>Layer::get<%- camelize(property.name) %>Transition() const { + return impl().paint.template get<<%- camelize(property.name) %>>().options; } <% } -%> diff --git a/src/mbgl/style/layers/layer_properties.hpp.ejs b/src/mbgl/style/layers/layer_properties.hpp.ejs index 2a736ca388..cde1b80b7b 100644 --- a/src/mbgl/style/layers/layer_properties.hpp.ejs +++ b/src/mbgl/style/layers/layer_properties.hpp.ejs @@ -10,7 +10,9 @@ #include <mbgl/style/types.hpp> #include <mbgl/style/layout_property.hpp> #include <mbgl/style/paint_property.hpp> +#include <mbgl/style/properties.hpp> #include <mbgl/programs/attributes.hpp> +#include <mbgl/programs/uniforms.hpp> namespace mbgl { namespace style { @@ -29,7 +31,7 @@ struct <%- camelize(property.name) %> : <%- paintPropertyType(property, type) %> <% } -%> <% if (layoutProperties.length) { -%> -class <%- camelize(type) %>LayoutProperties : public LayoutProperties< +class <%- camelize(type) %>LayoutProperties : public Properties< <% for (const property of layoutProperties.slice(0, -1)) { -%> <%- camelize(property.name) %>, <% } -%> @@ -37,7 +39,7 @@ class <%- camelize(type) %>LayoutProperties : public LayoutProperties< > {}; <% } -%> -class <%- camelize(type) %>PaintProperties : public PaintProperties< +class <%- camelize(type) %>PaintProperties : public Properties< <% for (const property of paintProperties.slice(0, -1)) { -%> <%- camelize(property.name) %>, <% } -%> diff --git a/src/mbgl/style/layers/line_layer.cpp b/src/mbgl/style/layers/line_layer.cpp index 7f1575aad5..1c7f0d28ee 100644 --- a/src/mbgl/style/layers/line_layer.cpp +++ b/src/mbgl/style/layers/line_layer.cpp @@ -2,63 +2,92 @@ #include <mbgl/style/layers/line_layer.hpp> #include <mbgl/style/layers/line_layer_impl.hpp> -#include <mbgl/style/conversion/stringify.hpp> +#include <mbgl/style/layer_observer.hpp> namespace mbgl { namespace style { LineLayer::LineLayer(const std::string& layerID, const std::string& sourceID) - : Layer(LayerType::Line, std::make_unique<Impl>()) - , impl(static_cast<Impl*>(baseImpl.get())) { - impl->id = layerID; - impl->source = sourceID; + : Layer(makeMutable<Impl>(LayerType::Line, layerID, sourceID)) { } -LineLayer::LineLayer(const Impl& other) - : Layer(LayerType::Line, std::make_unique<Impl>(other)) - , impl(static_cast<Impl*>(baseImpl.get())) { +LineLayer::LineLayer(Immutable<Impl> impl_) + : Layer(std::move(impl_)) { } LineLayer::~LineLayer() = default; -std::unique_ptr<Layer> LineLayer::Impl::clone() const { - return std::make_unique<LineLayer>(*this); +const LineLayer::Impl& LineLayer::impl() const { + return static_cast<const Impl&>(*baseImpl); } -std::unique_ptr<Layer> LineLayer::Impl::cloneRef(const std::string& id_) const { - auto result = std::make_unique<LineLayer>(*this); - result->impl->id = id_; - result->impl->cascading = LinePaintProperties::Cascading(); - return std::move(result); +Mutable<LineLayer::Impl> LineLayer::mutableImpl() const { + return makeMutable<Impl>(impl()); +} + +std::unique_ptr<Layer> LineLayer::cloneRef(const std::string& id_) const { + auto impl_ = mutableImpl(); + impl_->id = id_; + impl_->paint = LinePaintProperties::Transitionable(); + return std::make_unique<LineLayer>(std::move(impl_)); } void LineLayer::Impl::stringifyLayout(rapidjson::Writer<rapidjson::StringBuffer>& writer) const { - conversion::stringify(writer, layout); + layout.stringify(writer); } // Source const std::string& LineLayer::getSourceID() const { - return impl->source; + return impl().source; } void LineLayer::setSourceLayer(const std::string& sourceLayer) { - impl->sourceLayer = sourceLayer; + auto impl_ = mutableImpl(); + impl_->sourceLayer = sourceLayer; + baseImpl = std::move(impl_); } const std::string& LineLayer::getSourceLayer() const { - return impl->sourceLayer; + return impl().sourceLayer; } // Filter void LineLayer::setFilter(const Filter& filter) { - impl->filter = filter; - impl->observer->onLayerFilterChanged(*this); + auto impl_ = mutableImpl(); + impl_->filter = filter; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } const Filter& LineLayer::getFilter() const { - return impl->filter; + return impl().filter; +} + +// Visibility + +void LineLayer::setVisibility(VisibilityType value) { + if (value == getVisibility()) + return; + auto impl_ = mutableImpl(); + impl_->visibility = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); +} + +// Zoom range + +void LineLayer::setMinZoom(float minZoom) { + auto impl_ = mutableImpl(); + impl_->minZoom = minZoom; + baseImpl = std::move(impl_); +} + +void LineLayer::setMaxZoom(float maxZoom) { + auto impl_ = mutableImpl(); + impl_->maxZoom = maxZoom; + baseImpl = std::move(impl_); } // Layout properties @@ -68,56 +97,64 @@ PropertyValue<LineCapType> LineLayer::getDefaultLineCap() { } PropertyValue<LineCapType> LineLayer::getLineCap() const { - return impl->layout.unevaluated.get<LineCap>(); + return impl().layout.get<LineCap>(); } void LineLayer::setLineCap(PropertyValue<LineCapType> value) { if (value == getLineCap()) return; - impl->layout.unevaluated.get<LineCap>() = value; - impl->observer->onLayerLayoutPropertyChanged(*this, "line-cap"); + auto impl_ = mutableImpl(); + impl_->layout.get<LineCap>() = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } -PropertyValue<LineJoinType> LineLayer::getDefaultLineJoin() { +DataDrivenPropertyValue<LineJoinType> LineLayer::getDefaultLineJoin() { return LineJoin::defaultValue(); } -PropertyValue<LineJoinType> LineLayer::getLineJoin() const { - return impl->layout.unevaluated.get<LineJoin>(); +DataDrivenPropertyValue<LineJoinType> LineLayer::getLineJoin() const { + return impl().layout.get<LineJoin>(); } -void LineLayer::setLineJoin(PropertyValue<LineJoinType> value) { +void LineLayer::setLineJoin(DataDrivenPropertyValue<LineJoinType> value) { if (value == getLineJoin()) return; - impl->layout.unevaluated.get<LineJoin>() = value; - impl->observer->onLayerLayoutPropertyChanged(*this, "line-join"); + auto impl_ = mutableImpl(); + impl_->layout.get<LineJoin>() = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } PropertyValue<float> LineLayer::getDefaultLineMiterLimit() { return LineMiterLimit::defaultValue(); } PropertyValue<float> LineLayer::getLineMiterLimit() const { - return impl->layout.unevaluated.get<LineMiterLimit>(); + return impl().layout.get<LineMiterLimit>(); } void LineLayer::setLineMiterLimit(PropertyValue<float> value) { if (value == getLineMiterLimit()) return; - impl->layout.unevaluated.get<LineMiterLimit>() = value; - impl->observer->onLayerLayoutPropertyChanged(*this, "line-miter-limit"); + auto impl_ = mutableImpl(); + impl_->layout.get<LineMiterLimit>() = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } PropertyValue<float> LineLayer::getDefaultLineRoundLimit() { return LineRoundLimit::defaultValue(); } PropertyValue<float> LineLayer::getLineRoundLimit() const { - return impl->layout.unevaluated.get<LineRoundLimit>(); + return impl().layout.get<LineRoundLimit>(); } void LineLayer::setLineRoundLimit(PropertyValue<float> value) { if (value == getLineRoundLimit()) return; - impl->layout.unevaluated.get<LineRoundLimit>() = value; - impl->observer->onLayerLayoutPropertyChanged(*this, "line-round-limit"); + auto impl_ = mutableImpl(); + impl_->layout.get<LineRoundLimit>() = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } // Paint properties @@ -126,250 +163,270 @@ DataDrivenPropertyValue<float> LineLayer::getDefaultLineOpacity() { return { 1 }; } -DataDrivenPropertyValue<float> LineLayer::getLineOpacity(const optional<std::string>& klass) const { - return impl->cascading.template get<LineOpacity>().get(klass); +DataDrivenPropertyValue<float> LineLayer::getLineOpacity() const { + return impl().paint.template get<LineOpacity>().value; } -void LineLayer::setLineOpacity(DataDrivenPropertyValue<float> value, const optional<std::string>& klass) { - if (value == getLineOpacity(klass)) +void LineLayer::setLineOpacity(DataDrivenPropertyValue<float> value) { + if (value == getLineOpacity()) return; - impl->cascading.template get<LineOpacity>().set(value, klass); - if (value.isDataDriven()) { - impl->observer->onLayerDataDrivenPaintPropertyChanged(*this); - } else { - impl->observer->onLayerPaintPropertyChanged(*this); - } + auto impl_ = mutableImpl(); + impl_->paint.template get<LineOpacity>().value = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } -void LineLayer::setLineOpacityTransition(const TransitionOptions& value, const optional<std::string>& klass) { - impl->cascading.template get<LineOpacity>().setTransition(value, klass); +void LineLayer::setLineOpacityTransition(const TransitionOptions& options) { + auto impl_ = mutableImpl(); + impl_->paint.template get<LineOpacity>().options = options; + baseImpl = std::move(impl_); } -TransitionOptions LineLayer::getLineOpacityTransition(const optional<std::string>& klass) const { - return impl->cascading.template get<LineOpacity>().getTransition(klass); +TransitionOptions LineLayer::getLineOpacityTransition() const { + return impl().paint.template get<LineOpacity>().options; } DataDrivenPropertyValue<Color> LineLayer::getDefaultLineColor() { return { Color::black() }; } -DataDrivenPropertyValue<Color> LineLayer::getLineColor(const optional<std::string>& klass) const { - return impl->cascading.template get<LineColor>().get(klass); +DataDrivenPropertyValue<Color> LineLayer::getLineColor() const { + return impl().paint.template get<LineColor>().value; } -void LineLayer::setLineColor(DataDrivenPropertyValue<Color> value, const optional<std::string>& klass) { - if (value == getLineColor(klass)) +void LineLayer::setLineColor(DataDrivenPropertyValue<Color> value) { + if (value == getLineColor()) return; - impl->cascading.template get<LineColor>().set(value, klass); - if (value.isDataDriven()) { - impl->observer->onLayerDataDrivenPaintPropertyChanged(*this); - } else { - impl->observer->onLayerPaintPropertyChanged(*this); - } + auto impl_ = mutableImpl(); + impl_->paint.template get<LineColor>().value = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } -void LineLayer::setLineColorTransition(const TransitionOptions& value, const optional<std::string>& klass) { - impl->cascading.template get<LineColor>().setTransition(value, klass); +void LineLayer::setLineColorTransition(const TransitionOptions& options) { + auto impl_ = mutableImpl(); + impl_->paint.template get<LineColor>().options = options; + baseImpl = std::move(impl_); } -TransitionOptions LineLayer::getLineColorTransition(const optional<std::string>& klass) const { - return impl->cascading.template get<LineColor>().getTransition(klass); +TransitionOptions LineLayer::getLineColorTransition() const { + return impl().paint.template get<LineColor>().options; } PropertyValue<std::array<float, 2>> LineLayer::getDefaultLineTranslate() { return { {{ 0, 0 }} }; } -PropertyValue<std::array<float, 2>> LineLayer::getLineTranslate(const optional<std::string>& klass) const { - return impl->cascading.template get<LineTranslate>().get(klass); +PropertyValue<std::array<float, 2>> LineLayer::getLineTranslate() const { + return impl().paint.template get<LineTranslate>().value; } -void LineLayer::setLineTranslate(PropertyValue<std::array<float, 2>> value, const optional<std::string>& klass) { - if (value == getLineTranslate(klass)) +void LineLayer::setLineTranslate(PropertyValue<std::array<float, 2>> value) { + if (value == getLineTranslate()) return; - impl->cascading.template get<LineTranslate>().set(value, klass); - impl->observer->onLayerPaintPropertyChanged(*this); + auto impl_ = mutableImpl(); + impl_->paint.template get<LineTranslate>().value = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } -void LineLayer::setLineTranslateTransition(const TransitionOptions& value, const optional<std::string>& klass) { - impl->cascading.template get<LineTranslate>().setTransition(value, klass); +void LineLayer::setLineTranslateTransition(const TransitionOptions& options) { + auto impl_ = mutableImpl(); + impl_->paint.template get<LineTranslate>().options = options; + baseImpl = std::move(impl_); } -TransitionOptions LineLayer::getLineTranslateTransition(const optional<std::string>& klass) const { - return impl->cascading.template get<LineTranslate>().getTransition(klass); +TransitionOptions LineLayer::getLineTranslateTransition() const { + return impl().paint.template get<LineTranslate>().options; } PropertyValue<TranslateAnchorType> LineLayer::getDefaultLineTranslateAnchor() { return { TranslateAnchorType::Map }; } -PropertyValue<TranslateAnchorType> LineLayer::getLineTranslateAnchor(const optional<std::string>& klass) const { - return impl->cascading.template get<LineTranslateAnchor>().get(klass); +PropertyValue<TranslateAnchorType> LineLayer::getLineTranslateAnchor() const { + return impl().paint.template get<LineTranslateAnchor>().value; } -void LineLayer::setLineTranslateAnchor(PropertyValue<TranslateAnchorType> value, const optional<std::string>& klass) { - if (value == getLineTranslateAnchor(klass)) +void LineLayer::setLineTranslateAnchor(PropertyValue<TranslateAnchorType> value) { + if (value == getLineTranslateAnchor()) return; - impl->cascading.template get<LineTranslateAnchor>().set(value, klass); - impl->observer->onLayerPaintPropertyChanged(*this); + auto impl_ = mutableImpl(); + impl_->paint.template get<LineTranslateAnchor>().value = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } -void LineLayer::setLineTranslateAnchorTransition(const TransitionOptions& value, const optional<std::string>& klass) { - impl->cascading.template get<LineTranslateAnchor>().setTransition(value, klass); +void LineLayer::setLineTranslateAnchorTransition(const TransitionOptions& options) { + auto impl_ = mutableImpl(); + impl_->paint.template get<LineTranslateAnchor>().options = options; + baseImpl = std::move(impl_); } -TransitionOptions LineLayer::getLineTranslateAnchorTransition(const optional<std::string>& klass) const { - return impl->cascading.template get<LineTranslateAnchor>().getTransition(klass); +TransitionOptions LineLayer::getLineTranslateAnchorTransition() const { + return impl().paint.template get<LineTranslateAnchor>().options; } -PropertyValue<float> LineLayer::getDefaultLineWidth() { +DataDrivenPropertyValue<float> LineLayer::getDefaultLineWidth() { return { 1 }; } -PropertyValue<float> LineLayer::getLineWidth(const optional<std::string>& klass) const { - return impl->cascading.template get<LineWidth>().get(klass); +DataDrivenPropertyValue<float> LineLayer::getLineWidth() const { + return impl().paint.template get<LineWidth>().value; } -void LineLayer::setLineWidth(PropertyValue<float> value, const optional<std::string>& klass) { - if (value == getLineWidth(klass)) +void LineLayer::setLineWidth(DataDrivenPropertyValue<float> value) { + if (value == getLineWidth()) return; - impl->cascading.template get<LineWidth>().set(value, klass); - impl->observer->onLayerPaintPropertyChanged(*this); + auto impl_ = mutableImpl(); + impl_->paint.template get<LineWidth>().value = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } -void LineLayer::setLineWidthTransition(const TransitionOptions& value, const optional<std::string>& klass) { - impl->cascading.template get<LineWidth>().setTransition(value, klass); +void LineLayer::setLineWidthTransition(const TransitionOptions& options) { + auto impl_ = mutableImpl(); + impl_->paint.template get<LineWidth>().options = options; + baseImpl = std::move(impl_); } -TransitionOptions LineLayer::getLineWidthTransition(const optional<std::string>& klass) const { - return impl->cascading.template get<LineWidth>().getTransition(klass); +TransitionOptions LineLayer::getLineWidthTransition() const { + return impl().paint.template get<LineWidth>().options; } DataDrivenPropertyValue<float> LineLayer::getDefaultLineGapWidth() { return { 0 }; } -DataDrivenPropertyValue<float> LineLayer::getLineGapWidth(const optional<std::string>& klass) const { - return impl->cascading.template get<LineGapWidth>().get(klass); +DataDrivenPropertyValue<float> LineLayer::getLineGapWidth() const { + return impl().paint.template get<LineGapWidth>().value; } -void LineLayer::setLineGapWidth(DataDrivenPropertyValue<float> value, const optional<std::string>& klass) { - if (value == getLineGapWidth(klass)) +void LineLayer::setLineGapWidth(DataDrivenPropertyValue<float> value) { + if (value == getLineGapWidth()) return; - impl->cascading.template get<LineGapWidth>().set(value, klass); - if (value.isDataDriven()) { - impl->observer->onLayerDataDrivenPaintPropertyChanged(*this); - } else { - impl->observer->onLayerPaintPropertyChanged(*this); - } + auto impl_ = mutableImpl(); + impl_->paint.template get<LineGapWidth>().value = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } -void LineLayer::setLineGapWidthTransition(const TransitionOptions& value, const optional<std::string>& klass) { - impl->cascading.template get<LineGapWidth>().setTransition(value, klass); +void LineLayer::setLineGapWidthTransition(const TransitionOptions& options) { + auto impl_ = mutableImpl(); + impl_->paint.template get<LineGapWidth>().options = options; + baseImpl = std::move(impl_); } -TransitionOptions LineLayer::getLineGapWidthTransition(const optional<std::string>& klass) const { - return impl->cascading.template get<LineGapWidth>().getTransition(klass); +TransitionOptions LineLayer::getLineGapWidthTransition() const { + return impl().paint.template get<LineGapWidth>().options; } DataDrivenPropertyValue<float> LineLayer::getDefaultLineOffset() { return { 0 }; } -DataDrivenPropertyValue<float> LineLayer::getLineOffset(const optional<std::string>& klass) const { - return impl->cascading.template get<LineOffset>().get(klass); +DataDrivenPropertyValue<float> LineLayer::getLineOffset() const { + return impl().paint.template get<LineOffset>().value; } -void LineLayer::setLineOffset(DataDrivenPropertyValue<float> value, const optional<std::string>& klass) { - if (value == getLineOffset(klass)) +void LineLayer::setLineOffset(DataDrivenPropertyValue<float> value) { + if (value == getLineOffset()) return; - impl->cascading.template get<LineOffset>().set(value, klass); - if (value.isDataDriven()) { - impl->observer->onLayerDataDrivenPaintPropertyChanged(*this); - } else { - impl->observer->onLayerPaintPropertyChanged(*this); - } + auto impl_ = mutableImpl(); + impl_->paint.template get<LineOffset>().value = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } -void LineLayer::setLineOffsetTransition(const TransitionOptions& value, const optional<std::string>& klass) { - impl->cascading.template get<LineOffset>().setTransition(value, klass); +void LineLayer::setLineOffsetTransition(const TransitionOptions& options) { + auto impl_ = mutableImpl(); + impl_->paint.template get<LineOffset>().options = options; + baseImpl = std::move(impl_); } -TransitionOptions LineLayer::getLineOffsetTransition(const optional<std::string>& klass) const { - return impl->cascading.template get<LineOffset>().getTransition(klass); +TransitionOptions LineLayer::getLineOffsetTransition() const { + return impl().paint.template get<LineOffset>().options; } DataDrivenPropertyValue<float> LineLayer::getDefaultLineBlur() { return { 0 }; } -DataDrivenPropertyValue<float> LineLayer::getLineBlur(const optional<std::string>& klass) const { - return impl->cascading.template get<LineBlur>().get(klass); +DataDrivenPropertyValue<float> LineLayer::getLineBlur() const { + return impl().paint.template get<LineBlur>().value; } -void LineLayer::setLineBlur(DataDrivenPropertyValue<float> value, const optional<std::string>& klass) { - if (value == getLineBlur(klass)) +void LineLayer::setLineBlur(DataDrivenPropertyValue<float> value) { + if (value == getLineBlur()) return; - impl->cascading.template get<LineBlur>().set(value, klass); - if (value.isDataDriven()) { - impl->observer->onLayerDataDrivenPaintPropertyChanged(*this); - } else { - impl->observer->onLayerPaintPropertyChanged(*this); - } + auto impl_ = mutableImpl(); + impl_->paint.template get<LineBlur>().value = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } -void LineLayer::setLineBlurTransition(const TransitionOptions& value, const optional<std::string>& klass) { - impl->cascading.template get<LineBlur>().setTransition(value, klass); +void LineLayer::setLineBlurTransition(const TransitionOptions& options) { + auto impl_ = mutableImpl(); + impl_->paint.template get<LineBlur>().options = options; + baseImpl = std::move(impl_); } -TransitionOptions LineLayer::getLineBlurTransition(const optional<std::string>& klass) const { - return impl->cascading.template get<LineBlur>().getTransition(klass); +TransitionOptions LineLayer::getLineBlurTransition() const { + return impl().paint.template get<LineBlur>().options; } PropertyValue<std::vector<float>> LineLayer::getDefaultLineDasharray() { return { { } }; } -PropertyValue<std::vector<float>> LineLayer::getLineDasharray(const optional<std::string>& klass) const { - return impl->cascading.template get<LineDasharray>().get(klass); +PropertyValue<std::vector<float>> LineLayer::getLineDasharray() const { + return impl().paint.template get<LineDasharray>().value; } -void LineLayer::setLineDasharray(PropertyValue<std::vector<float>> value, const optional<std::string>& klass) { - if (value == getLineDasharray(klass)) +void LineLayer::setLineDasharray(PropertyValue<std::vector<float>> value) { + if (value == getLineDasharray()) return; - impl->cascading.template get<LineDasharray>().set(value, klass); - impl->observer->onLayerPaintPropertyChanged(*this); + auto impl_ = mutableImpl(); + impl_->paint.template get<LineDasharray>().value = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } -void LineLayer::setLineDasharrayTransition(const TransitionOptions& value, const optional<std::string>& klass) { - impl->cascading.template get<LineDasharray>().setTransition(value, klass); +void LineLayer::setLineDasharrayTransition(const TransitionOptions& options) { + auto impl_ = mutableImpl(); + impl_->paint.template get<LineDasharray>().options = options; + baseImpl = std::move(impl_); } -TransitionOptions LineLayer::getLineDasharrayTransition(const optional<std::string>& klass) const { - return impl->cascading.template get<LineDasharray>().getTransition(klass); +TransitionOptions LineLayer::getLineDasharrayTransition() const { + return impl().paint.template get<LineDasharray>().options; } PropertyValue<std::string> LineLayer::getDefaultLinePattern() { return { "" }; } -PropertyValue<std::string> LineLayer::getLinePattern(const optional<std::string>& klass) const { - return impl->cascading.template get<LinePattern>().get(klass); +PropertyValue<std::string> LineLayer::getLinePattern() const { + return impl().paint.template get<LinePattern>().value; } -void LineLayer::setLinePattern(PropertyValue<std::string> value, const optional<std::string>& klass) { - if (value == getLinePattern(klass)) +void LineLayer::setLinePattern(PropertyValue<std::string> value) { + if (value == getLinePattern()) return; - impl->cascading.template get<LinePattern>().set(value, klass); - impl->observer->onLayerPaintPropertyChanged(*this); + auto impl_ = mutableImpl(); + impl_->paint.template get<LinePattern>().value = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } -void LineLayer::setLinePatternTransition(const TransitionOptions& value, const optional<std::string>& klass) { - impl->cascading.template get<LinePattern>().setTransition(value, klass); +void LineLayer::setLinePatternTransition(const TransitionOptions& options) { + auto impl_ = mutableImpl(); + impl_->paint.template get<LinePattern>().options = options; + baseImpl = std::move(impl_); } -TransitionOptions LineLayer::getLinePatternTransition(const optional<std::string>& klass) const { - return impl->cascading.template get<LinePattern>().getTransition(klass); +TransitionOptions LineLayer::getLinePatternTransition() const { + return impl().paint.template get<LinePattern>().options; } } // namespace style diff --git a/src/mbgl/style/layers/line_layer_impl.cpp b/src/mbgl/style/layers/line_layer_impl.cpp index 973a77abf4..bee88d6a47 100644 --- a/src/mbgl/style/layers/line_layer_impl.cpp +++ b/src/mbgl/style/layers/line_layer_impl.cpp @@ -1,11 +1,15 @@ #include <mbgl/style/layers/line_layer_impl.hpp> -#include <mbgl/renderer/render_line_layer.hpp> namespace mbgl { namespace style { -std::unique_ptr<RenderLayer> LineLayer::Impl::createRenderLayer() const { - return std::make_unique<RenderLineLayer>(*this); +bool LineLayer::Impl::hasLayoutDifference(const Layer::Impl& other) const { + assert(dynamic_cast<const LineLayer::Impl*>(&other)); + const auto& impl = static_cast<const style::LineLayer::Impl&>(other); + return filter != impl.filter || + visibility != impl.visibility || + layout != impl.layout || + paint.hasDataDrivenPropertyDifference(impl.paint); } } // namespace style diff --git a/src/mbgl/style/layers/line_layer_impl.hpp b/src/mbgl/style/layers/line_layer_impl.hpp index 02c9c85f00..04adc0e85c 100644 --- a/src/mbgl/style/layers/line_layer_impl.hpp +++ b/src/mbgl/style/layers/line_layer_impl.hpp @@ -9,14 +9,13 @@ namespace style { class LineLayer::Impl : public Layer::Impl { public: - std::unique_ptr<Layer> clone() const override; - std::unique_ptr<Layer> cloneRef(const std::string& id) const override; - void stringifyLayout(rapidjson::Writer<rapidjson::StringBuffer>&) const override; + using Layer::Impl::Impl; - std::unique_ptr<RenderLayer> createRenderLayer() const override; + bool hasLayoutDifference(const Layer::Impl&) const override; + void stringifyLayout(rapidjson::Writer<rapidjson::StringBuffer>&) const override; - LineLayoutProperties layout; - LinePaintProperties::Cascading cascading; + LineLayoutProperties::Unevaluated layout; + LinePaintProperties::Transitionable paint; }; } // namespace style diff --git a/src/mbgl/style/layers/line_layer_properties.hpp b/src/mbgl/style/layers/line_layer_properties.hpp index 6c301e6a0e..aeaf51698a 100644 --- a/src/mbgl/style/layers/line_layer_properties.hpp +++ b/src/mbgl/style/layers/line_layer_properties.hpp @@ -5,6 +5,7 @@ #include <mbgl/style/types.hpp> #include <mbgl/style/layout_property.hpp> #include <mbgl/style/paint_property.hpp> +#include <mbgl/style/properties.hpp> #include <mbgl/programs/attributes.hpp> #include <mbgl/programs/uniforms.hpp> @@ -16,7 +17,7 @@ struct LineCap : LayoutProperty<LineCapType> { static LineCapType defaultValue() { return LineCapType::Butt; } }; -struct LineJoin : LayoutProperty<LineJoinType> { +struct LineJoin : DataDrivenLayoutProperty<LineJoinType> { static constexpr const char * key = "line-join"; static LineJoinType defaultValue() { return LineJoinType::Miter; } }; @@ -47,7 +48,7 @@ struct LineTranslateAnchor : PaintProperty<TranslateAnchorType> { static TranslateAnchorType defaultValue() { return TranslateAnchorType::Map; } }; -struct LineWidth : PaintProperty<float> { +struct LineWidth : DataDrivenPaintProperty<float, attributes::a_width, uniforms::u_width> { static float defaultValue() { return 1; } }; @@ -71,14 +72,14 @@ struct LinePattern : CrossFadedPaintProperty<std::string> { static std::string defaultValue() { return ""; } }; -class LineLayoutProperties : public LayoutProperties< +class LineLayoutProperties : public Properties< LineCap, LineJoin, LineMiterLimit, LineRoundLimit > {}; -class LinePaintProperties : public PaintProperties< +class LinePaintProperties : public Properties< LineOpacity, LineColor, LineTranslate, diff --git a/src/mbgl/style/layers/raster_layer.cpp b/src/mbgl/style/layers/raster_layer.cpp index b525f9eaa4..a9a8d273fa 100644 --- a/src/mbgl/style/layers/raster_layer.cpp +++ b/src/mbgl/style/layers/raster_layer.cpp @@ -2,34 +2,34 @@ #include <mbgl/style/layers/raster_layer.hpp> #include <mbgl/style/layers/raster_layer_impl.hpp> -#include <mbgl/style/conversion/stringify.hpp> +#include <mbgl/style/layer_observer.hpp> namespace mbgl { namespace style { RasterLayer::RasterLayer(const std::string& layerID, const std::string& sourceID) - : Layer(LayerType::Raster, std::make_unique<Impl>()) - , impl(static_cast<Impl*>(baseImpl.get())) { - impl->id = layerID; - impl->source = sourceID; + : Layer(makeMutable<Impl>(LayerType::Raster, layerID, sourceID)) { } -RasterLayer::RasterLayer(const Impl& other) - : Layer(LayerType::Raster, std::make_unique<Impl>(other)) - , impl(static_cast<Impl*>(baseImpl.get())) { +RasterLayer::RasterLayer(Immutable<Impl> impl_) + : Layer(std::move(impl_)) { } RasterLayer::~RasterLayer() = default; -std::unique_ptr<Layer> RasterLayer::Impl::clone() const { - return std::make_unique<RasterLayer>(*this); +const RasterLayer::Impl& RasterLayer::impl() const { + return static_cast<const Impl&>(*baseImpl); } -std::unique_ptr<Layer> RasterLayer::Impl::cloneRef(const std::string& id_) const { - auto result = std::make_unique<RasterLayer>(*this); - result->impl->id = id_; - result->impl->cascading = RasterPaintProperties::Cascading(); - return std::move(result); +Mutable<RasterLayer::Impl> RasterLayer::mutableImpl() const { + return makeMutable<Impl>(impl()); +} + +std::unique_ptr<Layer> RasterLayer::cloneRef(const std::string& id_) const { + auto impl_ = mutableImpl(); + impl_->id = id_; + impl_->paint = RasterPaintProperties::Transitionable(); + return std::make_unique<RasterLayer>(std::move(impl_)); } void RasterLayer::Impl::stringifyLayout(rapidjson::Writer<rapidjson::StringBuffer>&) const { @@ -38,10 +38,35 @@ void RasterLayer::Impl::stringifyLayout(rapidjson::Writer<rapidjson::StringBuffe // Source const std::string& RasterLayer::getSourceID() const { - return impl->source; + return impl().source; } +// Visibility + +void RasterLayer::setVisibility(VisibilityType value) { + if (value == getVisibility()) + return; + auto impl_ = mutableImpl(); + impl_->visibility = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); +} + +// Zoom range + +void RasterLayer::setMinZoom(float minZoom) { + auto impl_ = mutableImpl(); + impl_->minZoom = minZoom; + baseImpl = std::move(impl_); +} + +void RasterLayer::setMaxZoom(float maxZoom) { + auto impl_ = mutableImpl(); + impl_->maxZoom = maxZoom; + baseImpl = std::move(impl_); +} + // Layout properties @@ -51,161 +76,189 @@ PropertyValue<float> RasterLayer::getDefaultRasterOpacity() { return { 1 }; } -PropertyValue<float> RasterLayer::getRasterOpacity(const optional<std::string>& klass) const { - return impl->cascading.template get<RasterOpacity>().get(klass); +PropertyValue<float> RasterLayer::getRasterOpacity() const { + return impl().paint.template get<RasterOpacity>().value; } -void RasterLayer::setRasterOpacity(PropertyValue<float> value, const optional<std::string>& klass) { - if (value == getRasterOpacity(klass)) +void RasterLayer::setRasterOpacity(PropertyValue<float> value) { + if (value == getRasterOpacity()) return; - impl->cascading.template get<RasterOpacity>().set(value, klass); - impl->observer->onLayerPaintPropertyChanged(*this); + auto impl_ = mutableImpl(); + impl_->paint.template get<RasterOpacity>().value = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } -void RasterLayer::setRasterOpacityTransition(const TransitionOptions& value, const optional<std::string>& klass) { - impl->cascading.template get<RasterOpacity>().setTransition(value, klass); +void RasterLayer::setRasterOpacityTransition(const TransitionOptions& options) { + auto impl_ = mutableImpl(); + impl_->paint.template get<RasterOpacity>().options = options; + baseImpl = std::move(impl_); } -TransitionOptions RasterLayer::getRasterOpacityTransition(const optional<std::string>& klass) const { - return impl->cascading.template get<RasterOpacity>().getTransition(klass); +TransitionOptions RasterLayer::getRasterOpacityTransition() const { + return impl().paint.template get<RasterOpacity>().options; } PropertyValue<float> RasterLayer::getDefaultRasterHueRotate() { return { 0 }; } -PropertyValue<float> RasterLayer::getRasterHueRotate(const optional<std::string>& klass) const { - return impl->cascading.template get<RasterHueRotate>().get(klass); +PropertyValue<float> RasterLayer::getRasterHueRotate() const { + return impl().paint.template get<RasterHueRotate>().value; } -void RasterLayer::setRasterHueRotate(PropertyValue<float> value, const optional<std::string>& klass) { - if (value == getRasterHueRotate(klass)) +void RasterLayer::setRasterHueRotate(PropertyValue<float> value) { + if (value == getRasterHueRotate()) return; - impl->cascading.template get<RasterHueRotate>().set(value, klass); - impl->observer->onLayerPaintPropertyChanged(*this); + auto impl_ = mutableImpl(); + impl_->paint.template get<RasterHueRotate>().value = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } -void RasterLayer::setRasterHueRotateTransition(const TransitionOptions& value, const optional<std::string>& klass) { - impl->cascading.template get<RasterHueRotate>().setTransition(value, klass); +void RasterLayer::setRasterHueRotateTransition(const TransitionOptions& options) { + auto impl_ = mutableImpl(); + impl_->paint.template get<RasterHueRotate>().options = options; + baseImpl = std::move(impl_); } -TransitionOptions RasterLayer::getRasterHueRotateTransition(const optional<std::string>& klass) const { - return impl->cascading.template get<RasterHueRotate>().getTransition(klass); +TransitionOptions RasterLayer::getRasterHueRotateTransition() const { + return impl().paint.template get<RasterHueRotate>().options; } PropertyValue<float> RasterLayer::getDefaultRasterBrightnessMin() { return { 0 }; } -PropertyValue<float> RasterLayer::getRasterBrightnessMin(const optional<std::string>& klass) const { - return impl->cascading.template get<RasterBrightnessMin>().get(klass); +PropertyValue<float> RasterLayer::getRasterBrightnessMin() const { + return impl().paint.template get<RasterBrightnessMin>().value; } -void RasterLayer::setRasterBrightnessMin(PropertyValue<float> value, const optional<std::string>& klass) { - if (value == getRasterBrightnessMin(klass)) +void RasterLayer::setRasterBrightnessMin(PropertyValue<float> value) { + if (value == getRasterBrightnessMin()) return; - impl->cascading.template get<RasterBrightnessMin>().set(value, klass); - impl->observer->onLayerPaintPropertyChanged(*this); + auto impl_ = mutableImpl(); + impl_->paint.template get<RasterBrightnessMin>().value = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } -void RasterLayer::setRasterBrightnessMinTransition(const TransitionOptions& value, const optional<std::string>& klass) { - impl->cascading.template get<RasterBrightnessMin>().setTransition(value, klass); +void RasterLayer::setRasterBrightnessMinTransition(const TransitionOptions& options) { + auto impl_ = mutableImpl(); + impl_->paint.template get<RasterBrightnessMin>().options = options; + baseImpl = std::move(impl_); } -TransitionOptions RasterLayer::getRasterBrightnessMinTransition(const optional<std::string>& klass) const { - return impl->cascading.template get<RasterBrightnessMin>().getTransition(klass); +TransitionOptions RasterLayer::getRasterBrightnessMinTransition() const { + return impl().paint.template get<RasterBrightnessMin>().options; } PropertyValue<float> RasterLayer::getDefaultRasterBrightnessMax() { return { 1 }; } -PropertyValue<float> RasterLayer::getRasterBrightnessMax(const optional<std::string>& klass) const { - return impl->cascading.template get<RasterBrightnessMax>().get(klass); +PropertyValue<float> RasterLayer::getRasterBrightnessMax() const { + return impl().paint.template get<RasterBrightnessMax>().value; } -void RasterLayer::setRasterBrightnessMax(PropertyValue<float> value, const optional<std::string>& klass) { - if (value == getRasterBrightnessMax(klass)) +void RasterLayer::setRasterBrightnessMax(PropertyValue<float> value) { + if (value == getRasterBrightnessMax()) return; - impl->cascading.template get<RasterBrightnessMax>().set(value, klass); - impl->observer->onLayerPaintPropertyChanged(*this); + auto impl_ = mutableImpl(); + impl_->paint.template get<RasterBrightnessMax>().value = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } -void RasterLayer::setRasterBrightnessMaxTransition(const TransitionOptions& value, const optional<std::string>& klass) { - impl->cascading.template get<RasterBrightnessMax>().setTransition(value, klass); +void RasterLayer::setRasterBrightnessMaxTransition(const TransitionOptions& options) { + auto impl_ = mutableImpl(); + impl_->paint.template get<RasterBrightnessMax>().options = options; + baseImpl = std::move(impl_); } -TransitionOptions RasterLayer::getRasterBrightnessMaxTransition(const optional<std::string>& klass) const { - return impl->cascading.template get<RasterBrightnessMax>().getTransition(klass); +TransitionOptions RasterLayer::getRasterBrightnessMaxTransition() const { + return impl().paint.template get<RasterBrightnessMax>().options; } PropertyValue<float> RasterLayer::getDefaultRasterSaturation() { return { 0 }; } -PropertyValue<float> RasterLayer::getRasterSaturation(const optional<std::string>& klass) const { - return impl->cascading.template get<RasterSaturation>().get(klass); +PropertyValue<float> RasterLayer::getRasterSaturation() const { + return impl().paint.template get<RasterSaturation>().value; } -void RasterLayer::setRasterSaturation(PropertyValue<float> value, const optional<std::string>& klass) { - if (value == getRasterSaturation(klass)) +void RasterLayer::setRasterSaturation(PropertyValue<float> value) { + if (value == getRasterSaturation()) return; - impl->cascading.template get<RasterSaturation>().set(value, klass); - impl->observer->onLayerPaintPropertyChanged(*this); + auto impl_ = mutableImpl(); + impl_->paint.template get<RasterSaturation>().value = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } -void RasterLayer::setRasterSaturationTransition(const TransitionOptions& value, const optional<std::string>& klass) { - impl->cascading.template get<RasterSaturation>().setTransition(value, klass); +void RasterLayer::setRasterSaturationTransition(const TransitionOptions& options) { + auto impl_ = mutableImpl(); + impl_->paint.template get<RasterSaturation>().options = options; + baseImpl = std::move(impl_); } -TransitionOptions RasterLayer::getRasterSaturationTransition(const optional<std::string>& klass) const { - return impl->cascading.template get<RasterSaturation>().getTransition(klass); +TransitionOptions RasterLayer::getRasterSaturationTransition() const { + return impl().paint.template get<RasterSaturation>().options; } PropertyValue<float> RasterLayer::getDefaultRasterContrast() { return { 0 }; } -PropertyValue<float> RasterLayer::getRasterContrast(const optional<std::string>& klass) const { - return impl->cascading.template get<RasterContrast>().get(klass); +PropertyValue<float> RasterLayer::getRasterContrast() const { + return impl().paint.template get<RasterContrast>().value; } -void RasterLayer::setRasterContrast(PropertyValue<float> value, const optional<std::string>& klass) { - if (value == getRasterContrast(klass)) +void RasterLayer::setRasterContrast(PropertyValue<float> value) { + if (value == getRasterContrast()) return; - impl->cascading.template get<RasterContrast>().set(value, klass); - impl->observer->onLayerPaintPropertyChanged(*this); + auto impl_ = mutableImpl(); + impl_->paint.template get<RasterContrast>().value = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } -void RasterLayer::setRasterContrastTransition(const TransitionOptions& value, const optional<std::string>& klass) { - impl->cascading.template get<RasterContrast>().setTransition(value, klass); +void RasterLayer::setRasterContrastTransition(const TransitionOptions& options) { + auto impl_ = mutableImpl(); + impl_->paint.template get<RasterContrast>().options = options; + baseImpl = std::move(impl_); } -TransitionOptions RasterLayer::getRasterContrastTransition(const optional<std::string>& klass) const { - return impl->cascading.template get<RasterContrast>().getTransition(klass); +TransitionOptions RasterLayer::getRasterContrastTransition() const { + return impl().paint.template get<RasterContrast>().options; } PropertyValue<float> RasterLayer::getDefaultRasterFadeDuration() { return { 300 }; } -PropertyValue<float> RasterLayer::getRasterFadeDuration(const optional<std::string>& klass) const { - return impl->cascading.template get<RasterFadeDuration>().get(klass); +PropertyValue<float> RasterLayer::getRasterFadeDuration() const { + return impl().paint.template get<RasterFadeDuration>().value; } -void RasterLayer::setRasterFadeDuration(PropertyValue<float> value, const optional<std::string>& klass) { - if (value == getRasterFadeDuration(klass)) +void RasterLayer::setRasterFadeDuration(PropertyValue<float> value) { + if (value == getRasterFadeDuration()) return; - impl->cascading.template get<RasterFadeDuration>().set(value, klass); - impl->observer->onLayerPaintPropertyChanged(*this); + auto impl_ = mutableImpl(); + impl_->paint.template get<RasterFadeDuration>().value = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } -void RasterLayer::setRasterFadeDurationTransition(const TransitionOptions& value, const optional<std::string>& klass) { - impl->cascading.template get<RasterFadeDuration>().setTransition(value, klass); +void RasterLayer::setRasterFadeDurationTransition(const TransitionOptions& options) { + auto impl_ = mutableImpl(); + impl_->paint.template get<RasterFadeDuration>().options = options; + baseImpl = std::move(impl_); } -TransitionOptions RasterLayer::getRasterFadeDurationTransition(const optional<std::string>& klass) const { - return impl->cascading.template get<RasterFadeDuration>().getTransition(klass); +TransitionOptions RasterLayer::getRasterFadeDurationTransition() const { + return impl().paint.template get<RasterFadeDuration>().options; } } // namespace style diff --git a/src/mbgl/style/layers/raster_layer_impl.cpp b/src/mbgl/style/layers/raster_layer_impl.cpp index fa9f80dac6..a995f50dd3 100644 --- a/src/mbgl/style/layers/raster_layer_impl.cpp +++ b/src/mbgl/style/layers/raster_layer_impl.cpp @@ -1,11 +1,10 @@ #include <mbgl/style/layers/raster_layer_impl.hpp> -#include <mbgl/renderer/render_raster_layer.hpp> namespace mbgl { namespace style { -std::unique_ptr<RenderLayer> RasterLayer::Impl::createRenderLayer() const { - return std::make_unique<RenderRasterLayer>(*this); +bool RasterLayer::Impl::hasLayoutDifference(const Layer::Impl&) const { + return false; } } // namespace style diff --git a/src/mbgl/style/layers/raster_layer_impl.hpp b/src/mbgl/style/layers/raster_layer_impl.hpp index edf5f9111b..adbe703e92 100644 --- a/src/mbgl/style/layers/raster_layer_impl.hpp +++ b/src/mbgl/style/layers/raster_layer_impl.hpp @@ -9,13 +9,12 @@ namespace style { class RasterLayer::Impl : public Layer::Impl { public: - std::unique_ptr<Layer> clone() const override; - std::unique_ptr<Layer> cloneRef(const std::string& id) const override; - void stringifyLayout(rapidjson::Writer<rapidjson::StringBuffer>&) const override; + using Layer::Impl::Impl; - std::unique_ptr<RenderLayer> createRenderLayer() const override; + bool hasLayoutDifference(const Layer::Impl&) const override; + void stringifyLayout(rapidjson::Writer<rapidjson::StringBuffer>&) const override; - RasterPaintProperties::Cascading cascading; + RasterPaintProperties::Transitionable paint; }; } // namespace style diff --git a/src/mbgl/style/layers/raster_layer_properties.hpp b/src/mbgl/style/layers/raster_layer_properties.hpp index 219fe34d8c..12df09f32c 100644 --- a/src/mbgl/style/layers/raster_layer_properties.hpp +++ b/src/mbgl/style/layers/raster_layer_properties.hpp @@ -5,7 +5,9 @@ #include <mbgl/style/types.hpp> #include <mbgl/style/layout_property.hpp> #include <mbgl/style/paint_property.hpp> +#include <mbgl/style/properties.hpp> #include <mbgl/programs/attributes.hpp> +#include <mbgl/programs/uniforms.hpp> namespace mbgl { namespace style { @@ -38,7 +40,7 @@ struct RasterFadeDuration : PaintProperty<float> { static float defaultValue() { return 300; } }; -class RasterPaintProperties : public PaintProperties< +class RasterPaintProperties : public Properties< RasterOpacity, RasterHueRotate, RasterBrightnessMin, diff --git a/src/mbgl/style/layers/symbol_layer.cpp b/src/mbgl/style/layers/symbol_layer.cpp index 273a9fd24e..9a944657ca 100644 --- a/src/mbgl/style/layers/symbol_layer.cpp +++ b/src/mbgl/style/layers/symbol_layer.cpp @@ -2,63 +2,92 @@ #include <mbgl/style/layers/symbol_layer.hpp> #include <mbgl/style/layers/symbol_layer_impl.hpp> -#include <mbgl/style/conversion/stringify.hpp> +#include <mbgl/style/layer_observer.hpp> namespace mbgl { namespace style { SymbolLayer::SymbolLayer(const std::string& layerID, const std::string& sourceID) - : Layer(LayerType::Symbol, std::make_unique<Impl>()) - , impl(static_cast<Impl*>(baseImpl.get())) { - impl->id = layerID; - impl->source = sourceID; + : Layer(makeMutable<Impl>(LayerType::Symbol, layerID, sourceID)) { } -SymbolLayer::SymbolLayer(const Impl& other) - : Layer(LayerType::Symbol, std::make_unique<Impl>(other)) - , impl(static_cast<Impl*>(baseImpl.get())) { +SymbolLayer::SymbolLayer(Immutable<Impl> impl_) + : Layer(std::move(impl_)) { } SymbolLayer::~SymbolLayer() = default; -std::unique_ptr<Layer> SymbolLayer::Impl::clone() const { - return std::make_unique<SymbolLayer>(*this); +const SymbolLayer::Impl& SymbolLayer::impl() const { + return static_cast<const Impl&>(*baseImpl); } -std::unique_ptr<Layer> SymbolLayer::Impl::cloneRef(const std::string& id_) const { - auto result = std::make_unique<SymbolLayer>(*this); - result->impl->id = id_; - result->impl->cascading = SymbolPaintProperties::Cascading(); - return std::move(result); +Mutable<SymbolLayer::Impl> SymbolLayer::mutableImpl() const { + return makeMutable<Impl>(impl()); +} + +std::unique_ptr<Layer> SymbolLayer::cloneRef(const std::string& id_) const { + auto impl_ = mutableImpl(); + impl_->id = id_; + impl_->paint = SymbolPaintProperties::Transitionable(); + return std::make_unique<SymbolLayer>(std::move(impl_)); } void SymbolLayer::Impl::stringifyLayout(rapidjson::Writer<rapidjson::StringBuffer>& writer) const { - conversion::stringify(writer, layout); + layout.stringify(writer); } // Source const std::string& SymbolLayer::getSourceID() const { - return impl->source; + return impl().source; } void SymbolLayer::setSourceLayer(const std::string& sourceLayer) { - impl->sourceLayer = sourceLayer; + auto impl_ = mutableImpl(); + impl_->sourceLayer = sourceLayer; + baseImpl = std::move(impl_); } const std::string& SymbolLayer::getSourceLayer() const { - return impl->sourceLayer; + return impl().sourceLayer; } // Filter void SymbolLayer::setFilter(const Filter& filter) { - impl->filter = filter; - impl->observer->onLayerFilterChanged(*this); + auto impl_ = mutableImpl(); + impl_->filter = filter; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } const Filter& SymbolLayer::getFilter() const { - return impl->filter; + return impl().filter; +} + +// Visibility + +void SymbolLayer::setVisibility(VisibilityType value) { + if (value == getVisibility()) + return; + auto impl_ = mutableImpl(); + impl_->visibility = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); +} + +// Zoom range + +void SymbolLayer::setMinZoom(float minZoom) { + auto impl_ = mutableImpl(); + impl_->minZoom = minZoom; + baseImpl = std::move(impl_); +} + +void SymbolLayer::setMaxZoom(float maxZoom) { + auto impl_ = mutableImpl(); + impl_->maxZoom = maxZoom; + baseImpl = std::move(impl_); } // Layout properties @@ -68,476 +97,576 @@ PropertyValue<SymbolPlacementType> SymbolLayer::getDefaultSymbolPlacement() { } PropertyValue<SymbolPlacementType> SymbolLayer::getSymbolPlacement() const { - return impl->layout.unevaluated.get<SymbolPlacement>(); + return impl().layout.get<SymbolPlacement>(); } void SymbolLayer::setSymbolPlacement(PropertyValue<SymbolPlacementType> value) { if (value == getSymbolPlacement()) return; - impl->layout.unevaluated.get<SymbolPlacement>() = value; - impl->observer->onLayerLayoutPropertyChanged(*this, "symbol-placement"); + auto impl_ = mutableImpl(); + impl_->layout.get<SymbolPlacement>() = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } PropertyValue<float> SymbolLayer::getDefaultSymbolSpacing() { return SymbolSpacing::defaultValue(); } PropertyValue<float> SymbolLayer::getSymbolSpacing() const { - return impl->layout.unevaluated.get<SymbolSpacing>(); + return impl().layout.get<SymbolSpacing>(); } void SymbolLayer::setSymbolSpacing(PropertyValue<float> value) { if (value == getSymbolSpacing()) return; - impl->layout.unevaluated.get<SymbolSpacing>() = value; - impl->observer->onLayerLayoutPropertyChanged(*this, "symbol-spacing"); + auto impl_ = mutableImpl(); + impl_->layout.get<SymbolSpacing>() = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } PropertyValue<bool> SymbolLayer::getDefaultSymbolAvoidEdges() { return SymbolAvoidEdges::defaultValue(); } PropertyValue<bool> SymbolLayer::getSymbolAvoidEdges() const { - return impl->layout.unevaluated.get<SymbolAvoidEdges>(); + return impl().layout.get<SymbolAvoidEdges>(); } void SymbolLayer::setSymbolAvoidEdges(PropertyValue<bool> value) { if (value == getSymbolAvoidEdges()) return; - impl->layout.unevaluated.get<SymbolAvoidEdges>() = value; - impl->observer->onLayerLayoutPropertyChanged(*this, "symbol-avoid-edges"); + auto impl_ = mutableImpl(); + impl_->layout.get<SymbolAvoidEdges>() = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } PropertyValue<bool> SymbolLayer::getDefaultIconAllowOverlap() { return IconAllowOverlap::defaultValue(); } PropertyValue<bool> SymbolLayer::getIconAllowOverlap() const { - return impl->layout.unevaluated.get<IconAllowOverlap>(); + return impl().layout.get<IconAllowOverlap>(); } void SymbolLayer::setIconAllowOverlap(PropertyValue<bool> value) { if (value == getIconAllowOverlap()) return; - impl->layout.unevaluated.get<IconAllowOverlap>() = value; - impl->observer->onLayerLayoutPropertyChanged(*this, "icon-allow-overlap"); + auto impl_ = mutableImpl(); + impl_->layout.get<IconAllowOverlap>() = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } PropertyValue<bool> SymbolLayer::getDefaultIconIgnorePlacement() { return IconIgnorePlacement::defaultValue(); } PropertyValue<bool> SymbolLayer::getIconIgnorePlacement() const { - return impl->layout.unevaluated.get<IconIgnorePlacement>(); + return impl().layout.get<IconIgnorePlacement>(); } void SymbolLayer::setIconIgnorePlacement(PropertyValue<bool> value) { if (value == getIconIgnorePlacement()) return; - impl->layout.unevaluated.get<IconIgnorePlacement>() = value; - impl->observer->onLayerLayoutPropertyChanged(*this, "icon-ignore-placement"); + auto impl_ = mutableImpl(); + impl_->layout.get<IconIgnorePlacement>() = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } PropertyValue<bool> SymbolLayer::getDefaultIconOptional() { return IconOptional::defaultValue(); } PropertyValue<bool> SymbolLayer::getIconOptional() const { - return impl->layout.unevaluated.get<IconOptional>(); + return impl().layout.get<IconOptional>(); } void SymbolLayer::setIconOptional(PropertyValue<bool> value) { if (value == getIconOptional()) return; - impl->layout.unevaluated.get<IconOptional>() = value; - impl->observer->onLayerLayoutPropertyChanged(*this, "icon-optional"); + auto impl_ = mutableImpl(); + impl_->layout.get<IconOptional>() = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } PropertyValue<AlignmentType> SymbolLayer::getDefaultIconRotationAlignment() { return IconRotationAlignment::defaultValue(); } PropertyValue<AlignmentType> SymbolLayer::getIconRotationAlignment() const { - return impl->layout.unevaluated.get<IconRotationAlignment>(); + return impl().layout.get<IconRotationAlignment>(); } void SymbolLayer::setIconRotationAlignment(PropertyValue<AlignmentType> value) { if (value == getIconRotationAlignment()) return; - impl->layout.unevaluated.get<IconRotationAlignment>() = value; - impl->observer->onLayerLayoutPropertyChanged(*this, "icon-rotation-alignment"); + auto impl_ = mutableImpl(); + impl_->layout.get<IconRotationAlignment>() = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } DataDrivenPropertyValue<float> SymbolLayer::getDefaultIconSize() { return IconSize::defaultValue(); } DataDrivenPropertyValue<float> SymbolLayer::getIconSize() const { - return impl->layout.unevaluated.get<IconSize>(); + return impl().layout.get<IconSize>(); } void SymbolLayer::setIconSize(DataDrivenPropertyValue<float> value) { if (value == getIconSize()) return; - impl->layout.unevaluated.get<IconSize>() = value; - impl->observer->onLayerLayoutPropertyChanged(*this, "icon-size"); + auto impl_ = mutableImpl(); + impl_->layout.get<IconSize>() = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } PropertyValue<IconTextFitType> SymbolLayer::getDefaultIconTextFit() { return IconTextFit::defaultValue(); } PropertyValue<IconTextFitType> SymbolLayer::getIconTextFit() const { - return impl->layout.unevaluated.get<IconTextFit>(); + return impl().layout.get<IconTextFit>(); } void SymbolLayer::setIconTextFit(PropertyValue<IconTextFitType> value) { if (value == getIconTextFit()) return; - impl->layout.unevaluated.get<IconTextFit>() = value; - impl->observer->onLayerLayoutPropertyChanged(*this, "icon-text-fit"); + auto impl_ = mutableImpl(); + impl_->layout.get<IconTextFit>() = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } PropertyValue<std::array<float, 4>> SymbolLayer::getDefaultIconTextFitPadding() { return IconTextFitPadding::defaultValue(); } PropertyValue<std::array<float, 4>> SymbolLayer::getIconTextFitPadding() const { - return impl->layout.unevaluated.get<IconTextFitPadding>(); + return impl().layout.get<IconTextFitPadding>(); } void SymbolLayer::setIconTextFitPadding(PropertyValue<std::array<float, 4>> value) { if (value == getIconTextFitPadding()) return; - impl->layout.unevaluated.get<IconTextFitPadding>() = value; - impl->observer->onLayerLayoutPropertyChanged(*this, "icon-text-fit-padding"); + auto impl_ = mutableImpl(); + impl_->layout.get<IconTextFitPadding>() = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } DataDrivenPropertyValue<std::string> SymbolLayer::getDefaultIconImage() { return IconImage::defaultValue(); } DataDrivenPropertyValue<std::string> SymbolLayer::getIconImage() const { - return impl->layout.unevaluated.get<IconImage>(); + return impl().layout.get<IconImage>(); } void SymbolLayer::setIconImage(DataDrivenPropertyValue<std::string> value) { if (value == getIconImage()) return; - impl->layout.unevaluated.get<IconImage>() = value; - impl->observer->onLayerLayoutPropertyChanged(*this, "icon-image"); + auto impl_ = mutableImpl(); + impl_->layout.get<IconImage>() = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } DataDrivenPropertyValue<float> SymbolLayer::getDefaultIconRotate() { return IconRotate::defaultValue(); } DataDrivenPropertyValue<float> SymbolLayer::getIconRotate() const { - return impl->layout.unevaluated.get<IconRotate>(); + return impl().layout.get<IconRotate>(); } void SymbolLayer::setIconRotate(DataDrivenPropertyValue<float> value) { if (value == getIconRotate()) return; - impl->layout.unevaluated.get<IconRotate>() = value; - impl->observer->onLayerLayoutPropertyChanged(*this, "icon-rotate"); + auto impl_ = mutableImpl(); + impl_->layout.get<IconRotate>() = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } PropertyValue<float> SymbolLayer::getDefaultIconPadding() { return IconPadding::defaultValue(); } PropertyValue<float> SymbolLayer::getIconPadding() const { - return impl->layout.unevaluated.get<IconPadding>(); + return impl().layout.get<IconPadding>(); } void SymbolLayer::setIconPadding(PropertyValue<float> value) { if (value == getIconPadding()) return; - impl->layout.unevaluated.get<IconPadding>() = value; - impl->observer->onLayerLayoutPropertyChanged(*this, "icon-padding"); + auto impl_ = mutableImpl(); + impl_->layout.get<IconPadding>() = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } PropertyValue<bool> SymbolLayer::getDefaultIconKeepUpright() { return IconKeepUpright::defaultValue(); } PropertyValue<bool> SymbolLayer::getIconKeepUpright() const { - return impl->layout.unevaluated.get<IconKeepUpright>(); + return impl().layout.get<IconKeepUpright>(); } void SymbolLayer::setIconKeepUpright(PropertyValue<bool> value) { if (value == getIconKeepUpright()) return; - impl->layout.unevaluated.get<IconKeepUpright>() = value; - impl->observer->onLayerLayoutPropertyChanged(*this, "icon-keep-upright"); + auto impl_ = mutableImpl(); + impl_->layout.get<IconKeepUpright>() = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } DataDrivenPropertyValue<std::array<float, 2>> SymbolLayer::getDefaultIconOffset() { return IconOffset::defaultValue(); } DataDrivenPropertyValue<std::array<float, 2>> SymbolLayer::getIconOffset() const { - return impl->layout.unevaluated.get<IconOffset>(); + return impl().layout.get<IconOffset>(); } void SymbolLayer::setIconOffset(DataDrivenPropertyValue<std::array<float, 2>> value) { if (value == getIconOffset()) return; - impl->layout.unevaluated.get<IconOffset>() = value; - impl->observer->onLayerLayoutPropertyChanged(*this, "icon-offset"); + auto impl_ = mutableImpl(); + impl_->layout.get<IconOffset>() = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); +} +DataDrivenPropertyValue<SymbolAnchorType> SymbolLayer::getDefaultIconAnchor() { + return IconAnchor::defaultValue(); +} + +DataDrivenPropertyValue<SymbolAnchorType> SymbolLayer::getIconAnchor() const { + return impl().layout.get<IconAnchor>(); +} + +void SymbolLayer::setIconAnchor(DataDrivenPropertyValue<SymbolAnchorType> value) { + if (value == getIconAnchor()) + return; + auto impl_ = mutableImpl(); + impl_->layout.get<IconAnchor>() = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); +} +PropertyValue<AlignmentType> SymbolLayer::getDefaultIconPitchAlignment() { + return IconPitchAlignment::defaultValue(); +} + +PropertyValue<AlignmentType> SymbolLayer::getIconPitchAlignment() const { + return impl().layout.get<IconPitchAlignment>(); +} + +void SymbolLayer::setIconPitchAlignment(PropertyValue<AlignmentType> value) { + if (value == getIconPitchAlignment()) + return; + auto impl_ = mutableImpl(); + impl_->layout.get<IconPitchAlignment>() = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } PropertyValue<AlignmentType> SymbolLayer::getDefaultTextPitchAlignment() { return TextPitchAlignment::defaultValue(); } PropertyValue<AlignmentType> SymbolLayer::getTextPitchAlignment() const { - return impl->layout.unevaluated.get<TextPitchAlignment>(); + return impl().layout.get<TextPitchAlignment>(); } void SymbolLayer::setTextPitchAlignment(PropertyValue<AlignmentType> value) { if (value == getTextPitchAlignment()) return; - impl->layout.unevaluated.get<TextPitchAlignment>() = value; - impl->observer->onLayerLayoutPropertyChanged(*this, "text-pitch-alignment"); + auto impl_ = mutableImpl(); + impl_->layout.get<TextPitchAlignment>() = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } PropertyValue<AlignmentType> SymbolLayer::getDefaultTextRotationAlignment() { return TextRotationAlignment::defaultValue(); } PropertyValue<AlignmentType> SymbolLayer::getTextRotationAlignment() const { - return impl->layout.unevaluated.get<TextRotationAlignment>(); + return impl().layout.get<TextRotationAlignment>(); } void SymbolLayer::setTextRotationAlignment(PropertyValue<AlignmentType> value) { if (value == getTextRotationAlignment()) return; - impl->layout.unevaluated.get<TextRotationAlignment>() = value; - impl->observer->onLayerLayoutPropertyChanged(*this, "text-rotation-alignment"); + auto impl_ = mutableImpl(); + impl_->layout.get<TextRotationAlignment>() = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } DataDrivenPropertyValue<std::string> SymbolLayer::getDefaultTextField() { return TextField::defaultValue(); } DataDrivenPropertyValue<std::string> SymbolLayer::getTextField() const { - return impl->layout.unevaluated.get<TextField>(); + return impl().layout.get<TextField>(); } void SymbolLayer::setTextField(DataDrivenPropertyValue<std::string> value) { if (value == getTextField()) return; - impl->layout.unevaluated.get<TextField>() = value; - impl->observer->onLayerLayoutPropertyChanged(*this, "text-field"); + auto impl_ = mutableImpl(); + impl_->layout.get<TextField>() = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } PropertyValue<std::vector<std::string>> SymbolLayer::getDefaultTextFont() { return TextFont::defaultValue(); } PropertyValue<std::vector<std::string>> SymbolLayer::getTextFont() const { - return impl->layout.unevaluated.get<TextFont>(); + return impl().layout.get<TextFont>(); } void SymbolLayer::setTextFont(PropertyValue<std::vector<std::string>> value) { if (value == getTextFont()) return; - impl->layout.unevaluated.get<TextFont>() = value; - impl->observer->onLayerLayoutPropertyChanged(*this, "text-font"); + auto impl_ = mutableImpl(); + impl_->layout.get<TextFont>() = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } DataDrivenPropertyValue<float> SymbolLayer::getDefaultTextSize() { return TextSize::defaultValue(); } DataDrivenPropertyValue<float> SymbolLayer::getTextSize() const { - return impl->layout.unevaluated.get<TextSize>(); + return impl().layout.get<TextSize>(); } void SymbolLayer::setTextSize(DataDrivenPropertyValue<float> value) { if (value == getTextSize()) return; - impl->layout.unevaluated.get<TextSize>() = value; - impl->observer->onLayerLayoutPropertyChanged(*this, "text-size"); + auto impl_ = mutableImpl(); + impl_->layout.get<TextSize>() = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } -PropertyValue<float> SymbolLayer::getDefaultTextMaxWidth() { +DataDrivenPropertyValue<float> SymbolLayer::getDefaultTextMaxWidth() { return TextMaxWidth::defaultValue(); } -PropertyValue<float> SymbolLayer::getTextMaxWidth() const { - return impl->layout.unevaluated.get<TextMaxWidth>(); +DataDrivenPropertyValue<float> SymbolLayer::getTextMaxWidth() const { + return impl().layout.get<TextMaxWidth>(); } -void SymbolLayer::setTextMaxWidth(PropertyValue<float> value) { +void SymbolLayer::setTextMaxWidth(DataDrivenPropertyValue<float> value) { if (value == getTextMaxWidth()) return; - impl->layout.unevaluated.get<TextMaxWidth>() = value; - impl->observer->onLayerLayoutPropertyChanged(*this, "text-max-width"); + auto impl_ = mutableImpl(); + impl_->layout.get<TextMaxWidth>() = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } PropertyValue<float> SymbolLayer::getDefaultTextLineHeight() { return TextLineHeight::defaultValue(); } PropertyValue<float> SymbolLayer::getTextLineHeight() const { - return impl->layout.unevaluated.get<TextLineHeight>(); + return impl().layout.get<TextLineHeight>(); } void SymbolLayer::setTextLineHeight(PropertyValue<float> value) { if (value == getTextLineHeight()) return; - impl->layout.unevaluated.get<TextLineHeight>() = value; - impl->observer->onLayerLayoutPropertyChanged(*this, "text-line-height"); + auto impl_ = mutableImpl(); + impl_->layout.get<TextLineHeight>() = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } -PropertyValue<float> SymbolLayer::getDefaultTextLetterSpacing() { +DataDrivenPropertyValue<float> SymbolLayer::getDefaultTextLetterSpacing() { return TextLetterSpacing::defaultValue(); } -PropertyValue<float> SymbolLayer::getTextLetterSpacing() const { - return impl->layout.unevaluated.get<TextLetterSpacing>(); +DataDrivenPropertyValue<float> SymbolLayer::getTextLetterSpacing() const { + return impl().layout.get<TextLetterSpacing>(); } -void SymbolLayer::setTextLetterSpacing(PropertyValue<float> value) { +void SymbolLayer::setTextLetterSpacing(DataDrivenPropertyValue<float> value) { if (value == getTextLetterSpacing()) return; - impl->layout.unevaluated.get<TextLetterSpacing>() = value; - impl->observer->onLayerLayoutPropertyChanged(*this, "text-letter-spacing"); + auto impl_ = mutableImpl(); + impl_->layout.get<TextLetterSpacing>() = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } -PropertyValue<TextJustifyType> SymbolLayer::getDefaultTextJustify() { +DataDrivenPropertyValue<TextJustifyType> SymbolLayer::getDefaultTextJustify() { return TextJustify::defaultValue(); } -PropertyValue<TextJustifyType> SymbolLayer::getTextJustify() const { - return impl->layout.unevaluated.get<TextJustify>(); +DataDrivenPropertyValue<TextJustifyType> SymbolLayer::getTextJustify() const { + return impl().layout.get<TextJustify>(); } -void SymbolLayer::setTextJustify(PropertyValue<TextJustifyType> value) { +void SymbolLayer::setTextJustify(DataDrivenPropertyValue<TextJustifyType> value) { if (value == getTextJustify()) return; - impl->layout.unevaluated.get<TextJustify>() = value; - impl->observer->onLayerLayoutPropertyChanged(*this, "text-justify"); + auto impl_ = mutableImpl(); + impl_->layout.get<TextJustify>() = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } -PropertyValue<TextAnchorType> SymbolLayer::getDefaultTextAnchor() { +DataDrivenPropertyValue<SymbolAnchorType> SymbolLayer::getDefaultTextAnchor() { return TextAnchor::defaultValue(); } -PropertyValue<TextAnchorType> SymbolLayer::getTextAnchor() const { - return impl->layout.unevaluated.get<TextAnchor>(); +DataDrivenPropertyValue<SymbolAnchorType> SymbolLayer::getTextAnchor() const { + return impl().layout.get<TextAnchor>(); } -void SymbolLayer::setTextAnchor(PropertyValue<TextAnchorType> value) { +void SymbolLayer::setTextAnchor(DataDrivenPropertyValue<SymbolAnchorType> value) { if (value == getTextAnchor()) return; - impl->layout.unevaluated.get<TextAnchor>() = value; - impl->observer->onLayerLayoutPropertyChanged(*this, "text-anchor"); + auto impl_ = mutableImpl(); + impl_->layout.get<TextAnchor>() = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } PropertyValue<float> SymbolLayer::getDefaultTextMaxAngle() { return TextMaxAngle::defaultValue(); } PropertyValue<float> SymbolLayer::getTextMaxAngle() const { - return impl->layout.unevaluated.get<TextMaxAngle>(); + return impl().layout.get<TextMaxAngle>(); } void SymbolLayer::setTextMaxAngle(PropertyValue<float> value) { if (value == getTextMaxAngle()) return; - impl->layout.unevaluated.get<TextMaxAngle>() = value; - impl->observer->onLayerLayoutPropertyChanged(*this, "text-max-angle"); + auto impl_ = mutableImpl(); + impl_->layout.get<TextMaxAngle>() = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } DataDrivenPropertyValue<float> SymbolLayer::getDefaultTextRotate() { return TextRotate::defaultValue(); } DataDrivenPropertyValue<float> SymbolLayer::getTextRotate() const { - return impl->layout.unevaluated.get<TextRotate>(); + return impl().layout.get<TextRotate>(); } void SymbolLayer::setTextRotate(DataDrivenPropertyValue<float> value) { if (value == getTextRotate()) return; - impl->layout.unevaluated.get<TextRotate>() = value; - impl->observer->onLayerLayoutPropertyChanged(*this, "text-rotate"); + auto impl_ = mutableImpl(); + impl_->layout.get<TextRotate>() = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } PropertyValue<float> SymbolLayer::getDefaultTextPadding() { return TextPadding::defaultValue(); } PropertyValue<float> SymbolLayer::getTextPadding() const { - return impl->layout.unevaluated.get<TextPadding>(); + return impl().layout.get<TextPadding>(); } void SymbolLayer::setTextPadding(PropertyValue<float> value) { if (value == getTextPadding()) return; - impl->layout.unevaluated.get<TextPadding>() = value; - impl->observer->onLayerLayoutPropertyChanged(*this, "text-padding"); + auto impl_ = mutableImpl(); + impl_->layout.get<TextPadding>() = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } PropertyValue<bool> SymbolLayer::getDefaultTextKeepUpright() { return TextKeepUpright::defaultValue(); } PropertyValue<bool> SymbolLayer::getTextKeepUpright() const { - return impl->layout.unevaluated.get<TextKeepUpright>(); + return impl().layout.get<TextKeepUpright>(); } void SymbolLayer::setTextKeepUpright(PropertyValue<bool> value) { if (value == getTextKeepUpright()) return; - impl->layout.unevaluated.get<TextKeepUpright>() = value; - impl->observer->onLayerLayoutPropertyChanged(*this, "text-keep-upright"); + auto impl_ = mutableImpl(); + impl_->layout.get<TextKeepUpright>() = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } DataDrivenPropertyValue<TextTransformType> SymbolLayer::getDefaultTextTransform() { return TextTransform::defaultValue(); } DataDrivenPropertyValue<TextTransformType> SymbolLayer::getTextTransform() const { - return impl->layout.unevaluated.get<TextTransform>(); + return impl().layout.get<TextTransform>(); } void SymbolLayer::setTextTransform(DataDrivenPropertyValue<TextTransformType> value) { if (value == getTextTransform()) return; - impl->layout.unevaluated.get<TextTransform>() = value; - impl->observer->onLayerLayoutPropertyChanged(*this, "text-transform"); + auto impl_ = mutableImpl(); + impl_->layout.get<TextTransform>() = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } DataDrivenPropertyValue<std::array<float, 2>> SymbolLayer::getDefaultTextOffset() { return TextOffset::defaultValue(); } DataDrivenPropertyValue<std::array<float, 2>> SymbolLayer::getTextOffset() const { - return impl->layout.unevaluated.get<TextOffset>(); + return impl().layout.get<TextOffset>(); } void SymbolLayer::setTextOffset(DataDrivenPropertyValue<std::array<float, 2>> value) { if (value == getTextOffset()) return; - impl->layout.unevaluated.get<TextOffset>() = value; - impl->observer->onLayerLayoutPropertyChanged(*this, "text-offset"); + auto impl_ = mutableImpl(); + impl_->layout.get<TextOffset>() = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } PropertyValue<bool> SymbolLayer::getDefaultTextAllowOverlap() { return TextAllowOverlap::defaultValue(); } PropertyValue<bool> SymbolLayer::getTextAllowOverlap() const { - return impl->layout.unevaluated.get<TextAllowOverlap>(); + return impl().layout.get<TextAllowOverlap>(); } void SymbolLayer::setTextAllowOverlap(PropertyValue<bool> value) { if (value == getTextAllowOverlap()) return; - impl->layout.unevaluated.get<TextAllowOverlap>() = value; - impl->observer->onLayerLayoutPropertyChanged(*this, "text-allow-overlap"); + auto impl_ = mutableImpl(); + impl_->layout.get<TextAllowOverlap>() = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } PropertyValue<bool> SymbolLayer::getDefaultTextIgnorePlacement() { return TextIgnorePlacement::defaultValue(); } PropertyValue<bool> SymbolLayer::getTextIgnorePlacement() const { - return impl->layout.unevaluated.get<TextIgnorePlacement>(); + return impl().layout.get<TextIgnorePlacement>(); } void SymbolLayer::setTextIgnorePlacement(PropertyValue<bool> value) { if (value == getTextIgnorePlacement()) return; - impl->layout.unevaluated.get<TextIgnorePlacement>() = value; - impl->observer->onLayerLayoutPropertyChanged(*this, "text-ignore-placement"); + auto impl_ = mutableImpl(); + impl_->layout.get<TextIgnorePlacement>() = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } PropertyValue<bool> SymbolLayer::getDefaultTextOptional() { return TextOptional::defaultValue(); } PropertyValue<bool> SymbolLayer::getTextOptional() const { - return impl->layout.unevaluated.get<TextOptional>(); + return impl().layout.get<TextOptional>(); } void SymbolLayer::setTextOptional(PropertyValue<bool> value) { if (value == getTextOptional()) return; - impl->layout.unevaluated.get<TextOptional>() = value; - impl->observer->onLayerLayoutPropertyChanged(*this, "text-optional"); + auto impl_ = mutableImpl(); + impl_->layout.get<TextOptional>() = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } // Paint properties @@ -546,362 +675,378 @@ DataDrivenPropertyValue<float> SymbolLayer::getDefaultIconOpacity() { return { 1 }; } -DataDrivenPropertyValue<float> SymbolLayer::getIconOpacity(const optional<std::string>& klass) const { - return impl->cascading.template get<IconOpacity>().get(klass); +DataDrivenPropertyValue<float> SymbolLayer::getIconOpacity() const { + return impl().paint.template get<IconOpacity>().value; } -void SymbolLayer::setIconOpacity(DataDrivenPropertyValue<float> value, const optional<std::string>& klass) { - if (value == getIconOpacity(klass)) +void SymbolLayer::setIconOpacity(DataDrivenPropertyValue<float> value) { + if (value == getIconOpacity()) return; - impl->cascading.template get<IconOpacity>().set(value, klass); - if (value.isDataDriven()) { - impl->observer->onLayerDataDrivenPaintPropertyChanged(*this); - } else { - impl->observer->onLayerPaintPropertyChanged(*this); - } + auto impl_ = mutableImpl(); + impl_->paint.template get<IconOpacity>().value = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } -void SymbolLayer::setIconOpacityTransition(const TransitionOptions& value, const optional<std::string>& klass) { - impl->cascading.template get<IconOpacity>().setTransition(value, klass); +void SymbolLayer::setIconOpacityTransition(const TransitionOptions& options) { + auto impl_ = mutableImpl(); + impl_->paint.template get<IconOpacity>().options = options; + baseImpl = std::move(impl_); } -TransitionOptions SymbolLayer::getIconOpacityTransition(const optional<std::string>& klass) const { - return impl->cascading.template get<IconOpacity>().getTransition(klass); +TransitionOptions SymbolLayer::getIconOpacityTransition() const { + return impl().paint.template get<IconOpacity>().options; } DataDrivenPropertyValue<Color> SymbolLayer::getDefaultIconColor() { return { Color::black() }; } -DataDrivenPropertyValue<Color> SymbolLayer::getIconColor(const optional<std::string>& klass) const { - return impl->cascading.template get<IconColor>().get(klass); +DataDrivenPropertyValue<Color> SymbolLayer::getIconColor() const { + return impl().paint.template get<IconColor>().value; } -void SymbolLayer::setIconColor(DataDrivenPropertyValue<Color> value, const optional<std::string>& klass) { - if (value == getIconColor(klass)) +void SymbolLayer::setIconColor(DataDrivenPropertyValue<Color> value) { + if (value == getIconColor()) return; - impl->cascading.template get<IconColor>().set(value, klass); - if (value.isDataDriven()) { - impl->observer->onLayerDataDrivenPaintPropertyChanged(*this); - } else { - impl->observer->onLayerPaintPropertyChanged(*this); - } + auto impl_ = mutableImpl(); + impl_->paint.template get<IconColor>().value = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } -void SymbolLayer::setIconColorTransition(const TransitionOptions& value, const optional<std::string>& klass) { - impl->cascading.template get<IconColor>().setTransition(value, klass); +void SymbolLayer::setIconColorTransition(const TransitionOptions& options) { + auto impl_ = mutableImpl(); + impl_->paint.template get<IconColor>().options = options; + baseImpl = std::move(impl_); } -TransitionOptions SymbolLayer::getIconColorTransition(const optional<std::string>& klass) const { - return impl->cascading.template get<IconColor>().getTransition(klass); +TransitionOptions SymbolLayer::getIconColorTransition() const { + return impl().paint.template get<IconColor>().options; } DataDrivenPropertyValue<Color> SymbolLayer::getDefaultIconHaloColor() { return { {} }; } -DataDrivenPropertyValue<Color> SymbolLayer::getIconHaloColor(const optional<std::string>& klass) const { - return impl->cascading.template get<IconHaloColor>().get(klass); +DataDrivenPropertyValue<Color> SymbolLayer::getIconHaloColor() const { + return impl().paint.template get<IconHaloColor>().value; } -void SymbolLayer::setIconHaloColor(DataDrivenPropertyValue<Color> value, const optional<std::string>& klass) { - if (value == getIconHaloColor(klass)) +void SymbolLayer::setIconHaloColor(DataDrivenPropertyValue<Color> value) { + if (value == getIconHaloColor()) return; - impl->cascading.template get<IconHaloColor>().set(value, klass); - if (value.isDataDriven()) { - impl->observer->onLayerDataDrivenPaintPropertyChanged(*this); - } else { - impl->observer->onLayerPaintPropertyChanged(*this); - } + auto impl_ = mutableImpl(); + impl_->paint.template get<IconHaloColor>().value = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } -void SymbolLayer::setIconHaloColorTransition(const TransitionOptions& value, const optional<std::string>& klass) { - impl->cascading.template get<IconHaloColor>().setTransition(value, klass); +void SymbolLayer::setIconHaloColorTransition(const TransitionOptions& options) { + auto impl_ = mutableImpl(); + impl_->paint.template get<IconHaloColor>().options = options; + baseImpl = std::move(impl_); } -TransitionOptions SymbolLayer::getIconHaloColorTransition(const optional<std::string>& klass) const { - return impl->cascading.template get<IconHaloColor>().getTransition(klass); +TransitionOptions SymbolLayer::getIconHaloColorTransition() const { + return impl().paint.template get<IconHaloColor>().options; } DataDrivenPropertyValue<float> SymbolLayer::getDefaultIconHaloWidth() { return { 0 }; } -DataDrivenPropertyValue<float> SymbolLayer::getIconHaloWidth(const optional<std::string>& klass) const { - return impl->cascading.template get<IconHaloWidth>().get(klass); +DataDrivenPropertyValue<float> SymbolLayer::getIconHaloWidth() const { + return impl().paint.template get<IconHaloWidth>().value; } -void SymbolLayer::setIconHaloWidth(DataDrivenPropertyValue<float> value, const optional<std::string>& klass) { - if (value == getIconHaloWidth(klass)) +void SymbolLayer::setIconHaloWidth(DataDrivenPropertyValue<float> value) { + if (value == getIconHaloWidth()) return; - impl->cascading.template get<IconHaloWidth>().set(value, klass); - if (value.isDataDriven()) { - impl->observer->onLayerDataDrivenPaintPropertyChanged(*this); - } else { - impl->observer->onLayerPaintPropertyChanged(*this); - } + auto impl_ = mutableImpl(); + impl_->paint.template get<IconHaloWidth>().value = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } -void SymbolLayer::setIconHaloWidthTransition(const TransitionOptions& value, const optional<std::string>& klass) { - impl->cascading.template get<IconHaloWidth>().setTransition(value, klass); +void SymbolLayer::setIconHaloWidthTransition(const TransitionOptions& options) { + auto impl_ = mutableImpl(); + impl_->paint.template get<IconHaloWidth>().options = options; + baseImpl = std::move(impl_); } -TransitionOptions SymbolLayer::getIconHaloWidthTransition(const optional<std::string>& klass) const { - return impl->cascading.template get<IconHaloWidth>().getTransition(klass); +TransitionOptions SymbolLayer::getIconHaloWidthTransition() const { + return impl().paint.template get<IconHaloWidth>().options; } DataDrivenPropertyValue<float> SymbolLayer::getDefaultIconHaloBlur() { return { 0 }; } -DataDrivenPropertyValue<float> SymbolLayer::getIconHaloBlur(const optional<std::string>& klass) const { - return impl->cascading.template get<IconHaloBlur>().get(klass); +DataDrivenPropertyValue<float> SymbolLayer::getIconHaloBlur() const { + return impl().paint.template get<IconHaloBlur>().value; } -void SymbolLayer::setIconHaloBlur(DataDrivenPropertyValue<float> value, const optional<std::string>& klass) { - if (value == getIconHaloBlur(klass)) +void SymbolLayer::setIconHaloBlur(DataDrivenPropertyValue<float> value) { + if (value == getIconHaloBlur()) return; - impl->cascading.template get<IconHaloBlur>().set(value, klass); - if (value.isDataDriven()) { - impl->observer->onLayerDataDrivenPaintPropertyChanged(*this); - } else { - impl->observer->onLayerPaintPropertyChanged(*this); - } + auto impl_ = mutableImpl(); + impl_->paint.template get<IconHaloBlur>().value = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } -void SymbolLayer::setIconHaloBlurTransition(const TransitionOptions& value, const optional<std::string>& klass) { - impl->cascading.template get<IconHaloBlur>().setTransition(value, klass); +void SymbolLayer::setIconHaloBlurTransition(const TransitionOptions& options) { + auto impl_ = mutableImpl(); + impl_->paint.template get<IconHaloBlur>().options = options; + baseImpl = std::move(impl_); } -TransitionOptions SymbolLayer::getIconHaloBlurTransition(const optional<std::string>& klass) const { - return impl->cascading.template get<IconHaloBlur>().getTransition(klass); +TransitionOptions SymbolLayer::getIconHaloBlurTransition() const { + return impl().paint.template get<IconHaloBlur>().options; } PropertyValue<std::array<float, 2>> SymbolLayer::getDefaultIconTranslate() { return { {{ 0, 0 }} }; } -PropertyValue<std::array<float, 2>> SymbolLayer::getIconTranslate(const optional<std::string>& klass) const { - return impl->cascading.template get<IconTranslate>().get(klass); +PropertyValue<std::array<float, 2>> SymbolLayer::getIconTranslate() const { + return impl().paint.template get<IconTranslate>().value; } -void SymbolLayer::setIconTranslate(PropertyValue<std::array<float, 2>> value, const optional<std::string>& klass) { - if (value == getIconTranslate(klass)) +void SymbolLayer::setIconTranslate(PropertyValue<std::array<float, 2>> value) { + if (value == getIconTranslate()) return; - impl->cascading.template get<IconTranslate>().set(value, klass); - impl->observer->onLayerPaintPropertyChanged(*this); + auto impl_ = mutableImpl(); + impl_->paint.template get<IconTranslate>().value = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } -void SymbolLayer::setIconTranslateTransition(const TransitionOptions& value, const optional<std::string>& klass) { - impl->cascading.template get<IconTranslate>().setTransition(value, klass); +void SymbolLayer::setIconTranslateTransition(const TransitionOptions& options) { + auto impl_ = mutableImpl(); + impl_->paint.template get<IconTranslate>().options = options; + baseImpl = std::move(impl_); } -TransitionOptions SymbolLayer::getIconTranslateTransition(const optional<std::string>& klass) const { - return impl->cascading.template get<IconTranslate>().getTransition(klass); +TransitionOptions SymbolLayer::getIconTranslateTransition() const { + return impl().paint.template get<IconTranslate>().options; } PropertyValue<TranslateAnchorType> SymbolLayer::getDefaultIconTranslateAnchor() { return { TranslateAnchorType::Map }; } -PropertyValue<TranslateAnchorType> SymbolLayer::getIconTranslateAnchor(const optional<std::string>& klass) const { - return impl->cascading.template get<IconTranslateAnchor>().get(klass); +PropertyValue<TranslateAnchorType> SymbolLayer::getIconTranslateAnchor() const { + return impl().paint.template get<IconTranslateAnchor>().value; } -void SymbolLayer::setIconTranslateAnchor(PropertyValue<TranslateAnchorType> value, const optional<std::string>& klass) { - if (value == getIconTranslateAnchor(klass)) +void SymbolLayer::setIconTranslateAnchor(PropertyValue<TranslateAnchorType> value) { + if (value == getIconTranslateAnchor()) return; - impl->cascading.template get<IconTranslateAnchor>().set(value, klass); - impl->observer->onLayerPaintPropertyChanged(*this); + auto impl_ = mutableImpl(); + impl_->paint.template get<IconTranslateAnchor>().value = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } -void SymbolLayer::setIconTranslateAnchorTransition(const TransitionOptions& value, const optional<std::string>& klass) { - impl->cascading.template get<IconTranslateAnchor>().setTransition(value, klass); +void SymbolLayer::setIconTranslateAnchorTransition(const TransitionOptions& options) { + auto impl_ = mutableImpl(); + impl_->paint.template get<IconTranslateAnchor>().options = options; + baseImpl = std::move(impl_); } -TransitionOptions SymbolLayer::getIconTranslateAnchorTransition(const optional<std::string>& klass) const { - return impl->cascading.template get<IconTranslateAnchor>().getTransition(klass); +TransitionOptions SymbolLayer::getIconTranslateAnchorTransition() const { + return impl().paint.template get<IconTranslateAnchor>().options; } DataDrivenPropertyValue<float> SymbolLayer::getDefaultTextOpacity() { return { 1 }; } -DataDrivenPropertyValue<float> SymbolLayer::getTextOpacity(const optional<std::string>& klass) const { - return impl->cascading.template get<TextOpacity>().get(klass); +DataDrivenPropertyValue<float> SymbolLayer::getTextOpacity() const { + return impl().paint.template get<TextOpacity>().value; } -void SymbolLayer::setTextOpacity(DataDrivenPropertyValue<float> value, const optional<std::string>& klass) { - if (value == getTextOpacity(klass)) +void SymbolLayer::setTextOpacity(DataDrivenPropertyValue<float> value) { + if (value == getTextOpacity()) return; - impl->cascading.template get<TextOpacity>().set(value, klass); - if (value.isDataDriven()) { - impl->observer->onLayerDataDrivenPaintPropertyChanged(*this); - } else { - impl->observer->onLayerPaintPropertyChanged(*this); - } + auto impl_ = mutableImpl(); + impl_->paint.template get<TextOpacity>().value = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } -void SymbolLayer::setTextOpacityTransition(const TransitionOptions& value, const optional<std::string>& klass) { - impl->cascading.template get<TextOpacity>().setTransition(value, klass); +void SymbolLayer::setTextOpacityTransition(const TransitionOptions& options) { + auto impl_ = mutableImpl(); + impl_->paint.template get<TextOpacity>().options = options; + baseImpl = std::move(impl_); } -TransitionOptions SymbolLayer::getTextOpacityTransition(const optional<std::string>& klass) const { - return impl->cascading.template get<TextOpacity>().getTransition(klass); +TransitionOptions SymbolLayer::getTextOpacityTransition() const { + return impl().paint.template get<TextOpacity>().options; } DataDrivenPropertyValue<Color> SymbolLayer::getDefaultTextColor() { return { Color::black() }; } -DataDrivenPropertyValue<Color> SymbolLayer::getTextColor(const optional<std::string>& klass) const { - return impl->cascading.template get<TextColor>().get(klass); +DataDrivenPropertyValue<Color> SymbolLayer::getTextColor() const { + return impl().paint.template get<TextColor>().value; } -void SymbolLayer::setTextColor(DataDrivenPropertyValue<Color> value, const optional<std::string>& klass) { - if (value == getTextColor(klass)) +void SymbolLayer::setTextColor(DataDrivenPropertyValue<Color> value) { + if (value == getTextColor()) return; - impl->cascading.template get<TextColor>().set(value, klass); - if (value.isDataDriven()) { - impl->observer->onLayerDataDrivenPaintPropertyChanged(*this); - } else { - impl->observer->onLayerPaintPropertyChanged(*this); - } + auto impl_ = mutableImpl(); + impl_->paint.template get<TextColor>().value = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } -void SymbolLayer::setTextColorTransition(const TransitionOptions& value, const optional<std::string>& klass) { - impl->cascading.template get<TextColor>().setTransition(value, klass); +void SymbolLayer::setTextColorTransition(const TransitionOptions& options) { + auto impl_ = mutableImpl(); + impl_->paint.template get<TextColor>().options = options; + baseImpl = std::move(impl_); } -TransitionOptions SymbolLayer::getTextColorTransition(const optional<std::string>& klass) const { - return impl->cascading.template get<TextColor>().getTransition(klass); +TransitionOptions SymbolLayer::getTextColorTransition() const { + return impl().paint.template get<TextColor>().options; } DataDrivenPropertyValue<Color> SymbolLayer::getDefaultTextHaloColor() { return { {} }; } -DataDrivenPropertyValue<Color> SymbolLayer::getTextHaloColor(const optional<std::string>& klass) const { - return impl->cascading.template get<TextHaloColor>().get(klass); +DataDrivenPropertyValue<Color> SymbolLayer::getTextHaloColor() const { + return impl().paint.template get<TextHaloColor>().value; } -void SymbolLayer::setTextHaloColor(DataDrivenPropertyValue<Color> value, const optional<std::string>& klass) { - if (value == getTextHaloColor(klass)) +void SymbolLayer::setTextHaloColor(DataDrivenPropertyValue<Color> value) { + if (value == getTextHaloColor()) return; - impl->cascading.template get<TextHaloColor>().set(value, klass); - if (value.isDataDriven()) { - impl->observer->onLayerDataDrivenPaintPropertyChanged(*this); - } else { - impl->observer->onLayerPaintPropertyChanged(*this); - } + auto impl_ = mutableImpl(); + impl_->paint.template get<TextHaloColor>().value = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } -void SymbolLayer::setTextHaloColorTransition(const TransitionOptions& value, const optional<std::string>& klass) { - impl->cascading.template get<TextHaloColor>().setTransition(value, klass); +void SymbolLayer::setTextHaloColorTransition(const TransitionOptions& options) { + auto impl_ = mutableImpl(); + impl_->paint.template get<TextHaloColor>().options = options; + baseImpl = std::move(impl_); } -TransitionOptions SymbolLayer::getTextHaloColorTransition(const optional<std::string>& klass) const { - return impl->cascading.template get<TextHaloColor>().getTransition(klass); +TransitionOptions SymbolLayer::getTextHaloColorTransition() const { + return impl().paint.template get<TextHaloColor>().options; } DataDrivenPropertyValue<float> SymbolLayer::getDefaultTextHaloWidth() { return { 0 }; } -DataDrivenPropertyValue<float> SymbolLayer::getTextHaloWidth(const optional<std::string>& klass) const { - return impl->cascading.template get<TextHaloWidth>().get(klass); +DataDrivenPropertyValue<float> SymbolLayer::getTextHaloWidth() const { + return impl().paint.template get<TextHaloWidth>().value; } -void SymbolLayer::setTextHaloWidth(DataDrivenPropertyValue<float> value, const optional<std::string>& klass) { - if (value == getTextHaloWidth(klass)) +void SymbolLayer::setTextHaloWidth(DataDrivenPropertyValue<float> value) { + if (value == getTextHaloWidth()) return; - impl->cascading.template get<TextHaloWidth>().set(value, klass); - if (value.isDataDriven()) { - impl->observer->onLayerDataDrivenPaintPropertyChanged(*this); - } else { - impl->observer->onLayerPaintPropertyChanged(*this); - } + auto impl_ = mutableImpl(); + impl_->paint.template get<TextHaloWidth>().value = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } -void SymbolLayer::setTextHaloWidthTransition(const TransitionOptions& value, const optional<std::string>& klass) { - impl->cascading.template get<TextHaloWidth>().setTransition(value, klass); +void SymbolLayer::setTextHaloWidthTransition(const TransitionOptions& options) { + auto impl_ = mutableImpl(); + impl_->paint.template get<TextHaloWidth>().options = options; + baseImpl = std::move(impl_); } -TransitionOptions SymbolLayer::getTextHaloWidthTransition(const optional<std::string>& klass) const { - return impl->cascading.template get<TextHaloWidth>().getTransition(klass); +TransitionOptions SymbolLayer::getTextHaloWidthTransition() const { + return impl().paint.template get<TextHaloWidth>().options; } DataDrivenPropertyValue<float> SymbolLayer::getDefaultTextHaloBlur() { return { 0 }; } -DataDrivenPropertyValue<float> SymbolLayer::getTextHaloBlur(const optional<std::string>& klass) const { - return impl->cascading.template get<TextHaloBlur>().get(klass); +DataDrivenPropertyValue<float> SymbolLayer::getTextHaloBlur() const { + return impl().paint.template get<TextHaloBlur>().value; } -void SymbolLayer::setTextHaloBlur(DataDrivenPropertyValue<float> value, const optional<std::string>& klass) { - if (value == getTextHaloBlur(klass)) +void SymbolLayer::setTextHaloBlur(DataDrivenPropertyValue<float> value) { + if (value == getTextHaloBlur()) return; - impl->cascading.template get<TextHaloBlur>().set(value, klass); - if (value.isDataDriven()) { - impl->observer->onLayerDataDrivenPaintPropertyChanged(*this); - } else { - impl->observer->onLayerPaintPropertyChanged(*this); - } + auto impl_ = mutableImpl(); + impl_->paint.template get<TextHaloBlur>().value = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } -void SymbolLayer::setTextHaloBlurTransition(const TransitionOptions& value, const optional<std::string>& klass) { - impl->cascading.template get<TextHaloBlur>().setTransition(value, klass); +void SymbolLayer::setTextHaloBlurTransition(const TransitionOptions& options) { + auto impl_ = mutableImpl(); + impl_->paint.template get<TextHaloBlur>().options = options; + baseImpl = std::move(impl_); } -TransitionOptions SymbolLayer::getTextHaloBlurTransition(const optional<std::string>& klass) const { - return impl->cascading.template get<TextHaloBlur>().getTransition(klass); +TransitionOptions SymbolLayer::getTextHaloBlurTransition() const { + return impl().paint.template get<TextHaloBlur>().options; } PropertyValue<std::array<float, 2>> SymbolLayer::getDefaultTextTranslate() { return { {{ 0, 0 }} }; } -PropertyValue<std::array<float, 2>> SymbolLayer::getTextTranslate(const optional<std::string>& klass) const { - return impl->cascading.template get<TextTranslate>().get(klass); +PropertyValue<std::array<float, 2>> SymbolLayer::getTextTranslate() const { + return impl().paint.template get<TextTranslate>().value; } -void SymbolLayer::setTextTranslate(PropertyValue<std::array<float, 2>> value, const optional<std::string>& klass) { - if (value == getTextTranslate(klass)) +void SymbolLayer::setTextTranslate(PropertyValue<std::array<float, 2>> value) { + if (value == getTextTranslate()) return; - impl->cascading.template get<TextTranslate>().set(value, klass); - impl->observer->onLayerPaintPropertyChanged(*this); + auto impl_ = mutableImpl(); + impl_->paint.template get<TextTranslate>().value = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } -void SymbolLayer::setTextTranslateTransition(const TransitionOptions& value, const optional<std::string>& klass) { - impl->cascading.template get<TextTranslate>().setTransition(value, klass); +void SymbolLayer::setTextTranslateTransition(const TransitionOptions& options) { + auto impl_ = mutableImpl(); + impl_->paint.template get<TextTranslate>().options = options; + baseImpl = std::move(impl_); } -TransitionOptions SymbolLayer::getTextTranslateTransition(const optional<std::string>& klass) const { - return impl->cascading.template get<TextTranslate>().getTransition(klass); +TransitionOptions SymbolLayer::getTextTranslateTransition() const { + return impl().paint.template get<TextTranslate>().options; } PropertyValue<TranslateAnchorType> SymbolLayer::getDefaultTextTranslateAnchor() { return { TranslateAnchorType::Map }; } -PropertyValue<TranslateAnchorType> SymbolLayer::getTextTranslateAnchor(const optional<std::string>& klass) const { - return impl->cascading.template get<TextTranslateAnchor>().get(klass); +PropertyValue<TranslateAnchorType> SymbolLayer::getTextTranslateAnchor() const { + return impl().paint.template get<TextTranslateAnchor>().value; } -void SymbolLayer::setTextTranslateAnchor(PropertyValue<TranslateAnchorType> value, const optional<std::string>& klass) { - if (value == getTextTranslateAnchor(klass)) +void SymbolLayer::setTextTranslateAnchor(PropertyValue<TranslateAnchorType> value) { + if (value == getTextTranslateAnchor()) return; - impl->cascading.template get<TextTranslateAnchor>().set(value, klass); - impl->observer->onLayerPaintPropertyChanged(*this); + auto impl_ = mutableImpl(); + impl_->paint.template get<TextTranslateAnchor>().value = value; + baseImpl = std::move(impl_); + observer->onLayerChanged(*this); } -void SymbolLayer::setTextTranslateAnchorTransition(const TransitionOptions& value, const optional<std::string>& klass) { - impl->cascading.template get<TextTranslateAnchor>().setTransition(value, klass); +void SymbolLayer::setTextTranslateAnchorTransition(const TransitionOptions& options) { + auto impl_ = mutableImpl(); + impl_->paint.template get<TextTranslateAnchor>().options = options; + baseImpl = std::move(impl_); } -TransitionOptions SymbolLayer::getTextTranslateAnchorTransition(const optional<std::string>& klass) const { - return impl->cascading.template get<TextTranslateAnchor>().getTransition(klass); +TransitionOptions SymbolLayer::getTextTranslateAnchorTransition() const { + return impl().paint.template get<TextTranslateAnchor>().options; } } // namespace style diff --git a/src/mbgl/style/layers/symbol_layer_impl.cpp b/src/mbgl/style/layers/symbol_layer_impl.cpp index c99dd8ad70..b59768725d 100644 --- a/src/mbgl/style/layers/symbol_layer_impl.cpp +++ b/src/mbgl/style/layers/symbol_layer_impl.cpp @@ -1,11 +1,15 @@ #include <mbgl/style/layers/symbol_layer_impl.hpp> -#include <mbgl/renderer/render_symbol_layer.hpp> namespace mbgl { namespace style { -std::unique_ptr<RenderLayer> SymbolLayer::Impl::createRenderLayer() const { - return std::make_unique<RenderSymbolLayer>(*this); +bool SymbolLayer::Impl::hasLayoutDifference(const Layer::Impl& other) const { + assert(dynamic_cast<const SymbolLayer::Impl*>(&other)); + const auto& impl = static_cast<const style::SymbolLayer::Impl&>(other); + return filter != impl.filter || + visibility != impl.visibility || + layout != impl.layout || + paint.hasDataDrivenPropertyDifference(impl.paint); } } // namespace style diff --git a/src/mbgl/style/layers/symbol_layer_impl.hpp b/src/mbgl/style/layers/symbol_layer_impl.hpp index df145647a0..f8ef87dcdf 100644 --- a/src/mbgl/style/layers/symbol_layer_impl.hpp +++ b/src/mbgl/style/layers/symbol_layer_impl.hpp @@ -1,24 +1,21 @@ #pragma once -#include <mbgl/sprite/sprite_atlas.hpp> #include <mbgl/style/layer_impl.hpp> #include <mbgl/style/layers/symbol_layer.hpp> #include <mbgl/style/layers/symbol_layer_properties.hpp> namespace mbgl { - namespace style { class SymbolLayer::Impl : public Layer::Impl { public: - std::unique_ptr<Layer> clone() const override; - std::unique_ptr<Layer> cloneRef(const std::string& id) const override; - void stringifyLayout(rapidjson::Writer<rapidjson::StringBuffer>&) const override; + using Layer::Impl::Impl; - std::unique_ptr<RenderLayer> createRenderLayer() const override; + bool hasLayoutDifference(const Layer::Impl&) const override; + void stringifyLayout(rapidjson::Writer<rapidjson::StringBuffer>&) const override; - SymbolLayoutProperties layout; - SymbolPaintProperties::Cascading cascading; + SymbolLayoutProperties::Unevaluated layout; + SymbolPaintProperties::Transitionable paint; }; } // namespace style diff --git a/src/mbgl/style/layers/symbol_layer_properties.hpp b/src/mbgl/style/layers/symbol_layer_properties.hpp index 5b57175785..436b5cbd4f 100644 --- a/src/mbgl/style/layers/symbol_layer_properties.hpp +++ b/src/mbgl/style/layers/symbol_layer_properties.hpp @@ -5,6 +5,7 @@ #include <mbgl/style/types.hpp> #include <mbgl/style/layout_property.hpp> #include <mbgl/style/paint_property.hpp> +#include <mbgl/style/properties.hpp> #include <mbgl/programs/attributes.hpp> #include <mbgl/programs/uniforms.hpp> @@ -86,6 +87,16 @@ struct IconOffset : DataDrivenLayoutProperty<std::array<float, 2>> { static std::array<float, 2> defaultValue() { return {{ 0, 0 }}; } }; +struct IconAnchor : DataDrivenLayoutProperty<SymbolAnchorType> { + static constexpr const char * key = "icon-anchor"; + static SymbolAnchorType defaultValue() { return SymbolAnchorType::Center; } +}; + +struct IconPitchAlignment : LayoutProperty<AlignmentType> { + static constexpr const char * key = "icon-pitch-alignment"; + static AlignmentType defaultValue() { return AlignmentType::Auto; } +}; + struct TextPitchAlignment : LayoutProperty<AlignmentType> { static constexpr const char * key = "text-pitch-alignment"; static AlignmentType defaultValue() { return AlignmentType::Auto; } @@ -111,7 +122,7 @@ struct TextSize : DataDrivenLayoutProperty<float> { static float defaultValue() { return 16; } }; -struct TextMaxWidth : LayoutProperty<float> { +struct TextMaxWidth : DataDrivenLayoutProperty<float> { static constexpr const char * key = "text-max-width"; static float defaultValue() { return 10; } }; @@ -121,19 +132,19 @@ struct TextLineHeight : LayoutProperty<float> { static float defaultValue() { return 1.2; } }; -struct TextLetterSpacing : LayoutProperty<float> { +struct TextLetterSpacing : DataDrivenLayoutProperty<float> { static constexpr const char * key = "text-letter-spacing"; static float defaultValue() { return 0; } }; -struct TextJustify : LayoutProperty<TextJustifyType> { +struct TextJustify : DataDrivenLayoutProperty<TextJustifyType> { static constexpr const char * key = "text-justify"; static TextJustifyType defaultValue() { return TextJustifyType::Center; } }; -struct TextAnchor : LayoutProperty<TextAnchorType> { +struct TextAnchor : DataDrivenLayoutProperty<SymbolAnchorType> { static constexpr const char * key = "text-anchor"; - static TextAnchorType defaultValue() { return TextAnchorType::Center; } + static SymbolAnchorType defaultValue() { return SymbolAnchorType::Center; } }; struct TextMaxAngle : LayoutProperty<float> { @@ -237,7 +248,7 @@ struct TextTranslateAnchor : PaintProperty<TranslateAnchorType> { static TranslateAnchorType defaultValue() { return TranslateAnchorType::Map; } }; -class SymbolLayoutProperties : public LayoutProperties< +class SymbolLayoutProperties : public Properties< SymbolPlacement, SymbolSpacing, SymbolAvoidEdges, @@ -253,6 +264,8 @@ class SymbolLayoutProperties : public LayoutProperties< IconPadding, IconKeepUpright, IconOffset, + IconAnchor, + IconPitchAlignment, TextPitchAlignment, TextRotationAlignment, TextField, @@ -274,7 +287,7 @@ class SymbolLayoutProperties : public LayoutProperties< TextOptional > {}; -class SymbolPaintProperties : public PaintProperties< +class SymbolPaintProperties : public Properties< IconOpacity, IconColor, IconHaloColor, |