Create and style clusters
Use Unl Map Js' built-in functions to visualize points as clusters.
Note
If you want to test this example, edit it in JSFiddle or CodePen and replace the "YOUR-OWN-API-KEY" and "YOUR-OWN-VPM-ID" placeholders with your actual api key and vpm id.<!DOCTYPE html><html><head><meta charset="utf-8" /><title>Create and style clusters</title><meta name="viewport" content="initial-scale=1,maximum-scale=1,user-scalable=no" /><script src="https://unpkg.com/unl-map-js@0.1.5/lib/unl-map-js.js"></script><link href="https://unpkg.com/unl-map-js@0.1.5/lib/unl-map-js.css" rel="stylesheet" /><linkhref="https://unpkg.com/maplibre-gl@2.1.9/dist/maplibre-gl.css"rel="stylesheet"/><style> body { margin: 0; padding: 0; } #map { position: absolute; top: 0; bottom: 0; width: 100%; }</style></head><body><div id="map"></div> <script>var map = new UnlSdk.Map({container: "map",apiKey: "YOUR-OWN-API-KEY",vpmId: "YOUR-OWN-VPM-ID",center: [-103.59179687498357, 40.66995747013945],zoom: 3,}); map.on("load", function () {// Add a new source from our GeoJSON data and// set the 'cluster' option to true. GL-JS will// add the point_count property to your source data.map.addSource("earthquakes", {type: "geojson",// Point to GeoJSON data. This example visualizes all M1.0+ earthquakes// from 12/22/15 to 1/21/16 as logged by USGS' Earthquake hazards program.data: "https://u-n-l.github.io/unl-map-js-docs/assets/earthquakes.geojson",cluster: true,clusterMaxZoom: 14, // Max zoom to cluster points onclusterRadius: 50, // Radius of each cluster when clustering points (defaults to 50)}); map.addLayer({id: "clusters",type: "circle",source: "earthquakes",filter: ["has", "point_count"],paint: {// Use step expressions// with three steps to implement three types of circles:// * Blue, 20px circles when point count is less than 100// * Yellow, 30px circles when point count is between 100 and 750// * Pink, 40px circles when point count is greater than or equal to 750"circle-color": ["step",["get", "point_count"],"#51bbd6",100,"#f1f075",750,"#f28cb1",],"circle-radius": ["step", ["get", "point_count"], 20, 100, 30, 750, 40],},}); map.addLayer({id: "cluster-count",type: "symbol",source: "earthquakes",filter: ["has", "point_count"],layout: {"text-field": "{point_count_abbreviated}","text-size": 12,"text-font": ["Fira GO Regular"],},}); map.addLayer({id: "unclustered-point",type: "circle",source: "earthquakes",filter: ["!", ["has", "point_count"]],paint: {"circle-color": "#11b4da","circle-radius": 4,"circle-stroke-width": 1,"circle-stroke-color": "#fff",},}); // inspect a cluster on clickmap.on("click", "clusters", function (e) {var features = map.queryRenderedFeatures(e.point, {layers: ["clusters"],});var clusterId = features[0].properties.cluster_id;map.getSource("earthquakes").getClusterExpansionZoom(clusterId, function (err, zoom) {if (err) return; map.easeTo({center: features[0].geometry.coordinates,zoom: zoom,});});}); // When a click event occurs on a feature in// the unclustered-point layer, open a popup at// the location of the feature, with// description HTML from its properties.map.on("click", "unclustered-point", function (e) {var coordinates = e.features[0].geometry.coordinates.slice();var mag = e.features[0].properties.mag;var tsunami; if (e.features[0].properties.tsunami === 1) {tsunami = "yes";} else {tsunami = "no";} // Ensure that if the map is zoomed out such that// multiple copies of the feature are visible, the// popup appears over the copy being pointed to.while (Math.abs(e.lngLat.lng - coordinates[0]) > 180) {coordinates[0] += e.lngLat.lng > coordinates[0] ? 360 : -360;} new UnlSdk.Popup().setLngLat(coordinates).setHTML("magnitude: " + mag + "<br>Was there a tsunami?: " + tsunami).addTo(map);}); map.on("mouseenter", "clusters", function () {map.getCanvas().style.cursor = "pointer";});map.on("mouseleave", "clusters", function () {map.getCanvas().style.cursor = "";});});</script> </body></html>