Reverse geocoding
The Reverse Geocoding service converts geographic coordinates into human-readable addresses and location information. This service is essential for applications that need to display location details based on map clicks, GPS coordinates, or other coordinate-based inputs, transforming raw latitude/longitude pairs into meaningful address data.
Core reverse geocoding concepts
Reverse geocoding performs the inverse operation of standard geocoding, taking precise coordinate inputs and returning structured address information. This process involves spatial analysis to determine the most appropriate address or place name for a given geographic point.
Primary Applications:
- Map interaction feedback when users click on map locations
- GPS coordinate interpretation in mobile and navigation applications
- Location labeling for photos, check-ins, and social media posts
- Address discovery for delivery and logistics applications
- Geographic data enrichment in analytics and reporting systems
Basic reverse geocoding usage
Simple coordinate to address conversion
The fundamental reverse geocoding operation converts coordinates into readable address information:
import { reverseGeocode } from '@tomtom-org/maps-sdk/services';
const place = await reverseGeocode({
position: [4.9041, 52.3676] // Amsterdam Dam Square coordinates
});
console.log(place.properties?.address?.freeformAddress); // "Dam, 1012 Amsterdam, Netherlands"
reverseGeocode resolves one Place, typically the nearest addressable location. Its geometry is
the queried point; when nothing matches, it carries no properties.
Enhanced result processing
Process reverse geocoding results to extract specific address components and handle various response scenarios:
const place = await reverseGeocode({
position: [4.9041, 52.3676]
});
const address = place.properties?.address;
if (address) {
console.log(address.streetName); // "Dam"
console.log(address.municipality); // "Amsterdam"
console.log(address.country); // "Netherlands"
console.log(address.freeformAddress); // Complete formatted address
}
Address Component Availability: Address components vary based on the coordinate location and available geographic data. Urban areas typically provide more detailed information, while rural or remote locations may return broader regional information.
Advanced configuration options
Search radius and precision control
Configure the search scope and precision requirements for reverse geocoding operations:
const result = await reverseGeocode({
position: [4.9041, 52.3676],
radiusMeters: 100,
language: 'en-GB' // Response language preference
});
Parameter Effects:
- radiusMeters: Controls how far from the coordinate to search for addressable features
- language: Determines the language of returned address components and place names
- Smaller radius values provide more precise results but may return no results in sparse areas
- Larger radius values increase the likelihood of finding address information
Geopolitical view
In a disputed territory, the country an address belongs to depends on the geopolitical view. The same point in Gilgit is in Pakistan from the international view and in India from the Indian one:
const unified = await reverseGeocode({ position: [74.31, 35.92], geopoliticalView: 'Unified' });
const indian = await reverseGeocode({ position: [74.31, 35.92], geopoliticalView: 'IN' });
// unified.properties.address.country: 'Pakistan', indian.properties.address.country: 'India'
geopoliticalView defaults to the global one, which the map follows too. See Geopolitical views.
Result quality and relevance
The service prioritizes result relevance based on proximity and address completeness:
Quality Factors:
- Proximity: Closer addresses receive higher priority
- Completeness: Full addresses rank higher than partial information
- Accuracy: Verified addresses take precedence over estimated locations
- Relevance: More specific locations (building addresses) rank above general areas
Integration patterns
Map click integration
Clicks can come faster than answers, so run each lookup through createLatestRequest:
import { TomTomMap } from '@tomtom-org/maps-sdk/map';
import { createLatestRequest, reverseGeocode } from '@tomtom-org/maps-sdk/services';
const map = new TomTomMap({ mapLibre: { container: 'map' } });
const latestLookup = createLatestRequest();
map.mapLibreMap.on('click', async (event) => {
const lookup = await latestLookup.run((signal) =>
reverseGeocode({ position: event.lngLat.toArray(), signal })
);
if (!lookup.current) return; // a newer click retired this lookup
const address = lookup.value.properties?.address?.freeformAddress;
if (address) {
console.log(`Clicked location: ${address}`);
// Display address in popup or sidebar
}
});
Keeping only the latest request
covers what a retired lookup resolves to, cancel() and deadlines. The
reverse geocoding playground adds a pin and an address popup.
GPS location processing
Process GPS coordinates from mobile devices or location services:
// Get user's current location and convert to address
navigator.geolocation.getCurrentPosition(async (position) => {
const { longitude, latitude } = position.coords;
const place = await reverseGeocode({
position: [longitude, latitude],
radiusMeters: 50 // Precise local search
});
const currentAddress = place.properties?.address;
if (currentAddress) {
displayCurrentLocation(currentAddress.freeformAddress);
}
});
Batch processing
For applications requiring multiple coordinate conversions, implement efficient batch processing:
async function reverseGeocodeMultiple(coordinates) {
const places = await Promise.all(
coordinates.map((coordinate) =>
reverseGeocode({ position: coordinate })
)
);
return places.map((place) =>
place.properties?.address?.freeformAddress
).filter(Boolean);
}
// Usage example
const waypoints = [
[4.9041, 52.3676],
[2.3522, 48.8566],
[13.4050, 52.5200]
];
const addresses = await reverseGeocodeMultiple(waypoints);
Error handling and edge cases
Robust error management
Implement comprehensive error handling for various scenarios:
async function safeReverseGeocode(position, options = {}) {
try {
const place = await reverseGeocode({
position,
radiusMeters: options.radiusMeters || 1000,
...options
});
if (!place.properties) {
return {
success: false,
message: 'No address found for coordinates'
};
}
return {
success: true,
address: place.properties.address
};
} catch (error) {
return {
success: false,
message: `Reverse geocoding failed: ${error.message}`
};
}
}
Common Edge Cases:
- Ocean coordinates: Return regional or country-level information
- Remote locations: May return broader geographic areas instead of specific addresses
- Invalid coordinates: Handle coordinate validation and error responses
- Service limits: Implement retry logic and rate limiting
Performance optimization
For applications with frequent reverse geocoding needs, consider these optimization strategies:
Caching Strategy:
const reverseGeocodeCache = new Map();
async function cachedReverseGeocode(position, precision = 0.001) {
// Round coordinates for cache key
const key = `${Math.round(position[0]/precision)*precision},${Math.round(position[1]/precision)*precision}`;
if (reverseGeocodeCache.has(key)) {
return reverseGeocodeCache.get(key);
}
const result = await reverseGeocode({ position });
reverseGeocodeCache.set(key, result);
return result;
}
For complete reverse geocoding implementation examples and advanced integration patterns, go to the examples gallery.
Related guides and examples
Map integration
- Places Module - Learn how to display reverse geocoded locations as places on the map with popups and interactions
- User Interaction Events - Handle map click events to trigger reverse geocoding and display results
Related examples
- Reverse geocoding playground - Complete example showing reverse geocoding triggered by map clicks with marker placement and address popups
- Geopolitical views playground - The address of a place in a disputed territory, and the map around it, from each geopolitical view
- Reverse Geocoding JSON - Working with reverse geocoding response data structures
- Pin Interaction - Interactive map pins that show reverse geocoded addresses on click