/**
* @namespace WPGMZA
* @module OLGeocoder
* @requires WPGMZA.Geocoder
*/
(function($) {
/**
* @class OLGeocoder
* @extends Geocoder
* @summary OpenLayers geocoder - uses Nominatim by default
*/
WPGMZA.OLGeocoder = function()
{
}
WPGMZA.OLGeocoder.prototype = Object.create(WPGMZA.Geocoder.prototype);
WPGMZA.OLGeocoder.prototype.constructor = WPGMZA.OLGeocoder;
/**
* @function getResponseFromCache
* @access protected
* @summary Tries to retrieve cached coordinates from server cache
* @param {string} address The street address to geocode
* @param {function} callback Where to send the results, as an array
* @return {void}
*/
WPGMZA.OLGeocoder.prototype.getResponseFromCache = function(address, callback)
{
$.ajax(WPGMZA.ajaxurl, {
data: {
action: "wpgmza_query_nominatim_cache",
query: address
},
success: function(response, xhr, status) {
callback(response);
}
});
}
/**
* @function getResponseFromNominatim
* @access protected
* @summary Queries Nominatim on the specified address
* @param {object} options An object containing the options for geocoding, address is a mandatory field
* @param {function} callback The function to send the results to, as an array
*/
WPGMZA.OLGeocoder.prototype.getResponseFromNominatim = function(options, callback)
{
var data = {
q: options.address,
format: "json"
};
if(options.country)
data.countrycodes = options.country;
$.ajax("https://nominatim.openstreetmap.org/search/", {
data: data,
success: function(response, xhr, status) {
callback(response);
},
error: function(response, xhr, status) {
callback(null, WPGMZA.Geocoder.FAIL)
}
});
}
/**
* @function cacheResponse
* @access protected
* @summary Caches a response on the server, usually after it's been returned from Nominatim
* @param {string} address The street address
* @param {object|array} response The response to cache
* @returns {void}
*/
WPGMZA.OLGeocoder.prototype.cacheResponse = function(address, response)
{
$.ajax(WPGMZA.ajaxurl, {
data: {
action: "wpgmza_store_nominatim_cache",
query: address,
response: JSON.stringify(response)
},
method: "POST"
});
}
/**
* @function getLatLngFromAddress
* @access public
* @summary Attempts to geocode an address, firstly by checking the cache for previous
* results, if this fails the Nominatim server will be queried, cached and sent to the
* specified callback
* @param {object} options An object containing the options for geocoding, address is a mandatory field
* @param {function} callback The function to send the results to, as an array
* @returns {void}
*/
WPGMZA.OLGeocoder.prototype.getLatLngFromAddress = function(options, callback)
{
var self = this;
var address = options.address;
var latLng;
if(latLng = WPGMZA.isLatLngString(address))
return WPGMZA.Geocoder.prototype.getLatLngFromAddress.call(this, options, callback);
function finish(response, status)
{
for(var i = 0; i < response.length; i++)
{
response[i].geometry = {
location: new WPGMZA.LatLng({
lat: parseFloat(response[i].lat),
lng: parseFloat(response[i].lon)
})
};
response[i].lat = parseFloat(response[i].lat);
response[i].lng = parseFloat(response[i].lon);
}
callback(response, status);
}
this.getResponseFromCache(address, function(response) {
if(response.length)
{
finish(response, WPGMZA.Geocoder.SUCCESS);
return;
}
self.getResponseFromNominatim(options, function(response, status) {
if(status == WPGMZA.Geocoder.FAIL)
{
callback(null, WPGMZA.Geocoder.FAIL);
return;
}
if(response.length == 0)
{
callback(response, WPGMZA.Geocoder.ZERO_RESULTS);
return;
}
finish(response, WPGMZA.Geocoder.SUCCESS);
self.cacheResponse(address, response);
});
});
}
})(jQuery);