0

In my app I fetch GPS coordinates from the user. When the GPS was just activated my app continues even before the coordinates were fetched, so the location is null. I noticed that the onLocationChanged method does as it should and might somehow be a key to it, but how do I make sure that the code in the main class doesn’t fetch empty values and waits until the location is not null?

The main code:

if (ContextCompat.checkSelfPermission(getActivity(), Manifest.permission.ACCESS_FINE_LOCATION)
                    != PackageManager.PERMISSION_GRANTED) {
  requestPermissions(new String[]{Manifest.permission.ACCESS_FINE_LOCATION}, 1);
   } else {
    progressBar.setVisibility(View.VISIBLE);
    GPSFetch t = new GPSFetch(getActivity().getApplicationContext());
    Location location = t.getLocation();

    if (location == null) {
       //Toast
    } else {
        lat = location.getLatitude();
        lon = location.getLongitude();
    }
    new GetContacts().execute();
}

The GPSFetch:

public Location getLocation(){
    if (ContextCompat.checkSelfPermission( context, android.Manifest.permission.ACCESS_FINE_LOCATION ) != PackageManager.PERMISSION_GRANTED) 
{
        return null;
    }
    try {
        LocationManager lm = (LocationManager) context.getSystemService(LOCATION_SERVICE);
        boolean isGPSEnabled = lm.isProviderEnabled(LocationManager.GPS_PROVIDER);
        if (isGPSEnabled){
            lm.requestLocationUpdates(LocationManager.GPS_PROVIDER, 5000,10,this);
            Location loc = lm.getLastKnownLocation(LocationManager.GPS_PROVIDER);
            return loc;
        }else{

        }
    }catch (Exception e){
        e.printStackTrace();
    }
    return null;
}


@Override
public void onLocationChanged(Location location) {
      Log.d("4", "changed");
}
Mike Kng
  • 255
  • 2
  • 11
  • 1
    _"and waits until the location is not null"_ Don't wait. Structure your code in such a way that you deal with location data when you get it (i.e. when `onLocationChanged` is called), and until then your app behaves as if the location is unknown. – Michael Aug 09 '18 at 10:12
  • Okay, but how does the onLocationChanged method make itself noticable in my main code then? Do I need a listener in my main class to recognize that the value changed or can it be solved a way better way? – Mike Kng Aug 09 '18 at 10:45
  • If code outside of `GPSFetch` needs to know when there's new location data available, then yes, one way of solving that would be to pass some sort of callback to it or make it return an observable. – Michael Aug 09 '18 at 11:04
  • I thought about letting my main code return a toast for example if the location is null and as soon as the onLocationChanged method is called the main code continues with what it should acutally do. Is that recommendable? – Mike Kng Aug 09 '18 at 11:09
  • It depends a lot on what _"what it should actually do"_ means. Is it meaningful to tell the user that the current location is null? For example, if you're using the location to indicate a position on a map, then there are probably better ways of indicating to the user that the current location is unknown. – Michael Aug 09 '18 at 11:22
  • I need the location to fetch correct data from a server. It is not necessary to tell when the location is null, I just need the code to only call methods when the location is not null, but like it is now it’s not checking on the locations value and just can‘t continue when the location is null in the beginning – Mike Kng Aug 09 '18 at 11:34

2 Answers2

0

The method is called onLocationChanged. Which means that there IS a value.

Note: You are actually fetching a GPS coordinate from the local play services api of the android device. Read more about location services here

Alan Deep
  • 2,037
  • 1
  • 14
  • 22
  • Are you sure about that? At least at first my device returns whatever toast or logcat notification I enter into the if(location==null) statement? – Mike Kng Aug 09 '18 at 10:39
0
First you check your gps is on or not, if gps is on then onlocation changed method give lat and lon.



you can check using following code



  public static boolean checkGps(Activity mContext) {

        LocationManager service = (LocationManager) mContext.getSystemService(LOCATION_SERVICE);
        boolean enabled = service.isProviderEnabled(LocationManager.GPS_PROVIDER);

        return enabled;

    }




its return true then gps on otherwise not




if gps not on then on gps programatically using this code



    public void displayLocationSettingsRequest() {
        GoogleApiClient googleApiClient = new GoogleApiClient.Builder(this)
                .addApi(LocationServices.API).build();
        googleApiClient.connect();

        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(googleApiClient, builder.build());
        result.setResultCallback(new ResultCallback<LocationSettingsResult>() {
            @Override
            public void onResult(LocationSettingsResult result) {
                final Status status = result.getStatus();
                switch (status.getStatusCode()) {
                    case LocationSettingsStatusCodes.SUCCESS:
                        Log.e("LocationSetting.SUCCESS", "All location settings are satisfied.");
//                        openMap();
                        break;
                    case LocationSettingsStatusCodes.RESOLUTION_REQUIRED:
                        Log.e("LocationSetting.SUCCESS", "Location settings are not satisfied. Show the user a dialog to upgrade location settings ");

                        try {
                            // Show the dialog by calling startResolutionForResult(), and check the result
                            // in onActivityResult().
                            status.startResolutionForResult(HomeActivity.this, REQUEST_CHECK_SETTINGS);
                        } catch (IntentSender.SendIntentException e) {
                            Log.e("LocationSetting.SUCCESS", "PendingIntent unable to execute request.");
                        }
                        break;
                    case LocationSettingsStatusCodes.SETTINGS_CHANGE_UNAVAILABLE:
                        Log.e("LocationSetting.SUCCESS", "Location settings are inadequate, and cannot be fixed here. Dialog not created.");
                        break;
                }
            }
        });
    }



this ask you about gps on or cancel if you press ok then you can fetch result of its in onactivityresult method



like this



  @Override
    public void onActivityResult(int requestCode, int resultCode, Intent data) {

        if (requestCode == 100) {
            if (resultCode == Activity.RESULT_OK) {
                String result = data.getStringExtra("result");
                Log.e("RESULT_OK", result + "");


              // now your gps is on you can handle your location code here
            }
            if (resultCode == Activity.RESULT_CANCELED) {
                Utils.showToastPopup(this, "Please Turn On Gps");

                // show custom popup when user denied this gps permission and check again 
                when click button or on resume 
            }
        }
}



and then fetch your lat lon inside onlocationchanged



 @Override
    public void onLocationChanged(Location location) {


        latitude = location.getLatitude();
        longitude = location.getLongitude();

}
Vishnu Saini
  • 129
  • 5
  • Okay, but how do I notify the main class that the location data in the GPS class has been updated? – Mike Kng Aug 09 '18 at 12:49
  • you can create a service like GPSTracker which is continue running in background and also implement a locationlistener which calling onlocationchanged continue if gps is on then you can create a method inside service which is return lat and lon and you find your lat lon from anywhere using instance of gpsTracker class – Vishnu Saini Aug 09 '18 at 12:56
  • Can you show me how a listener would look like that recognizes a change of onLocationChanged? – Mike Kng Aug 09 '18 at 13:06
  • https://stackoverflow.com/questions/28535703/best-way-to-get-user-gps-location-in-background-in-android you can see background service just like it. – Vishnu Saini Aug 09 '18 at 13:17
  • Can you tell me why my location even returns null at first? Can‘t the device fetch it properly or what is that problem? – Mike Kng Aug 09 '18 at 13:44
  • 1
    check in another device sometime happen device issue i already faced device issue so check in another device – Vishnu Saini Aug 09 '18 at 14:18