@@ -111,11 +111,18 @@ void onAnswered(OneSignal.PromptActionResult result) {}
111
111
}
112
112
113
113
static boolean scheduleUpdate (Context context ) {
114
- if (!hasLocationPermission (context ) || !OneSignal .isLocationShared ())
114
+ if (!hasLocationPermission (context )) {
115
+ OneSignal .onesignalLog (OneSignal .LOG_LEVEL .DEBUG , "LocationController scheduleUpdate not possible, location permission not enabled" );
115
116
return false ;
116
-
117
+ }
118
+ if (!OneSignal .isLocationShared ()) {
119
+ OneSignal .onesignalLog (OneSignal .LOG_LEVEL .DEBUG , "LocationController scheduleUpdate not possible, location shared not enabled" );
120
+ return false ;
121
+ }
117
122
long lastTime = OneSignal .getTime ().getCurrentTimeMillis () - getLastLocationTime ();
118
123
long minTime = 1_000 * (OneSignal .isInForeground () ? TIME_FOREGROUND_SEC : TIME_BACKGROUND_SEC );
124
+
125
+ OneSignal .onesignalLog (OneSignal .LOG_LEVEL .DEBUG , "LocationController scheduleUpdate lastTime: " + lastTime + " minTime: " + minTime );
119
126
long scheduleTime = minTime - lastTime ;
120
127
121
128
OneSignalSyncServiceUtils .scheduleLocationUpdateTask (context , scheduleTime );
@@ -124,7 +131,7 @@ static boolean scheduleUpdate(Context context) {
124
131
125
132
private static void setLastLocationTime (long time ) {
126
133
OneSignalPrefs .saveLong (OneSignalPrefs .PREFS_ONESIGNAL ,
127
- OneSignalPrefs .PREFS_OS_LAST_LOCATION_TIME ,time );
134
+ OneSignalPrefs .PREFS_OS_LAST_LOCATION_TIME , time );
128
135
}
129
136
130
137
private static long getLastLocationTime () {
@@ -192,13 +199,16 @@ static void getLocation(Context context, boolean promptLocation, boolean fallbac
192
199
return ;
193
200
}
194
201
202
+ int locationBackgroundPermission = PackageManager .PERMISSION_DENIED ;
195
203
int locationCoarsePermission = PackageManager .PERMISSION_DENIED ;
196
204
197
205
int locationFinePermission = ContextCompat .checkSelfPermission (context , "android.permission.ACCESS_FINE_LOCATION" );
198
206
if (locationFinePermission == PackageManager .PERMISSION_DENIED ) {
199
207
locationCoarsePermission = ContextCompat .checkSelfPermission (context , "android.permission.ACCESS_COARSE_LOCATION" );
200
208
locationCoarse = true ;
201
209
}
210
+ if (Build .VERSION .SDK_INT >= 29 )
211
+ locationBackgroundPermission = ContextCompat .checkSelfPermission (context , "android.permission.ACCESS_BACKGROUND_LOCATION" );
202
212
203
213
if (Build .VERSION .SDK_INT < Build .VERSION_CODES .M ) {
204
214
if (locationFinePermission != PackageManager .PERMISSION_GRANTED && locationCoarsePermission != PackageManager .PERMISSION_GRANTED ) {
@@ -210,22 +220,25 @@ static void getLocation(Context context, boolean promptLocation, boolean fallbac
210
220
}
211
221
sendAndClearPromptHandlers (promptLocation , OneSignal .PromptActionResult .PERMISSION_GRANTED );
212
222
startGetLocation ();
213
- }
214
- else { // Android 6.0+
223
+ } else { // Android 6.0+
215
224
if (locationFinePermission != PackageManager .PERMISSION_GRANTED ) {
216
225
try {
217
226
PackageInfo packageInfo = context .getPackageManager ().getPackageInfo (context .getPackageName (), PackageManager .GET_PERMISSIONS );
218
227
List <String > permissionList = Arrays .asList (packageInfo .requestedPermissions );
219
228
OneSignal .PromptActionResult result = OneSignal .PromptActionResult .PERMISSION_DENIED ;
220
- if (permissionList .contains ("android.permission.ACCESS_FINE_LOCATION" ))
229
+
230
+ if (permissionList .contains ("android.permission.ACCESS_FINE_LOCATION" )) {
221
231
// ACCESS_FINE_LOCATION permission defined on Manifest, prompt for permission
222
232
// If permission already given prompt will return positive, otherwise will prompt again or show settings
223
233
requestPermission = "android.permission.ACCESS_FINE_LOCATION" ;
224
- else if (permissionList .contains ("android.permission.ACCESS_COARSE_LOCATION" )) {
234
+ } else if (permissionList .contains ("android.permission.ACCESS_COARSE_LOCATION" )) {
225
235
if (locationCoarsePermission != PackageManager .PERMISSION_GRANTED ) {
226
236
// ACCESS_COARSE_LOCATION permission defined on Manifest, prompt for permission
227
237
// If permission already given prompt will return positive, otherwise will prompt again or show settings
228
238
requestPermission = "android.permission.ACCESS_COARSE_LOCATION" ;
239
+ } else if (Build .VERSION .SDK_INT >= 29 && permissionList .contains ("android.permission.ACCESS_BACKGROUND_LOCATION" )) {
240
+ // ACCESS_BACKGROUND_LOCATION permission defined on Manifest, prompt for permission
241
+ requestPermission = "android.permission.ACCESS_BACKGROUND_LOCATION" ;
229
242
}
230
243
} else {
231
244
OneSignal .onesignalLog (OneSignal .LOG_LEVEL .INFO , "Location permissions not added on AndroidManifest file" );
@@ -252,11 +265,40 @@ else if (permissionList.contains("android.permission.ACCESS_COARSE_LOCATION")) {
252
265
sendAndClearPromptHandlers (promptLocation , OneSignal .PromptActionResult .ERROR );
253
266
e .printStackTrace ();
254
267
}
268
+ } else if (Build .VERSION .SDK_INT >= 29 && locationBackgroundPermission != PackageManager .PERMISSION_GRANTED ) {
269
+ backgroundLocationPermissionLogic (context , promptLocation , fallbackToSettings );
270
+ } else {
271
+ sendAndClearPromptHandlers (promptLocation , OneSignal .PromptActionResult .PERMISSION_GRANTED );
272
+ startGetLocation ();
255
273
}
256
- else {
274
+ }
275
+ }
276
+
277
+ /**
278
+ * On Android 10 background location permission is needed
279
+ * On Android 11 and greater, background location should be asked after fine and coarse permission
280
+ * If background permission is asked at the same time as fine and coarse then both permission request are ignored
281
+ * */
282
+ private static void backgroundLocationPermissionLogic (Context context , boolean promptLocation , boolean fallbackToSettings ) {
283
+ try {
284
+ PackageInfo packageInfo = context .getPackageManager ().getPackageInfo (context .getPackageName (), PackageManager .GET_PERMISSIONS );
285
+ List <String > permissionList = Arrays .asList (packageInfo .requestedPermissions );
286
+
287
+ if (permissionList .contains ("android.permission.ACCESS_BACKGROUND_LOCATION" )) {
288
+ // ACCESS_BACKGROUND_LOCATION permission defined on Manifest, prompt for permission
289
+ requestPermission = "android.permission.ACCESS_BACKGROUND_LOCATION" ;
290
+ }
291
+
292
+ if (requestPermission != null && promptLocation ) {
293
+ PermissionsActivity .startPrompt (fallbackToSettings );
294
+ } else {
295
+ // Fine permission already granted
257
296
sendAndClearPromptHandlers (promptLocation , OneSignal .PromptActionResult .PERMISSION_GRANTED );
258
297
startGetLocation ();
259
298
}
299
+ } catch (PackageManager .NameNotFoundException e ) {
300
+ sendAndClearPromptHandlers (promptLocation , OneSignal .PromptActionResult .ERROR );
301
+ e .printStackTrace ();
260
302
}
261
303
}
262
304
@@ -270,6 +312,7 @@ static void startGetLocation() {
270
312
} else if (isHMSAvailable ()) {
271
313
HMSLocationController .startGetLocation ();
272
314
} else {
315
+ OneSignal .Log (OneSignal .LOG_LEVEL .WARN , "LocationController startGetLocation not possible, no location dependency found" );
273
316
fireFailedComplete ();
274
317
}
275
318
} catch (Throwable t ) {
0 commit comments