Leaflet : création massive de markers

Leaflet

Dans la continuité de l’article sur la création d’une carte Leaflet (Leaflet, créer votre carte rapidement), voyons maintenant comment créer massivement des markers.

En effet, il est rare de créer une carte pour n’en créer qu’un seul, et si lorsqu’il y en a moins d’une 10aine, on peut se permettre de les créer unitairement, au delà il vaut mieux travailler avec une boucle qui lit un tableau contenant les markers.

Création de markers en série

Dans la continuité de notre exemple précédent, voici un tableau de POI (Points of Interest) :

var myItems = [
    ["Notre Dame de Paris", 48.853056, 2.349722],
    ["Musée d'Orsay", 48.86, 2.327],
    ["Muséum National d'Histoire Naturelle", 48.8422, 2.3564]
];

On pourra évidemment en créer bien d’autres…

Voyons maintenant la boucle qui va créer les markers sur la carte :

for (var i = 0; i < myItems.length; i++) {
    var item = myItems[i];
    marker = new L.marker([item[1],item[2]]).bindPopup(item[0]).addTo(map);
}

Cela fonctionne parfaitement quel que soit le nombre de markers, mais l’ajout un par un sur la carte va rapidement créer un problème de performance. On aura tendance à modifier légèrement le code pour créer un tableau contenant les objets L.marker Leaflet pour les afficher en une seule fois.

var markers = new L.layerGroup();
for (var i = 0; i < myItems.length; i++) {
    var item = myItems[i];
    marker = new L.marker([item[1],item[2]]).bindPopup(item[0]);
    markers.addLayer(marker);
}
map.addLayer(markers);

Chaque marker créé possède son infobulle qui s’ouvre quand on clique sur le marker lui même.

Miltiples Markers

Si les markers créés sont en dehors de la zone de carte initialisée par la fonction setView, vous devrez dézoomer manuellement pour les voir, ou modifier votre code légèrement.

var markers = new L.featureGroup();
for (var i = 0; i < myItems.length; i++) {
    var item = myItems[i];
    marker = new L.marker([item[1],item[2]]).bindPopup(item[0]);
    markers.addLayer(marker);
}
map.addLayer(markers);
map.fitBounds(markers.getBounds());

Gestion des événements individualisée

Par défaut, vos markers réagissent à l’événement ‘clic’. Pour reprendre la gestion des événements de survol de la souris comme dans l’article précédent, voici le code :

markers.on('mouseover', function(e){ e.layer.openPopup(); })
       .on('mouseout', function(e){ e.layer.closePopup(); });

Code complet
<!doctype html>
<html>
        <head>
                <title>leaflet demo</title>
                <meta name="viewport" content="width=device-width, initial-scale=1.0, maximum-scale=1.0, user-scalable=no" />
                <style>
                        html { height: 100% }
                        body { height: 100%; margin: 0; padding: 0 }
                        #map { 
                                width: 800px;
                                height: 480px; 
                        }
                </style>

                <link rel="stylesheet" href="http://cdn.leafletjs.com/leaflet-0.7.2/leaflet.css" />
                <script src="http://cdn.leafletjs.com/leaflet-0.7.2/leaflet.js"></script>
                </head>
        <body>
                <div id="map"></div>
                <script type="text/javascript">
                        var map = L.map('map').setView([48.856578, 2.351828], 18);
                        L.tileLayer('http://{s}.tile.openstreetmap.org/{z}/{x}/{y}.png', { attribution: 'Map data &copy; <a href="http://www.osm.org">OpenStreetMap</a>' }).addTo(map);

                        var myItems = [
                            ["Notre Dame de Paris", 48.853056, 2.349722],
                            ["Musée d'Orsay", 48.86, 2.327],
                            ["Museum National d'Histoire Naturelle", 48.8422, 2.3564]
            ];

                        var markers = new L.featureGroup();
            for (var i = 0; i < myItems.length; i++) {
                var item = myItems[i];
                marker = new L.marker([item[1],item[2]]).bindPopup(item[0]);
                markers.addLayer(marker);
            }

            markers.on('mouseover', function(e){ e.layer.openPopup(); })
                   .on('mouseout', function(e){ e.layer.closePopup(); });
            map.addLayer(markers);
            map.fitBounds(markers.getBounds());
                </script>
        </body>
</html>

Laisser un commentaire