diff options
Diffstat (limited to 'src/mbgl/layout')
-rw-r--r-- | src/mbgl/layout/pattern_layout.hpp | 128 | ||||
-rw-r--r-- | src/mbgl/layout/symbol_layout.cpp | 9 |
2 files changed, 132 insertions, 5 deletions
diff --git a/src/mbgl/layout/pattern_layout.hpp b/src/mbgl/layout/pattern_layout.hpp new file mode 100644 index 0000000000..9f4964ca6b --- /dev/null +++ b/src/mbgl/layout/pattern_layout.hpp @@ -0,0 +1,128 @@ +#pragma once +#include <mbgl/renderer/bucket_parameters.hpp> +#include <mbgl/geometry/feature_index.hpp> +#include <mbgl/renderer/render_layer.hpp> + +namespace mbgl { + +class PatternDependency { +public: + std::string min; + std::string mid; + std::string max; +}; + +using PatternLayerMap = std::unordered_map<std::string, PatternDependency>; + +class PatternFeature { +public: + const uint32_t i; + std::unique_ptr<GeometryTileFeature> feature; + PatternLayerMap patterns; +}; + +template <class B> +class PatternLayout { +public: + PatternLayout(const BucketParameters& parameters, + const std::vector<const RenderLayer*>& layers, + std::unique_ptr<GeometryTileLayer> sourceLayer_, + ImageDependencies& patternDependencies) + : bucketLeaderID(layers.at(0)->getID()), + sourceLayer(std::move(sourceLayer_)), + zoom(parameters.tileID.overscaledZ), + overscaling(parameters.tileID.overscaleFactor()), + hasPattern(false) { + + using PatternLayer = typename B::RenderLayerType; + const auto renderLayer = layers.at(0)->as<PatternLayer>(); + const typename PatternLayer::StyleLayerImpl& leader = renderLayer->impl(); + layout = leader.layout.evaluate(PropertyEvaluationParameters(zoom)); + sourceLayerID = leader.sourceLayer; + groupID = renderLayer->getID(); + + for (const auto& layer : layers) { + const typename B::PossiblyEvaluatedPaintProperties evaluatedProps = layer->as<PatternLayer>()->paintProperties(); + layerPaintProperties.emplace(layer->getID(), std::move(evaluatedProps)); + const auto patternProperty = evaluatedProps.template get<typename PatternLayer::PatternProperty>(); + const auto constantPattern = patternProperty.constantOr(Faded<std::basic_string<char> >{ "", ""}); + // determine if layer group has any layers that use *-pattern property and add + // constant pattern dependencies. + if (!patternProperty.isConstant()) { + hasPattern = true; + } else if (!constantPattern.to.empty()){ + hasPattern = true; + patternDependencies.emplace(constantPattern.to, ImageType::Pattern); + patternDependencies.emplace(constantPattern.from, ImageType::Pattern); + } + } + + const size_t featureCount = sourceLayer->featureCount(); + for (size_t i = 0; i < featureCount; ++i) { + auto feature = sourceLayer->getFeature(i); + if (!leader.filter(style::expression::EvaluationContext { this->zoom, feature.get() })) + continue; + + std::unordered_map<std::string, PatternDependency> patternDependencyMap; + if (hasPattern) { + for (const auto& layer : layers) { + const auto it = layerPaintProperties.find(layer->getID()); + if (it != layerPaintProperties.end()) { + const auto paint = it->second; + const auto patternProperty = paint.template get<typename PatternLayer::PatternProperty>(); + if (!patternProperty.isConstant()) { + // For layers with non-data-constant pattern properties, evaluate their expression and add + // the patterns to the dependency vector + const auto min = patternProperty.evaluate(*feature, zoom - 1, PatternLayer::PatternProperty::defaultValue()); + const auto mid = patternProperty.evaluate(*feature, zoom, PatternLayer::PatternProperty::defaultValue()); + const auto max = patternProperty.evaluate(*feature, zoom + 1, PatternLayer::PatternProperty::defaultValue()); + + patternDependencies.emplace(min.to, ImageType::Pattern); + patternDependencies.emplace(mid.to, ImageType::Pattern); + patternDependencies.emplace(max.to, ImageType::Pattern); + patternDependencyMap.emplace(layer->getID(), PatternDependency {min.to, mid.to, max.to}); + + } + } + } + } + features.push_back({static_cast<uint32_t>(i), std::move(feature), patternDependencyMap}); + } + }; + + bool pattern() { + return hasPattern; + } + + std::unique_ptr<B> createBucket(const ImagePositions& patternPositions, std::unique_ptr<FeatureIndex>& featureIndex) { + auto bucket = std::make_unique<B>(layout, layerPaintProperties, zoom, overscaling); + for (auto & patternFeature : features) { + const auto i = patternFeature.i; + std::unique_ptr<GeometryTileFeature> feature = std::move(patternFeature.feature); + PatternLayerMap patterns = patternFeature.patterns; + GeometryCollection geometries = feature->getGeometries(); + + bucket->addFeature(*feature, geometries, patternPositions, patterns); + featureIndex->insert(geometries, i, sourceLayerID, groupID); + } + return bucket; + }; + + std::map<std::string, typename B::PossiblyEvaluatedPaintProperties> layerPaintProperties; + const std::string bucketLeaderID; + + +private: + const std::unique_ptr<GeometryTileLayer> sourceLayer; + std::vector<PatternFeature> features; + typename B::PossiblyEvaluatedLayoutProperties layout; + + const float zoom; + const uint32_t overscaling; + std::string sourceLayerID; + std::string groupID; + bool hasPattern; +}; + +} // namespace mbgl + diff --git a/src/mbgl/layout/symbol_layout.cpp b/src/mbgl/layout/symbol_layout.cpp index ab718351ab..fd4dd2bedd 100644 --- a/src/mbgl/layout/symbol_layout.cpp +++ b/src/mbgl/layout/symbol_layout.cpp @@ -136,7 +136,7 @@ SymbolLayout::SymbolLayout(const BucketParameters& parameters, if (hasIcon) { ft.icon = layout.evaluate<IconImage>(zoom, ft); - imageDependencies.insert(*ft.icon); + imageDependencies.emplace(*ft.icon, ImageType::Icon); } if (ft.text || ft.icon) { @@ -455,15 +455,14 @@ std::unique_ptr<SymbolBucket> SymbolLayout::place(const bool showCollisionBoxes) symbolInstance.iconOffset, WritingModeType::None, symbolInstance.line, std::vector<float>()); symbolInstance.placedIconIndex = bucket->icon.placedSymbols.size() - 1; PlacedSymbol& iconSymbol = bucket->icon.placedSymbols.back(); - iconSymbol.vertexStartIndex = addSymbol( - bucket->icon, sizeData, *symbolInstance.iconQuad, + iconSymbol.vertexStartIndex = addSymbol(bucket->icon, sizeData, *symbolInstance.iconQuad, symbolInstance.anchor, iconSymbol); } } for (auto& pair : bucket->paintPropertyBinders) { - pair.second.first.populateVertexVectors(feature, bucket->icon.vertices.vertexSize()); - pair.second.second.populateVertexVectors(feature, bucket->text.vertices.vertexSize()); + pair.second.first.populateVertexVectors(feature, bucket->icon.vertices.vertexSize(), {}, {}); + pair.second.second.populateVertexVectors(feature, bucket->text.vertices.vertexSize(), {}, {}); } } |