Learn how to find a route and directions with the route service.
Routing is finding the path from an origin to a destination in a street network. You can use the Routing service to find routes, get driving directions, calculate drive times, and solve complicated, multiple-vehicle routing problems. To create a route, you typically define a set of stops (origin and one or more destinations) and use the service to find a route with directions. You can also use several additional parameters, such as barriers and mode of travel, to refine the results.
In this tutorial, you will define an origin and destination by clicking on the map. These values are used to get a route and directions from the route service. The directions are also displayed on the map.
Prerequisites
Steps
Create a new pen
- To get started, either complete the Display a map tutorial or .
Get an access token
You need an access token with the correct privileges to access the location services used in this tutorial.
- Go to the Create an API key tutorial and create an API key with the following privilege(s):
- Privileges
- Location services > Basemaps
- Location services > Geocoding
- Location services > Routing
- Privileges
- In CodePen, set
esri
to your access token.Config.api Key Use dark colors for code blocks var esriConfig = { apiKey: "YOUR_ACCESS_TOKEN" };
To learn about other ways to get an access token, go to Types of authentication.
Update the map
A streets basemap layer is typically used in routing applications. Update the basemap
attribute on the Map component to use the arcgis/navigation
basemap layer and change the position of the map to center on Los Angeles.
- Update the
basemap
,center
andzoom
attributes.Use dark colors for code blocks <arcgis-map basemap="arcgis/navigation" center="-118.24532, 34.05398" zoom="12"> <arcgis-zoom position="top-left"></arcgis-zoom> </arcgis-map>
Add HTML to display directions
-
Add an
arcgis-placement
with its position set to be the top right corner of the map.Use dark colors for code blocks <arcgis-map basemap="arcgis/navigation" center="-118.24532, 34.05398" zoom="12"> <arcgis-zoom position="top-left"></arcgis-zoom> <arcgis-placement position="top-right"> </arcgis-placement> </arcgis-map>
-
Inside the
arcgis-placement
add acalcite-panel
.Use dark colors for code blocks <arcgis-placement position="top-right"> <calcite-panel heading="Directions"> </calcite-panel> </arcgis-placement>
-
Inside the
calcite-panel
, add acalcite-notice
that displays the instructions.Use dark colors for code blocks <arcgis-placement position="top-right"> <calcite-panel heading="Directions"> <calcite-notice id="directions-notice" icon="driving-distance" open> <div slot="message">Click on the map in two different locations to solve the route.</div> </calcite-notice> </calcite-panel> </arcgis-placement>
-
Add a
div
element where the directions will be displayed.Use dark colors for code blocks <arcgis-placement position="top-right"> <calcite-panel heading="Directions"> <calcite-notice id="directions-notice" icon="driving-distance" open> <div slot="message">Click on the map in two different locations to solve the route.</div> </calcite-notice> <div id="directions-container"></div> </calcite-panel> </arcgis-placement>
-
Add some CSS styling to set the size of the directions container
div
andcalcite-notice
.Use dark colors for code blocks <style> html, body { margin: 0; } arcgis-map { display: block; height: 100vh; } #directions-container { max-height: 50vh; width: 25vw; overflow-y: auto; } #directions-notice { max-width: 25vw; } </style>
Add modules
-
Use an AMD
require
statement to add the necessary modules in a new<script
at the bottom of the> <body
. For more information, refer to the> Graphic
,route
,Route
,Parameters Feature
,Set Simple
andLine Symbol Simple
modules.Marker Symbol The ArcGIS Maps SDK for JavaScript is available as AMD modules and ES modules, but this tutorial is based on AMD. The AMD
require
function uses references to determine which modules will be loaded – for example, you can specify"esri/layers/
for loading the FeatureLayer module. After the modules are loaded, they are passed as parameters (e.g.Feature Layer" Feature
) to the callback function where they can be used in your application. It is important to keep the module references and callback parameters in the same order. To learn more about the API's different modules visit the Overview Guide page.Layer Use dark colors for code blocks <script> require([ "esri/Graphic", "esri/rest/route", "esri/rest/support/RouteParameters", "esri/rest/support/FeatureSet", "esri/symbols/SimpleLineSymbol", "esri/symbols/SimpleMarkerSymbol" ], (Graphic, route, RouteParameters, FeatureSet, SimpleLineSymbol, SimpleMarkerSymbol) => { }); </script>
Define the service url
The rest module makes a request to a service and returns the results. Use the route
module to access the Routing service.
-
Create a variable called
route
to reference the route service.Url Use dark colors for code blocks <script> require([ "esri/Graphic", "esri/rest/route", "esri/rest/support/RouteParameters", "esri/rest/support/FeatureSet", "esri/symbols/SimpleLineSymbol", "esri/symbols/SimpleMarkerSymbol" ], (Graphic, route, RouteParameters, FeatureSet, SimpleLineSymbol, SimpleMarkerSymbol) => { const routeUrl = "https://route-api.arcgis.com/arcgis/rest/services/World/Route/NAServer/Route_World"; }); </script>
Get an origin and destination
A route
module uses a stops
parameter to find a route. Stops are graphics that represent the origin and destination locations for a route. Use an arcgis
event listener on the arcgis-map
to add graphics when clicking on the map. The graphics will define the stops
for the route.
-
Add a
arcgis
event listener to the map to add graphics to the view.View Click Use dark colors for code blocks <script> require([ "esri/Graphic", "esri/rest/route", "esri/rest/support/RouteParameters", "esri/rest/support/FeatureSet", "esri/symbols/SimpleLineSymbol", "esri/symbols/SimpleMarkerSymbol" ], (Graphic, route, RouteParameters, FeatureSet, SimpleLineSymbol, SimpleMarkerSymbol) => { const routeUrl = "https://route-api.arcgis.com/arcgis/rest/services/World/Route/NAServer/Route_World"; const arcgisMap = document.querySelector("arcgis-map"); arcgisMap.addEventListener("arcgisViewClick", (event) => { }); }); </script>
-
Create an
add
function to display a white marker for the origin location and a black marker for the destination. Add theGraphic graphic
to the map component'sview
.Use dark colors for code blocks <script> require([ "esri/Graphic", "esri/rest/route", "esri/rest/support/RouteParameters", "esri/rest/support/FeatureSet", "esri/symbols/SimpleLineSymbol", "esri/symbols/SimpleMarkerSymbol" ], (Graphic, route, RouteParameters, FeatureSet, SimpleLineSymbol, SimpleMarkerSymbol) => { const routeUrl = "https://route-api.arcgis.com/arcgis/rest/services/World/Route/NAServer/Route_World"; const arcgisMap = document.querySelector("arcgis-map"); arcgisMap.addEventListener("arcgisViewClick", (event) => { }); function addGraphic(type, point) { const graphic = new Graphic({ symbol: new SimpleMarkerSymbol({ color: type === "origin" ? "white" : "black", size: "8px" }), geometry: point }); arcgisMap.view.graphics.add(graphic); } }); </script>
-
Update the
arcgis
event listener to reference theView Click add
function. The first click will create the origin. The second will make the destination and hide the notice. Subsequent clicks will clear the graphics to define a new origin and destination.Graphic Use dark colors for code blocks const arcgisMap = document.querySelector("arcgis-map"); arcgisMap.addEventListener("arcgisViewClick", (event) => { const directionsNotice = document.querySelector("#directions-notice"); if (arcgisMap.view.graphics.length === 0) { addGraphic("origin", event.detail.mapPoint); } else if (arcgisMap.view.graphics.length === 1) { directionsNotice.open = false; addGraphic("destination", event.detail.mapPoint); } else { arcgisMap.view.graphics.removeAll(); directionsNotice.open = true; document.querySelector("#directions-container").innerHTML = ""; addGraphic("origin", event.detail.mapPoint); } });
-
Click on the map repeatedly in different locations to ensure the graphics are created and the notice is only visible when there are less than two graphics.
Find the route
To solve the route, add the origin and destination graphics to the stops
parameter as a Feature
and then use the solve
method. The resulting route will be added to the map as a Graphic
.
Input parameters are necessary to solve the route. While there are many parameters you can add, such as stops and barriers, at minimum, you need to provide an origin and destination point.
-
Create a
get
function to calculate the route and directions. Create an instance ofRoute Route
and use the point graphics drawn on the map as the stops.Parameters Use dark colors for code blocks async function getRoute() { const routeParams = new RouteParameters({ stops: new FeatureSet({ features: arcgisMap.view.graphics.toArray() }), }); }
-
Call the
solve
method to get the route. When the method returns, get the route fromroute
and add it to the view as aResults Graphic
with a blue line.Use dark colors for code blocks async function getRoute() { const routeParams = new RouteParameters({ stops: new FeatureSet({ features: arcgisMap.view.graphics.toArray() }), }); try { const response = await route.solve(routeUrl, routeParams); response.routeResults.forEach((result) => { result.route.symbol = new SimpleLineSymbol({ color: [5, 150, 255], width: 3 }); arcgisMap.view.graphics.add(result.route); }); } catch (error) { console.log(error); } }
-
Update the
arcgis
event listener to call theView Click get
function after creating the destination graphic.Route Use dark colors for code blocks const arcgisMap = document.querySelector("arcgis-map"); arcgisMap.addEventListener("arcgisViewClick", (event) => { const directionsNotice = document.querySelector("#directions-notice"); if (arcgisMap.view.graphics.length === 0) { addGraphic("origin", event.detail.mapPoint); } else if (arcgisMap.view.graphics.length === 1) { directionsNotice.open = false; addGraphic("destination", event.detail.mapPoint); getRoute(); } else { arcgisMap.view.graphics.removeAll(); directionsNotice.open = true; document.querySelector("#directions-container").innerHTML = ""; addGraphic("origin", event.detail.mapPoint); } });
-
Click two locations on the map to display a route.
Get directions
You can get driving directions from the route service with the return
property on Route
. Use this property to return directions and add them to the map as HTML elements.
-
Go back to the
get
function and set theRoute return
property toDirections true
.Use dark colors for code blocks async function getRoute() { const routeParams = new RouteParameters({ stops: new FeatureSet({ features: arcgisMap.view.graphics.toArray() }), returnDirections: true }); try { const response = await route.solve(routeUrl, routeParams); response.routeResults.forEach((result) => { result.route.symbol = new SimpleLineSymbol({ color: [5, 150, 255], width: 3 }); arcgisMap.view.graphics.add(result.route); }); } catch (error) { console.log(error); } }
-
After the solve method has been resolved, and if there are results, create a calcite-list that will display the directions and append it to the div we created earlier with the id of
directions-container
.Use dark colors for code blocks async function getRoute() { const routeParams = new RouteParameters({ stops: new FeatureSet({ features: arcgisMap.view.graphics.toArray() }), returnDirections: true }); try { const response = await route.solve(routeUrl, routeParams); response.routeResults.forEach((result) => { result.route.symbol = new SimpleLineSymbol({ color: [5, 150, 255], width: 3 }); arcgisMap.view.graphics.add(result.route); }); if (response.routeResults.length > 0) { const directions = document.createElement("calcite-list"); document.querySelector("#directions-container").appendChild(directions); } } catch (error) { console.log(error); } }
-
Create a
calcite-list-item
for each route feature to generate an ordered list of directions with their distances in miles. Append eachdirection
to thedirections
list.Use dark colors for code blocks async function getRoute() { const routeParams = new RouteParameters({ stops: new FeatureSet({ features: arcgisMap.view.graphics.toArray() }), returnDirections: true }); try { const response = await route.solve(routeUrl, routeParams); response.routeResults.forEach((result) => { result.route.symbol = new SimpleLineSymbol({ color: [5, 150, 255], width: 3 }); arcgisMap.view.graphics.add(result.route); }); if (response.routeResults.length > 0) { const directions = document.createElement("calcite-list"); const features = response.routeResults[0].directions.features; features.forEach((feature, index) => { const direction = document.createElement("calcite-list-item"); const step = document.createElement("span"); step.innerText = `${index + 1}.`; step.slot = "content-start"; step.style.marginLeft = "10px"; direction.appendChild(step); direction.label = `${feature.attributes.text}`; direction.description = `${feature.attributes.length.toFixed(2)} miles`; directions.appendChild(direction); }); document.querySelector("#directions-container").appendChild(directions); } } catch (error) { console.log(error); } }
Run the App
In CodePen, run your code to display the map.
Click on the map twice to display the route directions. The map should support two clicks to create an origin and destination point and then use the route service to display the resulting route and turn-by-turn directions.
What's next?
Learn how to use additional API features and ArcGIS services in these tutorials: