Search code examples
javascriptopenlayers

Add multiple marker to a vector layer efficiently


I need to add multiple (like 20) markers on an openlayer map.
Right now I am able to do that, but I am sure its not the more efficient way to do that.

This is the code I found on the web:

var addressOSM = new ol.Map({
    controls: null,
    layers: [
        new ol.layer.Tile({
            source: new ol.source.OSM()
        })
    ],
    target: 'map',
    view: new ol.View({
        center: ol.proj.fromLonLat([lng, lat]),
        zoom: 15
    })
});

To add the markers I use this code:

for (let i = 0; i < data.length; i++) {
    addressOSM.addLayer(createMarker(data[i].longitude, data[i].latitude, data[i].id)));
}

The createMarker function is:

function createMarker(lng, lat, id) {
    var vectorLayer = new ol.layer.Vector({
        source: new ol.source.Vector({
            features: [new ol.Feature({
                geometry: new ol.geom.Point(ol.proj.fromLonLat([parseFloat(lng), parseFloat(lat)])),
                id: id
            })]
        }),
        style: new ol.style.Style({
            image: new ol.style.Icon({
                anchor: [0.5, 1],
                anchorXUnits: "fraction",
                anchorYUnits: "fraction",
                src: "url_to_png.png"
            })
        })
    });
    return vectorLayer;
}

This code works but it is pretty slow.
How can I improve it to be more efficient?


Solution

  • You don't need a new layer for each feature, they can all go in a single layer

    var vectorLayer = new ol.layer.Vector({
        source: new ol.source.Vector(),
        style: new ol.style.Style({
            image: new ol.style.Icon({
                anchor: [0.5, 1],
                anchorXUnits: "fraction",
                anchorYUnits: "fraction",
                src: "url_to_png.png"
            })
        })
    });
    addressOSM.addLayer(vectorLayer);
    
    for (let i = 0; i < data.length; i++) {
        vectorLayer.getSource().addFeature(createMarker(data[i].longitude, data[i].latitude, data[i].id)));
    }
    
    function createMarker(lng, lat, id) {
        return new ol.Feature({
            geometry: new ol.geom.Point(ol.proj.fromLonLat([parseFloat(lng), parseFloat(lat)])),
            id: id
        });
    }