[core][tile mode] Improve placement algorithm for variable labels
This commit is contained in:
@@ -390,7 +390,6 @@ void Placement::placeSymbol(const SymbolInstance& symbolInstance,
|
||||
const size_t placementAttempts = ctx.textAllowOverlap ? anchorsSize * 2 : anchorsSize;
|
||||
for (size_t i = 0u; i < placementAttempts; ++i) {
|
||||
auto anchor = variableTextAnchors[i % anchorsSize];
|
||||
const bool isFirstAnchor = (anchor == variableTextAnchors.front());
|
||||
const bool allowOverlap = (i >= anchorsSize);
|
||||
shift = calculateVariableLayoutOffset(anchor,
|
||||
width,
|
||||
@@ -401,9 +400,8 @@ void Placement::placeSymbol(const SymbolInstance& symbolInstance,
|
||||
ctx.pitchTextWithMap,
|
||||
ctx.getTransformState().getBearing());
|
||||
textBoxes.clear();
|
||||
if (!isFirstAnchor &&
|
||||
stickToFirstVariableAnchor(
|
||||
symbolInstance.textCollisionFeature.boxes.front(), shift, posMatrix, ctx.pixelRatio)) {
|
||||
if (!canPlaceAtVariableAnchor(
|
||||
textBox, anchor, shift, variableTextAnchors, posMatrix, ctx.pixelRatio)) {
|
||||
continue;
|
||||
}
|
||||
|
||||
@@ -1263,10 +1261,12 @@ private:
|
||||
const std::vector<PlacedSymbolData>& getPlacedSymbolsData() const override { return placedSymbolsData; }
|
||||
|
||||
optional<CollisionBoundaries> getAvoidEdges(const SymbolBucket&, const mat4&) override;
|
||||
bool stickToFirstVariableAnchor(const CollisionBox& box,
|
||||
Point<float> shift,
|
||||
const mat4& posMatrix,
|
||||
float textPixelRatio) override;
|
||||
bool canPlaceAtVariableAnchor(const CollisionBox& box,
|
||||
TextVariableAnchorType anchor,
|
||||
Point<float> shift,
|
||||
std::vector<style::TextVariableAnchorType>& anchors,
|
||||
const mat4& posMatrix,
|
||||
float textPixelRatio) override;
|
||||
void newSymbolPlaced(const SymbolInstance&,
|
||||
const JointPlacement&,
|
||||
style::SymbolPlacementType,
|
||||
@@ -1438,12 +1438,19 @@ void TilePlacement::placeSymbolBucket(const BucketPlacementData& params, std::se
|
||||
}
|
||||
}
|
||||
|
||||
bool TilePlacement::stickToFirstVariableAnchor(const CollisionBox& box,
|
||||
Point<float> shift,
|
||||
const mat4& posMatrix,
|
||||
float textPixelRatio) {
|
||||
bool TilePlacement::canPlaceAtVariableAnchor(const CollisionBox& box,
|
||||
TextVariableAnchorType anchor,
|
||||
Point<float> shift,
|
||||
std::vector<style::TextVariableAnchorType>& anchors,
|
||||
const mat4& posMatrix,
|
||||
float textPixelRatio) {
|
||||
assert(tileBorders);
|
||||
auto status = collisionIndex.intersectsTileEdges(box, shift, posMatrix, textPixelRatio, *tileBorders);
|
||||
if (status.flags == IntersectStatus::None) return true;
|
||||
|
||||
if (anchor != anchors.front()) return false;
|
||||
|
||||
status = collisionIndex.intersectsTileEdges(box, {}, posMatrix, textPixelRatio, *tileBorders);
|
||||
return status.flags != IntersectStatus::None;
|
||||
}
|
||||
|
||||
|
||||
@@ -157,11 +157,13 @@ protected:
|
||||
return nullopt;
|
||||
}
|
||||
SymbolInstanceReferences getSortedSymbols(const BucketPlacementData&, float pixelRatio);
|
||||
virtual bool stickToFirstVariableAnchor(const CollisionBox&,
|
||||
Point<float> /*shift*/,
|
||||
const mat4& /*posMatrix*/,
|
||||
float /*textPixelRatio*/) {
|
||||
return false;
|
||||
virtual bool canPlaceAtVariableAnchor(const CollisionBox&,
|
||||
style::TextVariableAnchorType,
|
||||
Point<float> /*shift*/,
|
||||
std::vector<style::TextVariableAnchorType>&,
|
||||
const mat4& /*posMatrix*/,
|
||||
float /*textPixelRatio*/) {
|
||||
return true;
|
||||
}
|
||||
|
||||
// Returns `true` if bucket vertices were updated; returns `false` otherwise.
|
||||
|
||||
Reference in New Issue
Block a user