The code below builds on the JavaScript from [Create a Vanilla JavaScript Application with Mapbox and Deck.gl], but uses a more realistic approach to loading data and adds two basic features.
Rather than setting the ScatterplotLayer.data
property to a static URL we make a fetch
call to load some API data and parse it to JSON ourselves, then provide that when creating our map.
In addition to more closely matching what you're likely to see and do in a real application, this also lets us inspect the data to do things like calculate a center point. We can then pass that center to initialViewState
, ensuring the data we render is in the viewport. Note that the zoom
is still hard coded for simplicity, but in a real application you'd want to calculate that from the data as well.
The other feature this code adds is a basic tooltip and interactivity. To make the Scatterplot
react to mouse events we specify pickable: true
. We then attach a getTooltip
function to the DeckGL
instance that will be called any time the mouse passes into or out of a point. When getTooltip
is called, it's passed a parameter describing the interaction. When a point is moused over, the parameter has an object
property that is the corresponding data item. When the mouse leaves a point, object
is undefined
, hence the check at the beginning of the function. You can return a simple string from getTooltip
or an object to specify HTML and CSS, as we've done here.
const {DeckGL, ScatterplotLayer} = deck;
const xhr = await fetch('/api/movebank/wildebeest/')
const arr = await xhr.json()
let minLng, minLat, maxLng, maxLat
for (let i = 0; i < arr.length; i++) {
const row = arr[i];
minLng = minLng ? Math.min(minLng, row.location_long) : row.location_long
maxLng = maxLng ? Math.max(maxLng, row.location_long) : row.location_long
minLat = minLat ? Math.min(minLat, row.location_lat) : row.location_lat
maxLat = maxLat ? Math.max(maxLat, row.location_lat) : row.location_lat
}
const longitude = (minLng + maxLng) / 2
const latitude = (minLat + maxLat) / 2
new DeckGL({
mapStyle: 'https://basemaps.cartocdn.com/gl/positron-gl-style/style.json',
initialViewState: {
longitude,
latitude,
zoom: 8,
maxZoom: 16
},
controller: true,
layers: [
new ScatterplotLayer({
id: 'scatter-plot',
data: arr,
pickable: true,
radiusScale: 10,
radiusMinPixels: 2,
getPosition: d => [d.location_long, d.location_lat, 0],
getFillColor: [255, 0, 255]
})
],
getTooltip: ({object}) => object && {
html: `<b>${object.individual_local_identifier}</b><br/>${object.timestamp}`,
style: {
fontFamily: 'Arial, Helvetica, sans-serif'
}
},
});