My goal is to move a pointer from one geo location to another based on the GPS location received from the device. however, i managed to do this by clearing the layer and re drawing the point on the map. but in a graphical prospective I need to move the pointer in a smooth way rather than clearing out the point and readding it to the maps. this application is related to fleet.
It would be great if someone could point me on the right direction on this.
im using Arcgis 4.17 Javascript API
You can use the mapview.goTo() method to animate from one location to another - supplying the new GPS location as the target.
mapview.goTo() this method is used to navigate from 1 point to another. that's not what I am looking for. actually im looking for something like this.
I need the point to be moved from 1 location to another without clearing the mapview and readding the point. I need to move the point by animating it
basically a fleet moving on the street. that's the whole goal
Thanks for clarifying - unfortunately I dont think there's any way to animate something in the framework without clearing and readding it - as effectively you need to redraw the frame for it to animate.
The smoothness comes into how often you update the frame and how far you're moving the point.
If you simply animating from one co-ordinate from another you can just calculate the steps inbetween the two endpoints and then remove and add a point to the new step.
If it's along a route you'll need to calculate the route and likely densify the results so you have more steps to animate through.
This is rough example based on the sample code, after you click two points on the map it draws a new symbol and clears and adds the point along the path effectively animating it.
To get even more smooth results you'd probably increase the density and decrease the time between updates.
<!--
To run this demo, you need to replace 'YOUR_API_KEY' with an API key from the ArcGIS Developers dashboard.
Sign up for a free account and get an API key.
https://developers.arcgis.com/documentation/mapping-apis-and-services/get-started/
-->
<html lang="en">
<head>
<meta charset="utf-8" />
<meta
name="viewport"
content="initial-scale=1,maximum-scale=1,user-scalable=no"
/>
<title>Route | Sample | ArcGIS Maps SDK for JavaScript 4.26</title>
<style>
html,
body,
#viewDiv {
padding: 0;
margin: 0;
height: 100%;
width: 100%;
}
#paneDiv {
position: absolute;
top: 10px;
left: 62px;
padding: 0 12px 0 12px;
background-color: rgba(0, 0, 0, 0.5);
color: white;
}
</style>
<link
rel="stylesheet"
href="https://js.arcgis.com/4.26/esri/themes/light/main.css"
/>
<script src="https://js.arcgis.com/4.26/"></script>
<script>
require([
"esri/Map",
"esri/views/MapView",
"esri/Graphic",
"esri/layers/GraphicsLayer",
"esri/rest/route",
"esri/rest/support/RouteParameters",
"esri/rest/support/FeatureSet",
"esri/geometry/geometryEngine"
], function (
Map,
MapView,
Graphic,
GraphicsLayer,
route,
RouteParameters,
FeatureSet,
geometryEngine
) {
// Point the URL to a valid routing service
const routeUrl =
"https://route-api.arcgis.com/arcgis/rest/services/World/Route/NAServer/Route_World";
// The stops and route result will be stored in this layer
const routeLayer = new GraphicsLayer();
const pinLayer = new GraphicsLayer();
let routeShowing = false;
let index = 0;
let routeResult = null
// Setup the route parameters
const routeParams = new RouteParameters({
// An authorization string used to access the routing service
apiKey: "%YOUR_API_KEY%",
stops: new FeatureSet(),
outSpatialReference: {
// autocasts as new SpatialReference()
wkid: 3857
}
});
// Define the symbology used to display the stops
const stopSymbol = {
type: "simple-marker", // autocasts as new SimpleMarkerSymbol()
style: "cross",
size: 15,
outline: {
// autocasts as new SimpleLineSymbol()
width: 4
}
};
const pinSymbol = {
type: "simple-marker", // autocasts as new SimpleMarkerSymbol()
style: "circle",
size: 10,
outline: {
// autocasts as new SimpleLineSymbol()
width: 6
}
};
// Define the symbology used to display the route
const routeSymbol = {
type: "simple-line", // autocasts as SimpleLineSymbol()
color: [0, 0, 255, 0.5],
width: 5
};
const map = new Map({
basemap: "streets-navigation-vector",
layers: [routeLayer, pinLayer] // Add the route layer to the map
});
const view = new MapView({
container: "viewDiv", // Reference to the scene div created in step 5
map: map, // Reference to the map object created before the scene
center: [-117.195, 34.057],
zoom: 13
});
// Adds a graphic when the user clicks the map. If 2 or more points exist, route is solved.
view.on("click", addStop);
function addStop(event) {
// Add a point at the location of the map click
const stop = new Graphic({
geometry: event.mapPoint,
symbol: stopSymbol
});
routeLayer.add(stop);
// Execute the route if 2 or more stops are input
routeParams.stops.features.push(stop);
if (routeParams.stops.features.length >= 2) {
route.solve(routeUrl, routeParams).then(showRoute);
}
}
// Adds the solved route to the map as a graphic
function showRoute(data) {
routeResult = data.routeResults[0].route;
routeResult.geometry = geometryEngine.densify(routeResult.geometry, 25);
routeResult.symbol = routeSymbol;
routeLayer.add(routeResult);
const pinPoint = new Graphic({
geometry: {
x: routeResult.geometry.paths[0][0][0],
y: routeResult.geometry.paths[0][0][1],
spatialReference: view.spatialReference,
type: "point"
},
symbol: pinSymbol
});
pinLayer.add(pinPoint);
routeShowing = true;
}
view.when(() => {
let timerControl = setInterval(() => {
if(routeShowing === true && index < routeResult.geometry.paths[0].length ) {
index++;
pinLayer.removeAll();
const pinPoint = new Graphic({
geometry: {
x: routeResult.geometry.paths[0][index][0],
y: routeResult.geometry.paths[0][index][1],
spatialReference: view.spatialReference,
type: "point"
},
symbol: pinSymbol
});
pinLayer.add(pinPoint);
}
}, 60);
})
});
</script>
</head>
<body>
<div id="viewDiv"></div>
<div id="paneDiv" class="esri-widget">
<div>
<p>
Click on the map to add stops to the route. The route from the last
stop to the newly added stop is calculated. If a stop is not
reachable, then the last valid point is set as the starting point.
</p>
</div>
</div>
</body>
</html>