Reputation: 21
I am working on location detection using GPS in a React Native app. However, I am encountering issues on both Android and iOS:
ACCESS_FINE_LOCATION
), not approximate (ACCESS_COARSE_LOCATION
).I am looking for best practices to handle GPS location detection properly for both Android & iOS, ensuring compatibility with both new and old architectures.
Here’s the implementation for checking and requesting location permissions:
export const checkLocationPermission = async () => {
const permission = Platform.OS === 'ios'
? Permission.PERMISSIONS.IOS.LOCATION_WHEN_IN_USE
: Platform.Version >= 29
? Permission.PERMISSIONS.ANDROID.ACCESS_FINE_LOCATION
: Permission.PERMISSIONS.ANDROID.ACCESS_COARSE_LOCATION;
try {
const result = await Permission.check(permission);
switch (result) {
case Permission.RESULTS.UNAVAILABLE:
console.log('Location feature is not available on this device');
return null;
case Permission.RESULTS.DENIED:
if (Platform.OS === 'android' && Platform.Version >= 29) {
const fineResult = await Permission.request(Permission.PERMISSIONS.ANDROID.ACCESS_FINE_LOCATION);
if (fineResult === Permission.RESULTS.GRANTED) {
const coarseResult = await Permission.request(Permission.PERMISSIONS.ANDROID.ACCESS_COARSE_LOCATION);
return coarseResult === Permission.RESULTS.GRANTED ? coarseResult : null;
}
return null;
}
if (Platform.OS === 'ios') {
const requestResult = await Permission.request(permission);
if (requestResult === Permission.RESULTS.GRANTED && parseInt(Platform.Version) >= 14) {
await Permission.request(Permission.PERMISSIONS.IOS.LOCATION_ACCURACY);
}
return requestResult;
}
return await Permission.request(permission);
case Permission.RESULTS.GRANTED:
if (Platform.OS === 'ios' && parseInt(Platform.Version) >= 14) {
await Permission.request(Permission.PERMISSIONS.IOS.LOCATION_ACCURACY);
}
return result;
case Permission.RESULTS.BLOCKED:
console.log('Location permission is denied and not requestable anymore');
return result;
default:
return null;
}
} catch (error) {
console.error('Error checking location permission:', error);
return null;
}
};
const onRequestTurnOnGPS = async () => {
setLoadingGPS(true);
try {
const enabled = await getGPSStatus();
if (enabled) {
console.log("Enabled GPS");
await dispatch(addUserLocationLog());
setLoadingGPS(false);
} else {
console.log("Disabled GPS");
setLoadingGPS(false);
ToastInterface.showInfo(translate('message.loc_device_body'));
}
} catch (error) {
setLoadingGPS(false);
AppLog.sendLog({title: 'GPS request error', error});
ToastInterface.showError(translate('message.loc_device_error'));
}
};
export const addUserLocationLog = () => async (dispatch, getState) => {
return new Promise(async (resolve, reject) => {
try {
const permResult = await checkLocationPermission();
if (permResult !== RESULTS.GRANTED) {
await dispatch(updateUserLocation(null, true, true));
resolve();
return;
}
Geolocation.getCurrentPosition(
async position => {
await dispatch(updateUserLocation(position?.coords, true));
resolve();
},
async error => {
await dispatch(updateUserLocation(null, true, true));
// AppLog.sendLog({title: 'get current position error', error});
resolve();
},
{
enableHighAccuracy: true,
timeout: 15000,
maximumAge: 10000,
},
);
} catch (e) {
AppLog.sendLog({title: 'addUserLocationLog error', error: e});
resolve();
}
});
};
Upvotes: 0
Views: 30