0
votes

I am trying to add a popup to my map icons in Mapbox GL JS. So far I have been unsuccessful.

When I create a layer, in the layer's data, I have specified several properties. However when I try and add a popup to the icon, all of the properties are not present. Attempting to access them simply returns undefined.

Adding the layer:

function addRedAirports() {
    map.addSource('hoggitRed', {
        type: 'geojson',
        cluster: true,
        clusterMaxZoom: 14, // Max zoom to cluster points on
        clusterRadius: 10, // Radius of each cluster when clustering points (defaults to 50)
        data: redAirportArray[0]
    });
    map.addLayer({
        "id": 'reds',
        "type": "symbol",
        "source": "hoggitRed",
        "layout": {
            "icon-image": "redIcon",
            "icon-size": 0.075,
            "icon-anchor": "bottom",
            "icon-allow-overlap": true
        }
    });

Here is the contents of the data (redAirportArray[0]). I am looping through an api to get this data.

When I pass this data to mapbox, the properties are complete and correct. However when I try access them for a popup, I get undefined. Console logging the mapbox layer shows none of the inputted properties present..

(I have condensed this code slightly.. every loop I create a feature and then push it to the feature collection. I combined the two in this snippet for the sake of simplicity)

let redAirportArray = [{
    "type": "FeatureCollection",
    "features": [{
    "type": "Feature",
    "properties": { //SETTING THE PROPERTIES
        "test": 'test',
        "ID": airportsRed[x].Id,
        "team": airportsRed[x].Coalition
    },
    "geometry": {
        "type": "Point",
        "coordinates": [airportsRed[x].LatLongAlt.Long, airportsRed[x].LatLongAlt.Lat]
    }
}]

Adding a popup on click

map.on('click', 'reds', function (e) {
    var coordinates = e.features[0].geometry.coordinates.slice();
    let team = e.features[0].properties.ID;


    while (Math.abs(e.lngLat.lng - coordinates[0]) > 180) {
    coordinates[0] += e.lngLat.lng > coordinates[0] ? 360 : -360;
    }

    new mapboxgl.Popup()
    .setLngLat(coordinates)
    .setHTML(team)
    .addTo(map);
});

Thanks in advance and I hope you can help!

1
What do you get when you console.log(team)? If you're seeing undefined, my guess is because e.features[0] is not defined - BDD
When I log it I get: js qu {type: "Feature", _vectorTileFeature: Co, properties: {…}, id: 7, layer: {…}, …} id: 7 layer: {id: "reds", type: "symbol", source: "hoggitRed", layout: {…}} properties: cluster: true cluster_id: 7 point_count: 2 point_count_abbreviated: 2 __proto__: Object source: "hoggitRed" state: {} type: "Feature" _geometry: {type: "Point", coordinates: Array(2)} _vectorTileFeature: Co {properties: {…}, extent: 8192, type: 1, _pbf: ru, _geometry: 43, …} geometry: (...) __proto__: Object It seems each feature is getting the props of the actual layer - Mark Doyle

1 Answers

1
votes

With the way your layer is currently being added, you're looking for properties in the wrong location. e.features[0] is not defined since e is the feature you just clicked. Your pop up code should look something like this:

map.on('click', 'reds', function (e) {
    var coordinates = e.geometry.coordinates.slice(); // Changed
    let team = e.properties.ID; // Changed


    while (Math.abs(e.lngLat.lng - coordinates[0]) > 180) {
    coordinates[0] += e.lngLat.lng > coordinates[0] ? 360 : -360;
    }

    new mapboxgl.Popup()
    .setLngLat(coordinates)
    .setHTML(team)
    .addTo(map);
});