Loading documentation...
Add CLU field boundaries to your MapLibre map in under 5 minutes using the LandMapMagic API.
If you already have a MapLibre map instance, install the PMTiles protocol and fetch the style.
npm install pmtilesimport maplibregl from 'maplibre-gl';
import { Protocol } from 'pmtiles';
// Register PMTiles protocol once at app startup
const protocol = new Protocol();
maplibregl.addProtocol('pmtiles', protocol.tile);Option A: Fetch and merge the style (Recommended)
// Fetch the CLU style from the API
const response = await fetch(
'https://api.landmapmagic.com/clu/style.json?key=YOUR_API_KEY'
);
const cluStyle = await response.json();
// Add the source
map.addSource('clu', cluStyle.sources.clu);
// Add all layers
cluStyle.layers.forEach(layer => {
map.addLayer(layer);
});Option B: Manual source and layer definition
// Add the PMTiles source
map.addSource('clu', {
type: 'vector',
url: 'pmtiles://https://api.landmapmagic.com/clu.pmtiles?key=YOUR_API_KEY',
attribution: 'USDA FSA CLU / LandMapMagic'
});
// Add the outline layer
map.addLayer({
id: 'clu-outline',
type: 'line',
source: 'clu',
'source-layer': 'clu',
paint: {
'line-color': '#fde047',
'line-width': 2,
'line-opacity': 0.9
},
layout: { 'line-cap': 'round', 'line-join': 'round' },
minzoom: 11
});
// Add the labels layer (optional)
map.addLayer({
id: 'clu-labels',
type: 'symbol',
source: 'clu',
'source-layer': 'clu_labels',
layout: {
'text-field': ['concat', ['get', 'calcacres'], ' ac'],
'text-size': 14,
'text-font': ['Open Sans Bold', 'Arial Unicode MS Bold'],
'text-anchor': 'center'
},
paint: {
'text-color': '#000000',
'text-halo-color': '#ffffff',
'text-halo-width': 3
},
minzoom: 13
});import maplibregl from 'maplibre-gl';
import { Protocol } from 'pmtiles';
import 'maplibre-gl/dist/maplibre-gl.css';
// Register PMTiles protocol
const protocol = new Protocol();
maplibregl.addProtocol('pmtiles', protocol.tile);
// Create your map
const map = new maplibregl.Map({
container: 'map',
style: 'https://demotiles.maplibre.org/style.json',
center: [-93.5, 42.0],
zoom: 12
});
map.on('load', async () => {
const response = await fetch(
'https://api.landmapmagic.com/clu/style.json?key=YOUR_API_KEY'
);
const cluStyle = await response.json();
map.addSource('clu', cluStyle.sources.clu);
cluStyle.layers.forEach(layer => map.addLayer(layer));
});Pass query parameters to the style endpoint:
const response = await fetch(
'https://api.landmapmagic.com/clu/style.json?key=YOUR_API_KEY' +
'&borderColor=ff6b35&hoverColor=ffd700&labels=false'
);borderColor — Hex color for field boundaries (default: fde047)hoverColor — Hex color for hover state (default: ffd700)labelColor — Hex color for acreage labels (default: 000000)labels — Show/hide labels (true or false, default: true)The style includes hover state support. Enable it with feature state:
let hoveredFeatureId = null;
map.on('mousemove', 'clu-outline', (e) => {
if (e.features.length > 0) {
if (hoveredFeatureId !== null) {
map.setFeatureState(
{ source: 'clu', sourceLayer: 'clu', id: hoveredFeatureId },
{ hover: false }
);
}
hoveredFeatureId = e.features[0].id;
map.setFeatureState(
{ source: 'clu', sourceLayer: 'clu', id: hoveredFeatureId },
{ hover: true }
);
}
});
map.on('mouseleave', 'clu-outline', () => {
if (hoveredFeatureId !== null) {
map.setFeatureState(
{ source: 'clu', sourceLayer: 'clu', id: hoveredFeatureId },
{ hover: false }
);
}
hoveredFeatureId = null;
});map.on('click', 'clu-outline', (e) => {
if (e.features.length > 0) {
const feature = e.features[0];
const acres = feature.properties.calcacres;
const id = feature.properties.id;
new maplibregl.Popup()
.setLngLat(e.lngLat)
.setHTML(`
<h3>CLU Field</h3>
<p><strong>Field ID:</strong> ${id}</p>
<p><strong>Acres:</strong> ${acres?.toFixed(2)}</p>
`)
.addTo(map);
}
});
// Change cursor on hover
map.on('mouseenter', 'clu-outline', () => {
map.getCanvas().style.cursor = 'pointer';
});
map.on('mouseleave', 'clu-outline', () => {
map.getCanvas().style.cursor = '';
});// Hide CLU layers
map.setLayoutProperty('clu-outline', 'visibility', 'none');
map.setLayoutProperty('clu-labels', 'visibility', 'none');
// Show CLU layers
map.setLayoutProperty('clu-outline', 'visibility', 'visible');
map.setLayoutProperty('clu-labels', 'visibility', 'visible');