2

我在使用PendingIntent獲取Location後理解最佳方法reference to my old postPendingIntent正如我所需。但它總是將位置返回爲空。使用PendingIntent提取位置返回空值始終爲空

Intent intent = new Intent(this, LocationReceiver.class); 
PendingIntent locationIntent = PendingIntent.getBroadcast(getApplicationContext(), 0, intent, PendingIntent.FLAG_CANCEL_CURRENT); 
LocationServices.FusedLocationApi.requestLocationUpdates(googleApiClient, locationRequest, locationIntent); 

在LocationReceiver(廣播接收器類),

public class LocationReceiver extends WakefulBroadcastReceiver { 

@Override 
public void onReceive(Context context, Intent intent) { 
    Log.i("LocationReceiver", "OnReceive"); 
    Location location = (Location) intent.getExtras().get(LocationManager.KEY_LOCATION_CHANGED); 
    if (location != null) { 
     double lat = location.getLatitude(); 
     double lng = location.getLongitude(); 

     Log.i("LocationReceiver", lat + ", " + lng); 
    } else { 
     Log.i("LocationReceiver", "Location is null"); 
    } 

    LocationReceiver.completeWakefulIntent(intent); 
    } 
} 

其他信息,

使用GooglePlayService 8.3.0buildToolVersion 23.0.2

我想知道在什麼情況下是它返回null !任何幫助將不勝感激!

編輯:清單

<uses-permission android:name="android.permission.INTERNET" /> 
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" /> 
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" /> 
<uses-permission android:name="android.permission.ACCESS_COARSE_LOCATION" /> 
<uses-permission android:name="android.permission.ACCESS_FINE_LOCATION" /> 
<uses-permission android:name="android.permission.READ_PHONE_STATE" /> 
<uses-permission android:name="com.google.android.providers.gsf.permission.READ_GSERVICES" /> 

<uses-feature 
    android:glEsVersion="0x00020000" 
    android:required="true" /> 

<application 
    android:name="package.ApplicationClass" 
    android:allowBackup="true" 
    android:icon="@mipmap/ic_launcher" 
    android:label="@string/app_name" 
    android:theme="@style/AppTheme"> 
    <activity 
     android:name=".activity.SplashScreen" 
     android:label="@string/app_name" 
     android:theme="@style/AppTheme.NoActionBar"> 
     <intent-filter> 
      <action android:name="android.intent.action.MAIN" /> 

      <category android:name="android.intent.category.LAUNCHER" /> 
     </intent-filter> 
    </activity> 

    <meta-data 
     android:name="com.google.android.gms.version" 
     android:value="@integer/google_play_services_version" /> 
    <meta-data 
     android:name="com.google.android.maps.v2.API_KEY" 
     android:value="@string/google_maps_key" /> 

    <activity 
     android:name=".activity.MapsActivity" 
     android:label="@string/app_name" 
     android:theme="@style/AppTheme.MapsActivity" /> 
    <activity 
     android:name=".activity.LoginActivity" 
     android:label="@string/title_activity_login" 
     android:theme="@style/AppTheme.NoActionBar" /> 

    <receiver android:name=".receiver.LocationReceiver"/> 

</application> 
</manifest> 

閃屏

public class SplashScreen extends AppCompatActivity implements GoogleApiClient.ConnectionCallbacks, 
    GoogleApiClient.OnConnectionFailedListener, ResultCallback<LocationSettingsResult>, 
    LocationListener { 

public static final long UPDATE_INTERVAL_IN_MILLISECONDS = 10000; 
public static final long FASTEST_UPDATE_INTERVAL_IN_MILLISECONDS = 
     UPDATE_INTERVAL_IN_MILLISECONDS/2; 

protected static final int REQUEST_CHECK_SETTINGS = 0x1; 
private final static String TAG = "SplashScreen"; 

protected Boolean mRequestingLocationUpdates; 

protected Location mCurrentLocation; 

protected GoogleApiClient googleApiClient; 
protected LocationSettingsRequest locationSettingsRequest; 
protected LocationRequest locationRequest; 

/** 
* Initialize GoogleApiClient Builder to fetch required Google Services 
*/ 
protected synchronized void buildGoogleApiClient() { 
    googleApiClient = new GoogleApiClient.Builder(this) 
      .addConnectionCallbacks(this) 
      .addOnConnectionFailedListener(this) 
      .addApi(LocationServices.API) 
      .build(); 
} 


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

    mRequestingLocationUpdates = false; 

    buildGoogleApiClient(); 

    createLocationRequest(); 

    buildLocationSettingsRequest(); 

    checkLocationSettings(); 
} 

@Override 
protected void onStart() { 
    super.onStart(); 

    // Establish the connection to GoogleApiClient 
    googleApiClient.connect(); 
} 

@Override 
protected void onResume() { 
    super.onResume(); 

    if (googleApiClient.isConnected() && mRequestingLocationUpdates) { 
     startLocationUpdates(); 
    } else 
     Log.i(TAG, "onResume - Failed"); 
} 

protected void createLocationRequest() { 
    locationRequest = new LocationRequest(); 

    locationRequest.setInterval(UPDATE_INTERVAL_IN_MILLISECONDS); 
     locationRequest.setFastestInterval(FASTEST_UPDATE_INTERVAL_IN_MILLISECONDS); 

    locationRequest.setPriority(LocationRequest.PRIORITY_HIGH_ACCURACY); 
} 

protected void buildLocationSettingsRequest() { 
    LocationSettingsRequest.Builder builder = new LocationSettingsRequest.Builder(); 
    builder.addLocationRequest(locationRequest); 
    builder.setAlwaysShow(true); 
    locationSettingsRequest = builder.build(); 
} 

protected void checkLocationSettings() { 
    PendingResult<LocationSettingsResult> result = 
      LocationServices.SettingsApi.checkLocationSettings(
        googleApiClient, 
        locationSettingsRequest); 
    result.setResultCallback(this); 
} 

@Override 
public void onConnected(Bundle bundle) { 

    if (mCurrentLocation == null) 
     mCurrentLocation = LocationServices.FusedLocationApi.getLastLocation(googleApiClient); 
} 

private void validateUserAndProcess() { 
    boolean isExistingUser = false; 
    try { 
     isExistingUser = (boolean) ApplicationClass.mSharedPreferenceOperation.getData(
       getString(R.string.is_existing_user), SharedPreferenceOperation.BOOLEAN); 
    } catch (Exception e) { 
     e.printStackTrace(); 
    } 

    if (isExistingUser) { 
     Intent intent = new Intent(this, MapsActivity.class); 
     startActivity(intent); 
     finish(); 
    } else { 
     int currentApiVersion = Build.VERSION.SDK_INT; 

     TelephonyManager telephonyManager = (TelephonyManager) getSystemService(Context.TELEPHONY_SERVICE); 
     String deviceId = telephonyManager.getDeviceId(); 

     Intent intent = new Intent(this, LoginActivity.class); 
     intent.putExtra(getString(R.string.intent_extra_user_imei), deviceId); 
     intent.putExtra(getString(R.string.intent_extra_user_android_api), currentApiVersion); 
     startActivity(intent); 
     finish(); 
    } 
} 


@Override 
public void onConnectionSuspended(int cause) { 

    // In case of connection is suspended. 
    switch (cause) { 
     case CAUSE_NETWORK_LOST: 
      Toast.makeText(this, "Connection Suspended due to Network Lost", Toast.LENGTH_LONG).show(); 
      break; 
     case CAUSE_SERVICE_DISCONNECTED: 
      Toast.makeText(this, "Connection Suspended due to Service Disconnection", Toast.LENGTH_LONG).show(); 
      break; 
     default: 
      Toast.makeText(this, "Connection Suspended due to Unknown Issue", Toast.LENGTH_LONG).show(); 
      break; 
    } 
} 

@Override 
public void onConnectionFailed(ConnectionResult connectionResult) { 
    Toast.makeText(this, "Failed to connect due to " + connectionResult.getErrorCode(), Toast.LENGTH_LONG).show(); 
} 

@Override 
public void onResult(LocationSettingsResult locationSettingsResult) { 
    final Status status = locationSettingsResult.getStatus(); 
    switch (status.getStatusCode()) { 
     case LocationSettingsStatusCodes.SUCCESS: 
      // Start Location Updates 
      startLocationUpdates(); 
      break; 
     case LocationSettingsStatusCodes.RESOLUTION_REQUIRED: 
      try { 
       // Show the dialog by calling startResolutionForResult(), and check the result 
       // in onActivityResult(). 
       status.startResolutionForResult(SplashScreen.this, REQUEST_CHECK_SETTINGS); 
      } catch (IntentSender.SendIntentException e) { 
       e.printStackTrace(); 
      } 
      break; 
     case LocationSettingsStatusCodes.SETTINGS_CHANGE_UNAVAILABLE: 
      Log.i(TAG, "Location settings are inadequate, and cannot be fixed here. Dialog " + 
        "not created."); 
      break; 
    } 
} 

@Override 
protected void onActivityResult(int requestCode, int resultCode, Intent data) { 
    super.onActivityResult(requestCode, resultCode, data); 

    switch (requestCode) { 
     // Check for the integer request code originally supplied to startResolutionForResult(). 
     case REQUEST_CHECK_SETTINGS: 
      switch (resultCode) { 
       case Activity.RESULT_OK: 
        // Start Location Updates 
        startLocationUpdates(); 
        break; 
       case Activity.RESULT_CANCELED: 
        finish(); 
        break; 
      } 
      break; 
    } 
} 

@Override 
public void onLocationChanged(Location location) { 
    mCurrentLocation = location; 

    Intent intent = new Intent(this, LocationReceiver.class); 
    PendingIntent locationIntent = PendingIntent.getBroadcast(getApplicationContext(), 0, intent, PendingIntent.FLAG_CANCEL_CURRENT); 
    LocationServices.FusedLocationApi.requestLocationUpdates(googleApiClient, locationRequest, locationIntent); 

    if (mCurrentLocation != null) { 

     ApplicationClass.LATITUDE = mCurrentLocation.getLatitude(); 
     ApplicationClass.LONGITUDE = mCurrentLocation.getLongitude(); 

     validateUserAndProcess(); 
    } 
} 

/** 
* Requests location updates from the FusedLocationApi. 
*/ 
protected void startLocationUpdates() { 
    LocationServices.FusedLocationApi.requestLocationUpdates(googleApiClient, locationRequest, 
      this).setResultCallback(new ResultCallback<Status>() { 
     @Override 
     public void onResult(Status status) { 
      mRequestingLocationUpdates = true; 
     } 
    }); 

    Log.i(TAG, "startLocationUpdates Invoked"); 
} 

@Override 
protected void onStop() { 
    super.onStop(); 
    //googleApiClient.disconnect(); 
} 

@Override 
protected void onPause() { 
    super.onPause(); 

    // Stop location updates to save battery, but don't disconnect the GoogleApiClient object. 
    /**if (googleApiClient.isConnected()) { 
     stopLocationUpdates(); 
    }*/ 
} 

/** 
* Removes location updates from the FusedLocationApi. 
*/ 
protected void stopLocationUpdates() { 
    LocationServices.FusedLocationApi.removeLocationUpdates(googleApiClient, this) 
      .setResultCallback(new ResultCallback<Status>() { 
       @Override 
       public void onResult(Status status) { 
        mRequestingLocationUpdates = false; 
       } 
      }); 
    } 
} 
+0

你確信,當它requestLocationUpdates的GoogleApiClient連接()? locationRequest都很好? – cgr

+0

是的,在SplashScreen活動中,我連接到'GoogleApiClient'並獲取位置,之後我註冊'PendingIntent'並完成活動。在完成活動時,我停止位置更新並斷開「GoogleApiClient」。我認爲斷開連接導致問題,所以刪除斷開部分和測試,但仍然收到相同的錯誤。 –

+0

1.您是否刪除了停止位置更新以及刪除diconnecting google api客戶端部分? – cgr

回答

0

的第一件事是要傳遞錯誤的鍵從額外獲得Location

通過這個鍵:com.google.android.location.LOCATION

我正確讀取你的問題,我也讀了answer我建議,正常。

我認爲這會幫助你解決你的問題。

請參考此答案:CLICK HERE