Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Fix icon-fit with variable label placement #8755

Merged
merged 11 commits into from Sep 20, 2019
132 changes: 132 additions & 0 deletions debug/variable-anchor-with-icon-text-fit.html
@@ -0,0 +1,132 @@
<!DOCTYPE html>
<html>
<head>
<meta charset='utf-8' />
<title>Mapbox GL JS debug page</title>
<meta charset='utf-8'>
<meta name="viewport" content="width=device-width, initial-scale=1.0, user-scalable=no">
<link rel='stylesheet' href='../dist/mapbox-gl.css' />
<style>
body { margin: 0; padding: 0; }
html, body, #map { height: 100%; }
</style>
</head>
<body>

<div id='map'></div>
<script src='../dist/mapbox-gl-dev.js'></script>
<script src='access_token_generated.js'></script>
<script>
var places = {
"type": "FeatureCollection",
"features": [{
"type": "Feature",
"properties": {
"description": "Ford's Theater",
"icon": "theatre"
},
"geometry": {
"type": "Point",
"coordinates": [-77.038659, 38.931567]
}
}, {
"type": "Feature",
"properties": {
"description": "The Gaslight",
"icon": "theatre"
},
"geometry": {
"type": "Point",
"coordinates": [-77.003168, 38.894651]
}
}, {
"type": "Feature",
"properties": {
"description": "Horrible Harry's",
"icon": "bar"
},
"geometry": {
"type": "Point",
"coordinates": [-77.090372, 38.881189]
}
}, {
"type": "Feature",
"properties": {
"description": "Bike Party",
"icon": "bicycle"
},
"geometry": {
"type": "Point",
"coordinates": [-77.052477, 38.943951]
}
}, {
"type": "Feature",
"properties": {
"description": "Rockabilly Rockstars",
"icon": "music"
},
"geometry": {
"type": "Point",
"coordinates": [-77.031706, 38.914581]
}
}, {
"type": "Feature",
"properties": {
"description": "District Drum Tribe",
"icon": "music"
},
"geometry": {
"type": "Point",
"coordinates": [-77.020945, 38.878241]
}
}, {
"type": "Feature",
"properties": {
"description": "Motown Memories",
"icon": "music"
},
"geometry": {
"type": "Point",
"coordinates": [-77.007481, 38.876516]
}
}]
};
var style = {
version: 8,
center: [-77.04, 38.907],
zoom: 12,
sources: {
places: {
type: 'geojson',
data: places,
}
},
sprite: 'mapbox://sprites/mapbox/streets-v11',
glyphs: "mapbox://fonts/mapbox/{fontstack}/{range}.pbf",
layers: [{
id: 'foo',
type: 'symbol',
source: 'places',
layout: {
'icon-image': 'rectangle-orange-6',
'text-field': ['get', 'description'],
'text-size': 12.5,
'text-variable-anchor': ['left', 'right', 'bottom', 'top'],
'text-justify': 'auto',
'icon-text-fit': 'width',
'icon-text-fit-padding': [0, 5, 1, 5]
},
paint: {
'text-color': '#3C77C0'
}
}]
};

var map = window.map = new mapboxgl.Map({
container: 'map',
style
});
</script>

</body>
</html>
107 changes: 58 additions & 49 deletions src/data/array_types.js
Expand Up @@ -422,10 +422,11 @@ register('StructArrayLayout2ub2f12', StructArrayLayout2ub2f12);
* [28]: Float32[2]
* [36]: Uint8[3]
* [40]: Uint32[1]
* [44]: Int16[1]
*
* @private
*/
class StructArrayLayout2i2ui3ul3ui2f3ub1ul44 extends StructArray {
class StructArrayLayout2i2ui3ul3ui2f3ub1ul1i48 extends StructArray {
asheemmamoowala marked this conversation as resolved.
Show resolved Hide resolved
uint8: Uint8Array;
int16: Int16Array;
uint16: Uint16Array;
Expand All @@ -440,16 +441,16 @@ class StructArrayLayout2i2ui3ul3ui2f3ub1ul44 extends StructArray {
this.float32 = new Float32Array(this.arrayBuffer);
}

emplaceBack(v0: number, v1: number, v2: number, v3: number, v4: number, v5: number, v6: number, v7: number, v8: number, v9: number, v10: number, v11: number, v12: number, v13: number, v14: number, v15: number) {
emplaceBack(v0: number, v1: number, v2: number, v3: number, v4: number, v5: number, v6: number, v7: number, v8: number, v9: number, v10: number, v11: number, v12: number, v13: number, v14: number, v15: number, v16: number) {
const i = this.length;
this.resize(i + 1);
return this.emplace(i, v0, v1, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15);
return this.emplace(i, v0, v1, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16);
}

emplace(i: number, v0: number, v1: number, v2: number, v3: number, v4: number, v5: number, v6: number, v7: number, v8: number, v9: number, v10: number, v11: number, v12: number, v13: number, v14: number, v15: number) {
const o2 = i * 22;
const o4 = i * 11;
const o1 = i * 44;
emplace(i: number, v0: number, v1: number, v2: number, v3: number, v4: number, v5: number, v6: number, v7: number, v8: number, v9: number, v10: number, v11: number, v12: number, v13: number, v14: number, v15: number, v16: number) {
const o2 = i * 24;
const o4 = i * 12;
const o1 = i * 48;
this.int16[o2 + 0] = v0;
this.int16[o2 + 1] = v1;
this.uint16[o2 + 2] = v2;
Expand All @@ -466,23 +467,24 @@ class StructArrayLayout2i2ui3ul3ui2f3ub1ul44 extends StructArray {
this.uint8[o1 + 37] = v13;
this.uint8[o1 + 38] = v14;
this.uint32[o4 + 10] = v15;
this.int16[o2 + 22] = v16;
return i;
}
}

StructArrayLayout2i2ui3ul3ui2f3ub1ul44.prototype.bytesPerElement = 44;
register('StructArrayLayout2i2ui3ul3ui2f3ub1ul44', StructArrayLayout2i2ui3ul3ui2f3ub1ul44);
StructArrayLayout2i2ui3ul3ui2f3ub1ul1i48.prototype.bytesPerElement = 48;
register('StructArrayLayout2i2ui3ul3ui2f3ub1ul1i48', StructArrayLayout2i2ui3ul3ui2f3ub1ul1i48);

/**
* Implementation of the StructArray layout:
* [0]: Int16[6]
* [12]: Uint16[11]
* [0]: Int16[7]
* [14]: Uint16[11]
* [36]: Uint32[1]
* [40]: Float32[3]
*
* @private
*/
class StructArrayLayout6i11ui1ul3f52 extends StructArray {
class StructArrayLayout7i11ui1ul3f52 extends StructArray {
uint8: Uint8Array;
int16: Int16Array;
uint16: Uint16Array;
Expand All @@ -497,13 +499,13 @@ class StructArrayLayout6i11ui1ul3f52 extends StructArray {
this.float32 = new Float32Array(this.arrayBuffer);
}

emplaceBack(v0: number, v1: number, v2: number, v3: number, v4: number, v5: number, v6: number, v7: number, v8: number, v9: number, v10: number, v11: number, v12: number, v13: number, v14: number, v15: number, v16: number, v17: number, v18: number, v19: number, v20: number) {
emplaceBack(v0: number, v1: number, v2: number, v3: number, v4: number, v5: number, v6: number, v7: number, v8: number, v9: number, v10: number, v11: number, v12: number, v13: number, v14: number, v15: number, v16: number, v17: number, v18: number, v19: number, v20: number, v21: number) {
const i = this.length;
this.resize(i + 1);
return this.emplace(i, v0, v1, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20);
return this.emplace(i, v0, v1, v2, v3, v4, v5, v6, v7, v8, v9, v10, v11, v12, v13, v14, v15, v16, v17, v18, v19, v20, v21);
}

emplace(i: number, v0: number, v1: number, v2: number, v3: number, v4: number, v5: number, v6: number, v7: number, v8: number, v9: number, v10: number, v11: number, v12: number, v13: number, v14: number, v15: number, v16: number, v17: number, v18: number, v19: number, v20: number) {
emplace(i: number, v0: number, v1: number, v2: number, v3: number, v4: number, v5: number, v6: number, v7: number, v8: number, v9: number, v10: number, v11: number, v12: number, v13: number, v14: number, v15: number, v16: number, v17: number, v18: number, v19: number, v20: number, v21: number) {
const o2 = i * 26;
const o4 = i * 13;
this.int16[o2 + 0] = v0;
Expand All @@ -512,7 +514,7 @@ class StructArrayLayout6i11ui1ul3f52 extends StructArray {
this.int16[o2 + 3] = v3;
this.int16[o2 + 4] = v4;
this.int16[o2 + 5] = v5;
this.uint16[o2 + 6] = v6;
this.int16[o2 + 6] = v6;
this.uint16[o2 + 7] = v7;
this.uint16[o2 + 8] = v8;
this.uint16[o2 + 9] = v9;
Expand All @@ -523,16 +525,17 @@ class StructArrayLayout6i11ui1ul3f52 extends StructArray {
this.uint16[o2 + 14] = v14;
this.uint16[o2 + 15] = v15;
this.uint16[o2 + 16] = v16;
this.uint32[o4 + 9] = v17;
this.float32[o4 + 10] = v18;
this.float32[o4 + 11] = v19;
this.float32[o4 + 12] = v20;
this.uint16[o2 + 17] = v17;
this.uint32[o4 + 9] = v18;
this.float32[o4 + 10] = v19;
this.float32[o4 + 11] = v20;
this.float32[o4 + 12] = v21;
return i;
}
}

StructArrayLayout6i11ui1ul3f52.prototype.bytesPerElement = 52;
register('StructArrayLayout6i11ui1ul3f52', StructArrayLayout6i11ui1ul3f52);
StructArrayLayout7i11ui1ul3f52.prototype.bytesPerElement = 52;
register('StructArrayLayout7i11ui1ul3f52', StructArrayLayout7i11ui1ul3f52);

/**
* Implementation of the StructArray layout:
Expand Down Expand Up @@ -874,6 +877,7 @@ class PlacedSymbolStruct extends Struct {
placedOrientation: number;
hidden: number;
crossTileID: number;
associatedIconIndex: number;
get anchorX() { return this._structArray.int16[this._pos2 + 0]; }
set anchorX(x: number) { this._structArray.int16[this._pos2 + 0] = x; }
get anchorY() { return this._structArray.int16[this._pos2 + 1]; }
Expand Down Expand Up @@ -906,16 +910,18 @@ class PlacedSymbolStruct extends Struct {
set hidden(x: number) { this._structArray.uint8[this._pos1 + 38] = x; }
get crossTileID() { return this._structArray.uint32[this._pos4 + 10]; }
set crossTileID(x: number) { this._structArray.uint32[this._pos4 + 10] = x; }
get associatedIconIndex() { return this._structArray.int16[this._pos2 + 22]; }
set associatedIconIndex(x: number) { this._structArray.int16[this._pos2 + 22] = x; }
}

PlacedSymbolStruct.prototype.size = 44;
PlacedSymbolStruct.prototype.size = 48;

export type PlacedSymbol = PlacedSymbolStruct;

/**
* @private
*/
export class PlacedSymbolArray extends StructArrayLayout2i2ui3ul3ui2f3ub1ul44 {
export class PlacedSymbolArray extends StructArrayLayout2i2ui3ul3ui2f3ub1ul1i48 {
/**
* Return the PlacedSymbolStruct at the given location in the array.
* @param {number} index The index of the element.
Expand All @@ -936,6 +942,7 @@ class SymbolInstanceStruct extends Struct {
centerJustifiedTextSymbolIndex: number;
leftJustifiedTextSymbolIndex: number;
verticalPlacedTextSymbolIndex: number;
placedIconSymbolIndex: number;
key: number;
textBoxStartIndex: number;
textBoxEndIndex: number;
Expand Down Expand Up @@ -963,28 +970,30 @@ class SymbolInstanceStruct extends Struct {
set leftJustifiedTextSymbolIndex(x: number) { this._structArray.int16[this._pos2 + 4] = x; }
get verticalPlacedTextSymbolIndex() { return this._structArray.int16[this._pos2 + 5]; }
set verticalPlacedTextSymbolIndex(x: number) { this._structArray.int16[this._pos2 + 5] = x; }
get key() { return this._structArray.uint16[this._pos2 + 6]; }
set key(x: number) { this._structArray.uint16[this._pos2 + 6] = x; }
get textBoxStartIndex() { return this._structArray.uint16[this._pos2 + 7]; }
set textBoxStartIndex(x: number) { this._structArray.uint16[this._pos2 + 7] = x; }
get textBoxEndIndex() { return this._structArray.uint16[this._pos2 + 8]; }
set textBoxEndIndex(x: number) { this._structArray.uint16[this._pos2 + 8] = x; }
get verticalTextBoxStartIndex() { return this._structArray.uint16[this._pos2 + 9]; }
set verticalTextBoxStartIndex(x: number) { this._structArray.uint16[this._pos2 + 9] = x; }
get verticalTextBoxEndIndex() { return this._structArray.uint16[this._pos2 + 10]; }
set verticalTextBoxEndIndex(x: number) { this._structArray.uint16[this._pos2 + 10] = x; }
get iconBoxStartIndex() { return this._structArray.uint16[this._pos2 + 11]; }
set iconBoxStartIndex(x: number) { this._structArray.uint16[this._pos2 + 11] = x; }
get iconBoxEndIndex() { return this._structArray.uint16[this._pos2 + 12]; }
set iconBoxEndIndex(x: number) { this._structArray.uint16[this._pos2 + 12] = x; }
get featureIndex() { return this._structArray.uint16[this._pos2 + 13]; }
set featureIndex(x: number) { this._structArray.uint16[this._pos2 + 13] = x; }
get numHorizontalGlyphVertices() { return this._structArray.uint16[this._pos2 + 14]; }
set numHorizontalGlyphVertices(x: number) { this._structArray.uint16[this._pos2 + 14] = x; }
get numVerticalGlyphVertices() { return this._structArray.uint16[this._pos2 + 15]; }
set numVerticalGlyphVertices(x: number) { this._structArray.uint16[this._pos2 + 15] = x; }
get numIconVertices() { return this._structArray.uint16[this._pos2 + 16]; }
set numIconVertices(x: number) { this._structArray.uint16[this._pos2 + 16] = x; }
get placedIconSymbolIndex() { return this._structArray.int16[this._pos2 + 6]; }
set placedIconSymbolIndex(x: number) { this._structArray.int16[this._pos2 + 6] = x; }
get key() { return this._structArray.uint16[this._pos2 + 7]; }
set key(x: number) { this._structArray.uint16[this._pos2 + 7] = x; }
get textBoxStartIndex() { return this._structArray.uint16[this._pos2 + 8]; }
set textBoxStartIndex(x: number) { this._structArray.uint16[this._pos2 + 8] = x; }
get textBoxEndIndex() { return this._structArray.uint16[this._pos2 + 9]; }
set textBoxEndIndex(x: number) { this._structArray.uint16[this._pos2 + 9] = x; }
get verticalTextBoxStartIndex() { return this._structArray.uint16[this._pos2 + 10]; }
set verticalTextBoxStartIndex(x: number) { this._structArray.uint16[this._pos2 + 10] = x; }
get verticalTextBoxEndIndex() { return this._structArray.uint16[this._pos2 + 11]; }
set verticalTextBoxEndIndex(x: number) { this._structArray.uint16[this._pos2 + 11] = x; }
get iconBoxStartIndex() { return this._structArray.uint16[this._pos2 + 12]; }
set iconBoxStartIndex(x: number) { this._structArray.uint16[this._pos2 + 12] = x; }
get iconBoxEndIndex() { return this._structArray.uint16[this._pos2 + 13]; }
set iconBoxEndIndex(x: number) { this._structArray.uint16[this._pos2 + 13] = x; }
get featureIndex() { return this._structArray.uint16[this._pos2 + 14]; }
set featureIndex(x: number) { this._structArray.uint16[this._pos2 + 14] = x; }
get numHorizontalGlyphVertices() { return this._structArray.uint16[this._pos2 + 15]; }
set numHorizontalGlyphVertices(x: number) { this._structArray.uint16[this._pos2 + 15] = x; }
get numVerticalGlyphVertices() { return this._structArray.uint16[this._pos2 + 16]; }
set numVerticalGlyphVertices(x: number) { this._structArray.uint16[this._pos2 + 16] = x; }
get numIconVertices() { return this._structArray.uint16[this._pos2 + 17]; }
set numIconVertices(x: number) { this._structArray.uint16[this._pos2 + 17] = x; }
get crossTileID() { return this._structArray.uint32[this._pos4 + 9]; }
set crossTileID(x: number) { this._structArray.uint32[this._pos4 + 9] = x; }
get textBoxScale() { return this._structArray.float32[this._pos4 + 10]; }
Expand All @@ -1002,7 +1011,7 @@ export type SymbolInstance = SymbolInstanceStruct;
/**
* @private
*/
export class SymbolInstanceArray extends StructArrayLayout6i11ui1ul3f52 {
export class SymbolInstanceArray extends StructArrayLayout7i11ui1ul3f52 {
/**
* Return the SymbolInstanceStruct at the given location in the array.
* @param {number} index The index of the element.
Expand Down Expand Up @@ -1124,8 +1133,8 @@ export {
StructArrayLayout6i1ul2ui2i24,
StructArrayLayout2i2i2i12,
StructArrayLayout2ub2f12,
StructArrayLayout2i2ui3ul3ui2f3ub1ul44,
StructArrayLayout6i11ui1ul3f52,
StructArrayLayout2i2ui3ul3ui2f3ub1ul1i48,
StructArrayLayout7i11ui1ul3f52,
StructArrayLayout1f4,
StructArrayLayout3i6,
StructArrayLayout1ul2ui8,
Expand Down
4 changes: 3 additions & 1 deletion src/data/bucket/symbol_attributes.js
Expand Up @@ -73,7 +73,8 @@ export const placement = createLayout([
{type: 'Uint8', name: 'writingMode'},
{type: 'Uint8', name: 'placedOrientation'},
{type: 'Uint8', name: 'hidden'},
{type: 'Uint32', name: 'crossTileID'}
{type: 'Uint32', name: 'crossTileID'},
{type: 'Int16', name: 'associatedIconIndex'}
]);

export const symbolInstance = createLayout([
Expand All @@ -83,6 +84,7 @@ export const symbolInstance = createLayout([
{type: 'Int16', name: 'centerJustifiedTextSymbolIndex'},
{type: 'Int16', name: 'leftJustifiedTextSymbolIndex'},
{type: 'Int16', name: 'verticalPlacedTextSymbolIndex'},
{type: 'Int16', name: 'placedIconSymbolIndex'},
{type: 'Uint16', name: 'key'},
{type: 'Uint16', name: 'textBoxStartIndex'},
{type: 'Uint16', name: 'textBoxEndIndex'},
Expand Down
7 changes: 5 additions & 2 deletions src/data/bucket/symbol_bucket.js
Expand Up @@ -539,7 +539,8 @@ class SymbolBucket implements Bucket {
writingMode: any,
labelAnchor: Anchor,
lineStartIndex: number,
lineLength: number) {
lineLength: number,
associatedIconIndex: number) {
mourner marked this conversation as resolved.
Show resolved Hide resolved
const indexArray = arrays.indexArray;
const layoutVertexArray = arrays.layoutVertexArray;
const dynamicLayoutVertexArray = arrays.dynamicLayoutVertexArray;
Expand Down Expand Up @@ -619,7 +620,9 @@ class SymbolBucket implements Bucket {
0,
(false: any),
// The crossTileID is only filled/used on the foreground for dynamic text anchors
0);
0,
associatedIconIndex
);
}

_addCollisionDebugVertex(layoutVertexArray: StructArray, collisionVertexArray: StructArray, point: Point, anchorX: number, anchorY: number, extrude: Point) {
Expand Down