This is the documentation of version 1.0.0-rc.1. Go to the latest version, 1.0.0-rc.5.

Routing module

The Routing module draws the routes calculateRoute returns, with their waypoints, guidance and traffic along the way, and handles their interactions.

The module owns the route lines, waypoints, section overlays, instruction arrows and summary bubbles it draws, and how they look (Route styling). It never restyles the roads underneath, which belong to the Styling Foundations module. Two looks reach it from outside:

No other knob reaches route layers. See Who owns what.

The code below geocodes four stops, calculates the route through them and draws both. The response goes to showRoutes unchanged. Change an address to re-plan it:

Two features of the module have a guide of their own:

Guide Covers
Route styling Colour, width, waypoint size, layers, the knob catalogue and layer positioning
Route sections The overlays drawn per stretch of road: tunnels, ferries, traffic, speed limit signs, border crossings and the rest

Initialization

import { TomTomMap, RoutingModule } from '@tomtom-org/maps-sdk/map';

const map = new TomTomMap({ mapLibre: { container: 'map' } });

const routingModule = await RoutingModule.create(map, {
    displayUnits: { distance: { type: 'metric' } }, // optional
    waypoints: { entryPoints: 'main-when-available' } // optional
});

Displaying routes

import { calculateRoute } from '@tomtom-org/maps-sdk/services';

const locations = [
    [4.9041, 52.3676], // Amsterdam
    [4.4777, 51.9244]  // Rotterdam
];
const routes = await calculateRoute({ locations });

await routingModule.showRoutes(routes);
await routingModule.showWaypoints(locations); // showRoutes draws no pins

showRoutes draws the lines, sections, guidance and summary bubbles, but no pins. showWaypoints draws the start, stop and destination pins. Locations describes what locations takes. Route planning parameters covers every other request option.

Displaying guidance on map

A route calculated with guidance: { type: 'coded' } draws its instruction lines and arrows with no extra configuration:

const route = await calculateRoute({ locations, guidance: { type: 'coded' } });
await routingModule.showRoutes(route);

Route selection

With alternatives, one route is drawn as selected, by default the first:

const routes = await calculateRoute({ locations, maxAlternatives: 2 });

await routingModule.showRoutes(routes, { selectedIndex: 1 });
await routingModule.selectRoute(0); // re-marks the shown routes, no recalculation

Waypoints

showWaypoints draws the pins, and clearWaypoints removes them. Neither touches the routes, and clearRoutes leaves the pins.

A stop's pin shows its name. If the stop has a pauseDurationSeconds, the pin also shows how long the route waits there, in the SDK's display units:

const locations = [
    [2.1734, 41.3851],
    {
        type: 'Feature',
        geometry: { type: 'Point', coordinates: [2.4467, 41.5381] },
        properties: { pauseDurationSeconds: 30 * 60 } // the pin reads "30 min" under the stop name
    },
    [2.8214, 41.9794]
];

await routingModule.showRoutes(await calculateRoute({ locations }));
await routingModule.showWaypoints(locations);

Waypoints or places

places.events.on('click', async (place) => {
    const locations = [origin, place, destination];
    await places.clear();
    await routingModule.showRoutes(await calculateRoute({ locations }));
    await routingModule.showWaypoints(locations);
});

If several routing modules share a location, such as the one destination of routes from several origins, you can mark it once with a Places module instead.

When you change any setting below through applyConfig, the waypoints already shown update and keep their ids and event states. Try it all on the waypoints playground:

Pins per role

waypoints.icon.style styles every pin. waypoints.icon.start, middle and finish each style one role on top of it. A pin without a fillColor takes the route's color:

const routingModule = await RoutingModule.create(map, {
    waypoints: {
        icon: {
            style: { outlineColor: '#FFFFFF' },
            start: { style: { fillColor: '#1B7A3E' } },
            finish: { style: { fillColor: '#C0392B' } }
        }
    }
});

Stop marks

Labels

Each pin is labelled with its POI name, otherwise its address, and its wait. waypoints.label.visible: false drops the labels. To write your own, set waypoints.label.title to a function of the waypoint or a MapLibre expression, like label.title for places:

import { buildWaypointTitle } from '@tomtom-org/maps-sdk/map';

routingModule.applyConfig({
    waypoints: {
        label: {
            title: (waypoint) => (waypoint.properties.indexType === 'finish' ? 'Home' : buildWaypointTitle(waypoint) ?? '')
        }
    }
});

Route styling covers the label's colour, halo and size.

Hover and click

Once a handler covers the waypoints, a hovered or clicked pin and its stop mark grow by waypoints.highlight.sizeFactor. It defaults to 1.2 and is clamped to 1 to 1.5, and 1 draws the pin like any other. The waypoints scope has the event state methods to set that state from your own UI:

routingModule.events.waypoints.on('hover', (waypoint) => showStopCard(waypoint.properties));
routingModule.events.waypoints.setEventState({ index: 1, state: 'click' });

Icons of your own

A role's image replaces its pin, and waypoints.icon.mapping picks a pin per waypoint from its data, as icon.mapping does for places:

const routingModule = await RoutingModule.create(map, {
    waypoints: {
        icon: {
            finish: { image: { image: chequeredFlagSVG } },
            mapping: { to: 'poiCategory', fn: (waypoint) => waypoint.properties.poi?.categories?.[0] }
        }
    }
});

Showing and hiding

setVisible(false) hides everything the module draws (route lines, waypoints, sections, guidance, charging stops, summary bubbles and border crossings) and keeps what it shows:

const routingModule = await RoutingModule.create(map, { visible: false }); // starts hidden
await routingModule.showRoutes(route);   // kept, not drawn
routingModule.setVisible(true);          // draws the route
routingModule.isVisible();               // true

Events

Each part of a route has its own scope on the user events surface:

routingModule.events.mainLines.on('click', (route, lngLat) => console.log(route.properties));
routingModule.events.waypoints.on('click', (waypoint) => console.log(waypoint.properties.indexType));
routingModule.events.incidents.on('hover', (section) => console.log(section.properties.delayInSeconds));
routingModule.events.instructionLines.on('click', (instruction) => console.log(instruction.properties));
routingModule.events.summaryBubbles.on('click', (summary) => console.log(summary.properties));

// Removes every click handler of the scope; `on` returns an unsubscribe for one handler
routingModule.events.mainLines.off('click');

Once a handler covers the routes, a hovered or clicked route draws its outline wider, selected or not. The module's event state methods act on the routes, and each named scope has them for its own features. A click marks the route, and selectRoute makes it the selected one:

routingModule.events.mainLines.on('click', (route) => routingModule.selectRoute(route.properties.index));

routingModule.setEventState({ index: 1, state: 'hover' });
const { click: [clickedRouteID] = [] } = routingModule.getEventStates();

highlight.outline.widthFactor sets how much wider. It defaults to 1.2 and is clamped to 1 to 1.25, so the outline never covers a section halo beneath the route. 1 draws a hovered route like any other. An outline width given through layers.mainLines.routeOutline is drawn as given, in every state.

routingModule.applyConfig({ highlight: { outline: { widthFactor: 1.25 } } });

Multiple module instances

Each instance has its own sources, layers, configuration and events, for comparing route types or showing routes for several users:

const carRoutes = await RoutingModule.create(map, { color: '#2ECC71' });
const truckRoutes = await RoutingModule.create(map, { color: '#E67E22' });

await carRoutes.showRoutes(carRoute);
await truckRoutes.showRoutes(truckRoute);

Reading shown data

getShown() returns what the module draws, as prepared for display, split by what draws it:

const shown = routingModule.getShown();
if (shown.mainLines.features.length > 0) {
    console.log(`Showing ${shown.mainLines.features.length} routes, ${shown.waypoints.features.length} waypoints`);
}

Its entries are mainLines, waypoints, incidents, ferries, tollRoads, tunnels, vehicleRestricted, instructionLines, instructionArrows, summaryBubbles and countryCrossings, plus one <type>Sections per generated section type, such as urbanSections and motorwaySections.

API reference

RoutingModule and RoutingModuleConfig.

Related guides and examples

Services integration

Related examples

Related map modules