The sample source code from google was to easy to implement continuous location updates on frontend, but I still can;t get or understand clearly how the background location updates work using FusedLocationApi and PendingIntent.
LocationService class:
public class LocationService extends IntentService {
private static final String TAG = LocationService.class.getSimpleName();
private static final String ACTION_LOCATION_UPDATED = "location_updated";
private static final String ACTION_REQUEST_LOCATION = "request_location";
public static IntentFilter getLocationUpdatedIntentFilter() {
return new IntentFilter(LocationService.ACTION_LOCATION_UPDATED);
}
public static void requestLocation(Context context) {
Intent intent = new Intent(context, LocationService.class);
intent.setAction(LocationService.ACTION_REQUEST_LOCATION);
context.startService(intent);
}
public LocationService() {
super(TAG);
}
@Override
protected void onHandleIntent(Intent intent) {
String action = intent != null ? intent.getAction() : null;
if (ACTION_REQUEST_LOCATION.equals(action)) {
onRequestLocation();
}
else if(ACTION_LOCATION_UPDATED.equals(action)) {
onLocationUpdated(intent);
}
}
/**
* Called when a location update is requested. We block until we get a result back.
* We are using Fused Location Api.
*/
private void onRequestLocation() {
Log.v(TAG, ACTION_REQUEST_LOCATION);
GoogleApiClient googleApiClient = new GoogleApiClient.Builder(this)
.addApi(LocationServices.API)
.build();
// we block here
ConnectionResult connectionResult = googleApiClient.blockingConnect(10, TimeUnit.SECONDS);
if (connectionResult.isSuccess() && googleApiClient.isConnected()) {
Intent locationUpdatedIntent = new Intent(this, LocationService.class);
locationUpdatedIntent.setAction(ACTION_LOCATION_UPDATED);
// Send last known location out first if available
Location location = FusedLocationApi.getLastLocation(googleApiClient);
if (location != null) {
Intent lastLocationIntent = new Intent(locationUpdatedIntent);
lastLocationIntent.putExtra(
FusedLocationProviderApi.KEY_LOCATION_CHANGED, location);
startService(lastLocationIntent);
}
// Request new location
LocationRequest mLocationRequest = new LocationRequest()
.setPriority(LocationRequest.PRIORITY_HIGH_ACCURACY);
FusedLocationApi.requestLocationUpdates(
googleApiClient, mLocationRequest,
PendingIntent.getService(this, 0, locationUpdatedIntent, 0));
googleApiClient.disconnect();
} else {
Log.e(TAG, String.format("Failed to connect to GoogleApiClient (error code = %d)",
connectionResult.getErrorCode()));
}
}
/**
* Called when the location has been updated & broadcast the new location
*/
private void onLocationUpdated(Intent intent) {
Log.v(TAG, ACTION_LOCATION_UPDATED);
// Extra new location
Location location =
intent.getParcelableExtra(FusedLocationProviderApi.KEY_LOCATION_CHANGED);
if (location != null) {
LatLng latLngLocation = new LatLng(location.getLatitude(), location.getLongitude());
LocalBroadcastManager.getInstance(this).sendBroadcast(intent);
}
}
}
MainActivity The code looks messy so I will share the code in a drive link: https://drive.google.com/open?id=0B7QMYFlbkUpOVjkxMUtfenRLXzA
However, I have followed the example from https://gist.githubusercontent.com/allenchi/c9659369c306752c0047/raw/16d6cd8e311013379e55b496d2b6d13347f418d6/gistfile1.txt
The following part in the example is what I just cannot understand placement in MainActivity. How do I receive location updates using Broadcast receiver? I would also require a clean understanding of FusedLocation running in background and how I can utilize to get an on the fly gps tracker implemented.
@Override
protected void onResume() {
super.onResume();
if(checkPlayServices()) {
LocationService.requestLocation(this);
LocalBroadcastManager.getInstance(getActivity())
.registerReceiver(locationReceiver, LocationService.getLocationUpdatedIntentFilter());
}
}
@Override
public void onResume() {
super.onResume();
LocalBroadcastManager.getInstance(getActivity()).registerReceiver(
locationReceiver, LocationService.getLocationUpdatedIntentFilter());
}
@Override
public void onPause() {
super.onPause();
LocalBroadcastManager.getInstance(getActivity()).unregisterReceiver(locationReceiver);
}
private BroadcastReceiver locationReceiver = new BroadcastReceiver() {
@Override
public void onReceive(Context context, Intent intent) {
Location location = intent.getParcelableExtra(FusedLocationProviderApi.KEY_LOCATION_CHANGED);
if (location != null) {
LatLng latestLocation = new LatLng(location.getLatitude(), location.getLongitude());
// do something with the location
}
}
};