Reversegeocoding

229
2
Jump to solution
06-06-2019 11:55 PM
SergeDe_Backer
New Contributor III

Hello,

I have a project which uses the Belgium geolocator to search for the adresses. This works, but when I want to reversegeocode I get in trouble

The url for the search should be this format: http://loc.geopunt.be/geolocation/location?latlon=51.03868741989108,3.7066240164852555&c=1

But the locator always adds a lot of other params with it and I can't find a way to get it working.

Any help is appreciated.

This is my code so far:

<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8" />
<meta name="viewport"
content="initial-scale=1,maximum-scale=1,user-scalable=no" />
<title>Search widget with custom source - 4.11</title>
<style>

html,
body,
#viewDiv {
padding: 0;
margin: 0;
height: 100%;
width: 100%;
}
</style>
<link rel="stylesheet"
href="https://js.arcgis.com/4.11/esri/themes/light/main.css" />
<script src="https://js.arcgis.com/4.11/"></script>
<script>
require([
"esri/tasks/Locator",
"esri/Map",
"esri/Graphic",
"esri/request",
"esri/views/MapView",
"esri/widgets/Search",
"esri/widgets/Search/SearchSource",
"esri/geometry/geometryEngine",
"esri/geometry/Point",
"esri/layers/WMSLayer"
], function (
Locator,
Map,
Graphic,
esriRequest,
MapView,
Search,
SearchSource,
geometryEngine,
Point,
WMSLayer
) {
var url = "https://loc.api.geopunt.be/geolocation/location?c=5",

layer = new WMSLayer({
url: 'https://geoservices.informatievlaanderen.be/raadpleegdiensten/GRB-basiskaart/wms'
});

var map = new Map({
basemap: "streets"
});

map.add(layer);

var view = new MapView({
map: map,
zoom: 8,
center: [4.402771, 51.260197], //lon, lat
container: "viewDiv"
});

var customSearchSource = new SearchSource({
name: "Vlaanderen zoekopdracht",
placeholder: "Geef je straatnaam in",
displayField: "name",
// Provide a getSuggestions method
// to provide suggestions to the Search widget
getSuggestions: function (params) {
// You can request data from a
// third-party source to find some
// suggestions with provided suggestTerm
// the user types in the Search widget
return esriRequest(url, {
query: {
q: params.suggestTerm
},
responseType: "json"
}).then(function (results) {
// Return Suggestion results to display
// in the Search widget
return results.data.LocationResult.map(function (item) {
return {
key: "name",
text: item.FormattedAddress,
sourceIndex: params.sourceIndex
};
});
});
},
// Provide a getResults method to find
// results from the suggestions
getResults: function (params) {
// If the Search widget passes the current location,
// you can use this in your own custom source
var operation = "&q=" + params.suggestResult.text.replace(/ /g, "+");
var query = {};
// You can perform a different query if a location
// is provided
if (params.location) {
query.lat = params.location.latitude;
query.lon = params.location.longitude;
} else {
query.q = params.suggestResult.text.replace(/ /g, "+");
}
return esriRequest(url + operation, {
query: query,
responseType: "json"
}).then(function (results) {
// Parse the results of your custom search
var searchResults = results.data.LocationResult.map(function (feature) {
// Create a Graphic the Search widget can display
var graphic = new Graphic({
geometry: new Point({
x: feature.Location.Lon_WGS84,
y: feature.Location.Lat_WGS84
}),
attributes: feature
});
// Optionally, you can provide an extent for
// a point result, so the view can zoom to it
var buffer = geometryEngine.geodesicBuffer(
graphic.geometry,
50,
"meters"
);
// Return a Search Result
var searchResult = {
extent: buffer.extent,
feature: graphic,
name: feature.FormattedAddress
};
return searchResult;
});

// Return an array of Search Results
return searchResults;
});
}
});

// Create Search widget using custom SearchSource
var searchWidget = new Search({
view: view,
sources: [customSearchSource],
includeDefaultSources: false
});

view.on("click", function (event) {
console.log(event.mapPoint.latitude + "," + event.mapPoint.longitude);
// Haal de co�rdinaten van het aangeklikte punt op
var rdx = Math.round(event.mapPoint.x);
var rdy = Math.round(event.mapPoint.y);

view.popup.open({
// Toon de gevonden RD co�rdinaten in de titel van de popup. De co�rdinaten worden
// afgerond op hele meters en er wordt een punt geplaatst tussen de duizendtallen
//title: "RD Coordinaten: X = " + rdx.toLocaleString() + " / Y = " + rdy.toLocaleString(),
location: event.mapPoint // Plaats de popup op de aangeklikte locatie
});

var locatorTask = new Locator({
url: "https://loc.api.geopunt.be/geolocation/location?&latlon=" + event.mapPoint.latitude + "," + event.mapPoint.longitude,
});


// Toon de popup
// Voer reverse geocoding uit voor de aangeklikte locatie
locatorTask
.locationToAddress(event.mapPoint)
.then(function (response) {
// Toon het gevonden adres in de popup
view.popup.content = response.address;
})
.catch(function (error) {
console.log(error);
// Toon een foutmelding als er geen adres gevonden wordt
view.popup.content = "Er is geen adres gevonden voor deze locatie";
});
});

// Add the search widget to the top left corner of the view
view.ui.add(searchWidget, {
position: "top-right"
});
});</script>
</head>
<body>
<div id="viewDiv"></div>
</body>
</html>

0 Kudos
1 Solution

Accepted Solutions
RobertScheitlin__GISP
MVP Esteemed Contributor

Serge,

   The Locator class is for use with esri locators services. So you have to do the location request manually. Here is your code modified for that:

<!DOCTYPE html>
<html>

<head>
  <meta charset="utf-8" />
  <meta name="viewport" content="initial-scale=1,maximum-scale=1,user-scalable=no" />
  <title>Search widget with custom source - 4.11</title>
  <style>
    html,
    body,
    #viewDiv {
      padding: 0;
      margin: 0;
      height: 100%;
      width: 100%;
    }
  </style>
  <link rel="stylesheet" href="https://js.arcgis.com/4.11/esri/themes/light/main.css" />
  <script src="https://js.arcgis.com/4.11/"></script>
  <script>
    require([
      "esri/Map",
      "esri/Graphic",
      "esri/request",
      "esri/views/MapView",
      "esri/widgets/Search",
      "esri/widgets/Search/SearchSource",
      "esri/geometry/geometryEngine",
      "esri/geometry/Point",
      "esri/layers/WMSLayer"
    ], function (
      Map,
      Graphic,
      esriRequest,
      MapView,
      Search,
      SearchSource,
      geometryEngine,
      Point,
      WMSLayer
    ) {
      var url = "https://loc.api.geopunt.be/geolocation/location",

        layer = new WMSLayer({
          url: 'https://geoservices.informatievlaanderen.be/raadpleegdiensten/GRB-basiskaart/wms'
        });

      var map = new Map({
        basemap: "streets"
      });

      map.add(layer);

      var view = new MapView({
        map: map,
        zoom: 8,
        center: [4.402771, 51.260197], //lon, lat
        container: "viewDiv"
      });

      var customSearchSource = new SearchSource({
        name: "Vlaanderen zoekopdracht",
        placeholder: "Geef je straatnaam in",
        displayField: "name",
        // Provide a getSuggestions method
        // to provide suggestions to the Search widget
        getSuggestions: function (params) {
          // You can request data from a
          // third-party source to find some
          // suggestions with provided suggestTerm
          // the user types in the Search widget
          return esriRequest(url, {
            query: {
              q: params.suggestTerm
            },
            responseType: "json"
          }).then(function (results) {
            // Return Suggestion results to display
            // in the Search widget
            return results.data.LocationResult.map(function (item) {
              return {
                key: "name",
                text: item.FormattedAddress,
                sourceIndex: params.sourceIndex
              };
            });
          });
        },
        // Provide a getResults method to find
        // results from the suggestions
        getResults: function (params) {
          // If the Search widget passes the current location,
          // you can use this in your own custom source
          var operation = "&q=" + params.suggestResult.text.replace(/ /g, "+");
          var query = {};
          // You can perform a different query if a location
          // is provided
          if (params.location) {
            query.lat = params.location.latitude;
            query.lon = params.location.longitude;
          } else {
            query.q = params.suggestResult.text.replace(/ /g, "+");
          }
          return esriRequest(url + operation, {
            query: query,
            responseType: "json"
          }).then(function (results) {
            // Parse the results of your custom search
            var searchResults = results.data.LocationResult.map(function (feature) {
              // Create a Graphic the Search widget can display
              var graphic = new Graphic({
                geometry: new Point({
                  x: feature.Location.Lon_WGS84,
                  y: feature.Location.Lat_WGS84
                }),
                attributes: feature
              });
              // Optionally, you can provide an extent for
              // a point result, so the view can zoom to it
              var buffer = geometryEngine.geodesicBuffer(
                graphic.geometry,
                50,
                "meters"
              );
              // Return a Search Result
              var searchResult = {
                extent: buffer.extent,
                feature: graphic,
                name: feature.FormattedAddress
              };
              return searchResult;
            });

            // Return an array of Search Results
            return searchResults;
          });
        }
      });

      // Create Search widget using custom SearchSource
      var searchWidget = new Search({
        view: view,
        sources: [customSearchSource],
        includeDefaultSources: false
      });

      view.on("click", function (event) {
        view.popup.clear();
        view.popup.content = "Geocoding location...";
        console.log(event.mapPoint.latitude + "," + event.mapPoint.longitude);
        // Haal de co�rdinaten van het aangeklikte punt op
        var rdx = Math.round(event.mapPoint.x);
        var rdy = Math.round(event.mapPoint.y);

        view.popup.open({
          // Toon de gevonden RD co�rdinaten in de titel van de popup. De co�rdinaten worden
          // afgerond op hele meters en er wordt een punt geplaatst tussen de duizendtallen
          //title: "RD Coordinaten: X = " + rdx.toLocaleString() + " / Y = " + rdy.toLocaleString(),
          location: event.mapPoint // Plaats de popup op de aangeklikte locatie
        });

        esriRequest(url, {
            query: "latlon=" + event.mapPoint.latitude + "," +
            event.mapPoint.longitude,
            responseType: "json"
          }).then(function (results) {
            
            var frslt = results.data.LocationResult[0];
            console.info(frslt);
            view.popup.content = frslt.FormattedAddress;
            view.popup.title = frslt.Location.Lat_WGS84 + ", " + frslt.Location.Lon_WGS84
          });
      });

      // Add the search widget to the top left corner of the view
      view.ui.add(searchWidget, {
        position: "top-right"
      });
    });
  </script>
</head>

<body>
  <div id="viewDiv"></div>
</body>

</html>

View solution in original post

2 Replies
RobertScheitlin__GISP
MVP Esteemed Contributor

Serge,

   The Locator class is for use with esri locators services. So you have to do the location request manually. Here is your code modified for that:

<!DOCTYPE html>
<html>

<head>
  <meta charset="utf-8" />
  <meta name="viewport" content="initial-scale=1,maximum-scale=1,user-scalable=no" />
  <title>Search widget with custom source - 4.11</title>
  <style>
    html,
    body,
    #viewDiv {
      padding: 0;
      margin: 0;
      height: 100%;
      width: 100%;
    }
  </style>
  <link rel="stylesheet" href="https://js.arcgis.com/4.11/esri/themes/light/main.css" />
  <script src="https://js.arcgis.com/4.11/"></script>
  <script>
    require([
      "esri/Map",
      "esri/Graphic",
      "esri/request",
      "esri/views/MapView",
      "esri/widgets/Search",
      "esri/widgets/Search/SearchSource",
      "esri/geometry/geometryEngine",
      "esri/geometry/Point",
      "esri/layers/WMSLayer"
    ], function (
      Map,
      Graphic,
      esriRequest,
      MapView,
      Search,
      SearchSource,
      geometryEngine,
      Point,
      WMSLayer
    ) {
      var url = "https://loc.api.geopunt.be/geolocation/location",

        layer = new WMSLayer({
          url: 'https://geoservices.informatievlaanderen.be/raadpleegdiensten/GRB-basiskaart/wms'
        });

      var map = new Map({
        basemap: "streets"
      });

      map.add(layer);

      var view = new MapView({
        map: map,
        zoom: 8,
        center: [4.402771, 51.260197], //lon, lat
        container: "viewDiv"
      });

      var customSearchSource = new SearchSource({
        name: "Vlaanderen zoekopdracht",
        placeholder: "Geef je straatnaam in",
        displayField: "name",
        // Provide a getSuggestions method
        // to provide suggestions to the Search widget
        getSuggestions: function (params) {
          // You can request data from a
          // third-party source to find some
          // suggestions with provided suggestTerm
          // the user types in the Search widget
          return esriRequest(url, {
            query: {
              q: params.suggestTerm
            },
            responseType: "json"
          }).then(function (results) {
            // Return Suggestion results to display
            // in the Search widget
            return results.data.LocationResult.map(function (item) {
              return {
                key: "name",
                text: item.FormattedAddress,
                sourceIndex: params.sourceIndex
              };
            });
          });
        },
        // Provide a getResults method to find
        // results from the suggestions
        getResults: function (params) {
          // If the Search widget passes the current location,
          // you can use this in your own custom source
          var operation = "&q=" + params.suggestResult.text.replace(/ /g, "+");
          var query = {};
          // You can perform a different query if a location
          // is provided
          if (params.location) {
            query.lat = params.location.latitude;
            query.lon = params.location.longitude;
          } else {
            query.q = params.suggestResult.text.replace(/ /g, "+");
          }
          return esriRequest(url + operation, {
            query: query,
            responseType: "json"
          }).then(function (results) {
            // Parse the results of your custom search
            var searchResults = results.data.LocationResult.map(function (feature) {
              // Create a Graphic the Search widget can display
              var graphic = new Graphic({
                geometry: new Point({
                  x: feature.Location.Lon_WGS84,
                  y: feature.Location.Lat_WGS84
                }),
                attributes: feature
              });
              // Optionally, you can provide an extent for
              // a point result, so the view can zoom to it
              var buffer = geometryEngine.geodesicBuffer(
                graphic.geometry,
                50,
                "meters"
              );
              // Return a Search Result
              var searchResult = {
                extent: buffer.extent,
                feature: graphic,
                name: feature.FormattedAddress
              };
              return searchResult;
            });

            // Return an array of Search Results
            return searchResults;
          });
        }
      });

      // Create Search widget using custom SearchSource
      var searchWidget = new Search({
        view: view,
        sources: [customSearchSource],
        includeDefaultSources: false
      });

      view.on("click", function (event) {
        view.popup.clear();
        view.popup.content = "Geocoding location...";
        console.log(event.mapPoint.latitude + "," + event.mapPoint.longitude);
        // Haal de co�rdinaten van het aangeklikte punt op
        var rdx = Math.round(event.mapPoint.x);
        var rdy = Math.round(event.mapPoint.y);

        view.popup.open({
          // Toon de gevonden RD co�rdinaten in de titel van de popup. De co�rdinaten worden
          // afgerond op hele meters en er wordt een punt geplaatst tussen de duizendtallen
          //title: "RD Coordinaten: X = " + rdx.toLocaleString() + " / Y = " + rdy.toLocaleString(),
          location: event.mapPoint // Plaats de popup op de aangeklikte locatie
        });

        esriRequest(url, {
            query: "latlon=" + event.mapPoint.latitude + "," +
            event.mapPoint.longitude,
            responseType: "json"
          }).then(function (results) {
            
            var frslt = results.data.LocationResult[0];
            console.info(frslt);
            view.popup.content = frslt.FormattedAddress;
            view.popup.title = frslt.Location.Lat_WGS84 + ", " + frslt.Location.Lon_WGS84
          });
      });

      // Add the search widget to the top left corner of the view
      view.ui.add(searchWidget, {
        position: "top-right"
      });
    });
  </script>
</head>

<body>
  <div id="viewDiv"></div>
</body>

</html>
SergeDe_Backer
New Contributor III

Thanks Robert, spot on.

0 Kudos