2015-11-16 10 views
5

Der Beispiel-Quelltext von Google war einfach zu implementieren kontinuierliche Standortaktualisierungen am Frontend, aber ich kann noch nicht klar, wie die Hintergrund Standortaktualisierungen mit FusedLocationApi und PendingIntent funktionieren.FusedLocationApi mit PendingIntent für Aktualisierungen des Hintergrundstandorts. Unfähig, Updates zu erhalten

LocationService Klasse:

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 Der Code chaotisch sieht so werde ich den Code in ein Laufwerk Link teilen: https://drive.google.com/open?id=0B7QMYFlbkUpOVjkxMUtfenRLXzA

Allerdings habe ich das Beispiel von https://gist.githubusercontent.com/allenchi/c9659369c306752c0047/raw/16d6cd8e311013379e55b496d2b6d13347f418d6/gistfile1.txt

gefolgt

Der folgende Teil im Beispiel ist, was ich einfach nicht verstehen kann Platzierung in MainActivity. Wie erhalte ich Standort-Updates mit dem Broadcast-Empfänger? Ich würde auch ein sauberes Verständnis von FusedLocation erfordern, das im Hintergrund läuft und wie ich verwenden kann, um einen On-The-Fly-GPS-Tracker zu implementieren.

@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 
     } 
    } 
}; 

Antwort

4

Im Beispiel unten können Sie die Lage-Updates erhalten, wenn die App alle 5 Sekunden mit dem PRIORITY_HIGH_ACCURACY Modus im Hintergrund ausgeführt wird. Sie werden diese Updates sehen, indem Sie Benachrichtigungen erhalten, die die Koordinaten Ihres Standorts angeben.

Ich wollte auch, ob die Updates testen, erhalten werden kann, nachdem die App vom System getötet wurde, wie es here heißt:

public abstract PendingResult requestLocationUpdates (GoogleApiClient Client, Location Anfrage, PendingIntent callbackIntent)

Diese Methode eignet sich für Anwendungsfälle im Hintergrund, genauer gesagt für das Empfangen von Standortaktualisierungen, , auch wenn die App vom System getötet wurde. Verwenden Sie dazu einen PendingIntent für einen gestarteten Dienst.

Deshalb habe ich die System.exit (0) in der onBackPressed() Methode der Aktivität aufgerufen, die Sie natürlich weglassen können.

Der Service:

public class LocationService extends IntentService{ 

private static final String INTENT_SERVICE_NAME = LocationService.class.getName(); 

public LocationService() { 
    super(INTENT_SERVICE_NAME); 
} 

@Override 
protected void onHandleIntent(Intent intent) { 
    if (null == intent) { 
     return; 
    } 

    Bundle bundle = intent.getExtras(); 

    if (null == bundle) { 
     return; 
    } 

    Location location = bundle.getParcelable("com.google.android.location.LOCATION"); 

    if (null == location) { 
     return; 
    } 

    if (null != location) { 
     // TODO: Handle the incoming location 

     Log.i(INTENT_SERVICE_NAME, "onHandleIntent " + location.getLatitude() + ", " + location.getLongitude()); 

     // Just show a notification with the location's coordinates 
     NotificationManager notificationManager = (NotificationManager)getSystemService(NOTIFICATION_SERVICE); 
     NotificationCompat.Builder notification = new NotificationCompat.Builder(this); 
     notification.setContentTitle("Location"); 
     notification.setContentText(location.getLatitude() + ", " + location.getLongitude()); 
     notification.setSmallIcon(R.drawable.ic_audiotrack); 
     notificationManager.notify(1234, notification.build()); 
    } 
} 

}

Die Aktivität:

public class MainActivity extends Activity implements GoogleApiClient.ConnectionCallbacks, 
    GoogleApiClient.OnConnectionFailedListener{ 

private GoogleApiClient googleApiClient; 

@Override 
protected void onCreate(Bundle savedInstanceState) { 
    super.onCreate(savedInstanceState); 
    setContentView(R.layout.activity_main); 

    googleApiClient = new GoogleApiClient.Builder(this) 
      .addApi(LocationServices.API) 
      .addConnectionCallbacks(this) 
      .addOnConnectionFailedListener(this) 
      .build(); 

} 

@Override 
public void onStart() { 
    super.onStart(); 
    googleApiClient.connect(); 
} 

@Override 
public void onStop() { 
    super.onStop(); 
    if (googleApiClient.isConnected()) { 
     googleApiClient.disconnect(); 
    } 
} 

@Override 
public void onBackPressed() { 
    // Check whether you receive location updates after the app has been killed by the system 
    System.exit(0); 
} 

@Override 
public void onConnected(Bundle bundle) { 
    requestLocationUpdates(); 
} 

@Override 
public void onConnectionSuspended(int cause) { 
    googleApiClient.connect(); 
} 

@Override 
public void onConnectionFailed(ConnectionResult result) { 

} 

public void requestLocationUpdates() { 
    LocationRequest locationRequest = new LocationRequest() 
      .setInterval(5 * 1000) 
      .setPriority(LocationRequest.PRIORITY_HIGH_ACCURACY); 

    Intent intent = new Intent(this, LocationService.class); 
    PendingIntent pendingIntent = PendingIntent.getService(this, 0, intent, PendingIntent.FLAG_UPDATE_CURRENT); 
    LocationServices.FusedLocationApi.requestLocationUpdates(googleApiClient, locationRequest, pendingIntent); 
} 

}

Die Erlaubnis im Manifest:

<uses-permission android:name="android.permission.ACCESS_FINE_LOCATION"/>