3

I'm having the issue that Android 10 can't read GPS information from my jpeg files. The exact same files are working on Android 9. I tried the ExifInterface (androidx) which returns null, as well as apache commons imaging which is saying "GPSLatitude: Invalid rational (0/0), Invalid rational (0/0)". Other exif information like the rating or XPKeywords are read correctly.

How to fix that?

Test code:

import androidx.exifinterface.media.ExifInterface;
ExifInterface exif2 = new ExifInterface(is);
double[] latLngArray = exif2.getLatLong();

getLatLong Implementation:

public double[] getLatLong() {
    String latValue = getAttribute(TAG_GPS_LATITUDE);
    String latRef = getAttribute(TAG_GPS_LATITUDE_REF);
    String lngValue = getAttribute(TAG_GPS_LONGITUDE);
    String lngRef = getAttribute(TAG_GPS_LONGITUDE_REF);
    if (latValue != null && latRef != null && lngValue != null && lngRef != null) {
        try {
            double latitude = convertRationalLatLonToDouble(latValue, latRef);
            double longitude = convertRationalLatLonToDouble(lngValue, lngRef);
            return new double[] {latitude, longitude};
        } catch (IllegalArgumentException e) {
            Log.w(TAG, "Latitude/longitude values are not parseable. " +
                    String.format("latValue=%s, latRef=%s, lngValue=%s, lngRef=%s",
                            latValue, latRef, lngValue, lngRef));
        }
    }
    return null;
}

All getAttribute calls are returning null on Android Q/10. On Android 9 it is working. My test photo does contain GPS information. Even Android itself was unable to index the GPS location into their media store. The field is null as well in their database. I transferred the test photo via mail.

Cœur
  • 37,241
  • 25
  • 195
  • 267
Denny Weinberg
  • 2,492
  • 1
  • 21
  • 34

1 Answers1

8

As mentioned in developer android, now, on Android 10, the location embed on image files is not directly available to the apps:

Because this location information is sensitive, however, Android 10 by default hides this information from your app if it uses scoped storage.

On that same link, you can check how to fix:

  1. Request the ACCESS_MEDIA_LOCATION permission in your app's manifest.

  2. From your MediaStore object, call setRequireOriginal(), passing in the URI of the photograph, as shown in the following code snippet:

Code snippet:

Uri photoUri = Uri.withAppendedPath(
        MediaStore.Images.Media.EXTERNAL_CONTENT_URI,
        cursor.getString(idColumnIndex));

// Get location data from the ExifInterface class.
photoUri = MediaStore.setRequireOriginal(photoUri);
InputStream stream = getContentResolver().openInputStream(photoUri);
if (stream != null) {
    ExifInterface exifInterface = new ExifInterface(stream);
    // Don't reuse the stream associated with the instance of "ExifInterface".
    stream.close();
} else {
    // Failed to load the stream, so return the coordinates (0, 0).
    latLong = new double[2];
}

Note how they are now using Uri, InputStream (and also FileDescriptor) to access the file since now, you can't access a file using its file path.

guipivoto
  • 18,327
  • 9
  • 60
  • 75
  • The MediaStore still returns null. "This constant was deprecated in API level 29. location details are no longer indexed for privacy reasons, and this value is now always null." --> https://developer.android.com/reference/android/provider/MediaStore.Images.ImageColumns – Denny Weinberg Sep 18 '19 at 07:11
  • You have to read using one of the new methods: (ExifInterface.getLatLong(float[]) for example) – guipivoto Sep 18 '19 at 11:23
  • the link no longer works. what's idColumnIndex and cursor ? – jab11 Feb 05 '20 at 21:17
  • Can setRequireOriginal() also be used to amend an Uri which is passed via Intent for sharing a photo to another app? See issue for further details: https://stackoverflow.com/questions/68442139/exif-location-data-removed-when-sharing-photo-via-intent – Mike Jul 29 '21 at 08:56
  • 1
    Not working solution! exifInterface.getLatLong(latLong) returns 0.0 values for latitude and longitude always. But coordinates are exists in image - in image viewer I can see this info. Anybody can help with issue? – Vitaly Apr 26 '22 at 04:12
  • Anyone found solution? Not working in Android 12 – Krutika Chotara Jun 22 '22 at 18:30
  • @KrutikaChotara were you able to find a solution for Android 12? – martin petrov Oct 11 '22 at 12:12