FlowX
FlowX

Reputation: 102

AngularJs GPS access denied in other state

I'm working on a Cordova app and I use different AngularJs states. If I call in the first state geolocation.watchposition it works perfect, but if I call it in the second state, I get access denied...

I change the states with a Button. No matter, which state I start first, the first one has GPS, the second one don't.

EDIT: I should mention, that its working in a browser, but not on my android device.

Do you know why?

index.js

.config(function ($stateProvider, $urlRouterProvider) {
    $stateProvider
    .state('app', {
      url: '/app',
      templateUrl: 'templates/main_menu.html',
      controller: 'AppCtrl'
    })

   .state('map', {
       url: '/map',
       templateUrl: 'templates/map.html',
       controller: 'MapCtrl'
   });

   //First State
   $urlRouterProvider.otherwise('/app');
});

controller.js

.controller('AppCtrl', function ($scope, $rootScope, $ionicHistory, $http, $window) { 
  $scope.accPos = function () {
      var id, target, options;

      function success(pos) {
          alert("Pos: " + pos.coords.latitude + " " + pos.coords.longitude);
      }

      function error(err) {
          alert('ERROR(' + err.code + '): ' + err.message);
      }

      options = {
          enableHighAccuracy: false,
          timeout: 6000,
          maximumAge: 0
      };

      id = navigator.geolocation.watchPosition(success, error, options);
   };

   $scope.accPos();
}

//Looks exactly the same
.controller('MapCtrl', function ($scope, $rootScope, $ionicHistory, $http, $window) { ... }

Upvotes: 0

Views: 195

Answers (1)

Brent McFerrin
Brent McFerrin

Reputation: 528

You should really move this kind of code to a service so it can be shared among your controllers. On top of that, you could utilize the ui-router's resolve functionality to resolve the GPS location for each state that needs it.

For example:

service.js

.factory('GeoLocationService', function ($window) { 
    var id, target, options, lastPosition;
    options = {
        enableHighAccuracy: false,
        timeout: 6000,
        maximumAge: 0
    };

    var geoLocationService = {
        startWatching: startWatching,
        stopWatching: stopWatching,
        getLastPosition: getLastPosition,
        options: options
    };  
    startWatching();
    return geoLocationService;

    function getLastPosition() {
        return lastPosition;
    }

    function startWatching() {
        id = $window.navigator.geolocation.watchPosition(success, error, options);
    }

    function stopWatching() {
        $window.navigator.geolocation.clearWatch(id);
    }

    function success(pos) {
        lastPosition = pos;
        alert("Pos: " + pos.coords.latitude + " " + pos.coords.longitude);
    }

    function error(err) {
        alert('ERROR(' + err.code + '): ' + err.message);
    }
});

index.js

.config(function ($stateProvider, $urlRouterProvider) {
    $stateProvider
    .state('app', {
      url: '/app',
      templateUrl: 'templates/main_menu.html',
      controller: 'AppCtrl',
      resolve: {
         location: function(GeoLocationService){
            return GeoLocationService.getLastPosition();
         }
      }
    })

   .state('map', {
       url: '/map',
       templateUrl: 'templates/map.html',
       controller: 'MapCtrl',
       resolve: {
         location: function(GeoLocationService){
            return GeoLocationService.getLastPosition();
         }
      }
   });

   //First State
   $urlRouterProvider.otherwise('/app');
});

controller.js

.controller('AppCtrl', function ($scope, $rootScope, $ionicHistory, $http, $window, GeoLocationService, location) {
    // show the location at start
    alert("Pos: " + location.coords.latitude + " " + location.coords.longitude);

    // maybe watch the location from the service
    $scope.$watch(function () {
        return GeoLocationService.getLastPosition();
    },
    function (newValue, oldValue) {
        if (newValue !== oldValue) {
            // do something
        }            
    }, true);
}

Note that this code is completely untested. I'm just trying to get the idea across.

Cheers!

Upvotes: 1

Related Questions