Try to check if GPS is enabled on SDK 25.
Do this:
LocationManager manager = (LocationManager)
view.getContext().getSystemService(Context.LOCATION_SERVICE);
boolean isGpsEnabled =
manager.isProviderEnabled(LocationManager.GPS_PROVIDER);
it always returns false. Then I start startActivityForResult as:
view.getFragment().startActivityForResult(intent,
Constants.GPS_ENABLE);
this opens me settings windows, I swtich GPS on, push back button, go back to fragment and got:
1. On Activity Result responsecode 0 (always)
2. GPS enabled checking again say "false", as it is not enabled.
Moreover, I tried this:
String provider =
Secure.getString(view.getContext().getContentResolver(),
Settings.Secure.LOCATION_PROVIDERS_ALLOWED);
if(!provider.contains("gps")){}
And as google tutorial says task.locationsettings.
All tries always say GPS disabled and onActivityResult always 0.
I need both: know when GPS enabled/disaabled and recieve correct resultCode in onActivityResult(onActivityResult is called in Fragment and it is called succesfully, but with wrong responseCode in it)
What I do wrong?
UPDATE
#Override
public void onActivityResult(int requestCode, int resultCode, Intent data) {
super.onActivityResult(requestCode, resultCode, data);
Log.e("ACTIVITY RESULT", "RqC:" + requestCode + "; ReSC" + resultCode);
if (requestCode == Constants.GPS_ENABLE && resultCode == RESULT_OK) {
presenter.getGPS();
} else {
Log.e("ON ACTIVITY RESULT", "Не дал мне прав");
}
}
public void onPermissionResult(int requestCode, String[] permissions, int[] grantResults) {
switch (requestCode) {
case Constants.GPS_PERMISSION:
if (grantResults.length > 0 && grantResults[0] == PackageManager.PERMISSION_GRANTED) {
getGPS();
}
default:
requestPermissions();
}
}
public void checkGpsEnabled(String caller) {
Log.e("I AM CALLED FROM", caller);
LocationManager manager = (LocationManager) view.getContext().getSystemService(Context.LOCATION_SERVICE);
boolean isGpsEnabled = manager.isProviderEnabled(LocationManager.GPS_PROVIDER);
if (isGpsEnabled) {
Log.e("CheckGPSENABLED", "Включен");
getGPS();
} else {
Log.e("CheckGPSENABLED", "ВЫЫЫключен");
Toast.makeText(view.getContext(), "Для продолжения работы приложения, пожалуйста, включите GPS", Toast.LENGTH_SHORT).show();
Intent intent = new Intent(Settings.ACTION_LOCATION_SOURCE_SETTINGS);
view.getFragment().startActivityForResult(intent, Constants.GPS_ENABLE);
}
}
#SuppressLint("MissingPermission")
public void getGPS() {
Log.e(getClass().getName(), "getGPSFUSE");
mFusedLocationClient = LocationServices.getFusedLocationProviderClient(view.getViewActivity());
mFusedLocationClient.getLastLocation()
.addOnSuccessListener(view.getViewActivity(), location -> {
if (location != null) {
Log.e("LOCATION", location.toString());
//Если получил координаты, вернуть
} else {
requestNewLocation();
}
});
}
#SuppressLint("MissingPermission")
public void requestNewLocation() {
Log.e(getClass().getName(), "request new location");
mLocationRequest = new LocationRequest();
mLocationCallback = new LocationCallback() {
#Override
public void onLocationResult(LocationResult locationResult) {
if (locationResult == null) {
Toast.makeText(view.getContext(), "Координаты не найдены", Toast.LENGTH_SHORT).show();
return;
}
for (Location location : locationResult.getLocations()) {
Log.e("NEW", location.toString());
}
}
};
mFusedLocationClient.requestLocationUpdates(mLocationRequest,
mLocationCallback,
null /* Looper */);
}
}
public void requestPermissions() {
if (ActivityCompat.checkSelfPermission(view.getContext(), Manifest.permission.ACCESS_FINE_LOCATION) != PackageManager.PERMISSION_GRANTED
|| ActivityCompat.checkSelfPermission(view.getContext(), Manifest.permission.ACCESS_COARSE_LOCATION) != PackageManager.PERMISSION_GRANTED) {
ActivityCompat.requestPermissions(view.getViewActivity(), new String[]{
Manifest.permission.ACCESS_FINE_LOCATION, Manifest.permission.ACCESS_COARSE_LOCATION,
Manifest.permission.INTERNET}, Constants.GPS_PERMISSION);
} else {
checkGpsEnabled("request");
}
}
I think you are too much confused in using FusedLocation API and GPS etc. Also in your question code snippet I dont see where you are acquiring runtime permission from user since your build target is 25. So you need to ask for some permissions. Like location permissions. here is a link of runtime permissions
Your manifest must contain these permissions and you must acquire run time permissions.
<uses-permission android:name="android.permission.INTERNET" />
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />
<uses-permission android:name="android.permission.ACCESS_COARSE_LOCATION" />
<uses-permission android:name="android.permission.ACCESS_FINE_LOCATION" />
Here the below code is for a quick over view. This snippet is taken from this link. And I think this link is also good for you.
public class MainActivity extends AppCompatActivity implements GoogleApiClient.ConnectionCallbacks,
GoogleApiClient.OnConnectionFailedListener,
LocationListener {
protected static final String TAG = "location-updates-sample";
public static final long UPDATE_INTERVAL_IN_MILLISECONDS = 10000;
public static final long FASTEST_UPDATE_INTERVAL_IN_MILLISECONDS =
UPDATE_INTERVAL_IN_MILLISECONDS / 2;
private final static String REQUESTING_LOCATION_UPDATES_KEY = "requesting-location-updates-key";
private final static String LOCATION_KEY = "location-key";
private final static String LAST_UPDATED_TIME_STRING_KEY = "last-updated-time-string-key";
private static final int PERMISSIONS_REQUEST_ACCESS_FINE_LOCATION = 1;
private static final int REQUEST_CHECK_SETTINGS = 10;
private ActivityMainBinding mBinding;
private GoogleApiClient mGoogleApiClient;
private LocationRequest mLocationRequest;
private Location mCurrentLocation;
private Boolean mRequestingLocationUpdates;
private String mLastUpdateTime;
private String mLatitudeLabel;
private String mLongitudeLabel;
private String mLastUpdateTimeLabel;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
mBinding = DataBindingUtil.setContentView(this, R.layout.activity_main);
mLatitudeLabel = getResources().getString(R.string.latitude_label);
mLongitudeLabel = getResources().getString(R.string.longitude_label);
mLastUpdateTimeLabel = getResources().getString(R.string.last_update_time_label);
mRequestingLocationUpdates = false;
mLastUpdateTime = "";
updateValuesFromBundle(savedInstanceState);
buildGoogleApiClient();
}
private void updateValuesFromBundle(Bundle savedInstanceState) {
Log.i(TAG, "Updating values from bundle");
if (savedInstanceState != null) {
if (savedInstanceState.keySet().contains(REQUESTING_LOCATION_UPDATES_KEY)) {
mRequestingLocationUpdates = savedInstanceState.getBoolean(
REQUESTING_LOCATION_UPDATES_KEY);
setButtonsEnabledState();
}
if (savedInstanceState.keySet().contains(LOCATION_KEY)) {
mCurrentLocation = savedInstanceState.getParcelable(LOCATION_KEY);
}
if (savedInstanceState.keySet().contains(LAST_UPDATED_TIME_STRING_KEY)) {
mLastUpdateTime = savedInstanceState.getString(LAST_UPDATED_TIME_STRING_KEY);
}
updateUI();
}
}
protected synchronized void buildGoogleApiClient() {
Log.i(TAG, "Building GoogleApiClient");
mGoogleApiClient = new GoogleApiClient.Builder(this)
.addConnectionCallbacks(this)
.addOnConnectionFailedListener(this)
.addApi(LocationServices.API)
.build();
createLocationRequest();
}
protected void createLocationRequest() {
mLocationRequest = new LocationRequest();
mLocationRequest.setInterval(UPDATE_INTERVAL_IN_MILLISECONDS);
mLocationRequest.setFastestInterval(FASTEST_UPDATE_INTERVAL_IN_MILLISECONDS);
mLocationRequest.setPriority(LocationRequest.PRIORITY_HIGH_ACCURACY);
}
public void startUpdatesButtonHandler(View view) {
clearUI();
if (!isPlayServicesAvailable(this)) return;
if (!mRequestingLocationUpdates) {
mRequestingLocationUpdates = true;
} else {
return;
}
if (Build.VERSION.SDK_INT < 23) {
setButtonsEnabledState();
startLocationUpdates();
return;
}
if (ContextCompat.checkSelfPermission(this, Manifest.permission.ACCESS_FINE_LOCATION) == PackageManager.PERMISSION_GRANTED) {
setButtonsEnabledState();
startLocationUpdates();
} else {
if (ActivityCompat.shouldShowRequestPermissionRationale(this, android.Manifest.permission.ACCESS_FINE_LOCATION)) {
showRationaleDialog();
} else {
ActivityCompat.requestPermissions(this, new String[]{android.Manifest.permission.ACCESS_FINE_LOCATION}, PERMISSIONS_REQUEST_ACCESS_FINE_LOCATION);
}
}
}
public void stopUpdatesButtonHandler(View view) {
if (mRequestingLocationUpdates) {
mRequestingLocationUpdates = false;
setButtonsEnabledState();
stopLocationUpdates();
}
}
private void startLocationUpdates() {
Log.i(TAG, "startLocationUpdates");
LocationSettingsRequest.Builder builder = new LocationSettingsRequest.Builder()
.addLocationRequest(mLocationRequest);
PendingResult<LocationSettingsResult> result =
LocationServices.SettingsApi.checkLocationSettings(mGoogleApiClient, builder.build());
result.setResultCallback(new ResultCallback<LocationSettingsResult>() {
#Override
public void onResult(#NonNull LocationSettingsResult locationSettingsResult) {
final Status status = locationSettingsResult.getStatus();
switch (status.getStatusCode()) {
case LocationSettingsStatusCodes.SUCCESS:
if (ContextCompat.checkSelfPermission(MainActivity.this, Manifest.permission.ACCESS_FINE_LOCATION) == PackageManager.PERMISSION_GRANTED) {
LocationServices.FusedLocationApi.requestLocationUpdates(mGoogleApiClient, mLocationRequest, MainActivity.this);
}
break;
case LocationSettingsStatusCodes.RESOLUTION_REQUIRED:
try {
status.startResolutionForResult(MainActivity.this, REQUEST_CHECK_SETTINGS);
} catch (IntentSender.SendIntentException e) {
// Ignore the error.
}
break;
case LocationSettingsStatusCodes.SETTINGS_CHANGE_UNAVAILABLE:
// Location settings are not satisfied. However, we have no way
// to fix the settings so we won't show the dialog.
break;
}
}
});
}
private void setButtonsEnabledState() {
if (mRequestingLocationUpdates) {
mBinding.startUpdatesButton.setEnabled(false);
mBinding.stopUpdatesButton.setEnabled(true);
} else {
mBinding.startUpdatesButton.setEnabled(true);
mBinding.stopUpdatesButton.setEnabled(false);
}
}
private void clearUI() {
mBinding.latitudeText.setText("");
mBinding.longitudeText.setText("");
mBinding.lastUpdateTimeText.setText("");
}
private void updateUI() {
if (mCurrentLocation == null) return;
mBinding.latitudeText.setText(String.format("%s: %f", mLatitudeLabel,
mCurrentLocation.getLatitude()));
mBinding.longitudeText.setText(String.format("%s: %f", mLongitudeLabel,
mCurrentLocation.getLongitude()));
mBinding.lastUpdateTimeText.setText(String.format("%s: %s", mLastUpdateTimeLabel,
mLastUpdateTime));
}
protected void stopLocationUpdates() {
Log.i(TAG, "stopLocationUpdates");
// The final argument to {#code requestLocationUpdates()} is a LocationListener
// (http://developer.android.com/reference/com/google/android/gms/location/LocationListener.html).
LocationServices.FusedLocationApi.removeLocationUpdates(mGoogleApiClient, this);
}
#Override
public void onRequestPermissionsResult(int requestCode, String permissions[], int[] grantResults) {
switch (requestCode) {
case PERMISSIONS_REQUEST_ACCESS_FINE_LOCATION: {
if (grantResults.length > 0 && grantResults[0] == PackageManager.PERMISSION_GRANTED) {
setButtonsEnabledState();
startLocationUpdates();
} else {
if (!ActivityCompat.shouldShowRequestPermissionRationale(this, Manifest.permission.ACCESS_FINE_LOCATION)) {
mRequestingLocationUpdates = false;
Toast.makeText(MainActivity.this, "このアプリの機能を有効にするには端末の設定画面からアプリの位置情報パーミッションを有効にして下さい。", Toast.LENGTH_SHORT).show();
} else {
showRationaleDialog();
}
}
break;
}
}
}
private void showRationaleDialog() {
new AlertDialog.Builder(this)
.setPositiveButton("許可する", new DialogInterface.OnClickListener() {
#Override
public void onClick(DialogInterface dialog, int which) {
ActivityCompat.requestPermissions(MainActivity.this,
new String[]{android.Manifest.permission.ACCESS_FINE_LOCATION}, PERMISSIONS_REQUEST_ACCESS_FINE_LOCATION);
}
})
.setNegativeButton("しない", new DialogInterface.OnClickListener() {
#Override
public void onClick(DialogInterface dialog, int which) {
Toast.makeText(MainActivity.this, "位置情報パーミッションが許可されませんでした。", Toast.LENGTH_SHORT).show();
mRequestingLocationUpdates = false;
}
})
.setCancelable(false)
.setMessage("このアプリは位置情報の利用を許可する必要があります。")
.show();
}
public static boolean isPlayServicesAvailable(Context context) {
// Google Play Service APKが有効かどうかチェックする
int resultCode = GoogleApiAvailability.getInstance().isGooglePlayServicesAvailable(context);
if (resultCode != ConnectionResult.SUCCESS) {
GoogleApiAvailability.getInstance().getErrorDialog((Activity) context, resultCode, 2).show();
return false;
}
return true;
}
#Override
public void onActivityResult(int requestCode, int resultCode, Intent data) {
switch (requestCode) {
case REQUEST_CHECK_SETTINGS:
switch (resultCode) {
case Activity.RESULT_OK:
startLocationUpdates();
break;
case Activity.RESULT_CANCELED:
break;
}
break;
}
}
#Override
protected void onStart() {
super.onStart();
mGoogleApiClient.connect();
}
#Override
public void onResume() {
super.onResume();
isPlayServicesAvailable(this);
// Within {#code onPause()}, we pause location updates, but leave the
// connection to GoogleApiClient intact. Here, we resume receiving
// location updates if the user has requested them.
if (mGoogleApiClient.isConnected() && mRequestingLocationUpdates) {
startLocationUpdates();
}
}
#Override
protected void onPause() {
super.onPause();
// Stop location updates to save battery, but don't disconnect the GoogleApiClient object.
if (mGoogleApiClient.isConnected()) {
stopLocationUpdates();
}
}
#Override
protected void onStop() {
stopLocationUpdates();
mGoogleApiClient.disconnect();
super.onStop();
}
#Override
protected void onDestroy() {
super.onDestroy();
}
#Override
public void onConnected(#Nullable Bundle bundle) {
Log.i(TAG, "onConnected");
if (ActivityCompat.checkSelfPermission(this, Manifest.permission.ACCESS_FINE_LOCATION) != PackageManager.PERMISSION_GRANTED) {
return;
}
if (mCurrentLocation == null) {
mCurrentLocation = LocationServices.FusedLocationApi.getLastLocation(mGoogleApiClient);
mLastUpdateTime = DateFormat.getTimeInstance().format(new Date());
updateUI();
}
if (mRequestingLocationUpdates) {
startLocationUpdates();
}
}
#Override
public void onLocationChanged(Location location) {
Log.i(TAG, "onLocationChanged");
mCurrentLocation = location;
mLastUpdateTime = DateFormat.getTimeInstance().format(new Date());
updateUI();
Toast.makeText(this, getResources().getString(R.string.location_updated_message), Toast.LENGTH_SHORT).show();
}
#Override
public void onConnectionSuspended(int i) {
// The connection to Google Play services was lost for some reason. We call connect() to
// attempt to re-establish the connection.
Log.i(TAG, "Connection suspended");
mGoogleApiClient.connect();
}
#Override
public void onConnectionFailed(#NonNull ConnectionResult connectionResult) {
// Refer to the javadoc for ConnectionResult to see what error codes might be returned in
// onConnectionFailed.
Log.i(TAG, "Connection failed: ConnectionResult.getErrorCode() = " + connectionResult.getErrorCode());
}
public void onSaveInstanceState(Bundle savedInstanceState) {
savedInstanceState.putBoolean(REQUESTING_LOCATION_UPDATES_KEY, mRequestingLocationUpdates);
savedInstanceState.putParcelable(LOCATION_KEY, mCurrentLocation);
savedInstanceState.putString(LAST_UPDATED_TIME_STRING_KEY, mLastUpdateTime);
super.onSaveInstanceState(savedInstanceState);
}
}
Related
I am trying to get current location using FusedLocationAPI in my application. It works just fine in both android API>23 and <23. The issue is in case of GPS is not enabled, the app prompts the user to enable the GPS and after that the location returns null. But while restarting the app, it works just fine. In case of GPS not being turned OFF, the app just works fine. Is there any way that the app can wait for the GPS to be enabled before getting the location? below I am posting my code. Please have a look.
Inside onCreate():
manager = (LocationManager) getSystemService(Context.LOCATION_SERVICE);
statusOfGPS = manager.isProviderEnabled(LocationManager.GPS_PROVIDER);
if (!statusOfGPS) {
displayPromptForEnablingGPS(this);
}
Log.d("permipart", "before");
if(CheckingPermissionIsEnabledOrNot())
{
Toast.makeText(MainActivity.this, "All Permissions Granted Successfully", Toast.LENGTH_LONG).show();
}
else {
RequestMultiplePermission();
}
if(Build.VERSION.SDK_INT<= 23)
{
buildGoogleApiClient();
if (!mGoogleApiClient.isConnected()) {
mGoogleApiClient.connect();
}
}
Log.d("permipart", "out");
Other methods:
#Override
public void onLocationChanged(Location location) {
Log.d("onconnectedlocchange","called");
if (location != null) {
lat = location.getLatitude();
lon = location.getLongitude();
if (!String.valueOf(lat).equals("0.0"))
{
latitudeVal = location.getLatitude();
longitudeVal = location.getLongitude();
Log.e("Lat and Lng", String.valueOf(latitudeVal) + longitudeVal);
}
}
}
#Override
public void onConnected(#Nullable Bundle bundle) {
if(CheckingPermissionIsEnabledOrNot())
{
Toast.makeText(MainActivity.this, "All Permissions Granted Successfully", Toast.LENGTH_LONG).show();
}
// If, If permission is not enabled then else condition will execute.
else {
//Calling method to enable permission.
RequestMultiplePermission();
}
Log.d("onconnected","called");
mLocationRequest = LocationRequest.create();
mLocationRequest.setPriority(LocationRequest.PRIORITY_HIGH_ACCURACY);
// Update location every second
if (ActivityCompat.checkSelfPermission(this, ACCESS_FINE_LOCATION) != PackageManager.PERMISSION_GRANTED && ActivityCompat.checkSelfPermission(this, ACCESS_COARSE_LOCATION) != PackageManager.PERMISSION_GRANTED) {
}
else
{
LocationServices.FusedLocationApi.requestLocationUpdates(mGoogleApiClient, mLocationRequest, this);
mLastLocation = LocationServices.FusedLocationApi.getLastLocation(
mGoogleApiClient);
if (mLastLocation != null) {
lat = mLastLocation.getLatitude();
lon = mLastLocation.getLongitude();
if (!String.valueOf(lat).equals("0.0")){
latitudeVal = mLastLocation.getLatitude();
longitudeVal = mLastLocation.getLongitude();
Log.e("Lat and Lng", String.valueOf(latitudeVal)+ longitudeVal);
}
}
}
}
#Override
public void onConnectionSuspended(int i) {
}
synchronized void buildGoogleApiClient() {
mGoogleApiClient = new GoogleApiClient.Builder(this)
.addConnectionCallbacks(this)
.addOnConnectionFailedListener(this)
.addApi(LocationServices.API)
.build();
}
#Override
public void onConnectionFailed(#NonNull ConnectionResult connectionResult) {
}
public void displayPromptForEnablingGPS(final Activity activity) {
final android.support.v7.app.AlertDialog.Builder builder = new android.support.v7.app.AlertDialog.Builder(activity);
final String action = Settings.ACTION_LOCATION_SOURCE_SETTINGS;
final String message = "Do you want open GPS setting?";
builder.setMessage(message)
.setPositiveButton("OK",
new DialogInterface.OnClickListener() {
public void onClick(DialogInterface d, int id) {
activity.startActivity(new Intent(action));
d.dismiss();
}
})
.setNegativeButton("Cancel",
new DialogInterface.OnClickListener() {
public void onClick(DialogInterface d, int id) {
d.cancel();
}
});
builder.create().show();
}
String[] permissions = new String[]{ACCESS_FINE_LOCATION,
ACCESS_COARSE_LOCATION, READ_EXTERNAL_STORAGE, WRITE_EXTERNAL_STORAGE };
//Permission function starts from here
private void RequestMultiplePermission() {
// Creating String Array with Permissions.
Log.d("permipart", "RequestMultiplePermission");
ActivityCompat.requestPermissions(MainActivity.this, new String[]
{
READ_EXTERNAL_STORAGE,
WRITE_EXTERNAL_STORAGE,
ACCESS_FINE_LOCATION,
ACCESS_COARSE_LOCATION
}, RequestPermissionCode);
}
private boolean checkPermission() {
int result;
List<String> listPermissionsNeeded = new ArrayList<>();
for (String p:permissions) {
result = ContextCompat.checkSelfPermission(this,p);
if (result != PackageManager.PERMISSION_GRANTED) {
listPermissionsNeeded.add(p);
}
}
if (!listPermissionsNeeded.isEmpty()) {
ActivityCompat.requestPermissions(this, listPermissionsNeeded.toArray(new String[listPermissionsNeeded.size()]),10 );
Log.d("permissionissue","no");
return false;
}
Log.d("permissionissue","yes");
return true;
}
#Override
public void onRequestPermissionsResult(int requestCode, String permissions[], int[] grantResults) {
Log.d("permipart", "onRequestPermissionsResult");
switch (requestCode) {
case RequestPermissionCode:
if (grantResults.length > 0) {
boolean CameraPermission = grantResults[0] == PackageManager.PERMISSION_GRANTED;
boolean RecordAudioPermission = grantResults[1] == PackageManager.PERMISSION_GRANTED;
boolean SendSMSPermission = grantResults[2] == PackageManager.PERMISSION_GRANTED;
boolean GetAccountsPermission = grantResults[3] == PackageManager.PERMISSION_GRANTED;
if (CameraPermission && RecordAudioPermission && SendSMSPermission && GetAccountsPermission) {
Log.d("permipart", "done");
buildGoogleApiClient();
Toast.makeText(MainActivity.this, "Permission Granted", Toast.LENGTH_LONG).show();
if (!mGoogleApiClient.isConnected()) {
mGoogleApiClient.connect();
}
}
else {
Toast.makeText(MainActivity.this,"Permission Denied",Toast.LENGTH_LONG).show();
}
}
break;
}
}
/**
* Checking permission is enabled or not using function starts from here.
*
*/
public boolean CheckingPermissionIsEnabledOrNot() {
int FirstPermissionResult = ContextCompat.checkSelfPermission(getApplicationContext(), READ_EXTERNAL_STORAGE);
int SecondPermissionResult = ContextCompat.checkSelfPermission(getApplicationContext(), WRITE_EXTERNAL_STORAGE);
int ThirdPermissionResult = ContextCompat.checkSelfPermission(getApplicationContext(), ACCESS_FINE_LOCATION);
int ForthPermissionResult = ContextCompat.checkSelfPermission(getApplicationContext(), ACCESS_COARSE_LOCATION);
return FirstPermissionResult == PackageManager.PERMISSION_GRANTED &&
SecondPermissionResult == PackageManager.PERMISSION_GRANTED &&
ThirdPermissionResult == PackageManager.PERMISSION_GRANTED &&
ForthPermissionResult == PackageManager.PERMISSION_GRANTED ;
}
You need to recieve the broadcast of the GPS status something like this:
public class GpsLocationReceiver extends BroadcastReceiver {
#Override
public void onReceive(Context context, Intent intent) {
if (intent.getAction().matches("android.location.PROVIDERS_CHANGED")) {
// here you can get the location or start a service to get it.
// example
// Intent getLocationService = new Intent(context,YourService.class);
// context.startService(getLocationService);
}
}
}
update
according to comment below
use this in your code
manager = (LocationManager) getSystemService(Context.LOCATION_SERVICE);
if(manager.isProviderEnabled( LocationManager.GPS_PROVIDER)){
// it is enabled
}else{
// it is not
}
Use my code, it will ask the user to turn on GPS if it is turned off. It will never return you anything until GPS turned on.
Note: you have to get location permission before using it for marshmallow and above mobiles.
Try this:
#SuppressWarnings("MissingPermission")
public class LocationFinder implements LocationListener, GoogleApiClient.ConnectionCallbacks, GoogleApiClient.OnConnectionFailedListener {
public static final String TAG = "LocationFinder";
private static final String BROADCAST_GPS_REQ = "LocationFinder.GPS_REQ";
private static final String KEY_GPS_REQ = "key.gps.req";
private static final int GPS_REQUEST = 2301;
private Activity activity;
private FinderType finderType;
private GoogleApiClient googleApiClient;
private LocationRequest locationRequest;
private long updateInterval;
private long fastestInterval;
private GpsRequestListener gpsRequestListener;
private LocationUpdateListener locationUpdateListener;
public LocationFinder(Activity activity, FinderType finderType) {
this.activity = activity;
this.finderType = finderType;
}
private void connectGoogleApiClient() {
googleApiClient = new GoogleApiClient.Builder(activity)
.addApi(LocationServices.API).addConnectionCallbacks(this)
.addOnConnectionFailedListener(this).build();
googleApiClient.connect();
}
private void createLocationRequest() {
locationRequest = LocationRequest.create();
locationRequest.setPriority(LocationRequest.PRIORITY_HIGH_ACCURACY);
locationRequest.setInterval(updateInterval);
locationRequest.setFastestInterval(fastestInterval);
}
private BroadcastReceiver receiver = new BroadcastReceiver() {
#Override
public void onReceive(Context context, Intent intent) {
int intExtra = intent.getIntExtra(KEY_GPS_REQ, 0);
switch (intExtra) {
case Activity.RESULT_OK:
try {
LocationServices.FusedLocationApi.requestLocationUpdates(googleApiClient, locationRequest, LocationFinder.this);
} catch (Exception e) {
e.printStackTrace();
}
gpsRequestListener.gpsTurnedOn();
break;
case Activity.RESULT_CANCELED:
gpsRequestListener.gpsNotTurnedOn();
}
}
};
public void gpsRequestCallback(GpsRequestListener gpsRequestListener) {
this.gpsRequestListener = gpsRequestListener;
LocalBroadcastManager.getInstance(activity).registerReceiver(receiver, new IntentFilter(BROADCAST_GPS_REQ));
}
public void config(long updateInterval, long fastestInterval) {
this.updateInterval = updateInterval;
this.fastestInterval = fastestInterval;
}
public void find(LocationUpdateListener listener) {
this.locationUpdateListener = listener;
createLocationRequest();
connectGoogleApiClient();
}
private void find() {
LocationSettingsRequest.Builder builder = new LocationSettingsRequest.Builder()
.addLocationRequest(locationRequest);
builder.setAlwaysShow(true);
PendingResult<LocationSettingsResult> result = LocationServices.SettingsApi.checkLocationSettings(googleApiClient, builder.build());
result.setResultCallback(new ResultCallback<LocationSettingsResult>() {
#Override
public void onResult(#NonNull LocationSettingsResult locationSettingsResult) {
Status status = locationSettingsResult.getStatus();
switch (status.getStatusCode()) {
case LocationSettingsStatusCodes.SUCCESS:
LocationServices.FusedLocationApi.requestLocationUpdates(googleApiClient, locationRequest, LocationFinder.this);
break;
case LocationSettingsStatusCodes.RESOLUTION_REQUIRED:
try {
status.startResolutionForResult(activity, GPS_REQUEST);
} catch (IntentSender.SendIntentException e) {
e.printStackTrace();
}
break;
case LocationSettingsStatusCodes.SETTINGS_CHANGE_UNAVAILABLE:
Log.d(TAG, "No GPS Hardware");
break;
}
}
});
}
public void stopFinder() {
if (googleApiClient.isConnected()) {
LocationServices.FusedLocationApi.removeLocationUpdates(googleApiClient, this);
googleApiClient.disconnect();
}
try {
activity.unregisterReceiver(receiver);
} catch (Exception e) {
e.printStackTrace();
}
}
#Override
public void onConnected(#Nullable Bundle bundle) {
Log.d(TAG, "GoogleApiClient: Connected");
find();
}
#Override
public void onConnectionSuspended(int i) {
Log.d(TAG, "GoogleApiClient: onConnectionSuspended");
}
#Override
public void onConnectionFailed(#NonNull ConnectionResult connectionResult) {
Log.d(TAG, "GoogleApiClient: onConnectionFailed");
}
#Override
public void onLocationChanged(Location location) {
if (finderType != FinderType.TRACK)
stopFinder();
locationUpdateListener.onLocationUpdate(new LatLng(location.getLatitude(), location.getLongitude()));
}
public void setGpsRequestListener(GpsRequestListener gpsRequestListener) {
this.gpsRequestListener = gpsRequestListener;
}
public static void onRequestResult(Activity activity, int requestCode, int resultCode) {
if (requestCode == GPS_REQUEST) {
Intent intent = new Intent(BROADCAST_GPS_REQ);
intent.putExtra(KEY_GPS_REQ, resultCode);
LocalBroadcastManager.getInstance(activity).sendBroadcast(intent);
}
}
public enum FinderType {
// It will update the current GPS location once.
GPS,
//It will update the user location continuously.
TRACK
}
public interface LocationUpdateListener {
void onLocationUpdate(LatLng latLng);
}
public interface GpsRequestListener {
void gpsTurnedOn();
void gpsNotTurnedOn();
}
}
To get location update initialize the class like this:
public class MyActivity extends AppCompatActivity implements
LocationFinder.GpsRequestListener,
LocationFinder.LocationUpdateListener {
private LocationFinder locationUpdater;
#Override
public void onCreate(#Nullable Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
locationUpdater = new LocationFinder(this, LocationFinder.FinderType.TRACK);
driverLocationUpdater.gpsRequestCallback(this);
driverLocationUpdater.config(5000, 5000);
driverLocationUpdater.find(this);
}
#Override
protected void onDestroy(){
super.onDestroy()
driverLocationUpdater.stopFinder();
}
#Override
public void onLocationUpdate(LatLng latLng) {
}
#Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
super.onActivityResult(requestCode, resultCode, data);
LocationFinder.onRequestResult(this, requestCode, resultCode);
}
}
I want to implement a service that will show the loading screen till the GPS dont find location in it. After some time it shows alert and return the place last known location or the basic cord (0.0). Unfortunatly the first read is null and it stays like this no matter if the GPS is on or off.
GPS HANDLER
public class GPSLocation implements ConnectionCallbacks,OnConnectionFailedListener,
LocationListener,
GPSStatusReceiver.GpsStatusChangeListener{
public static final int REQUEST_CHECK_SETTINGS = 100;
public static final int LOCATION_PERMISSION_REQUEST_CODE = 200;
private static final int PERMISSION_GRANTED = 0;
private static final int PERMISSION_DENIED = 1;
private static final int PERMISSION_BLOCKED = 2;
private GoogleApiClient mGoogleApiClient;
private Location mCurrentLocation;
private LocationCallback mCallback;
private Activity mActivity;
private Context mContext;
private LocationRequest mLocationRequest;
private GPSStatusReceiver mGPSStatusReceiver;
private long intervalMillis = 10000;
private long fastestIntervalMillis = 5000;
private int accuracy = LocationRequest.PRIORITY_HIGH_ACCURACY;
private boolean isInitialized = false;
private boolean isLocationEnabled = false;
private boolean isPermissionLocked = false;
public GPSLocation(Activity activity, LocationCallback callback) {
mActivity = activity;
mContext = activity.getApplicationContext();
mCallback = callback;
//creating new client Api
if (mGoogleApiClient == null) {
mGoogleApiClient = new GoogleApiClient.Builder(mContext)
.addConnectionCallbacks(this)
.addOnConnectionFailedListener(this)
.addApi(LocationServices.API)
.build();
}
createLocationRequest();
mGPSStatusReceiver = new GPSStatusReceiver(mContext, this);
}
public void init(){
isInitialized = true;
if(mGoogleApiClient != null) {
if (mGoogleApiClient.isConnected()) {
requestPermission();
} else {
connect();
}
}
}
public void createLocationRequest() {
mLocationRequest = new LocationRequest();
mLocationRequest.setInterval(intervalMillis);
mLocationRequest.setFastestInterval(fastestIntervalMillis);
mLocationRequest.setPriority(accuracy);
}
public LocationRequest getLocationRequest() {
return mLocationRequest;
}
public void connect(){
if(mGoogleApiClient != null && isInitialized) {
mGoogleApiClient.connect();
}
}
public void disconnect(){
if(mGoogleApiClient != null && isInitialized) {
mGoogleApiClient.disconnect();
}
}
private void getLastKnownLocation(){
if(!mGoogleApiClient.isConnected()){
Log.i(TAG, "getLastKnownLocation restart ");
mGoogleApiClient.connect();
}
else {
if (checkLocationPermission(mContext) && isLocationEnabled) {
Log.i(TAG, "getLastKnownLocation read ");
if(mCurrentLocation==null){
mCurrentLocation = LocationServices.FusedLocationApi.getLastLocation(mGoogleApiClient);
mCallback.onLastKnowLocationFetch(mCurrentLocation);
Log.i(TAG,"mCurrentLocation is "+mCurrentLocation);
}
startLocationUpdates();
}else{
Log.i(TAG, "getLastKnownLocation get permission ");
requestPermission();
}
}
Log.i(TAG, "mCurrentLocation " + mCurrentLocation);
}
public void startLocationUpdates() {
if(checkLocationPermission(mContext)
&& mGoogleApiClient != null
&& mGoogleApiClient.isConnected()
&& isLocationEnabled) {
LocationServices.FusedLocationApi.requestLocationUpdates(
mGoogleApiClient, mLocationRequest, this);
}
}
public void stopLocationUpdates() {
if(mGoogleApiClient != null
&& mGoogleApiClient.isConnected()) {
LocationServices.FusedLocationApi.removeLocationUpdates(
mGoogleApiClient, this);
}
}
#Override
public void onConnected(#Nullable Bundle bundle) {
if (checkLocationPermission(mContext) && isLocationEnabled) {
Log.i(TAG, "getLastKnownLocation read ");
if (mGoogleApiClient == null) {
mGoogleApiClient = new GoogleApiClient.Builder(mContext)
.addConnectionCallbacks(this)
.addOnConnectionFailedListener(this)
.addApi(LocationServices.API)
.build();
}
if(mCurrentLocation == null ) {
mCurrentLocation = LocationServices.FusedLocationApi.getLastLocation(mGoogleApiClient);
mCallback.onLastKnowLocationFetch(mCurrentLocation);
}
startLocationUpdates();
}
Log.i(TAG, "onConnected");
mCallback.onLocationUpdate(mCurrentLocation);
requestPermission();
}
#Override
public void onConnectionSuspended(int i) {
Log.i(TAG, "onConnectionSuspended");
}
#Override
public void onConnectionFailed(#NonNull ConnectionResult connectionResult) {
Log.i(TAG, "onConnectionFailed");
}
#Override
public void onLocationChanged(Location location) {
Log.i(TAG, "onLocationChanged : " + location);
if(location!=null)
mCallback.onLocationUpdate(location);
}
#Override
public void onGpsStatusChange() {
Log.i(TAG, "onGpsStatusChange");
if(isInitialized && !isPermissionLocked) {
if (!isLocationEnabled(mContext)) {
isLocationEnabled = false;
isPermissionLocked = true;
stopLocationUpdates();
requestPermission();
}
}
}
private void requestPermission(){
if (ContextCompat.checkSelfPermission(mContext, Manifest.permission.ACCESS_FINE_LOCATION)
!= PackageManager.PERMISSION_GRANTED){
String[] appPerm = new String[]{Manifest.permission.ACCESS_FINE_LOCATION};
ActivityCompat.requestPermissions(mActivity, appPerm, LOCATION_PERMISSION_REQUEST_CODE);
}else{
getLocationSetting();
}
}
public void onActivityResult(int requestCode, int resultCode, Intent data) {
if (requestCode == GPSLocation.REQUEST_CHECK_SETTINGS) {
if (resultCode == Activity.RESULT_OK) {
getLastKnownLocation();
}else{
Toast.makeText(mContext, "Permission Denied", Toast.LENGTH_SHORT).show();
mCallback.onLocationSettingsError();
}
}
}
private void getLocationSetting(){
LocationSettingsRequest.Builder builder =
new LocationSettingsRequest
.Builder()
.addLocationRequest(mLocationRequest);
PendingResult<LocationSettingsResult> result =
LocationServices.SettingsApi.checkLocationSettings(mGoogleApiClient, builder.build());
result.setResultCallback(new ResultCallback<LocationSettingsResult>(){
#Override
public void onResult(LocationSettingsResult result) {
final Status status = result.getStatus();
final LocationSettingsStates locationSettingsStates = result.getLocationSettingsStates();
switch (status.getStatusCode()) {
case LocationSettingsStatusCodes.SUCCESS:
Log.i(TAG, "SUCCESS");
isLocationEnabled = true;
isPermissionLocked = false;
getLastKnownLocation();
break;
case LocationSettingsStatusCodes.RESOLUTION_REQUIRED:
Log.i(TAG, "RESOLUTION_REQUIRED");
try {
status.startResolutionForResult(
mActivity,
REQUEST_CHECK_SETTINGS);
} catch (IntentSender.SendIntentException e) {
e.printStackTrace();
mCallback.onLocationSettingsError();
}finally {
isPermissionLocked = false;
}
break;
case LocationSettingsStatusCodes.SETTINGS_CHANGE_UNAVAILABLE:
Log.i(TAG, "SETTINGS_CHANGE_UNAVAILABLE");
Toast.makeText(mContext, "Location Unavailable", Toast.LENGTH_SHORT).show();
mCallback.onLocationSettingsError();
isPermissionLocked = false;
break;
}
}
});
}
public void onRequestPermissionsResult(int requestCode, String permissions[], int[] grantResults) {
int permState;
switch (requestCode) {
case LOCATION_PERMISSION_REQUEST_CODE:
if (grantResults.length > 0) {
if(grantResults[0] != PackageManager.PERMISSION_GRANTED) {
if(!ActivityCompat.shouldShowRequestPermissionRationale(
mActivity,
Manifest.permission.ACCESS_FINE_LOCATION)){
permState = PERMISSION_BLOCKED;
}else{permState = PERMISSION_DENIED;}
}else {permState = PERMISSION_GRANTED;}
}
else{permState = PERMISSION_DENIED;}
switch (permState){
case PERMISSION_BLOCKED:
Toast.makeText(mContext,"Please give gps location permission to use the app.",Toast.LENGTH_LONG).show();
startInstalledAppDetailsActivity(mContext);
mCallback.onLocationPermissionDenied();
break;
case PERMISSION_DENIED:
Toast.makeText(mContext,"Permission Denied, app cannot access the gps location.", Toast.LENGTH_LONG).show();
break;
case PERMISSION_GRANTED:
getLocationSetting();
break;
}
break;
}
}
public static boolean isLocationEnabled(Context context){
LocationManager locationManager = (LocationManager)context.getSystemService(Context.LOCATION_SERVICE);
boolean gpsEnabled = false;
boolean networkEnabled = false;
try {
gpsEnabled = locationManager.isProviderEnabled(LocationManager.GPS_PROVIDER);
} catch(Exception ex) {}
try {
networkEnabled = locationManager.isProviderEnabled(LocationManager.NETWORK_PROVIDER);
} catch(Exception ex) {}
return gpsEnabled && networkEnabled;
}
public static void startInstalledAppDetailsActivity(final Context context) {
if (context == null) {
return;
}
final Intent i = new Intent();
i.setAction(Settings.ACTION_APPLICATION_DETAILS_SETTINGS);
i.addCategory(Intent.CATEGORY_DEFAULT);
i.setData(Uri.parse("package:" + context.getPackageName()));
i.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
i.addFlags(Intent.FLAG_ACTIVITY_NO_HISTORY);
i.addFlags(Intent.FLAG_ACTIVITY_EXCLUDE_FROM_RECENTS);
context.startActivity(i);
}
public static boolean checkLocationPermission(Context context) {
String permission = "android.permission.ACCESS_FINE_LOCATION";
int res = context.checkCallingOrSelfPermission(permission);
return (res == PackageManager.PERMISSION_GRANTED);
}
public interface LocationCallback {
void onLastKnowLocationFetch(Location location);
void onLocationUpdate(Location location);
void onLocationPermissionDenied();
void onLocationSettingsError();
}
public void close() {
mGPSStatusReceiver.unRegisterReceiver();
}}
Recivier Class
public class GPSStatusReceiver extends BroadcastReceiver {
private GpsStatusChangeListener mCallback;
private Context mContext;
public GPSStatusReceiver(Context context, GpsStatusChangeListener callback) {
mCallback = callback;
mContext = context;
IntentFilter intentFilter = new IntentFilter();
intentFilter.addAction("android.location.PROVIDERS_CHANGED");
intentFilter.addCategory(Intent.CATEGORY_DEFAULT);
context.registerReceiver(this, intentFilter);
}
public void unRegisterReceiver(){
Log.i(TAG, "unRegisterReceiver");
mContext.unregisterReceiver(this);
}
#Override
public void onReceive(Context context, Intent intent) {
if (intent.getAction().matches("android.location.PROVIDERS_CHANGED")) {
Log.i(TAG, "in PROVIDERS_CHANGED");
mCallback.onGpsStatusChange();
}
}
public interface GpsStatusChangeListener{
void onGpsStatusChange();
}}
Activity Class
public class LocationFinder extends AppCompatActivity implements GPSLocation.LocationCallback,OnMapReadyCallback {
Log log;
private GoogleMap mMap;
Button confirmLocalizationButton;
private GPSLocation mGPSLocation;
private LatLng currentPosition= new LatLng(0,0);
MarkerOptions markerOptions;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_maps);
mGPSLocation = new GPSLocation(this, this);
mGPSLocation.init();
mapInit();
buttonInit();
checkInternetStatus();
}
private void buttonInit() {
confirmLocalizationButton = (Button)findViewById(R.id.confirm_location);
confirmLocalizationButton.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
currentPosition=markerOptions.getPosition();
log.i(TAG,"currentPosition:: "+currentPosition);
Intent i = new Intent(LocationFinder.this,MainActivity.class);
i.putExtra("coordinates",currentPosition);
startActivity(i);
finish();
}
});
}
#Override
public void onLastKnowLocationFetch(Location location) {
if(location != null) {
Log.i(TAG, "onLastKnowLocationFetch " + location);
}
}
#Override
public void onLocationUpdate(Location location) {
if(location != null) {
Log.i(TAG, "onLocationUpdate " + location);
}
}
#Override
public void onLocationPermissionDenied() {
}
#Override
public void onLocationSettingsError() {
}
#Override
protected void onStart() {
mGPSLocation.connect();
super.onStart();
}
#Override
public void onResume() {
super.onResume();
mGPSLocation.startLocationUpdates();
}
#Override
protected void onPause() {
super.onPause();
mGPSLocation.stopLocationUpdates();
}
#Override
protected void onStop() {
mGPSLocation.disconnect();
super.onStop();
}
#Override
protected void onDestroy() {
mGPSLocation.close();
super.onDestroy();
}
#Override
public void onRequestPermissionsResult(int requestCode, String permissions[], int[] grantResults) {
super.onRequestPermissionsResult(requestCode, permissions, grantResults);
if(requestCode == GPSLocation.LOCATION_PERMISSION_REQUEST_CODE) {
mGPSLocation.onRequestPermissionsResult(requestCode, permissions, grantResults);
}
}
#Override
public void onActivityResult(int requestCode, int resultCode, Intent data) {
super.onActivityResult(requestCode, resultCode, data);
if (requestCode == GPSLocation.REQUEST_CHECK_SETTINGS) {
mGPSLocation.onActivityResult(requestCode, resultCode, data);
}
}
#Override
public void onMapReady(GoogleMap googleMap) {
mMap = googleMap;
googleMap.getUiSettings().setCompassEnabled(true);
googleMap.getUiSettings().setZoomControlsEnabled(true);
CameraUpdate camera = CameraUpdateFactory.newLatLngZoom(currentPosition, 1);
mMap.moveCamera(camera);
markerOptions = new MarkerOptions()
.position(currentPosition);
mMap.addMarker(markerOptions);
mMap.setOnCameraMoveListener(new GoogleMap.OnCameraMoveListener() {
#Override
public void onCameraMove() {
markerOptions = new MarkerOptions().position(mMap.getCameraPosition().target);
mMap.clear();
mMap.addMarker(markerOptions);
}
});
}
private void mapInit(){
SupportMapFragment mapFragment = (SupportMapFragment)getSupportFragmentManager()
.findFragmentById(R.id.map);
mapFragment.getMapAsync(this);
}
private void checkInternetStatus(){
if(!InternetConnection.getConnectivityStatus(this)) {
new android.app.AlertDialog.Builder(this)
.setMessage("Turn on your network service to enjoy full functionality of this application ")
.setCancelable(true).
setPositiveButton("Confirm", new DialogInterface.OnClickListener() {
#Override
public void onClick(DialogInterface dialog, int which) {
dialog.cancel();
}
})
.show();
}
}
UPDATE: Ive made function that will wait for GPS signal but still does make a connection
private void waitForGPSSignal(){
progressWindow();
new Handler().postDelayed(new Runnable() {
#Override
public void run() {
getLastKnownLocation();
if(mCurrentLocation!=null)
progress.dismiss();
}
}, 10000);
}
ProgressDialog progress;
private void progressWindow() {
progress = new ProgressDialog(mContext);
progress.setMessage("waiting");
progress.setProgressStyle(ProgressDialog.STYLE_SPINNER);
progress.setIndeterminate(true);
if (mContext != null) {
progress.show();
}}
I called it for GPSLocation in here:
result.setResultCallback(new ResultCallback<LocationSettingsResult>(){
#Override
public void onResult(LocationSettingsResult result) {
final Status status = result.getStatus();
final LocationSettingsStates locationSettingsStates = result.getLocationSettingsStates();
switch (status.getStatusCode()) {
case LocationSettingsStatusCodes.SUCCESS:
Log.i(TAG, "SUCCESS");
isLocationEnabled = true;
isPermissionLocked = false;
waitForGPSSignal();
getLastKnownLocation();
break;
case LocationSettingsStatusCodes.RESOLUTION_REQUIRED:
Log.i(TAG, "RESOLUTION_REQUIRED");
try {
status.startResolutionForResult(
mActivity,
REQUEST_CHECK_SETTINGS);
} catch (IntentSender.SendIntentException e) {
e.printStackTrace();
mCallback.onLocationSettingsError();
}finally {
isPermissionLocked = false;
}
break;
case LocationSettingsStatusCodes.SETTINGS_CHANGE_UNAVAILABLE:
Log.i(TAG, "SETTINGS_CHANGE_UNAVAILABLE");
Toast.makeText(mContext, "Location Unavailable", Toast.LENGTH_SHORT).show();
mCallback.onLocationSettingsError();
isPermissionLocked = false;
break;
}
}
});
And Im still obtain null.
Here is what you can do.
if (Utility.isLocationEnabled(Splash_Activity.this)) {
new FetchCordinates.execute();
} else {
buildAlertMessageNoGps();
}
FetchCordinates.java
public class FetchCordinates extends AsyncTask<String, Integer, String> {
public LocationManager mLocationManager;
public VeggsterLocationListener mVeggsterLocationListener;
ProgressDialog pDialog;
#Override
protected void onPreExecute() {
pDialog = ProgressDialog.show(InitialRegistration.this, "",
"Fetching Location");
mVeggsterLocationListener = new VeggsterLocationListener();
mLocationManager = (LocationManager) getSystemService(Context.LOCATION_SERVICE);
mLocationManager.requestLocationUpdates(
LocationManager.NETWORK_PROVIDER, 0, 0,
mVeggsterLocationListener);
}
#Override
protected void onCancelled() {
System.out.println("Cancelled by user!");
mLocationManager.removeUpdates(mVeggsterLocationListener);
}
#Override
protected void onPostExecute(String result) {
// Log.e("AsynckLL", "LATITUDE :" + mLatitude + " LONGITUDE :"
// + mLongitude);
if (pDialog.isShowing()) {
pDialog.dismiss();
}
// do your logic
mLocationManager.removeUpdates(mVeggsterLocationListener);
}
#Override
protected String doInBackground(String... params) {
while (mLatitude == 0.0) {
}
return null;
}
public class VeggsterLocationListener implements LocationListener {
#Override
public void onLocationChanged(Location location) {
mLatitude = location.getLatitude();
mLongitude = location.getLongitude();
}
#Override
public void onProviderDisabled(String provider) {
// Log.e("OnProviderDisabled", "OnProviderDisabled");
}
#Override
public void onProviderEnabled(String provider) {
// Log.e("onProviderEnabled", "onProviderEnabled");
}
#Override
public void onStatusChanged(String provider, int status,
Bundle extras) {
// Log.e("onStatusChanged", "onStatusChanged");
}
}
}
if Location is not enabled.
private void buildAlertMessageNoGps() {
final AlertDialog.Builder builder = new AlertDialog.Builder(
Splash_Activity.this);
builder.setMessage(
"Your GPS seems to be disabled, do you want to enable it?")
.setCancelable(false)
.setPositiveButton("Yes",
new DialogInterface.OnClickListener() {
public void onClick(final DialogInterface dialog,
final int id) {
startActivityForResult(
new Intent(
Settings.ACTION_LOCATION_SOURCE_SETTINGS),
100);
}
})
.setNegativeButton("No", new DialogInterface.OnClickListener() {
public void onClick(final DialogInterface dialog,
final int id) {
dialog.cancel();
}
});
final AlertDialog alert = builder.create();
alert.show();
}
and inside onActivityResults
#Override
public void onActivityResult(int requestCode, int resultCode, Intent data) {
super.onActivityResult(requestCode, resultCode, data);
if (requestCode == 100) {
if (Utility.isLocationEnabled(Splash_Activity.this)) {
new FetchCordinates().execute();
} else {
buildAlertMessageNoGps();
}
} else {
Toast.makeText(getApplicationContext(), "Location Off", 1000)
.show();
}
}
This is not service as you mentioned in your question. but i hope somehow it will help you.
Happy Coding.
I want to check if the GPS is on if it is should show the current location. If not it should ask to turn it on. If user click cancel or dont turn the coordinates will be set as basic. Unfortunetly allways choose the basic. Even if the GPS is of (i dont get the message to turn on GPS)
#Override
public void onMapReady(GoogleMap googleMap) {
mMap = googleMap;
locationManagerr = (LocationManager) getSystemService(LOCATION_SERVICE);
currentLocation=new Location("location");
if (ActivityCompat.checkSelfPermission(this, Manifest.permission.ACCESS_FINE_LOCATION) != PackageManager.PERMISSION_GRANTED
&& ActivityCompat.checkSelfPermission(this, Manifest.permission.ACCESS_COARSE_LOCATION)
!= PackageManager.PERMISSION_GRANTED) {
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) {
requestPermissions(new String[]{Manifest.permission.ACCESS_COARSE_LOCATION,
Manifest.permission.ACCESS_FINE_LOCATION, Manifest.permission.INTERNET}
, 10);
}
}else
getLocation();
log.i(TAG,"latitude "+currentLocation.getLatitude());
}
private Location getLocation(){
locationListener= new LocationListener() {
#Override
public void onLocationChanged(Location location) {
currentLocation=location;
}
#Override
public void onStatusChanged(String provider, int status, Bundle extras) {
}
#Override
public void onProviderEnabled(String provider) {
}
#Override
public void onProviderDisabled(String provider) {
AlertDialog.Builder alertDialogBuilder = new AlertDialog.Builder(LocationFinder.this);
alertDialogBuilder.setMessage("GPS is off. Want to turn on GPS?")
.setCancelable(false)
.setPositiveButton("Turn On",
new DialogInterface.OnClickListener() {
public void onClick(DialogInterface dialog, int id) {
Intent callGPSSettingIntent = new Intent(
android.provider.Settings.ACTION_LOCATION_SOURCE_SETTINGS);
startActivity(callGPSSettingIntent);
}
});
alertDialogBuilder.setNegativeButton("Cancel",
new DialogInterface.OnClickListener() {
public void onClick(DialogInterface dialog, int id) {
currentLocation=setStartCoordinate();
dialog.cancel();
}
});
AlertDialog alert = alertDialogBuilder.create();
alert.show();
}
};
return currentLocation;
}
private Location setStartCoordinate(){
Location primaryLocalization= new Location("Basic");
primaryLocalization.setLongitude(0);
primaryLocalization.setLatitude(0);
return primaryLocalization;
}
#Override
public void onRequestPermissionsResult(int requestCode, #NonNull String[] permissions, #NonNull int[] grantResults) {
switch (requestCode){
case 10:
try{
getLocation();
log.i(TAG,"latitude "+currentLocation.getLatitude());
}
catch (SecurityException ex){log.i(TAG,"security error");}
break;
default:
break;
}
}
This requires a lot of case handling and I am providing a complete implementation of the all the features you requested with brief explanations below.
1. Provide location permission in the manifest
<uses-permission android:name="android.permission.ACCESS_FINE_LOCATION"/>
2. Add location dependency in app's build.gradle
compile 'com.google.android.gms:play-services-location:9.2.1'
3. extend BroadcastReceiver and create GPSStatusReceiver
public class GPSStatusReceiver extends BroadcastReceiver {
private GpsStatusChangeListener mCallback;
private Context mContext;
public GPSStatusReceiver(Context context, GpsStatusChangeListener callback) {
mCallback = callback;
mContext = context;
IntentFilter intentFilter = new IntentFilter();
intentFilter.addAction("android.location.PROVIDERS_CHANGED");
intentFilter.addCategory(Intent.CATEGORY_DEFAULT);
context.registerReceiver(this, intentFilter);
}
public void unRegisterReceiver(){
Log.d("ali", "unRegisterReceiver");
mContext.unregisterReceiver(this);
}
#Override
public void onReceive(Context context, Intent intent) {
if (intent.getAction().matches("android.location.PROVIDERS_CHANGED")) {
Log.d("ali", "in PROVIDERS_CHANGED");
mCallback.onGpsStatusChange();
}
}
public interface GpsStatusChangeListener{
void onGpsStatusChange();
}
}
4. Create a class GPSLocation
public class GPSLocation implements
ConnectionCallbacks,
OnConnectionFailedListener,
LocationListener,
GPSStatusReceiver.GpsStatusChangeListener {
public static final int REQUEST_CHECK_SETTINGS = 100;
public static final int LOCATION_PERMISSION_REQUEST_CODE = 200;
private static final int PERMISSION_GRANTED = 0;
private static final int PERMISSION_DENIED = 1;
private static final int PERMISSION_BLOCKED = 2;
private GoogleApiClient mGoogleApiClient;
private Location mCurrentLocation;
private LocationCallback mCallback;
private Activity mActivity;
private Context mContext;
private LocationRequest mLocationRequest;
private GPSStatusReceiver mGPSStatusReceiver;
private long intervalMillis = 10000;
private long fastestIntervalMillis = 5000;
private int accuracy = LocationRequest.PRIORITY_HIGH_ACCURACY;
private boolean isInitialized = false;
private boolean isLocationEnabled = false;
private boolean isPermissionLocked = false;
public GPSLocation(Activity activity, LocationCallback callback) {
mActivity = activity;
mContext = activity.getApplicationContext();
mCallback = callback;
if (mGoogleApiClient == null) {
mGoogleApiClient = new GoogleApiClient.Builder(mContext)
.addConnectionCallbacks(this)
.addOnConnectionFailedListener(this)
.addApi(LocationServices.API)
.build();
}
createLocationRequest();
mGPSStatusReceiver = new GPSStatusReceiver(mContext, this);
}
public void init(){
isInitialized = true;
if(mGoogleApiClient != null) {
if (mGoogleApiClient.isConnected()) {
requestPermission();
} else {
connect();
}
}
}
public void createLocationRequest() {
mLocationRequest = new LocationRequest();
mLocationRequest.setInterval(intervalMillis);
mLocationRequest.setFastestInterval(fastestIntervalMillis);
mLocationRequest.setPriority(accuracy);
}
public LocationRequest getLocationRequest() {
return mLocationRequest;
}
public void connect(){
if(mGoogleApiClient != null && isInitialized) {
mGoogleApiClient.connect();
}
}
public void disconnect(){
if(mGoogleApiClient != null && isInitialized) {
mGoogleApiClient.disconnect();
}
}
private void getLastKnownLocation(){
if(!mGoogleApiClient.isConnected()){
Log.d("ali", "getLastKnownLocation restart ");
mGoogleApiClient.connect();
}
else {
if (checkLocationPermission(mContext) && isLocationEnabled) {
Log.d("ali", "getLastKnownLocation read ");
if(mCurrentLocation == null) {
mCurrentLocation = LocationServices.FusedLocationApi.getLastLocation(mGoogleApiClient);
mCallback.onLastKnowLocationFetch(mCurrentLocation);
}
startLocationUpdates();
}else{
Log.d("ali", "getLastKnownLocation get permission ");
requestPermission();
}
}
Log.d("ali", "mCurrentLocation " + mCurrentLocation);
}
public void startLocationUpdates() {
if(checkLocationPermission(mContext)
&& mGoogleApiClient != null
&& mGoogleApiClient.isConnected()
&& isLocationEnabled) {
LocationServices.FusedLocationApi.requestLocationUpdates(
mGoogleApiClient, mLocationRequest, this);
}
}
public void stopLocationUpdates() {
if(mGoogleApiClient != null
&& mGoogleApiClient.isConnected()) {
LocationServices.FusedLocationApi.removeLocationUpdates(
mGoogleApiClient, this);
}
}
#Override
public void onConnected(#Nullable Bundle bundle) {
Log.d("ali", "onConnected");
requestPermission();
}
#Override
public void onConnectionSuspended(int i) {
Log.d("ali", "onConnectionSuspended");
}
#Override
public void onConnectionFailed(#NonNull ConnectionResult connectionResult) {
Log.d("ali", "onConnectionFailed");
}
#Override
public void onLocationChanged(Location location) {
Log.d("ali", "onLocationChanged : " + location);
mCallback.onLocationUpdate(location);
}
#Override
public void onGpsStatusChange() {
Log.d("ali", "onGpsStatusChange");
if(isInitialized && !isPermissionLocked) {
if (!isLocationEnabled(mContext)) {
isLocationEnabled = false;
isPermissionLocked = true;
stopLocationUpdates();
requestPermission();
}
}
}
private void requestPermission(){
if (ContextCompat.checkSelfPermission(mContext, Manifest.permission.ACCESS_FINE_LOCATION)
!= PackageManager.PERMISSION_GRANTED){
String[] appPerm = new String[]{Manifest.permission.ACCESS_FINE_LOCATION};
ActivityCompat.requestPermissions(mActivity, appPerm, LOCATION_PERMISSION_REQUEST_CODE);
}else{
getLocationSetting();
}
}
public void onActivityResult(int requestCode, int resultCode, Intent data) {
if (requestCode == GPSLocation.REQUEST_CHECK_SETTINGS) {
if (resultCode == Activity.RESULT_OK) {
getLastKnownLocation();
}else{
Toast.makeText(mContext, "Permission Denied", Toast.LENGTH_SHORT).show();
mCallback.onLocationSettingsError();
}
}
}
private void getLocationSetting(){
LocationSettingsRequest.Builder builder =
new LocationSettingsRequest
.Builder()
.addLocationRequest(mLocationRequest);
PendingResult<LocationSettingsResult> result =
LocationServices.SettingsApi.checkLocationSettings(mGoogleApiClient, builder.build());
result.setResultCallback(new ResultCallback<LocationSettingsResult>(){
#Override
public void onResult(LocationSettingsResult result) {
final Status status = result.getStatus();
final LocationSettingsStates locationSettingsStates = result.getLocationSettingsStates();
switch (status.getStatusCode()) {
case LocationSettingsStatusCodes.SUCCESS:
Log.d("ali", "SUCCESS");
isLocationEnabled = true;
isPermissionLocked = false;
getLastKnownLocation();
break;
case LocationSettingsStatusCodes.RESOLUTION_REQUIRED:
Log.d("ali", "RESOLUTION_REQUIRED");
try {
status.startResolutionForResult(
mActivity,
REQUEST_CHECK_SETTINGS);
} catch (IntentSender.SendIntentException e) {
e.printStackTrace();
mCallback.onLocationSettingsError();
}finally {
isPermissionLocked = false;
}
break;
case LocationSettingsStatusCodes.SETTINGS_CHANGE_UNAVAILABLE:
Log.d("ali", "SETTINGS_CHANGE_UNAVAILABLE");
Toast.makeText(mContext, "Location Unavailable", Toast.LENGTH_SHORT).show();
mCallback.onLocationSettingsError();
isPermissionLocked = false;
break;
}
}
});
}
public void onRequestPermissionsResult(int requestCode, String permissions[], int[] grantResults) {
int permState;
switch (requestCode) {
case LOCATION_PERMISSION_REQUEST_CODE:
if (grantResults.length > 0) {
if(grantResults[0] != PackageManager.PERMISSION_GRANTED) {
if(!ActivityCompat.shouldShowRequestPermissionRationale(
mActivity,
Manifest.permission.ACCESS_FINE_LOCATION)){
permState = PERMISSION_BLOCKED;
}else{permState = PERMISSION_DENIED;}
}else {permState = PERMISSION_GRANTED;}
}
else{permState = PERMISSION_DENIED;}
switch (permState){
case PERMISSION_BLOCKED:
Toast.makeText(mContext,"Please give gps location permission to use the app.",Toast.LENGTH_LONG).show();
startInstalledAppDetailsActivity(mContext);
mCallback.onLocationPermissionDenied();
break;
case PERMISSION_DENIED:
Toast.makeText(mContext,"Permission Denied, app cannot access the gps location.", Toast.LENGTH_LONG).show();
break;
case PERMISSION_GRANTED:
getLocationSetting();
break;
}
break;
}
}
public static boolean isLocationEnabled(Context context){
LocationManager locationManager = (LocationManager)context.getSystemService(Context.LOCATION_SERVICE);
boolean gpsEnabled = false;
boolean networkEnabled = false;
try {
gpsEnabled = locationManager.isProviderEnabled(LocationManager.GPS_PROVIDER);
} catch(Exception ex) {}
try {
networkEnabled = locationManager.isProviderEnabled(LocationManager.NETWORK_PROVIDER);
} catch(Exception ex) {}
return gpsEnabled && networkEnabled;
}
public static void startInstalledAppDetailsActivity(final Context context) {
if (context == null) {
return;
}
final Intent i = new Intent();
i.setAction(Settings.ACTION_APPLICATION_DETAILS_SETTINGS);
i.addCategory(Intent.CATEGORY_DEFAULT);
i.setData(Uri.parse("package:" + context.getPackageName()));
i.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
i.addFlags(Intent.FLAG_ACTIVITY_NO_HISTORY);
i.addFlags(Intent.FLAG_ACTIVITY_EXCLUDE_FROM_RECENTS);
context.startActivity(i);
}
public static boolean checkLocationPermission(Context context) {
String permission = "android.permission.ACCESS_FINE_LOCATION";
int res = context.checkCallingOrSelfPermission(permission);
return (res == PackageManager.PERMISSION_GRANTED);
}
public interface LocationCallback {
void onLastKnowLocationFetch(Location location);
void onLocationUpdate(Location location);
void onLocationPermissionDenied();
void onLocationSettingsError();
}
public void close() {
mGPSStatusReceiver.unRegisterReceiver();
}
}
5. In the activity use the below code
public class MainActivity extends AppCompatActivity implements GPSLocation.LocationCallback {
private GPSLocation mGPSLocation;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
mGPSLocation = new GPSLocation(this, this);
mGPSLocation.init();
}
#Override
public void onLastKnowLocationFetch(Location location) {
if(location != null) {
Log.d("ali ", "onLastKnowLocationFetch " + location);
}
}
#Override
public void onLocationUpdate(Location location) {
if(location != null) {
Log.d("ali ", "onLocationUpdate " + location);
}
}
#Override
public void onLocationPermissionDenied() {
}
#Override
public void onLocationSettingsError() {
}
#Override
protected void onStart() {
mGPSLocation.connect();
super.onStart();
}
#Override
public void onResume() {
super.onResume();
mGPSLocation.startLocationUpdates();
}
#Override
protected void onPause() {
super.onPause();
mGPSLocation.stopLocationUpdates();
}
#Override
protected void onStop() {
mGPSLocation.disconnect();
super.onStop();
}
#Override
protected void onDestroy() {
mGPSLocation.close();
super.onDestroy();
}
#Override
public void onRequestPermissionsResult(int requestCode, String permissions[], int[] grantResults) {
super.onRequestPermissionsResult(requestCode, permissions, grantResults);
if(requestCode == GPSLocation.LOCATION_PERMISSION_REQUEST_CODE) {
mGPSLocation.onRequestPermissionsResult(requestCode, permissions, grantResults);
}
}
#Override
public void onActivityResult(int requestCode, int resultCode, Intent data) {
super.onActivityResult(requestCode, resultCode, data);
if (requestCode == GPSLocation.REQUEST_CHECK_SETTINGS) {
mGPSLocation.onActivityResult(requestCode, resultCode, data);
}
}
}
The following code checks, if location is enabled or not. If not it shows alert dialog to enable location service.
LocationManager lm = (LocationManager)getSystemService(Context.LOCATION_SERVICE);
try {
gps_enabled = lm.isProviderEnabled(LocationManager.GPS_PROVIDER);
}catch (Exception ex){}
try{
network_enabled = lm.isProviderEnabled(LocationManager.NETWORK_PROVIDER);
}catch (Exception ex){}
if(!gps_enabled && !network_enabled){
AlertDialog.Builder dialog = new AlertDialog.Builder(this);
dialog.setMessage(getResources().getString(R.string.gps_network_not_enabled));
dialog.setPositiveButton(getResources().getString(R.string.open_location_settings), new DialogInterface.OnClickListener() {
#Override
public void onClick(DialogInterface paramDialogInterface, int paramInt) {
Intent myIntent = new Intent( Settings.ACTION_LOCATION_SOURCE_SETTINGS);
Startup.this.startActivity(myIntent);
}
});
dialog.setNegativeButton(getString(R.string.Cancel), new DialogInterface.OnClickListener() {
#Override
public void onClick(DialogInterface paramDialogInterface, int paramInt) {
// TODO Auto-generated method stub
}
});
dialog.show();
}
add below code in AndroidManifest.xml
<uses-permission android:name="android.permission.INTERNET" />
<uses-permission android:name="android.permission.ACCESS_FINE_LOCATION" />
<uses-permission android:name="android.permission.ACCESS_COARSE_LOCATION" />
Add this override method for me its worked fine--
#Override
public void onLocationChanged(Location location) {
getLocation("onLocationChanged");
}
I want to fetch user's current lat long on click of a button. I know that you can get the last known location using FusedLocationApi. But what I am not able to understand is, gps or location services needs to be turned on for this? If yes, how to check that the user has turned on location and get the current location. Also, how to include marshmallow permission checks in getting the location.
I have already referred:
1) googlesamples/android-play-location
2) googlesamples/android-XYZTouristAttractions
and many other links but unable to make a complete flow.
Code
public class AccessLocationFragment extends BaseFragment implements View.OnClickListener, LocationListener,
GoogleApiClient.ConnectionCallbacks, GoogleApiClient.OnConnectionFailedListener, GeneralDialogFragment.GeneralDialogClickListener {
private static final int MY_PERMISSIONS_REQUEST_LOCATION = 101;
private static final String TAG = AccessLocationFragment.class.getSimpleName();
private static final int REQUEST_CHECK_SETTINGS = 102;
private Button mAccessLocation;
private EditText mZipCode;
private Dialog progressDialog;
private GoogleApiClient mGoogleApiClient;
private Location mLastLocation;
public static AccessLocationFragment newInstance() {
return new AccessLocationFragment();
}
#Nullable
#Override
public View onCreateView(LayoutInflater inflater, #Nullable ViewGroup container, #Nullable Bundle savedInstanceState) {
return inflater.inflate(R.layout.fragment_access_location, container, false);
}
#Override
public void onViewCreated(View view, #Nullable Bundle savedInstanceState) {
super.onViewCreated(view, savedInstanceState);
RecycleApplication.getEventBus().register(this);
mAccessLocation = (Button) view.findViewById(R.id.access_location);
mZipCode = (EditText) view.findViewById(R.id.zip_code);
mAccessLocation.setOnClickListener(this);
mZipCode.setOnEditorActionListener(new TextView.OnEditorActionListener() {
#Override
public boolean onEditorAction(TextView v, int actionId, KeyEvent event) {
if (actionId == EditorInfo.IME_ACTION_DONE) {
String zipCode = mZipCode.getText().toString().trim();
if (TextUtils.isEmpty(zipCode)) {
Toast.makeText(mActivity, "Please enter zip code", Toast.LENGTH_SHORT).show();
} else {
Call<Address> response = mRecycleService.getAddress(zipCode);
response.enqueue(new GetLocationCallback(AccessLocationFragment.this));
}
}
return false;
}
});
// Create an instance of GoogleAPIClient.
if (mGoogleApiClient == null) {
mGoogleApiClient = new GoogleApiClient.Builder(mActivity)
.addConnectionCallbacks(this)
.addOnConnectionFailedListener(this)
.addApi(LocationServices.API)
.build();
}
if (!LocationUtils.checkFineLocationPermission(mActivity)) {
// See if user has denied permission in the past
if (shouldShowRequestPermissionRationale(android.Manifest.permission.ACCESS_FINE_LOCATION)) {
// Show a simple snackbar explaining the request instead
showPermissionSnackbar();
} else {
requestFineLocationPermission();
}
} else {
displayLocationSettingsRequest();
}
}
private void startHomeActivity(Address address) {
RecyclePreferences.getInstance().setCity(address.getCity());
RecyclePreferences.getInstance().setState(address.getState());
RecyclePreferences.getInstance().setLatitude(address.getLatitude());
RecyclePreferences.getInstance().setLongitude(address.getLongitude());
RecyclePreferences.getInstance().setZipCode(address.getZipCode());
startActivity(new Intent(mActivity, HomeActivity.class));
mActivity.finish();
}
#Override
public void onSuccess(Call<Address> call, Response<Address> response) {
mActivity.hideProgressDialog(progressDialog);
if (response.isSuccessful()) {
Address address = response.body();
startHomeActivity(address);
}
}
#Override
public void onFailure(Call<Address> call, Throwable t) {
mActivity.hideProgressDialog(progressDialog);
}
#Override
public void onClick(View view) {
if (view.getId() == R.id.access_location) {
fetchAddress(mLastLocation);
}
}
#Override
public void onRequestPermissionsResult(int requestCode, String permissions[], int[] grantResults) {
switch (requestCode) {
case MY_PERMISSIONS_REQUEST_LOCATION: {
if (grantResults[0] == PackageManager.PERMISSION_GRANTED) {
displayLocationSettingsRequest();
}
}
}
}
private void fetchAddress(Location location) {
mRecycleService = new RecycleRetrofitBuilder(mActivity).getService();
Call<Address> response = mRecycleService.getAddress(String.valueOf(location.getLatitude()), String.valueOf(location.getLongitude()));
progressDialog = mActivity.showProgressDialog(mActivity);
response.enqueue(new GetLocationCallback(AccessLocationFragment.this));
}
private void requestFineLocationPermission() {
requestPermissions(new String[]{Manifest.permission.ACCESS_FINE_LOCATION}, MY_PERMISSIONS_REQUEST_LOCATION);
}
private void showPermissionSnackbar() {
GeneralDialogFragment generalDialogFragment = GeneralDialogFragment.
newInstance("Permissions", "Allow Recycle the World to use your location.", "Allow", "Go Back", this);
mActivity.showDialogFragment(generalDialogFragment);
displayLocationSettingsRequest();
}
private void displayLocationSettingsRequest() {
LocationRequest locationRequest = LocationRequest.create();
locationRequest.setPriority(LocationRequest.PRIORITY_HIGH_ACCURACY);
locationRequest.setInterval(10000);
locationRequest.setFastestInterval(10000 / 2);
LocationSettingsRequest.Builder builder = new LocationSettingsRequest.Builder().addLocationRequest(locationRequest);
builder.setAlwaysShow(true);
PendingResult<LocationSettingsResult> result = LocationServices.SettingsApi.checkLocationSettings(mGoogleApiClient, builder.build());
result.setResultCallback(new ResultCallback<LocationSettingsResult>() {
#Override
public void onResult(LocationSettingsResult result) {
final Status status = result.getStatus();
switch (status.getStatusCode()) {
case LocationSettingsStatusCodes.SUCCESS:
getLocation();
break;
case LocationSettingsStatusCodes.RESOLUTION_REQUIRED:
Log.i(TAG, "Location settings are not satisfied. Show the user a dialog to upgrade location settings ");
try {
status.startResolutionForResult(mActivity, REQUEST_CHECK_SETTINGS);
} catch (IntentSender.SendIntentException e) {
Log.i(TAG, "PendingIntent unable to execute request.");
}
break;
case LocationSettingsStatusCodes.SETTINGS_CHANGE_UNAVAILABLE:
Log.i(TAG, "Location settings are inadequate, and cannot be fixed here. Dialog not created.");
break;
}
}
});
}
private void getLocation() {
if (ActivityCompat.checkSelfPermission(mActivity, Manifest.permission.ACCESS_FINE_LOCATION) != PackageManager.PERMISSION_GRANTED
&& ActivityCompat.checkSelfPermission(mActivity, Manifest.permission.ACCESS_COARSE_LOCATION) != PackageManager.PERMISSION_GRANTED) {
return;
}
mLastLocation = LocationServices.FusedLocationApi.getLastLocation(mGoogleApiClient);
}
#Override
public void onActivityResult(int requestCode, int resultCode, Intent data) {
super.onActivityResult(requestCode, resultCode, data);
if (requestCode == REQUEST_CHECK_SETTINGS) {
getLocation();
}
}
#Override
public void onStart() {
mGoogleApiClient.connect();
super.onStart();
}
#Override
public void onStop() {
mGoogleApiClient.disconnect();
super.onStop();
}
#Override
public void onConnected(#Nullable Bundle bundle) {
getLocation();
}
#Override
public void onDestroy() {
super.onDestroy();
RecycleApplication.getEventBus().unregister(this);
}
#Override
public void onConnectionSuspended(int i) {
}
#Override
public void onConnectionFailed(#NonNull ConnectionResult connectionResult) {
}
#Override
public void onOk(DialogFragment dialogFragment) {
dialogFragment.dismiss();
requestFineLocationPermission();
}
#Override
public void onCancel(DialogFragment dialogFragment) {
dialogFragment.dismiss();
}
}
Sorry, I haven't go through your code, I am just writing the functions that you have asked for in your question.
First, you need to build a connection to google api client like:
private synchronized void buildGoogleApiClient(){
mGoogleApiClient = new GoogleApiClient.Builder(GTApplication.getContext())
.addConnectionCallbacks(this)
.addOnConnectionFailedListener(this)
.addApi(LocationServices.API)
.build();
mGoogleApiClient.connect();
}
After this in my experience, you almost always get called onConnected() function where you can ask for the location permission after API level 23:
public void checkLocationPermission(){
if(ContextCompat.checkSelfPermission(this, Manifest.permission.ACCESS_FINE_LOCATION) != PackageManager.PERMISSION_GRANTED){
// You don't have the permission you need to request it
ActivityCompat.requestPermissions(this, Manifest.permission.ACCESS_FINE_LOCATION), REQ_CODE);
}else{
// You have the permission.
requestLocationAccess();
}
}
If you requested the permission your onRequestPermissionsResult() function will be called with the REQ_CODE. If you need more info to implement the events check the original documentation for runtime permissions it is very useful.
When you have the permission you can check if the location is enabled like:
public void requestLocationAccess(){
LocationRequest mLocationRequest = new LocationRequest();
mLocationRequest.setInterval((long) (LocationHelper.UPDATE_INTERVAL_IN_MILLISECONDS*1.1));
mLocationRequest.setFastestInterval(LocationHelper.UPDATE_INTERVAL_IN_MILLISECONDS);
mLocationRequest.setPriority(LocationRequest.PRIORITY_HIGH_ACCURACY);
final LocationSettingsRequest.Builder builder = new LocationSettingsRequest.Builder().addLocationRequest(mLocationRequest);
builder.setAlwaysShow(true); //this is the key ingredient
com.google.android.gms.common.api.PendingResult<LocationSettingsResult> result =
LocationServices.SettingsApi.checkLocationSettings(mGoogleApiClient, builder.build());
result.setResultCallback(new ResultCallback<LocationSettingsResult>(){
#Override
public void onResult(#NonNull LocationSettingsResult result){
if(requester != null){
final Status resultStatus = result.getStatus();
switch(resultStatus.getStatusCode()){
case LocationSettingsStatusCodes.SUCCESS:
// All location settings are satisfied. You can ask for the user's location HERE
break;
case LocationSettingsStatusCodes.RESOLUTION_REQUIRED:
// Location settings are not satisfied. But could be fixed by showing the user a dialog.
try{
resultStatus.startResolutionForResult(this, REQUEST_LOCATION);
break;
}catch(IntentSender.SendIntentException ignored){}
}
}
}
}
});
}
If the enable location dialog needed to be shown to the user you will get a callback in onActivityResult() function with the request code REQUEST_LOCATION)
That's it after you done with all this process you can call locationManager.getLastKnownLocation() or start location request or whatever you want.
PS.: I have cut this code from my bigger class, so please if you find any mistakes feel free to ask. I have specified only the case when everything goes well, because it contains the essence, you can handle the exceptions yourself I hope.
try this code:
public void showMap() {
mapFragment = (SupportMapFragment)getChildFragmentManager().findFragmentById(R.id.map);
if (map == null) {
map = mapFragment.getMap();
}
// Enable Zoom
map.getUiSettings().setZoomGesturesEnabled(true);
//set Map TYPE
map.setMapType(GoogleMap.MAP_TYPE_NORMAL);
//enable Current location Button
map.setMyLocationEnabled(true);
LocationManager locationManager = (LocationManager)getActivity().getSystemService(getActivity().LOCATION_SERVICE);
Criteria criteria = new Criteria();
String bestProvider = locationManager.getBestProvider(criteria, true);
if (ActivityCompat.checkSelfPermission(getContext(), Manifest.permission.ACCESS_FINE_LOCATION) != PackageManager.PERMISSION_GRANTED && ActivityCompat.checkSelfPermission(getActivity(), Manifest.permission.ACCESS_COARSE_LOCATION) != PackageManager.PERMISSION_GRANTED) {
// TODO: Consider calling
// ActivityCompat#requestPermissions
// here to request the missing permissions, and then overriding
// public void onRequestPermissionsResult(int requestCode, String[] permissions,
// int[] grantResults)
// to handle the case where the user grants the permission. See the documentation
// for ActivityCompat#requestPermissions for more details.
return;
}
Location location = locationManager.getLastKnownLocation(bestProvider);
if (location != null) {
onLocationChanged(location);
}
locationManager.requestLocationUpdates(bestProvider, 2000, 0, this);
}
#Override
public void onLocationChanged(Location location) {
latitude= location.getLatitude();
longitude=location.getLongitude();
LatLng loc = new LatLng(latitude, longitude);
if (marker!=null){
marker.remove();
}
marker= map.addMarker(new MarkerOptions().position(loc).title("Sparx IT Solutions"));
map.moveCamera(CameraUpdateFactory.newLatLng(loc));
map.animateCamera(CameraUpdateFactory.newLatLngZoom(loc, 16.0f));
}
#Override
public void onProviderDisabled(String provider) {
Intent intent = new Intent(Settings.ACTION_LOCATION_SOURCE_SETTINGS);
startActivity(intent);
Toast.makeText(getActivity().getBaseContext(), "Gps is turned off!!",
Toast.LENGTH_SHORT).show();
}
#Override
public void onProviderEnabled(String provider) {
Toast.makeText(getActivity().getBaseContext(), "Gps is turned on!! ",
Toast.LENGTH_SHORT).show();
}
I am coding to detect my current location in android marshmallow,but I am getting null location.Please tell any solution to resolve this problem.Google Map is working in my phone so why its returning null.
MainActivity.class
if (isGPSEnabled) {
if (location == null) {
mLocationManager.requestLocationUpdates(LocationManager.GPS_PROVIDER, 0, 0, locationListener);
if (mLocationManager != null) {
// mLocationManager.removeUpdates(locationListener);
location = mLocationManager.getLastKnownLocation(LocationManager.GPS_PROVIDER);
Log.i("location","location-->"+location);
tv_new.setText("Location:" +String.valueOf(location));
if (location != null) {
latitude = location.getLatitude();
longitude = location.getLongitude();
tv_lat.setText("Latitude:" + String.valueOf(latitude));
tv_lon.setText("Longitude:" +String.valueOf(longitude));
String filterAddress = "";
try {
Log.i("TAG", "geoCoder" + geoCoder);
List<Address> addresses = geoCoder.getFromLocation(latitude, longitude, 1);
Log.i("TAG", "addresses" + addresses.size()+latitude+longitude);
for (int i = 0; i < addresses.get(0)
.getMaxAddressLineIndex(); i++) {
filterAddress += addresses.get(0).getAddressLine(i)
+ " ";
Log.i("TAG", "filterAddress" + filterAddress);
tv_address.setText("Address"+ filterAddress);
}
}
catch (IOException ex) {
Log.i("TAG", "filterAddress catch 1st"+ ex+ filterAddress);
ex.printStackTrace();
} catch (Exception e2) {
Log.i("TAG", "filterAddress catch 2nd"+e2+"--->"+geoCoder);
// TODO: handle exception
e2.printStackTrace();
}
}
}
}
}
Output
Location:null in ASUS_ZOOLD Phone
Try like this ..
public class Splash extends AppCompatActivity implements GoogleApiClient.ConnectionCallbacks, GoogleApiClient.OnConnectionFailedListener, LocationListener, ResultCallback<LocationSettingsResult> {
/** Define all global variables over here */
Context context;
private static final int PLAY_SERVICES_RESOLUTION_REQUEST = 9000;
// All GPS based work goes over here ..
protected static final String TAG = "UserNavigation";
protected static final int REQUEST_CHECK_SETTINGS = 0x1;
public static final long UPDATE_INTERVAL_IN_MILLISECONDS = 1000;
public static final long FASTEST_UPDATE_INTERVAL_IN_MILLISECONDS = UPDATE_INTERVAL_IN_MILLISECONDS / 2;
protected GoogleApiClient mGoogleApiClient;
protected LocationRequest mLocationRequest;
protected LocationSettingsRequest mLocationSettingsRequest;
protected Location mCurrentLocation;
protected Boolean mRequestingLocationUpdates = false;
protected String mLastUpdateTime;
private static final int PERMISSION_ACCESS_COARSE_LOCATION = 1;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_splash);
context = Splash.this;
SharedPrefUtil.setSharedPref(context, "alert", false);
new TestAsync().execute();
initui();
PulsatorLayout pulsator = (PulsatorLayout) findViewById(R.id.pulsator);
pulsator.start();
if(Build.VERSION.SDK_INT >= Build.VERSION_CODES.M)
{
if (ContextCompat.checkSelfPermission(this, Manifest.permission.ACCESS_FINE_LOCATION) != PackageManager.PERMISSION_GRANTED || ContextCompat.checkSelfPermission(this, Manifest.permission.CALL_PHONE) != PackageManager.PERMISSION_GRANTED)
ActivityCompat.requestPermissions(this, new String[]{Manifest.permission.ACCESS_FINE_LOCATION, Manifest.permission.CALL_PHONE}, PERMISSION_ACCESS_COARSE_LOCATION);
else
checkLocationSettings();
}
else
checkLocationSettings();
}
#Override
public void onRequestPermissionsResult(int requestCode, String[] permissions, int[] grantResults) {
switch (requestCode) {
case PERMISSION_ACCESS_COARSE_LOCATION:
if (grantResults.length > 0 && grantResults[0] == PackageManager.PERMISSION_GRANTED && grantResults[1] == PackageManager.PERMISSION_GRANTED)
checkLocationSettings();
else
finish();
break;
}
}
private void initui() {
initiateSplashWork();
}
private void initiateSplashWork() {
if (checkPlayServices()) {
initiateGPS();
}
}
private void initiateGPS()
{
buildGoogleApiClient();
createLocationRequest();
buildLocationSettingsRequest();
}
private boolean checkPlayServices() {
GoogleApiAvailability apiAvailability = GoogleApiAvailability.getInstance();
int resultCode = apiAvailability.isGooglePlayServicesAvailable(this);
if (resultCode != ConnectionResult.SUCCESS) {
if (apiAvailability.isUserResolvableError(resultCode)) {
apiAvailability.getErrorDialog(this, resultCode, PLAY_SERVICES_RESOLUTION_REQUEST)
.show();
} else {
Toast.makeText(context, R.string.toast_device_not_support, Toast.LENGTH_SHORT).show();
finish();
}
return false;
}
return true;
}
/** All GPS based method callback */
#Override
public void onConnected(Bundle bundle) {
Thread logoTimer = new Thread() {
public void run() {
try {
int logoTimer = 0;
while (logoTimer < 5000) {
sleep(100);
logoTimer = logoTimer + 100;
}
} catch (InterruptedException e) {
e.printStackTrace();
}
}
};
logoTimer.start();
if (mCurrentLocation == null)
{
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M)
{
if (checkSelfPermission(Manifest.permission.ACCESS_FINE_LOCATION) != PackageManager.PERMISSION_GRANTED)
{
mCurrentLocation = LocationServices.FusedLocationApi.getLastLocation(mGoogleApiClient);
mLastUpdateTime = DateFormat.getTimeInstance().format(new Date());
return;
}
else
{
mCurrentLocation = LocationServices.FusedLocationApi.getLastLocation(mGoogleApiClient);
mLastUpdateTime = DateFormat.getTimeInstance().format(new Date());
}
}
else
{
mCurrentLocation = LocationServices.FusedLocationApi.getLastLocation(mGoogleApiClient);
mLastUpdateTime = DateFormat.getTimeInstance().format(new Date());
}
}
}
private void initiateNext()
{
Thread logoTimer = new Thread() {
public void run()
{
try
{
int logoTimer = 0;
while (logoTimer < 5000) {
sleep(100);
logoTimer = logoTimer + 100;
}
Intent intent = new Intent(context, OneClassBuilt.class);
startActivity(intent);
}
catch (InterruptedException e)
{
e.printStackTrace();
}
finally
{
finish();
}
}
};
logoTimer.start();
}
#Override
public void onConnectionSuspended(int i) {
}
#Override
public void onConnectionFailed(ConnectionResult connectionResult) {
}
#Override
public void onLocationChanged(Location location) {
mCurrentLocation = location;
mLastUpdateTime = DateFormat.getTimeInstance().format(new Date());
Toast.makeText(context, "onLocationChanged method : " + location.getLatitude() + " ____ " + location.getLongitude(), Toast.LENGTH_SHORT).show();
SharedPrefUtil.setSharedPref(context, "lat", String.valueOf(location.getLatitude()));
SharedPrefUtil.setSharedPref(context, "lon", String.valueOf(location.getLongitude()));
}
protected synchronized void buildGoogleApiClient() {
Log.i(TAG, "Building GoogleApiClient");
mGoogleApiClient = new GoogleApiClient.Builder(this).addConnectionCallbacks(this).addOnConnectionFailedListener(this).addApi(LocationServices.API).build();
}
protected void createLocationRequest() {
mLocationRequest = new LocationRequest();
mLocationRequest.setInterval(UPDATE_INTERVAL_IN_MILLISECONDS);
mLocationRequest.setFastestInterval(FASTEST_UPDATE_INTERVAL_IN_MILLISECONDS);
mLocationRequest.setPriority(LocationRequest.PRIORITY_HIGH_ACCURACY);
}
protected void buildLocationSettingsRequest() {
LocationSettingsRequest.Builder builder = new LocationSettingsRequest.Builder();
builder.addLocationRequest(mLocationRequest);
builder.setAlwaysShow(true);
mLocationSettingsRequest = builder.build();
}
protected void checkLocationSettings() {
PendingResult<LocationSettingsResult> result = LocationServices.SettingsApi.checkLocationSettings(mGoogleApiClient, mLocationSettingsRequest);
result.setResultCallback(this);
}
#Override
public void onResult(LocationSettingsResult locationSettingsResult) {
final Status status = locationSettingsResult.getStatus();
switch (status.getStatusCode()) {
case LocationSettingsStatusCodes.SUCCESS:
Log.i(TAG, "All location settings are satisfied.");
startLocationUpdates();
initiateNext();
break;
case LocationSettingsStatusCodes.RESOLUTION_REQUIRED:
Log.i(TAG, "Location settings are not satisfied. Show the user a dialog to" + "upgrade location settings ");
try {
status.startResolutionForResult(Splash.this, REQUEST_CHECK_SETTINGS);
} catch (IntentSender.SendIntentException e) {
Log.i(TAG, "PendingIntent unable to execute request.");
}
break;
case LocationSettingsStatusCodes.SETTINGS_CHANGE_UNAVAILABLE:
finish();
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) {
switch (requestCode) {
case REQUEST_CHECK_SETTINGS:
switch (resultCode) {
case Activity.RESULT_OK:
Log.i(TAG, "User agreed to make required location settings changes.");
startLocationUpdates();
initiateNext();
break;
case Activity.RESULT_CANCELED:
Log.i(TAG, "User chose not to make required location settings changes.");
finish();
break;
}
break;
}
}
protected void startLocationUpdates() {
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) {
if (checkSelfPermission(Manifest.permission.ACCESS_FINE_LOCATION) != PackageManager.PERMISSION_GRANTED && checkSelfPermission(Manifest.permission.ACCESS_COARSE_LOCATION) != PackageManager.PERMISSION_GRANTED) {
return;
}
}
LocationServices.FusedLocationApi.requestLocationUpdates(mGoogleApiClient, mLocationRequest, this).setResultCallback(new ResultCallback<Status>() {
#Override
public void onResult(Status status) {
mRequestingLocationUpdates = true;
}
});
}
protected void stopLocationUpdates() {
LocationServices.FusedLocationApi.removeLocationUpdates(mGoogleApiClient, this).setResultCallback(new ResultCallback<Status>() {
#Override
public void onResult(Status status) {
mRequestingLocationUpdates = false;
}
});
}
#Override
protected void onStart() {
super.onStart();
if (mGoogleApiClient != null)
mGoogleApiClient.connect();
}
#Override
public void onResume() {
super.onResume();
if (mGoogleApiClient != null && mGoogleApiClient.isConnected() && mRequestingLocationUpdates)
startLocationUpdates();
}
#Override
protected void onPause() {
super.onPause();
if (mGoogleApiClient != null && mGoogleApiClient.isConnected())
stopLocationUpdates();
}
#Override
protected void onStop() {
if (mGoogleApiClient != null && mGoogleApiClient.isConnected()) {
mGoogleApiClient.disconnect();
}
super.onStop();
}
} // End of main class over here ..
In Manifest :
<uses-permission android:name="android.permission.ACCESS_FINE_LOCATION" />
And in App gradle file over dependency add..
compile 'com.google.android.gms:play-services:8.4.0'
compile 'com.google.android.gms:play-services-location:8.1.0'
Add this code to ask for permission
`
private void checkForPermisson {
if (ActivityCompat.checkSelfPermission(this,
Manifest.permission.ACCESS_FINE_LOCATION) != PackageManager.PERMISSION_GRANTED &&
ActivityCompat.checkSelfPermission(this,
Manifest.permission.ACCESS_COARSE_LOCATION) != PackageManager.PERMISSION_GRANTED) {
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) {
requestPermissions(new String[]{Manifest.permission.ACCESS_FINE_LOCATION}, 202);
}
return;
} else {
//add your if block here
}
}
#Override
public void onRequestPermissionsResult(int requestCode, String[] permissions, int[] grantResults) {
switch (requestCode) {
case 202:
if (grantResults.length > 0 && grantResults[0] == PackageManager.PERMISSION_GRANTED) {
//add your if block here
} else {
Log.e(TAG, "else RequestPermission");
}
break;
default:
return;
}
}
`