diff --git a/src/geocoder-control.tsx b/src/geocoder-control.tsx index 40dcfcd..cc6302d 100644 --- a/src/geocoder-control.tsx +++ b/src/geocoder-control.tsx @@ -40,10 +40,58 @@ export default function GeocoderControl( ): React.ReactElement { const [marker, setMarker] = useState(null); + const coordinatesGeocoder = function (query) { + // Match anything which looks like + // decimal degrees coordinate pair. + const matches = query.match( + /^[ ]*(?:Lat: )?(-?\d+\.?\d*)[, ]+(?:Lng: )?(-?\d+\.?\d*)[ ]*$/i + ); + if (!matches) { + return null; + } + + function coordinateFeature(lng:any, lat:any) { + return { + center: [lng, lat], + geometry: { + type: 'Point', + coordinates: [lng, lat] + }, + place_name: 'Lat: ' + lat + ' Lng: ' + lng, + place_type: ['coordinate'], + properties: {}, + type: 'Feature' + }; + } + + const coord1 = Number(matches[1]); + const coord2 = Number(matches[2]); + const geocodes = []; + + if (coord1 < -90 || coord1 > 90) { + // must be lng, lat + geocodes.push(coordinateFeature(coord1, coord2)); + } + + if (coord2 < -90 || coord2 > 90) { + // must be lat, lng + geocodes.push(coordinateFeature(coord2, coord1)); + } + + if (geocodes.length === 0) { + // else could be either lng, lat or lat, lng + geocodes.push(coordinateFeature(coord1, coord2)); + geocodes.push(coordinateFeature(coord2, coord1)); + } + + return geocodes; + }; + const geocoder = useControl( () => { const ctrl = new MapboxGeocoder({ ...props, + localGeocoder: coordinatesGeocoder, marker: false, accessToken: props.mapboxAccessToken, flyTo: { duration: 0 },