0

I'm trying to create a Leaflet map, that automatically adds markers and polylines between destinations from a Google sheet.

I've managed to set up a map from other examples which is linked to my Google Sheet. You see the example here:

<!DOCTYPE html>
<html>

  <head>
    <script src='//cdn.jsdelivr.net/npm/tabletop@1.5.2/src/tabletop.min.js'></script>
    <link rel="stylesheet" href="https://unpkg.com/leaflet@1.3.4/dist/leaflet.css" />
    <script src="//unpkg.com/leaflet@1.3.4/dist/leaflet.js"></script>
    <style>
      #map-div {
        position: absolute;
        height: 100%;
        width: 100%;
      }

    </style>
  </head>

  <body>
    <div id="map-div"></div>
  </body>

</html>
var map = L.map('map-div').setView([60.1682653, 24.9422078], 5);
var basemap = L.tileLayer('http://{s}.tile.openstreetmap.org/{z}/{x}/{y}.png', {
  attribution: 'Basemap (c) <a href="http://openstreetmap.org">OpenStreetMap</a>',
  minZoom: 5,
  maxZoom: 100
});
basemap.addTo(map);

function addPoints(data, tabletop) {
  for (var row in data) {
    var marker = L.marker([
      data[row].Latitude,
      data[row].Longitude
    ]).addTo(map);
    marker.bindPopup('<strong>' + data[row].Info + '</strong>');
  }
}

function init() {
  Tabletop.init({
    key: 'https://docs.google.com/spreadsheets/d/1Rs6xPlJ8pU4UFfmokjATaf4dArMWxQxZcyS-xRIIFuY/edit?usp=sharing',
    callback: addPoints,
    simpleSheet: true
  })
}
init()

https://jsfiddle.net/Enounce/kwvn5e6z/12/

But unfortunately, I don't have the skills to make the map do what I want:

I'm unsure if this is at all possible with the destinations being in an external source. Any help is appreciated!

Enounce
  • 17
  • 5

1 Answers1

1

Draw Line between markers:

You need to create a L.Polyline and add the latlngs to it:

function addPoints(data, tabletop) {
    var line = L.polyline([]).addTo(map);
    for (var row in data) {
    var marker = L.marker([
      data[row].Latitude,
      data[row].Longitude
    ]).addTo(map);
    line.addLatLng(marker.getLatLng());
    marker.bindPopup('<strong>' + data[row].Info + '</strong>');
  }
}

Zoom to fit all markers:

Add the markers to a L.FeatureGroup() and then you can fit the map bounds to the group bounds with map.fitBounds(fg.getBounds());

var fg = L.featureGroup().addTo(map);

function addPoints(data, tabletop) {
    var line = L.polyline([]).addTo(map);
    for (var row in data) {
    var marker = L.marker([
      data[row].Latitude,
      data[row].Longitude
    ]).addTo(fg);
    line.addLatLng(marker.getLatLng());
    marker.bindPopup('<strong>' + data[row].Info + '</strong>');
  }
  
  map.fitBounds(fg.getBounds());
}

BUT you need to remove minZoom: 5 from the TileLayer.

Destinations

Store the destinations in an array and then create a html element in the loop and add a click listener:

var destinationHTML = document.getElementById("destinations-body");

var fg = L.featureGroup().addTo(map);
var destinations = [];
function addPoints(data, tabletop) {
    var line = L.polyline([]).addTo(map);
    for (var row in data) {
    var marker = L.marker([
      data[row].Latitude,
      data[row].Longitude
    ]).addTo(fg);
    line.addLatLng(marker.getLatLng());
    marker.bindPopup('<strong>' + data[row].Info + '</strong>');
    destinations.push({
        marker,
      data: data[row],
      id: row
    });
    
    
  destinationHTML.innerHTML += "<div class='destination-elm' onclick='destinationClick(\""+row+"\")'><span>"+data[row].Info+"</span></div>"
  }
  
  map.fitBounds(fg.getBounds());
}

function destinationClick(id){
    console.log(id)
  destinations.forEach(function(obj){
    if(obj.id == id){
        map.panTo(obj.marker.getLatLng());
    }
  })
}

Example: https://jsfiddle.net/falkedesign/k3b4nups/

Falke Design
  • 10,635
  • 3
  • 15
  • 30
  • Thanks, Falke-Design. That was everything I could ever ask for! How would the code look if I wanted a version without the destinations overview? I tried deleting parts in the HTML, but that took out most markers altogether. – Enounce May 25 '21 at 11:51
  • Look into: https://jsfiddle.net/falkedesign/Lh2p61jy/ Please don't forgett to accept the answer as correct – Falke Design May 25 '21 at 11:55