Skip to content

Instantly share code, notes, and snippets.

@tkh44
Last active August 29, 2015 14:04
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save tkh44/969105d7358072bbe818 to your computer and use it in GitHub Desktop.
Save tkh44/969105d7358072bbe818 to your computer and use it in GitHub Desktop.
Angular service for working with geoLocations using ngCordova
((angular, window) => {
/**
* GeoLocation Utility Service
* @param $localStorage
* @param $cordovaGeolocation
* @param $q
* @returns {{getCachedGeoLocation: getCachedGeoLocation, getDistance: getDistance}}
* @constructor
*/
var GeoService = function($localStorage, $cordovaGeolocation, $q) {
var $storage = $localStorage,
cachedLocation = $storage.currentLocation,
isUS = navigator.language.match(/us/ig);
var isLocationExpired = () =>
angular.isUndefined(cachedLocation)
|| cachedLocation.error
|| cachedLocation.lookupTime - +new Date() > 3E5;
/**
* Return the distance in miles if `navigator.language` is 'en-US' otherwise
* returns distance in kilometers
*
* @param {number} distance
* @returns {string} distance in either miles or km
*/
var getLocaleDistance = (distance) =>
isUS ? (distance / 1.609344).toFixed(1) + ' mi' : distance.toFixed(1) + ' km';
/**
* Calculates the distance between two latitude-longitude points
*
* Taken from {@link http://stackoverflow.com/a/7179026}
* @param {number} lat1
* @param {number} lon1
* @param {number} lat2
* @param {number} lon2
* @returns {number}
*/
var computeDistanceBetween = (lat1, lon1, lat2, lon2) => {
var toRad = (val) => val * Math.PI / 180;
var R = 6371 | 0, // Radius of the earth 6371 km
dLat = toRad(lat2 - lat1),
dLon = toRad(lon2 - lon1);
var a = Math.sin(dLat / 2) * Math.sin(dLat / 2) + Math.cos(toRad(lat1)) * Math.cos(toRad(lat2)) * Math.sin(dLon / 2) * Math.sin(dLon / 2);
var c = 2 * Math.atan(Math.sqrt(a), Math.sqrt(1 - a));
return R * c;
};
this.getCachedGeoLocation = function() {
var deferred = $q.defer();
// Was the last lookup more than 5 min ago.
if (!isLocationExpired()) {
return $q.when(cachedLocation);
} else {
$cordovaGeolocation.getCurrentPosition().then((position) => {
console.log(position.timestamp);
var currentPosition = {
'latitude': position.coords.latitude,
'longitude': position.coords.longitude,
'accuracy': position.coords.accuracy ,
'lookupTime': +new Date()
};
$storage.currentLocation = currentPosition;
deferred.resolve(currentPosition);
}, (err) => {
cachedLocation['error'] = err;
deferred.reject(err)
});
}
return deferred.promise;
};
/**
* Get the distance of the building from the cached geolocation of user
*
* @param {number} latitude
* @param {number} longitude
* @returns {string} prettyDistance
*/
this.getDistance = function(latitude, longitude) {
return getLocaleDistance(computeDistanceBetween(cachedLocation.latitude, cachedLocation.longitude, latitude, longitude));
}
};
angular.module('iOffice.geo', ['ngCordova']).service('GeoService', GeoService);
})(angular, window);
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment