2

I am using fused location by comparing the current location with given location from response.

It's working fine. But when I turn off the location in settings and then turn on the location, the below method is not working. It directly falls in else part, where showing as location : null in toast message.. Only when I uninstall the app and then install, it works. I couldn't figure out why fused location is not working after turning off and on the location in google settings.

In onCreate method

call_permissions();

private void call_permissions() {
        int result;
        List<String> listPermissionsNeeded = new ArrayList<>();
        for (String p : permissions) {
            result = ContextCompat.checkSelfPermission(getApplicationContext(), p);
            if (result != PackageManager.PERMISSION_GRANTED) {
                listPermissionsNeeded.add(p);
            }
        }
        if (!listPermissionsNeeded.isEmpty()) {
            ActivityCompat.requestPermissions(this, listPermissionsNeeded.toArray
                    (new String[listPermissionsNeeded.size()]), MULTIPLE_PERMISSIONS);
        } else {

            getLocation(); //here using getLocation.
            //    splash_timer();
        }
        return;
    }



public static final int MULTIPLE_PERMISSIONS = 10;
    String[] permissions = new String[]{
            Manifest.permission.WRITE_EXTERNAL_STORAGE,
            Manifest.permission.CAMERA,
            Manifest.permission.ACCESS_FINE_LOCATION};


void getLocation() {
        if (ContextCompat.checkSelfPermission(EducationAndFeedbackActivity.this, Manifest.permission.ACCESS_FINE_LOCATION) == PackageManager.PERMISSION_GRANTED) {
            FusedLocationProviderClient mFusedLocationClient = LocationServices.getFusedLocationProviderClient(this);

            mFusedLocationClient.getLastLocation()
                    .addOnCompleteListener(this, new OnCompleteListener<Location>() {
                        @Override
                        public void onComplete(@NonNull Task<Location> task) {
                            if (task.isSuccessful() && task.getResult() != null) {
                                Location mLastLocation = task.getResult();
                                if (AppUtils.isMockLocationEnabled(mLastLocation, EducationAndFeedbackActivity.this)) {
                                    //Toast.makeText(EducationAndFeedbackActivity.this, "Matikan Fake Gps", Toast.LENGTH_SHORT).show();
                                    final Dialog dialog = new Dialog(EducationAndFeedbackActivity.this);
                                    dialog.requestWindowFeature(Window.FEATURE_NO_TITLE);
                                    dialog.setContentView(R.layout.custom_alert_response_accepted1);

                                    Button ok = (Button) dialog.findViewById(R.id.ok_button);
                                    TextView textView = (TextView) dialog.findViewById(R.id.response);
                                    textView.setText("Matikan Fake Gps!\nMohon matikan lokasi tiruan di setting pengembang");

                                    Button cancel = (Button) dialog.findViewById(R.id.Cancel_button);

                                    dialog.setCancelable(false);
                                    dialog.show();

                                    ok.setOnClickListener(new View.OnClickListener() {
                                        @Override
                                        public void onClick(View view) {
                                            startActivity(new Intent(android.provider.Settings.ACTION_APPLICATION_DEVELOPMENT_SETTINGS));
                                            dialog.dismiss();
                                            finish();
                                        }
                                    });
                                    cancel.setOnClickListener(new View.OnClickListener() {
                                        @Override
                                        public void onClick(View view) {
                                            dialog.dismiss();
                                            finish();
                                        }
                                    });
                                    return;
                                } else {
                                    Log.e("Current lat", "Current lat" + mLastLocation.getLatitude());
                                    Log.e("Current long", "Current long" + mLastLocation.getLongitude());
                                    Log.e("retailer lat", latitude);
                                    Log.e("retailer long", longitude);
                                    double rangess = AppUtils.distance(Double.parseDouble(latitude), Double.parseDouble(longitude) , mLastLocation.getLatitude(), mLastLocation.getLongitude());
                                    Log.e("ranges", "rangess" + rangess);
                                    Log.e("feedback range", "feedback range" + rangess);
                                    if(feedbackrange!=null) {
                                        if (rangess <= Double.parseDouble(feedbackrange)) {
                                            Log.e("Range is less", "Range is less"); //nothing to do.
                                        } else {
                                            showDialogAlert(EducationAndFeedbackActivity.this, getString(R.string.education_feedback_alert));
                                        }
                                    }
                                }

                            } /*else {
                                Toast.makeText(getApplicationContext(), "Location null", Toast.LENGTH_LONG).show();

                            }*/
                        }
                    });
        }
    }

In the above method, it displays location null after turning off and on the location from google settings. :(

 @Override
    public void onRequestPermissionsResult(int requestCode, String permissions[], int[] grantResults) {
        switch (requestCode) {
            case MULTIPLE_PERMISSIONS: {
                if (grantResults.length > 0 && grantResults[0] == PackageManager.PERMISSION_GRANTED) {
                    // permissions granted.
                    Toast.makeText(this, "Permission Granted, Now you can Location access.", Toast.LENGTH_LONG).show();
                    getLocation();
                    //  splash_timer();
                } /*else {
                   *//* Toast.makeText(this, "Permission Denied, Now you cannot Location access.", Toast.LENGTH_LONG).show();
                    finish();*//*
                    // no permissions granted.
                }*/
                return;
            }

        }
    }
Walter
  • 189
  • 2
  • 16

2 Answers2

0

According to the documentation

The location object may be null in the following situations:

Location is turned off in the device settings. The result could be null even if the last location was previously retrieved because disabling location also clears the cache.

The device never recorded its location, which could be the case of a new device or a device that has been restored to factory settings.

Google Play services on the device has restarted, and there is no active Fused Location Provider client that has requested location after the services restarted. To avoid this situation you can create a new client and request location updates yourself. For more information, see Receiving Location Updates.

The first point describes your current situation as turning location off clears the cache and thus getLastLocation() returns a null as there is no previously known location stored.

You could instead use getCurrentLocation(...) if your current Play services version supports it or do a one-off requestLocationUpdates(...) to fetch live location.

Droid
  • 528
  • 1
  • 5
  • 12
0

As Droid said, disabling and re-enabling device location clears the cache, meaning that getLastLocation() returns null.

I got around this by then calling getCurrentLocation()

However, it seems that you must use LocationRequest.PRIORITY_HIGH_ACCURACY or else even getCurrentLocation() returns null. This worked on my Oneplus6t with only the ACCESS_COARSE_LOCATION granted. However, for other devices (including Pixels) the ACCESS_FINE_LOCATION permission is also required.

The documentation does not mention either of these things, but my guess that the first location the device calculates must be fairly precise, meaning that a high accuracy priority is required. Later requests can be less precise because the device already knows where in the world you are.

John
  • 1