[core] Improve performance for query rendered features
- query rendered symbols only from layers that support it - remove unnecessary iterations over vectors
This commit is contained in:
@@ -46,7 +46,7 @@ void RenderAnnotationSource::update(Immutable<style::Source::Impl> baseImpl_,
|
||||
std::unordered_map<std::string, std::vector<Feature>>
|
||||
RenderAnnotationSource::queryRenderedFeatures(const ScreenLineString& geometry,
|
||||
const TransformState& transformState,
|
||||
const std::vector<const RenderLayer*>& layers,
|
||||
const std::unordered_map<std::string, const RenderLayer*>& layers,
|
||||
const RenderedQueryOptions& options,
|
||||
const mat4& projMatrix) const {
|
||||
return tilePyramid.queryRenderedFeatures(geometry, transformState, layers, options, projMatrix);
|
||||
|
||||
@@ -18,7 +18,7 @@ public:
|
||||
std::unordered_map<std::string, std::vector<Feature>>
|
||||
queryRenderedFeatures(const ScreenLineString& geometry,
|
||||
const TransformState& transformState,
|
||||
const std::vector<const RenderLayer*>& layers,
|
||||
const std::unordered_map<std::string, const RenderLayer*>& layers,
|
||||
const RenderedQueryOptions& options,
|
||||
const mat4& projMatrix) const final;
|
||||
|
||||
|
||||
@@ -47,7 +47,7 @@ void FeatureIndex::query(
|
||||
const double scale,
|
||||
const RenderedQueryOptions& queryOptions,
|
||||
const UnwrappedTileID& tileID,
|
||||
const std::vector<const RenderLayer*>& layers,
|
||||
const std::unordered_map<std::string, const RenderLayer*>& layers,
|
||||
const float additionalQueryPadding) const {
|
||||
|
||||
if (!tileData) {
|
||||
@@ -81,7 +81,7 @@ void FeatureIndex::query(
|
||||
std::unordered_map<std::string, std::vector<Feature>>
|
||||
FeatureIndex::lookupSymbolFeatures(const std::vector<IndexedSubfeature>& symbolFeatures,
|
||||
const RenderedQueryOptions& queryOptions,
|
||||
const std::vector<const RenderLayer*>& layers,
|
||||
const std::unordered_map<std::string, const RenderLayer*>& layers,
|
||||
const OverscaledTileID& tileID,
|
||||
const std::shared_ptr<std::vector<size_t>>& featureSortOrder) const {
|
||||
std::unordered_map<std::string, std::vector<Feature>> result;
|
||||
@@ -123,31 +123,24 @@ void FeatureIndex::addFeature(
|
||||
const IndexedSubfeature& indexedFeature,
|
||||
const RenderedQueryOptions& options,
|
||||
const CanonicalTileID& tileID,
|
||||
const std::vector<const RenderLayer*>& layers,
|
||||
const std::unordered_map<std::string, const RenderLayer*>& layers,
|
||||
const GeometryCoordinates& queryGeometry,
|
||||
const TransformState& transformState,
|
||||
const float pixelsToTileUnits,
|
||||
const mat4& posMatrix) const {
|
||||
|
||||
auto getRenderLayer = [&] (const std::string& layerID) -> const RenderLayer* {
|
||||
for (const auto& layer : layers) {
|
||||
if (layer->getID() == layerID) {
|
||||
return layer;
|
||||
}
|
||||
}
|
||||
return nullptr;
|
||||
};
|
||||
|
||||
// Lazily calculated.
|
||||
std::unique_ptr<GeometryTileLayer> sourceLayer;
|
||||
std::unique_ptr<GeometryTileFeature> geometryTileFeature;
|
||||
|
||||
for (const std::string& layerID : bucketLayerIDs.at(indexedFeature.bucketLeaderID)) {
|
||||
const RenderLayer* renderLayer = getRenderLayer(layerID);
|
||||
if (!renderLayer) {
|
||||
const auto it = layers.find(layerID);
|
||||
if (it == layers.end()) {
|
||||
continue;
|
||||
}
|
||||
|
||||
const RenderLayer* renderLayer = it->second;
|
||||
|
||||
if (!geometryTileFeature) {
|
||||
sourceLayer = tileData->getLayer(indexedFeature.sourceLayerName);
|
||||
assert(sourceLayer);
|
||||
|
||||
@@ -67,7 +67,7 @@ public:
|
||||
const double scale,
|
||||
const RenderedQueryOptions& options,
|
||||
const UnwrappedTileID&,
|
||||
const std::vector<const RenderLayer*>&,
|
||||
const std::unordered_map<std::string, const RenderLayer*>&,
|
||||
const float additionalQueryPadding) const;
|
||||
|
||||
static optional<GeometryCoordinates> translateQueryGeometry(
|
||||
@@ -82,7 +82,7 @@ public:
|
||||
std::unordered_map<std::string, std::vector<Feature>> lookupSymbolFeatures(
|
||||
const std::vector<IndexedSubfeature>& symbolFeatures,
|
||||
const RenderedQueryOptions& options,
|
||||
const std::vector<const RenderLayer*>& layers,
|
||||
const std::unordered_map<std::string, const RenderLayer*>& layers,
|
||||
const OverscaledTileID& tileID,
|
||||
const std::shared_ptr<std::vector<size_t>>& featureSortOrder) const;
|
||||
|
||||
@@ -92,7 +92,7 @@ private:
|
||||
const IndexedSubfeature&,
|
||||
const RenderedQueryOptions& options,
|
||||
const CanonicalTileID&,
|
||||
const std::vector<const RenderLayer*>&,
|
||||
const std::unordered_map<std::string, const RenderLayer*>&,
|
||||
const GeometryCoordinates& queryGeometry,
|
||||
const TransformState& transformState,
|
||||
const float pixelsToTileUnits,
|
||||
|
||||
@@ -409,16 +409,16 @@ std::unique_ptr<RenderTree> RenderOrchestrator::createRenderTree(const UpdatePar
|
||||
}
|
||||
|
||||
std::vector<Feature> RenderOrchestrator::queryRenderedFeatures(const ScreenLineString& geometry, const RenderedQueryOptions& options) const {
|
||||
std::vector<const RenderLayer*> layers;
|
||||
std::unordered_map<std::string, const RenderLayer*> layers;
|
||||
if (options.layerIDs) {
|
||||
for (const auto& layerID : *options.layerIDs) {
|
||||
if (const RenderLayer* layer = getRenderLayer(layerID)) {
|
||||
layers.emplace_back(layer);
|
||||
layers.emplace(layer->getID(), layer);
|
||||
}
|
||||
}
|
||||
} else {
|
||||
for (const auto& entry : renderLayers) {
|
||||
layers.emplace_back(entry.second.get());
|
||||
layers.emplace(entry.second->getID(), entry.second.get());
|
||||
}
|
||||
}
|
||||
|
||||
@@ -427,9 +427,22 @@ std::vector<Feature> RenderOrchestrator::queryRenderedFeatures(const ScreenLineS
|
||||
|
||||
void RenderOrchestrator::queryRenderedSymbols(std::unordered_map<std::string, std::vector<Feature>>& resultsByLayer,
|
||||
const ScreenLineString& geometry,
|
||||
const std::vector<const RenderLayer*>& layers,
|
||||
const std::unordered_map<std::string, const RenderLayer*>& layers,
|
||||
const RenderedQueryOptions& options) const {
|
||||
|
||||
const auto hasCrossTileIndex = [] (const auto& pair) {
|
||||
return pair.second->baseImpl->getTypeInfo()->crossTileIndex == style::LayerTypeInfo::CrossTileIndex::Required;
|
||||
};
|
||||
|
||||
std::unordered_map<std::string, const RenderLayer*> crossTileSymbolIndexLayers;
|
||||
std::copy_if(layers.begin(),
|
||||
layers.end(),
|
||||
std::inserter(crossTileSymbolIndexLayers, crossTileSymbolIndexLayers.begin()),
|
||||
hasCrossTileIndex);
|
||||
|
||||
if (crossTileSymbolIndexLayers.empty()) {
|
||||
return;
|
||||
}
|
||||
|
||||
auto renderedSymbols = placement->getCollisionIndex().queryRenderedSymbols(geometry);
|
||||
std::vector<std::reference_wrapper<const RetainedQueryData>> bucketQueryData;
|
||||
for (auto entry : renderedSymbols) {
|
||||
@@ -447,7 +460,7 @@ void RenderOrchestrator::queryRenderedSymbols(std::unordered_map<std::string, st
|
||||
auto& queryData = wrappedQueryData.get();
|
||||
auto bucketSymbols = queryData.featureIndex->lookupSymbolFeatures(renderedSymbols[queryData.bucketInstanceId],
|
||||
options,
|
||||
layers,
|
||||
crossTileSymbolIndexLayers,
|
||||
queryData.tileID,
|
||||
queryData.featureSortOrder);
|
||||
|
||||
@@ -458,10 +471,10 @@ void RenderOrchestrator::queryRenderedSymbols(std::unordered_map<std::string, st
|
||||
}
|
||||
}
|
||||
|
||||
std::vector<Feature> RenderOrchestrator::queryRenderedFeatures(const ScreenLineString& geometry, const RenderedQueryOptions& options, const std::vector<const RenderLayer*>& layers) const {
|
||||
std::vector<Feature> RenderOrchestrator::queryRenderedFeatures(const ScreenLineString& geometry, const RenderedQueryOptions& options, const std::unordered_map<std::string, const RenderLayer*>& layers) const {
|
||||
std::unordered_set<std::string> sourceIDs;
|
||||
for (const RenderLayer* layer : layers) {
|
||||
sourceIDs.emplace(layer->baseImpl->source);
|
||||
for (const auto& pair : layers) {
|
||||
sourceIDs.emplace(pair.second->baseImpl->source);
|
||||
}
|
||||
|
||||
mat4 projMatrix;
|
||||
@@ -484,13 +497,12 @@ std::vector<Feature> RenderOrchestrator::queryRenderedFeatures(const ScreenLineS
|
||||
}
|
||||
|
||||
// Combine all results based on the style layer renderItems.
|
||||
for (const auto& layerImpl : *layerImpls) {
|
||||
const RenderLayer* layer = getRenderLayer(layerImpl->id);
|
||||
if (!layer->needsRendering() || !layer->supportsZoom(zoomHistory.lastZoom)) {
|
||||
for (const auto& pair : layers) {
|
||||
if (!pair.second->needsRendering() || !pair.second->supportsZoom(zoomHistory.lastZoom)) {
|
||||
continue;
|
||||
}
|
||||
|
||||
auto it = resultsByLayer.find(layer->baseImpl->id);
|
||||
auto it = resultsByLayer.find(pair.second->baseImpl->id);
|
||||
if (it != resultsByLayer.end()) {
|
||||
std::move(it->second.begin(), it->second.end(), std::back_inserter(result));
|
||||
}
|
||||
@@ -501,13 +513,13 @@ std::vector<Feature> RenderOrchestrator::queryRenderedFeatures(const ScreenLineS
|
||||
|
||||
std::vector<Feature> RenderOrchestrator::queryShapeAnnotations(const ScreenLineString& geometry) const {
|
||||
assert(LayerManager::annotationsEnabled);
|
||||
std::vector<const RenderLayer*> shapeAnnotationLayers;
|
||||
std::unordered_map<std::string, const RenderLayer*> shapeAnnotationLayers;
|
||||
RenderedQueryOptions options;
|
||||
for (const auto& layerImpl : *layerImpls) {
|
||||
if (std::mismatch(layerImpl->id.begin(), layerImpl->id.end(),
|
||||
AnnotationManager::ShapeLayerID.begin(), AnnotationManager::ShapeLayerID.end()).second == AnnotationManager::ShapeLayerID.end()) {
|
||||
if (const RenderLayer* layer = getRenderLayer(layerImpl->id)) {
|
||||
shapeAnnotationLayers.emplace_back(layer);
|
||||
shapeAnnotationLayers.emplace(layer->getID(), layer);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -74,10 +74,10 @@ private:
|
||||
|
||||
void queryRenderedSymbols(std::unordered_map<std::string, std::vector<Feature>>& resultsByLayer,
|
||||
const ScreenLineString& geometry,
|
||||
const std::vector<const RenderLayer*>& layers,
|
||||
const std::unordered_map<std::string, const RenderLayer*>& layers,
|
||||
const RenderedQueryOptions& options) const;
|
||||
|
||||
std::vector<Feature> queryRenderedFeatures(const ScreenLineString&, const RenderedQueryOptions&, const std::vector<const RenderLayer*>&) const;
|
||||
std::vector<Feature> queryRenderedFeatures(const ScreenLineString&, const RenderedQueryOptions&, const std::unordered_map<std::string, const RenderLayer*>&) const;
|
||||
|
||||
// GlyphManagerObserver implementation.
|
||||
void onGlyphsError(const FontStack&, const GlyphRange&, std::exception_ptr) override;
|
||||
|
||||
@@ -72,7 +72,7 @@ public:
|
||||
virtual std::unordered_map<std::string, std::vector<Feature>>
|
||||
queryRenderedFeatures(const ScreenLineString& geometry,
|
||||
const TransformState& transformState,
|
||||
const std::vector<const RenderLayer*>& layers,
|
||||
const std::unordered_map<std::string, const RenderLayer*>& layers,
|
||||
const RenderedQueryOptions& options,
|
||||
const mat4& projMatrix) const = 0;
|
||||
|
||||
|
||||
@@ -106,7 +106,7 @@ void RenderImageSource::prepare(const SourcePrepareParameters& parameters) {
|
||||
std::unordered_map<std::string, std::vector<Feature>>
|
||||
RenderImageSource::queryRenderedFeatures(const ScreenLineString&,
|
||||
const TransformState&,
|
||||
const std::vector<const RenderLayer*>&,
|
||||
const std::unordered_map<std::string, const RenderLayer*>&,
|
||||
const RenderedQueryOptions&,
|
||||
const mat4&) const {
|
||||
return std::unordered_map<std::string, std::vector<Feature>> {};
|
||||
|
||||
@@ -57,7 +57,7 @@ public:
|
||||
std::unordered_map<std::string, std::vector<Feature>>
|
||||
queryRenderedFeatures(const ScreenLineString& geometry,
|
||||
const TransformState& transformState,
|
||||
const std::vector<const RenderLayer*>& layers,
|
||||
const std::unordered_map<std::string, const RenderLayer*>& layers,
|
||||
const RenderedQueryOptions& options,
|
||||
const mat4& projMatrix) const final;
|
||||
|
||||
|
||||
@@ -125,7 +125,7 @@ void RenderRasterDEMSource::onTileChanged(Tile& tile){
|
||||
std::unordered_map<std::string, std::vector<Feature>>
|
||||
RenderRasterDEMSource::queryRenderedFeatures(const ScreenLineString&,
|
||||
const TransformState&,
|
||||
const std::vector<const RenderLayer*>&,
|
||||
const std::unordered_map<std::string, const RenderLayer*>&,
|
||||
const RenderedQueryOptions&,
|
||||
const mat4&) const {
|
||||
return std::unordered_map<std::string, std::vector<Feature>>{};
|
||||
|
||||
@@ -19,7 +19,7 @@ public:
|
||||
std::unordered_map<std::string, std::vector<Feature>>
|
||||
queryRenderedFeatures(const ScreenLineString& geometry,
|
||||
const TransformState& transformState,
|
||||
const std::vector<const RenderLayer*>& layers,
|
||||
const std::unordered_map<std::string, const RenderLayer*>& layers,
|
||||
const RenderedQueryOptions& options,
|
||||
const mat4& projMatrix) const override;
|
||||
|
||||
|
||||
@@ -60,7 +60,7 @@ void RenderRasterSource::prepare(const SourcePrepareParameters& parameters) {
|
||||
std::unordered_map<std::string, std::vector<Feature>>
|
||||
RenderRasterSource::queryRenderedFeatures(const ScreenLineString&,
|
||||
const TransformState&,
|
||||
const std::vector<const RenderLayer*>&,
|
||||
const std::unordered_map<std::string, const RenderLayer*>&,
|
||||
const RenderedQueryOptions&,
|
||||
const mat4&) const {
|
||||
return std::unordered_map<std::string, std::vector<Feature>>{};
|
||||
|
||||
@@ -19,7 +19,7 @@ public:
|
||||
std::unordered_map<std::string, std::vector<Feature>>
|
||||
queryRenderedFeatures(const ScreenLineString& geometry,
|
||||
const TransformState& transformState,
|
||||
const std::vector<const RenderLayer*>& layers,
|
||||
const std::unordered_map<std::string, const RenderLayer*>& layers,
|
||||
const RenderedQueryOptions& options,
|
||||
const mat4& projMatrix) const override;
|
||||
|
||||
|
||||
@@ -84,7 +84,7 @@ const Tile* RenderTileSource::getRenderedTile(const UnwrappedTileID& tileID) con
|
||||
std::unordered_map<std::string, std::vector<Feature>>
|
||||
RenderTileSource::queryRenderedFeatures(const ScreenLineString& geometry,
|
||||
const TransformState& transformState,
|
||||
const std::vector<const RenderLayer*>& layers,
|
||||
const std::unordered_map<std::string, const RenderLayer*>& layers,
|
||||
const RenderedQueryOptions& options,
|
||||
const mat4& projMatrix) const {
|
||||
return tilePyramid.queryRenderedFeatures(geometry, transformState, layers, options, projMatrix);
|
||||
|
||||
@@ -27,7 +27,7 @@ public:
|
||||
std::unordered_map<std::string, std::vector<Feature>>
|
||||
queryRenderedFeatures(const ScreenLineString& geometry,
|
||||
const TransformState& transformState,
|
||||
const std::vector<const RenderLayer*>& layers,
|
||||
const std::unordered_map<std::string, const RenderLayer*>& layers,
|
||||
const RenderedQueryOptions& options,
|
||||
const mat4& projMatrix) const override;
|
||||
|
||||
|
||||
@@ -284,7 +284,7 @@ void TilePyramid::handleWrapJump(float lng) {
|
||||
|
||||
std::unordered_map<std::string, std::vector<Feature>> TilePyramid::queryRenderedFeatures(const ScreenLineString& geometry,
|
||||
const TransformState& transformState,
|
||||
const std::vector<const RenderLayer*>& layers,
|
||||
const std::unordered_map<std::string, const RenderLayer*>& layers,
|
||||
const RenderedQueryOptions& options,
|
||||
const mat4& projMatrix) const {
|
||||
std::unordered_map<std::string, std::vector<Feature>> result;
|
||||
|
||||
@@ -52,7 +52,7 @@ public:
|
||||
std::unordered_map<std::string, std::vector<Feature>>
|
||||
queryRenderedFeatures(const ScreenLineString& geometry,
|
||||
const TransformState& transformState,
|
||||
const std::vector<const RenderLayer*>&,
|
||||
const std::unordered_map<std::string, const RenderLayer*>&,
|
||||
const RenderedQueryOptions& options,
|
||||
const mat4& projMatrix) const;
|
||||
|
||||
|
||||
@@ -291,12 +291,12 @@ LayerRenderData* GeometryTile::getLayerRenderData(const style::Layer::Impl& laye
|
||||
return layoutResult ? layoutResult->getLayerRenderData(layerImpl) : nullptr;
|
||||
}
|
||||
|
||||
float GeometryTile::getQueryPadding(const std::vector<const RenderLayer*>& layers) {
|
||||
float GeometryTile::getQueryPadding(const std::unordered_map<std::string, const RenderLayer*>& layers) {
|
||||
float queryPadding = 0;
|
||||
for (const RenderLayer* layer : layers) {
|
||||
const LayerRenderData* data = getLayerRenderData(*layer->baseImpl);
|
||||
for (const auto& pair : layers) {
|
||||
const LayerRenderData* data = getLayerRenderData(*pair.second->baseImpl);
|
||||
if (data && data->bucket && data->bucket->hasData()) {
|
||||
queryPadding = std::max(queryPadding, data->bucket->getQueryRadius(*layer));
|
||||
queryPadding = std::max(queryPadding, data->bucket->getQueryRadius(*pair.second));
|
||||
}
|
||||
}
|
||||
return queryPadding;
|
||||
@@ -306,7 +306,7 @@ void GeometryTile::queryRenderedFeatures(
|
||||
std::unordered_map<std::string, std::vector<Feature>>& result,
|
||||
const GeometryCoordinates& queryGeometry,
|
||||
const TransformState& transformState,
|
||||
const std::vector<const RenderLayer*>& layers,
|
||||
const std::unordered_map<std::string, const RenderLayer*>& layers,
|
||||
const RenderedQueryOptions& options,
|
||||
const mat4& projMatrix) {
|
||||
|
||||
|
||||
@@ -52,7 +52,7 @@ public:
|
||||
std::unordered_map<std::string, std::vector<Feature>>& result,
|
||||
const GeometryCoordinates& queryGeometry,
|
||||
const TransformState&,
|
||||
const std::vector<const RenderLayer*>& layers,
|
||||
const std::unordered_map<std::string, const RenderLayer*>& layers,
|
||||
const RenderedQueryOptions& options,
|
||||
const mat4& projMatrix) override;
|
||||
|
||||
@@ -60,7 +60,7 @@ public:
|
||||
std::vector<Feature>& result,
|
||||
const SourceQueryOptions&) override;
|
||||
|
||||
float getQueryPadding(const std::vector<const RenderLayer*>&) override;
|
||||
float getQueryPadding(const std::unordered_map<std::string, const RenderLayer*>&) override;
|
||||
|
||||
void cancel() override;
|
||||
|
||||
|
||||
@@ -43,11 +43,11 @@ void Tile::queryRenderedFeatures(
|
||||
std::unordered_map<std::string, std::vector<Feature>>&,
|
||||
const GeometryCoordinates&,
|
||||
const TransformState&,
|
||||
const std::vector<const RenderLayer*>&,
|
||||
const std::unordered_map<std::string, const RenderLayer*>&,
|
||||
const RenderedQueryOptions&,
|
||||
const mat4&) {}
|
||||
|
||||
float Tile::getQueryPadding(const std::vector<const RenderLayer*>&) {
|
||||
float Tile::getQueryPadding(const std::unordered_map<std::string, const RenderLayer*>&) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
@@ -71,7 +71,7 @@ public:
|
||||
std::unordered_map<std::string, std::vector<Feature>>& result,
|
||||
const GeometryCoordinates& queryGeometry,
|
||||
const TransformState&,
|
||||
const std::vector<const RenderLayer*>&,
|
||||
const std::unordered_map<std::string, const RenderLayer*>&,
|
||||
const RenderedQueryOptions& options,
|
||||
const mat4& projMatrix);
|
||||
|
||||
@@ -79,7 +79,7 @@ public:
|
||||
std::vector<Feature>& result,
|
||||
const SourceQueryOptions&);
|
||||
|
||||
virtual float getQueryPadding(const std::vector<const RenderLayer*>&);
|
||||
virtual float getQueryPadding(const std::unordered_map<std::string, const RenderLayer*>&);
|
||||
|
||||
void setTriedCache();
|
||||
|
||||
|
||||
Reference in New Issue
Block a user