I had a goal in mind: I needed a GPS tracking app that would replace a my handheld GPS device as a location tracker and that would automatically load the track (or parts of it) to my desired location for others to see.
Companies Mentioned
Photo by on
I had a goal in mind: I needed a GPS tracking app that would replace a my handheld GPS device as a location tracker and that would automatically load the track (or parts of it) to my desired location for others to see.
Background
For a while now I’ve used my portal to share my GPS tracks with others. I used to travel around, track my route with a handheld GPS and afterwards I’d upload the track for others to see. This was quite useful about 10 years ago. Today I mostly use a phone for navigation and carrying a GPS just for tracking purposes doesn’t seem that reasonable. I also wanted to share my routes online.
So I decided to write my first Android application that does the following:
The app uses the devices’ GPS and fetches my location in every 0.7 seconds;
The data is being gathered and uploaded to my web service once a minute (or if no internet connection then buffer the data and send it when network connection can be established);
Since I’ll be using another application for navigating, my tracker must be able to run while being on background.
Tutorials and examples
There are plenty of great examples out there. Unfortunately they didn’t help me with the third point of my “functional requirements”. Most of the examples stopped when navigating to Desktop or opening the ‘Overview’ screen. I looked through background services, using pendingIntents, created custom locationListeners etc, but nothing seemed to work.
Root of the problem
Android Developers site has an articale called “”, that reveals the cause of this behaviour: “In an effort to reduce power consumption, Android 8.0 (API level 26) limits how frequently background apps can retrieve the user’s current location. Apps can receive location updates only a few times each hour.”. Or in other words: don’t use background services for location services if you need frequent location update as I did!
Solution
How ever — this doesn’t mean that there is no solution: applications like Google Maps etc still use your location while being on the background, so there has to be a solution. The same page gives you some hints:
An app is considered to be in the foreground if any of the following is true:* It has a visible activity, whether the activity is started or paused.* It has a foreground service.* Another foreground app is connected to the app /../
So as a solution: create a foreground service!
Some say that it is possible to bind the service as a foreground service as follows:
final Intent intent = new Intent(this.getApplication(), BackgroundService.class);this.getApplication().startForegroundService(intent);this.getApplication().bindService(intent, serviceConnection, Context.BIND_AUTO_CREATE);
Well, for some reason this didn’t work. So I took a different approach. I created a notification generator
private Notification getNotification() {NotificationChannel channel = new NotificationChannel(“channel_01”,“My Channel”,NotificationManager.IMPORTANCE_DEFAULT);
NotificationManager notificationManager = getSystemService(NotificationManager.class);notificationManager.createNotificationChannel(channel);Notification.Builder builder = new Notification.Builder(getApplicationContext(), “channel_01”);
return builder.build();}and added the following to my service’s onCreate() method:
public void onCreate() {startForeground(12345678, getNotification());}
and Voila: the application works as needed. Even when sending the Application to the background for a longer period of time, it still fetches the coordinates and is able to deal with them.
The full PoC application can be found . NB! Be aware, that Notification channel is not needed before Android 8.0 (API level 26).