Skip to content
This repository has been archived by the owner on Aug 8, 2023. It is now read-only.

[core] Release quad data after vertex buffers are created #15189

Merged
merged 3 commits into from
Jul 23, 2019
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
136 changes: 94 additions & 42 deletions src/mbgl/layout/symbol_instance.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -18,36 +18,79 @@ const Shaping& getAnyShaping(const ShapedTextOrientations& shapedTextOrientation

} // namespace

SymbolInstanceSharedData::SymbolInstanceSharedData(GeometryCoordinates line_,
const ShapedTextOrientations& shapedTextOrientations,
const optional<PositionedIcon>& shapedIcon,
const style::SymbolLayoutProperties::Evaluated& layout,
const float layoutTextSize,
const style::SymbolPlacementType textPlacement,
const std::array<float, 2>& textOffset,
const GlyphPositions& positions) : line(std::move(line_)) {
// Create the quads used for rendering the icon and glyphs.
if (shapedIcon) {
iconQuad = getIconQuad(*shapedIcon, layout, layoutTextSize, shapedTextOrientations.horizontal);
}

bool singleLineInitialized = false;
const auto initHorizontalGlyphQuads = [&] (SymbolQuads& quads, const Shaping& shaping) {
if (!shapedTextOrientations.singleLine) {
quads = getGlyphQuads(shaping, textOffset, layout, textPlacement, positions);
return;
}
if (!singleLineInitialized) {
rightJustifiedGlyphQuads = getGlyphQuads(shaping, textOffset, layout, textPlacement, positions);
singleLineInitialized = true;
}
};

if (shapedTextOrientations.right) {
initHorizontalGlyphQuads(rightJustifiedGlyphQuads, shapedTextOrientations.right);
}

if (shapedTextOrientations.center) {
initHorizontalGlyphQuads(centerJustifiedGlyphQuads, shapedTextOrientations.center);
}

if (shapedTextOrientations.left) {
initHorizontalGlyphQuads(leftJustifiedGlyphQuads, shapedTextOrientations.left);
}

if (shapedTextOrientations.vertical) {
verticalGlyphQuads = getGlyphQuads(shapedTextOrientations.vertical, textOffset, layout, textPlacement, positions);
}
}

bool SymbolInstanceSharedData::empty() const {
return rightJustifiedGlyphQuads.empty() && centerJustifiedGlyphQuads.empty() && leftJustifiedGlyphQuads.empty() && verticalGlyphQuads.empty();
}

SymbolInstance::SymbolInstance(Anchor& anchor_,
GeometryCoordinates line_,
std::shared_ptr<SymbolInstanceSharedData> sharedData_,
const ShapedTextOrientations& shapedTextOrientations,
optional<PositionedIcon> shapedIcon,
const SymbolLayoutProperties::Evaluated& layout,
const float layoutTextSize,
const optional<PositionedIcon>& shapedIcon,
const float textBoxScale_,
const float textPadding,
const SymbolPlacementType textPlacement,
const std::array<float, 2> textOffset_,
const std::array<float, 2>& textOffset_,
astojilj marked this conversation as resolved.
Show resolved Hide resolved
const float iconBoxScale,
const float iconPadding,
const std::array<float, 2> iconOffset_,
const GlyphPositions& positions,
const std::array<float, 2>& iconOffset_,
const IndexedSubfeature& indexedFeature,
const std::size_t layoutFeatureIndex_,
const std::size_t dataFeatureIndex_,
std::u16string key_,
const float overscaling,
const float rotate,
float radialTextOffset_) :
sharedData(std::move(sharedData_)),
anchor(anchor_),
line(line_),
hasText(false),
// 'hasText' depends on finding at least one glyph in the shaping that's also in the GlyphPositionMap
hasText(!sharedData->empty()),
hasIcon(shapedIcon),

// Create the collision features that will be used to check whether this symbol instance can be placed
// As a collision approximation, we can use either the vertical or any of the horizontal versions of the feature
textCollisionFeature(line_, anchor, getAnyShaping(shapedTextOrientations), textBoxScale_, textPadding, textPlacement, indexedFeature, overscaling, rotate),
iconCollisionFeature(line_, anchor, shapedIcon, iconBoxScale, iconPadding, indexedFeature, rotate),
textCollisionFeature(sharedData->line, anchor, getAnyShaping(shapedTextOrientations), textBoxScale_, textPadding, textPlacement, indexedFeature, overscaling, rotate),
iconCollisionFeature(sharedData->line, anchor, shapedIcon, iconBoxScale, iconPadding, indexedFeature, rotate),
writingModes(WritingModeType::None),
layoutFeatureIndex(layoutFeatureIndex_),
dataFeatureIndex(dataFeatureIndex_),
Expand All @@ -58,43 +101,52 @@ SymbolInstance::SymbolInstance(Anchor& anchor_,
radialTextOffset(radialTextOffset_),
singleLine(shapedTextOrientations.singleLine) {

// Create the quads used for rendering the icon and glyphs.
if (shapedIcon) {
iconQuad = getIconQuad(*shapedIcon, layout, layoutTextSize, shapedTextOrientations.horizontal);
}

bool singleLineInitialized = false;
const auto initHorizontalGlyphQuads = [&] (SymbolQuads& quads, const Shaping& shaping) {
rightJustifiedGlyphQuadsSize = sharedData->rightJustifiedGlyphQuads.size();
centerJustifiedGlyphQuadsSize = sharedData->centerJustifiedGlyphQuads.size();
leftJustifiedGlyphQuadsSize = sharedData->leftJustifiedGlyphQuads.size();
verticalGlyphQuadsSize = sharedData->verticalGlyphQuads.size();

if (rightJustifiedGlyphQuadsSize || centerJustifiedGlyphQuadsSize || leftJustifiedGlyphQuadsSize) {
writingModes |= WritingModeType::Horizontal;
if (!singleLine) {
quads = getGlyphQuads(shaping, textOffset, layout, textPlacement, positions);
return;
}
if (!singleLineInitialized) {
rightJustifiedGlyphQuads = getGlyphQuads(shaping, textOffset, layout, textPlacement, positions);
singleLineInitialized = true;
}
};

if (shapedTextOrientations.right) {
initHorizontalGlyphQuads(rightJustifiedGlyphQuads, shapedTextOrientations.right);
}

if (shapedTextOrientations.center) {
initHorizontalGlyphQuads(centerJustifiedGlyphQuads, shapedTextOrientations.center);
if (verticalGlyphQuadsSize) {
writingModes |= WritingModeType::Vertical;
}
}

if (shapedTextOrientations.left) {
initHorizontalGlyphQuads(leftJustifiedGlyphQuads, shapedTextOrientations.left);
}
const GeometryCoordinates& SymbolInstance::line() const {
assert(sharedData);
return sharedData->line;
}

if (shapedTextOrientations.vertical) {
writingModes |= WritingModeType::Vertical;
verticalGlyphQuads = getGlyphQuads(shapedTextOrientations.vertical, textOffset, layout, textPlacement, positions);
}
const SymbolQuads& SymbolInstance::rightJustifiedGlyphQuads() const {
assert(sharedData);
return sharedData->rightJustifiedGlyphQuads;
}

// 'hasText' depends on finding at least one glyph in the shaping that's also in the GlyphPositionMap
hasText = !rightJustifiedGlyphQuads.empty() || !centerJustifiedGlyphQuads.empty() || !leftJustifiedGlyphQuads.empty() || !verticalGlyphQuads.empty();
const SymbolQuads& SymbolInstance::leftJustifiedGlyphQuads() const {
assert(sharedData);
return sharedData->leftJustifiedGlyphQuads;
}

const SymbolQuads& SymbolInstance::centerJustifiedGlyphQuads() const {
assert(sharedData);
return sharedData->centerJustifiedGlyphQuads;
}

const SymbolQuads& SymbolInstance::verticalGlyphQuads() const {
assert(sharedData);
return sharedData->verticalGlyphQuads;
}

const optional<SymbolQuad>& SymbolInstance::iconQuad() const {
assert(sharedData);
return sharedData->iconQuad;
}

void SymbolInstance::releaseSharedData() {
sharedData.reset();
}

optional<size_t> SymbolInstance::getDefaultHorizontalPlacedTextIndex() const {
Expand Down
59 changes: 42 additions & 17 deletions src/mbgl/layout/symbol_instance.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -21,23 +21,39 @@ struct ShapedTextOrientations {
bool singleLine = false;
};

struct SymbolInstanceSharedData {
SymbolInstanceSharedData(GeometryCoordinates line,
const ShapedTextOrientations& shapedTextOrientations,
const optional<PositionedIcon>& shapedIcon,
const style::SymbolLayoutProperties::Evaluated& layout,
const float layoutTextSize,
const style::SymbolPlacementType textPlacement,
const std::array<float, 2>& textOffset,
const GlyphPositions& positions);
bool empty() const;
GeometryCoordinates line;
astojilj marked this conversation as resolved.
Show resolved Hide resolved
// Note: When singleLine == true, only `rightJustifiedGlyphQuads` is populated.
SymbolQuads rightJustifiedGlyphQuads;
SymbolQuads centerJustifiedGlyphQuads;
SymbolQuads leftJustifiedGlyphQuads;
SymbolQuads verticalGlyphQuads;
optional<SymbolQuad> iconQuad;
};

class SymbolInstance {
public:
SymbolInstance(Anchor& anchor,
GeometryCoordinates line,
SymbolInstance(Anchor& anchor_,
std::shared_ptr<SymbolInstanceSharedData> sharedData,
const ShapedTextOrientations& shapedTextOrientations,
optional<PositionedIcon> shapedIcon,
const style::SymbolLayoutProperties::Evaluated&,
const float layoutTextSize,
const optional<PositionedIcon>& shapedIcon,
const float textBoxScale,
const float textPadding,
style::SymbolPlacementType textPlacement,
const std::array<float, 2> textOffset,
const style::SymbolPlacementType textPlacement,
const std::array<float, 2>& textOffset,
const float iconBoxScale,
const float iconPadding,
const std::array<float, 2> iconOffset,
const GlyphPositions&,
const IndexedSubfeature&,
const std::array<float, 2>& iconOffset,
const IndexedSubfeature& indexedFeature,
const std::size_t layoutFeatureIndex,
const std::size_t dataFeatureIndex,
std::u16string key,
Expand All @@ -46,18 +62,27 @@ class SymbolInstance {
float radialTextOffset);

optional<size_t> getDefaultHorizontalPlacedTextIndex() const;
const GeometryCoordinates& line() const;
const SymbolQuads& rightJustifiedGlyphQuads() const;
const SymbolQuads& leftJustifiedGlyphQuads() const;
const SymbolQuads& centerJustifiedGlyphQuads() const;
const SymbolQuads& verticalGlyphQuads() const;
const optional<SymbolQuad>& iconQuad() const;
void releaseSharedData();

private:
std::shared_ptr<SymbolInstanceSharedData> sharedData;

public:
Anchor anchor;
GeometryCoordinates line;
bool hasText;
bool hasIcon;
// Note: When singleLine == true, only `rightJustifiedGlyphQuads` is populated.
SymbolQuads rightJustifiedGlyphQuads;
SymbolQuads centerJustifiedGlyphQuads;
SymbolQuads leftJustifiedGlyphQuads;

SymbolQuads verticalGlyphQuads;
std::size_t rightJustifiedGlyphQuadsSize;
std::size_t centerJustifiedGlyphQuadsSize;
std::size_t leftJustifiedGlyphQuadsSize;
std::size_t verticalGlyphQuadsSize;

optional<SymbolQuad> iconQuad;
CollisionFeature textCollisionFeature;
CollisionFeature iconCollisionFeature;
WritingModeType writingModes;
Expand Down
Loading