Loading GeoJSON data with Leaflet Maps

Loading GeoJSON data files can be network intensive if the GIS data has good resolution or if the number of features being added is high.

In such scenario, it is better to load the GeoJSON data file separately and not include it as part of the main HTML or main JS file where the mapping logic lives.

This brings in the issue of XHR based data loading and related matter of Asynchronous JS execution. The basic stepwise process is as below

  1. Initialize the map
  2. Call for data loading
  3. AFTER data has loaded, attach the data as GeoJSON Layer
  4. Add the Layer to the map

Let us see various approaches to loading data. Download the India.geojson file used in these examples here: LINK . It should be in the geo subfolder.

Also, the examples require a webserver to run. Simply opeing the HTML file by double clicking will NOT BE SUCCESSFULL. Please use a webserver. Simplest would be using Viosual Studio Code with Live Server extension.

Basic HTML Setup

<!DOCTYPE html> <html> <head> <link rel="stylesheet" href="https://unpkg.com/leaflet@1.7.1/dist/leaflet.css" integrity="sha512-xodZBNTC5n17Xt2atTPuE1HxjVMSvLVW9ocqUKLsCC5CXdbqCmblAshOMAS6/keqq/sMZMZ19scR4PsZChSR7A==" crossorigin=""/> <script src="https://unpkg.com/leaflet@1.7.1/dist/leaflet.js" integrity="sha512-XQoYMqMTK8LvdxXYG3nZ448hOEQiglfqkJs1NOQV44cWnUrBc8PkAOcXy20w0vlaXaVUearIOBhiXZ5V3ynxwA==" crossorigin=""></script> <script src = "https://cdnjs.cloudflare.com/ajax/libs/leaflet-ajax/2.1.0/leaflet.ajax.min.js"></script> <script src="https://ajax.googleapis.com/ajax/libs/jquery/3.5.1/jquery.min.js"></script> </head> <body> <div class="mapArea" id="map" style="height: 500px;"> </div> </body> <script> var map= L.map('map'); /// Initialize LEAFLET MAP function addTileLayer() { // ADD TILE Layer tilelayer = L.tileLayer('https://{s}.basemaps.cartocdn.com/light_nolabels/{z}/{x}/{y}{r}.png', { attribution: '&copy; <a href="https://www.openstreetmap.org/copyright">OpenStreetMap</a> contributors &copy; <a href="https://carto.com/attributions">CARTO</a>', subdomains: 'abcd' }); tilelayer.addTo(map); } function buildIndiaMap(data) { // Add India Layer let iMap = L.geoJson(data); iMap.addTo(map); map.fitBounds(iMap.getBounds()); } </script> </html>
Code language: JavaScript (javascript)

Approach 1: Using FETCH API: LINK to Downloadable code

// Async Function To Load Data geoJSON async function loadMapGeoJSON(unit){ let response = await fetch('../geo/'+unit+'.geojson'); if (!response.ok) { const message = `An error loading geoJson for ${unit} -- HTTP Response Code ${response.status}`; throw new Error(message); } else { return await response.json(); } } // Chained function to LOAD DATA AND THEN BUILD Map function addIndiaMap() { loadMapGeoJSON("india") // LOADs INDIA GEOJSON with State coordinates .then((v) => {buildIndiaMap(v); }) // Build India map .catch(e => console.log(e)); /// Catch Errors } // WHEN Document is Ready --> Create Map $(document).ready(function(){ addTileLayer() addIndiaMap(); });
Code language: JavaScript (javascript)

Approach 2: Using JQuery getJSON method’s promise based API. LINK to Downloadable code

function addIndiaMap(unit) { var promise = $.getJSON('../geo/'+unit+'.geojson'); promise.then(function(data) { buildIndiaMap(data); }); } $(document).ready(function(){ addTileLayer() addIndiaMap('India'); });
Code language: JavaScript (javascript)

Approach 3: Using Leaflet AJAX Plugin – LINK to downloadable code

This approach combines AJAX data load as well as map creation in a single function. There is no need for the ‘buildIndiaMap‘ function we had made above.

function buildIndiaMap2(unit) { let iMapData = new L.GeoJSON.AJAX("../geo/"+ unit +".geojson"); iMapData.on('data:loaded', function() { iMapData.addTo(map); map.fitBounds(iMapData.getBounds()); }); } // WHEN Document is Ready --> Create Map $(document).ready(function(){ addTileLayer(); buildIndiaMap2('India'); });
Code language: JavaScript (javascript)

Full Example FIles Folder here: LINK