78 lines
2.3 KiB
HTML
78 lines
2.3 KiB
HTML
<!DOCTYPE html>
|
|
<html>
|
|
<head>
|
|
<meta charset="utf-8" />
|
|
<title>Mapbox GL JS + D3.js Example</title>
|
|
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
|
|
|
<link href="https://api.tiles.mapbox.com/mapbox-gl-js/v3.0.1/mapbox-gl.css" rel="stylesheet" />
|
|
<script src="https://api.tiles.mapbox.com/mapbox-gl-js/v3.0.1/mapbox-gl.js"></script>
|
|
<script src="https://d3js.org/d3.v4.min.js"></script>
|
|
|
|
<style>
|
|
body { margin: 0; padding: 0; }
|
|
#map { position: absolute; top: 0; bottom: 0; width: 100%; }
|
|
|
|
/* SVG overlay on top of Mapbox canvas */
|
|
svg {
|
|
position: absolute;
|
|
top: 0;
|
|
left: 0;
|
|
pointer-events: none; /* so it doesn't block map interaction */
|
|
}
|
|
</style>
|
|
</head>
|
|
<body>
|
|
<div id="map"></div>
|
|
|
|
<script>
|
|
// 🔑 Replace with your own Mapbox access token
|
|
mapboxgl.accessToken = 'pk.eyJ1Ijoiam9yZGl0b3N0IiwiYSI6ImQtcVkyclEifQ.vwKrOGZoZSj3N-9MB6FF_A';
|
|
|
|
// Initialize Mapbox map
|
|
const map = new mapboxgl.Map({
|
|
container: 'map',
|
|
style: 'mapbox://styles/mapbox/light-v11',
|
|
center: [-122.4194, 37.7749], // San Francisco
|
|
zoom: 10
|
|
});
|
|
|
|
// Sample data: Some points in San Francisco
|
|
const data = [
|
|
{ name: 'Golden Gate Bridge', coords: [-122.4783, 37.8199] },
|
|
{ name: 'Alcatraz Island', coords: [-122.4231, 37.8267] },
|
|
{ name: 'Downtown SF', coords: [-122.4194, 37.7749] }
|
|
];
|
|
|
|
// Create SVG overlay once map is loaded
|
|
map.on('load', () => {
|
|
const container = map.getCanvasContainer();
|
|
const svg = d3.select(container).append('svg');
|
|
|
|
// Bind data to SVG circles
|
|
const circles = svg.selectAll('circle')
|
|
.data(data)
|
|
.enter()
|
|
.append('circle')
|
|
.attr('r', 16)
|
|
.attr('fill', 'red');
|
|
/*.attr('stroke', 'white')
|
|
.attr('stroke-width', 2)
|
|
.attr('opacity', 0.8);*/
|
|
|
|
// Update function to project geo coords to screen coords
|
|
function updatePositions() {
|
|
circles
|
|
.attr('cx', d => map.project(d.coords).x)
|
|
.attr('cy', d => map.project(d.coords).y);
|
|
}
|
|
|
|
// Call update initially and on map move/zoom
|
|
updatePositions();
|
|
map.on('move', updatePositions);
|
|
map.on('zoom', updatePositions);
|
|
map.on('resize', updatePositions);
|
|
});
|
|
</script>
|
|
</body>
|
|
</html> |