Cordova Geolocation plugin returning empty position object on Android

I’ve had quite some issues with the Geolocation Cordova plugin (org.apache.cordova.geolocation). It works fine on iOS, but it doesn’t at all on Android.

As I understand, the plugin used to include native Android code, but this was removed at some point, because it was too buggy/slow and the native web HTML5 implementation was much more stable and fast.

  • Get day of the week from GregorianCalendar
  • How to programmatically add view in ViewFlipper
  • Textview Gravity not working properly in android
  • How to find ARM processor version on android device?
  • Android: toggle text color of ToggleButton
  • Android AlertDialog box WindowManager$BadTokenException problem
  • If I use the latest plugin version (0.3.2) which still has the native code, it does work (but slow and indeed, not always). But when it does return, the position object is always populated.

    If I use the latest plugin version (1.0.1), the getCurrentPosition() immediately returns with an empty object ({}). It does not throw an error.

    If I remove the plugin completely, and add the permissions manually to the Android project:

    <uses-permission android:name="android.permission.ACCESS_COARSE_LOCATION" />
    <uses-permission android:name="android.permission.ACCESS_FINE_LOCATION" />
    <uses-permission android:name="android.permission.ACCESS_LOCATION_EXTRA_COMMANDS" />
    

    The same thing happens. I just can’t get it to work, but it doesn’t make sense. No errors are displayed in the Android console. Any thoughts?

    Related posts:

    How to take screenshot in android emulator
    mapFragment.getMapAsync(this) - NullPointerException
    Playing multiple songs with MediaPlayer at the same time: only one is really playing
    Android Webview - Webpage should fit the device screen
    Show ProgressDialog in Fragment class
    Make one IAP valid for different applications
  • How can I launch mobile network settings screen from my code
  • ActionBar Dropdown Spinner item defaults to first item
  • Resume my application in the same way it resumed from history
  • Activity lifecycle - onCreate called on every re-orientation
  • Android: getString(R.string) in static method
  • Go back to previous screen without creating new instance
  • 3 Solutions collect form web for “Cordova Geolocation plugin returning empty position object on Android”

    OK, after a long long time of debugging, I found the problem. Apparently, the getCurrentPosition() function returns a ‘special’ object in Android, which evaluates to {} when using JSON.stringify(). If I outputted the raw return object to the console, it turned out it wasn’t empty at all.

    So, following ridiculous adjustments fixed my code:

    navigator.geolocation.getCurrentPosition(function (position) {
        var positionObject = {};
    
        if ('coords' in position) {
            positionObject.coords = {};
    
            if ('latitude' in position.coords) {
                positionObject.coords.latitude = position.coords.latitude;
            }
            if ('longitude' in position.coords) {
                positionObject.coords.longitude = position.coords.longitude;
            }
            if ('accuracy' in position.coords) {
                positionObject.coords.accuracy = position.coords.accuracy;
            }
            if ('altitude' in position.coords) {
                positionObject.coords.altitude = position.coords.altitude;
            }
            if ('altitudeAccuracy' in position.coords) {
                positionObject.coords.altitudeAccuracy = position.coords.altitudeAccuracy;
            }
            if ('heading' in position.coords) {
                positionObject.coords.heading = position.coords.heading;
            }
            if ('speed' in position.coords) {
                positionObject.coords.speed = position.coords.speed;
            }
        }
    
        if ('timestamp' in position) {
            positionObject.timestamp = position.timestamp;
        }
    
        // Use the positionObject instead of the position 'object'
        alert(JSON.stringify(positionObject));            
    }
    

    iOS works fine without above adjustments, but as my app is a Phonegap application, I always apply the above.

    The Geolocation object passed to the callbacks in navigator.geolocation.getCurrentLocation() contains two prototype getters coords and timestamp, which means that hasOwnProperty will return false, which I assume that JSON.stringify excludes.

    When logging all keys on the object I get the following:

    [object Geoposition]
      .coords [object Coordinates]
         .latitude
         .longitude
         .altitude
         .accuracy 
         .altitudeAccuracy
         .heading
         .speed
      .timestamp
    

    Never the less, these values are valid when accessed normally.

    With Angular, you can fix this with :

    location = angular.copy(location)
    
    Android Babe is a Google Android Fan, All about Android Phones, Android Wear, Android Dev and Android Games Apps and so on.