如何在Android上以编程方式启用或禁用GPS ?

时间:2022-08-26 00:02:21

I know that the question about turning on/off GPS programatically on android has been discussed many times, and the answer is always the same:

我知道关于在android上按程序打开/关闭GPS的问题已经讨论过很多次了,答案总是一样的:

"You can't for security/privacy reasons, you have to forward to location preferences screen and let the user enable/disable it."

“你不能出于安全或隐私的原因,你必须转发到位置设置界面,让用户启用/禁用它。”

I understand that, however I recently bought Tasker from the market and, among many other things that you can accomplish with it, you can set rules to auto-enable GPS on entering pre-determined applications and disable it on exit (see here for the tutorial on how to do it, and it just works!) and this app can't be signed with the firmware signing key as it works on many android versions and different devices and you don't even need to be rooted.

Tasker我明白了,但是我最近买了从市场,在许多其他的事情,你可以完成,你可以设置规则auto-enable GPS进入预先确定的应用程序,禁用它退出(看到的教程怎么做,和它的作品!)和这个程序不能签署与固件签署主要适用于许多android版本和不同的设备,你甚至不需要扎根。

I would like to do this in my app. Of course, I don't want to blow up the users privacy, so I would first ask the user if he wants to turn it on automatically with the typical "remember my decision" checkbox and if he answers yes, enable it.

我想在我的app中这样做。当然,我不想破坏用户的隐私,所以我首先会问用户,他是否想用典型的“记住我的决定”复选框自动打开它,如果他回答是,启用它。

Does anybody have any idea or clue on how Tasker achieves this?

有人知道Tasker公司是如何做到这一点的吗?

12 个解决方案

#1


150  

the GPS can be toggled by exploiting a bug in the power manager widget. see this xda thread for discussion.

可以利用power manager小部件中的一个bug来切换GPS。请参阅此xda线程进行讨论。

here's some example code i use

下面是我使用的一些示例代码

private void turnGPSOn(){
    String provider = Settings.Secure.getString(getContentResolver(), Settings.Secure.LOCATION_PROVIDERS_ALLOWED);

    if(!provider.contains("gps")){ //if gps is disabled
        final Intent poke = new Intent();
        poke.setClassName("com.android.settings", "com.android.settings.widget.SettingsAppWidgetProvider"); 
        poke.addCategory(Intent.CATEGORY_ALTERNATIVE);
        poke.setData(Uri.parse("3")); 
        sendBroadcast(poke);
    }
}

private void turnGPSOff(){
    String provider = Settings.Secure.getString(getContentResolver(), Settings.Secure.LOCATION_PROVIDERS_ALLOWED);

    if(provider.contains("gps")){ //if gps is enabled
        final Intent poke = new Intent();
        poke.setClassName("com.android.settings", "com.android.settings.widget.SettingsAppWidgetProvider");
        poke.addCategory(Intent.CATEGORY_ALTERNATIVE);
        poke.setData(Uri.parse("3")); 
        sendBroadcast(poke);
    }
}

use the following to test if the existing version of the power control widget is one which will allow you to toggle the gps.

使用以下工具来测试电源控制小部件的现有版本是否允许您切换gps。

private boolean canToggleGPS() {
    PackageManager pacman = getPackageManager();
    PackageInfo pacInfo = null;

    try {
        pacInfo = pacman.getPackageInfo("com.android.settings", PackageManager.GET_RECEIVERS);
    } catch (NameNotFoundException e) {
        return false; //package not found
    }

    if(pacInfo != null){
        for(ActivityInfo actInfo : pacInfo.receivers){
            //test if recevier is exported. if so, we can toggle GPS.
            if(actInfo.name.equals("com.android.settings.widget.SettingsAppWidgetProvider") && actInfo.exported){
                return true;
            }
        }
    }

    return false; //default
}

#2


55  

All these answers are not allowed now. Here is the correct one:

所有这些答案现在都不允许。这是正确的一条:

For all those still looking for the Answer:

对于那些仍在寻找答案的人:

Here is how OLA Cabs and other such apps are doing it.

以下是OLA Cabs和其他类似应用程序是如何做到这一点的。

Add this in your onCreate

在onCreate中添加这个

if (googleApiClient == null) {
    googleApiClient = new GoogleApiClient.Builder(this)
            .addApi(LocationServices.API).addConnectionCallbacks(this)
            .addOnConnectionFailedListener(Login.this).build();
    googleApiClient.connect();
            LocationRequest locationRequest = LocationRequest.create();
    locationRequest.setPriority(LocationRequest.PRIORITY_HIGH_ACCURACY);
    locationRequest.setInterval(30 * 1000);
    locationRequest.setFastestInterval(5 * 1000);
    LocationSettingsRequest.Builder builder = new LocationSettingsRequest.Builder()
            .addLocationRequest(locationRequest);

    // **************************
    builder.setAlwaysShow(true); // this is the key ingredient
    // **************************

    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();
            final LocationSettingsStates state = result
                    .getLocationSettingsStates();
            switch (status.getStatusCode()) {
            case LocationSettingsStatusCodes.SUCCESS:
                // All location settings are satisfied. The client can
                // initialize location
                // requests here.
                break;
            case LocationSettingsStatusCodes.RESOLUTION_REQUIRED:
                // Location settings are not satisfied. But could be
                // fixed by showing the user
                // a dialog.
                try {
                    // Show the dialog by calling
                    // startResolutionForResult(),
                    // and check the result in onActivityResult().
                    status.startResolutionForResult(Login.this, 1000);
                } 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;
            }
        }
    });
}

These are the implmented methods:

这些都是被要求的方法:

@Override
public void onConnected(Bundle arg0) {
    // TODO Auto-generated method stub

}

@Override
public void onConnectionSuspended(int arg0) {
    // TODO Auto-generated method stub

}

@Override
public void onConnectionFailed(ConnectionResult arg0) {
    // TODO Auto-generated method stub

}

Here is the Android Documentation for the same.

这是同样的Android文档。

This is to help other guys if they are still struggling:

这是为了帮助那些还在挣扎的人:

Edit: Adding Irfan Raza's comment for more help.

编辑:添加Irfan Raza的评论以获得更多帮助。

@Override protected void onActivityResult(int requestCode, int resultCode, Intent data) {
     if (requestCode == 1000) {
         if(resultCode == Activity.RESULT_OK){
             String result=data.getStringExtra("result"); 
         } if (resultCode == Activity.RESULT_CANCELED) {
             //Write your code if there's no result 
         } 
    } 
} 

#3


47  

ENABLE GPS:

启用GPS:

Intent intent=new Intent("android.location.GPS_ENABLED_CHANGE");
intent.putExtra("enabled", true);
sendBroadcast(intent);

DISABLE GPS:

禁用GPS:

Intent intent = new Intent("android.location.GPS_ENABLED_CHANGE");
intent.putExtra("enabled", false);
sendBroadcast(intent);

#4


28  

This code works on ROOTED phones if the app is moved to /system/aps, and they have the following permissions in the manifest:

如果将应用程序移动到/system/aps中,则此代码可以在有根的手机上工作,并且在清单中具有以下权限:

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

Code

代码

private void turnGpsOn (Context context) {
    beforeEnable = Settings.Secure.getString (context.getContentResolver(),
                                              Settings.Secure.LOCATION_PROVIDERS_ALLOWED);
    String newSet = String.format ("%s,%s",
                                   beforeEnable,
                                   LocationManager.GPS_PROVIDER);
    try {
        Settings.Secure.putString (context.getContentResolver(),
                                   Settings.Secure.LOCATION_PROVIDERS_ALLOWED,
                                   newSet); 
    } catch(Exception e) {}
}


private void turnGpsOff (Context context) {
    if (null == beforeEnable) {
        String str = Settings.Secure.getString (context.getContentResolver(),
                                                Settings.Secure.LOCATION_PROVIDERS_ALLOWED);
        if (null == str) {
            str = "";
        } else {                
            String[] list = str.split (",");
            str = "";
            int j = 0;
            for (int i = 0; i < list.length; i++) {
                if (!list[i].equals (LocationManager.GPS_PROVIDER)) {
                    if (j > 0) {
                        str += ",";
                    }
                    str += list[i];
                    j++;
                }
            }
            beforeEnable = str;
        }
    }
    try {
        Settings.Secure.putString (context.getContentResolver(),
                                   Settings.Secure.LOCATION_PROVIDERS_ALLOWED,
                                   beforeEnable);
    } catch(Exception e) {}
}

#5


20  

Since Android version 4.4, you can't enable/disable gps programatically. If you try the code proposed on this answer, an exception will be fired.

由于Android版本4.4,您不能按程序启用/禁用gps。如果您尝试在此答案上建议的代码,就会触发异常。

java.lang.SecurityException: Permission Denial: not allowed to send broadcast android.location.GPS_ENABLED_CHANGE

#6


13  

Instead of using intent Settings.ACTION_LOCATION_SOURCE_SETTINGS you can directly able to show pop up in your app like Google Map & on Gps on click of ok button their is no need to redirect to setting simply you need to use my code as

而不是使用意图设置。ACTION_LOCATION_SOURCE_SETTINGS你可以直接显示在你的应用中,比如谷歌Map和Gps上点击ok按钮,你不需要重定向到设置你只需要使用我的代码

Note : This line of code automatic open the dialog box if Location is not on. This piece of line is used in Google Map also

注意:如果位置不在,这行代码自动打开对话框。这条线也用在谷歌地图中

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


LocationRequest mLocationRequest;
GoogleApiClient mGoogleApiClient;
PendingResult<LocationSettingsResult> result;
final static int REQUEST_LOCATION = 199;

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

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

}

@Override
public void onConnected(Bundle bundle) {

    mLocationRequest = LocationRequest.create();
    mLocationRequest.setPriority(LocationRequest.PRIORITY_HIGH_ACCURACY);
    mLocationRequest.setInterval(30 * 1000);
    mLocationRequest.setFastestInterval(5 * 1000);

    LocationSettingsRequest.Builder builder = new LocationSettingsRequest.Builder()
            .addLocationRequest(mLocationRequest);
    builder.setAlwaysShow(true);

    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 state = result.getLocationSettingsStates();
            switch (status.getStatusCode()) {
                case LocationSettingsStatusCodes.SUCCESS:
                    // All location settings are satisfied. The client can initialize location
                    // requests here.
                    //...
                    break;
                case LocationSettingsStatusCodes.RESOLUTION_REQUIRED:
                    // Location settings are not satisfied. But could be fixed by showing the user
                    // a dialog.
                    try {
                        // Show the dialog by calling startResolutionForResult(),
                        // and check the result in onActivityResult().
                        status.startResolutionForResult(
                                MainActivity.this,
                                REQUEST_LOCATION);
                    } catch (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;
            }
        }
    });

}

@Override
public void onActivityResult(int requestCode, int resultCode, Intent data)
{
    Log.d("onActivityResult()", Integer.toString(resultCode));

    //final LocationSettingsStates states = LocationSettingsStates.fromIntent(data);
    switch (requestCode)
    {
        case REQUEST_LOCATION:
            switch (resultCode)
            {
                case Activity.RESULT_OK:
                {
                    // All required changes were successfully made
                    Toast.makeText(MainActivity.this, "Location enabled by user!", Toast.LENGTH_LONG).show();
                    break;
                }
                case Activity.RESULT_CANCELED:
                {
                    // The user was asked to change settings, but chose not to
                    Toast.makeText(MainActivity.this, "Location not enabled, user cancelled.", Toast.LENGTH_LONG).show();
                    break;
                }
                default:
                {
                    break;
                }
            }
            break;
    }
}

@Override
public void onConnectionSuspended(int i) {

}

@Override
public void onConnectionFailed(ConnectionResult connectionResult) {

}

}

}

Note : This line of code automatic open the dialog box if Location is not on. This piece of line is used in Google Map also

注意:如果位置不在,这行代码自动打开对话框。这条线也用在谷歌地图中

#7


6  

To turn GPS on or off programatically you need 'root' access and BusyBox installed. Even with those, the task is not trivial.

要按程序打开或关闭GPS,需要安装“root”访问和BusyBox。即使有了这些,任务也不是微不足道的。

Sample's here: Google Drive, Github, Sourceforge

样品在这里:谷歌驱动器,Github, Sourceforge

Tested with 2.3.5 and 4.1.2 Androids.

使用2.3.5和4.1.2的机器人进行测试。

#8


2  

An answer was developed in another question, but it was closed, and I'd like the community to try it out as well.

一个答案在另一个问题中得到了发展,但是它被关闭了,我希望社区也能尝试一下。

boolean gpsStatus = locmanager.isProviderEnabled(LocationManager.GPS_PROVIDER);
if (!gpsStatus) {
    Settings.Secure.putString(getContentResolver(), Settings.Secure.LOCATION_PROVIDERS_ALLOWED, "network,gps");
}

See this comment

看到这个评论

This solution would require the WRITE_SETTINGS and WRITE_SECURE_SETTINGS permissions.

这个解决方案需要WRITE_SETTINGS和WRITE_SECURE_SETTINGS权限。

#9


2  

Maybe with reflection tricks around the class android.server.LocationManagerService.

也许可以使用android.server.LocationManagerService类的反射技巧。

Also, there is a method (since API 8) android.provider.Settings.Secure.setLocationProviderEnabled

此外,还有一个方法(自API 8以来)android.provider.Settings.Secure.setLocationProviderEnabled

#10


1  

Things have changed since this question was posted, now with new Google Services API, you can prompt users to enable GPS:

这个问题发布后,情况发生了变化,现在有了新的谷歌服务API,您可以提示用户启用GPS:

https://developers.google.com/places/android-api/current-place

https://developers.google.com/places/android-api/current-place

You will need to request ACCESS_FINE_LOCATION permission in your manifest:

您将需要在您的清单中请求ACCESS_FINE_LOCATION权限:

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

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

Also watch this video:

还看这个视频:

https://www.youtube.com/watch?v=F0Kh_RnSM0w

https://www.youtube.com/watch?v=F0Kh_RnSM0w

#11


1  

This code works on ROOTED phones:

这个代码适用于有根的手机:

public class MainActivity extends AppCompatActivity {

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);

        String[] cmds = {"cd /system/bin" ,"settings put secure location_providers_allowed +gps"};
        try {
            Process p = Runtime.getRuntime().exec("su");
            DataOutputStream os = new DataOutputStream(p.getOutputStream());
            for (String tmpCmd : cmds) {
                os.writeBytes(tmpCmd + "\n");
            }
            os.writeBytes("exit\n");
            os.flush();
        }
        catch (IOException e){
            e.printStackTrace();
        }
    }
}

#12


1  

This is the best solution provided by Google Developers. Simply call this method in onResume of onCreate after initializing GoogleApiClient.

这是谷歌开发人员提供的最佳解决方案。在初始化GoogleApiClient之后,只需在onCreate的onResume中调用这个方法。

private void updateMarkers() {
    if (mMap == null) {
        return;
    }

    if (mLocationPermissionGranted) {
        // Get the businesses and other points of interest located
        // nearest to the device's current location.
         mGoogleApiClient = new GoogleApiClient.Builder(this)
                .addApi(LocationServices.API).build();
        mGoogleApiClient.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);


        LocationSettingsRequest.Builder builder = new LocationSettingsRequest
                .Builder()
                .addLocationRequest(mLocationRequest);
        PendingResult<LocationSettingsResult> resultPendingResult = LocationServices
                .SettingsApi
                .checkLocationSettings(mGoogleApiClient, builder.build());

        resultPendingResult.setResultCallback(new ResultCallback<LocationSettingsResult>() {
            @Override
            public void onResult(@NonNull LocationSettingsResult locationSettingsResult) {
                final Status status = locationSettingsResult.getStatus();
                final LocationSettingsStates locationSettingsStates = locationSettingsResult.getLocationSettingsStates();
                switch (status.getStatusCode()) {
                    case LocationSettingsStatusCodes.SUCCESS:
                        // All location settings are satisfied. The client can
                        // initialize location requests here.

                        break;
                    case LocationSettingsStatusCodes.RESOLUTION_REQUIRED:
                        // Location settings are not satisfied, but this can be fixed
                        // by showing the user a dialog.


                        try {
                            // Show the dialog by calling startResolutionForResult(),
                            // and check the result in onActivityResult().
                            status.startResolutionForResult(
                                    MainActivity.this,
                                    PERMISSIONS_REQUEST_ACCESS_FINE_LOCATION);
                        } 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;
                }

            }
        });


        @SuppressWarnings("MissingPermission")
        PendingResult<PlaceLikelihoodBuffer> result = Places.PlaceDetectionApi
                .getCurrentPlace(mGoogleApiClient, null);
        result.setResultCallback(new ResultCallback<PlaceLikelihoodBuffer>() {
            @Override
            public void onResult(@NonNull PlaceLikelihoodBuffer likelyPlaces) {
                for (PlaceLikelihood placeLikelihood : likelyPlaces) {
                    // Add a marker for each place near the device's current location, with an
                    // info window showing place information.
                    String attributions = (String) placeLikelihood.getPlace().getAttributions();
                    String snippet = (String) placeLikelihood.getPlace().getAddress();
                    if (attributions != null) {
                        snippet = snippet + "\n" + attributions;
                    }

                    mMap.addMarker(new MarkerOptions()
                            .position(placeLikelihood.getPlace().getLatLng())
                            .title((String) placeLikelihood.getPlace().getName())
                            .snippet(snippet));
                }
                // Release the place likelihood buffer.
                likelyPlaces.release();
            }
        });
    } else {
        mMap.addMarker(new MarkerOptions()
                .position(mDefaultLocation)
                .title(getString(R.string.default_info_title))
                .snippet(getString(R.string.default_info_snippet)));
    }
}

Note : This line of code automatic open the dialog box if Location is not on. This piece of line is used in Google Map also

注意:如果位置不在,这行代码自动打开对话框。这条线也用在谷歌地图中

 status.startResolutionForResult(
 MainActivity.this,
 PERMISSIONS_REQUEST_ACCESS_FINE_LOCATION);

#1


150  

the GPS can be toggled by exploiting a bug in the power manager widget. see this xda thread for discussion.

可以利用power manager小部件中的一个bug来切换GPS。请参阅此xda线程进行讨论。

here's some example code i use

下面是我使用的一些示例代码

private void turnGPSOn(){
    String provider = Settings.Secure.getString(getContentResolver(), Settings.Secure.LOCATION_PROVIDERS_ALLOWED);

    if(!provider.contains("gps")){ //if gps is disabled
        final Intent poke = new Intent();
        poke.setClassName("com.android.settings", "com.android.settings.widget.SettingsAppWidgetProvider"); 
        poke.addCategory(Intent.CATEGORY_ALTERNATIVE);
        poke.setData(Uri.parse("3")); 
        sendBroadcast(poke);
    }
}

private void turnGPSOff(){
    String provider = Settings.Secure.getString(getContentResolver(), Settings.Secure.LOCATION_PROVIDERS_ALLOWED);

    if(provider.contains("gps")){ //if gps is enabled
        final Intent poke = new Intent();
        poke.setClassName("com.android.settings", "com.android.settings.widget.SettingsAppWidgetProvider");
        poke.addCategory(Intent.CATEGORY_ALTERNATIVE);
        poke.setData(Uri.parse("3")); 
        sendBroadcast(poke);
    }
}

use the following to test if the existing version of the power control widget is one which will allow you to toggle the gps.

使用以下工具来测试电源控制小部件的现有版本是否允许您切换gps。

private boolean canToggleGPS() {
    PackageManager pacman = getPackageManager();
    PackageInfo pacInfo = null;

    try {
        pacInfo = pacman.getPackageInfo("com.android.settings", PackageManager.GET_RECEIVERS);
    } catch (NameNotFoundException e) {
        return false; //package not found
    }

    if(pacInfo != null){
        for(ActivityInfo actInfo : pacInfo.receivers){
            //test if recevier is exported. if so, we can toggle GPS.
            if(actInfo.name.equals("com.android.settings.widget.SettingsAppWidgetProvider") && actInfo.exported){
                return true;
            }
        }
    }

    return false; //default
}

#2


55  

All these answers are not allowed now. Here is the correct one:

所有这些答案现在都不允许。这是正确的一条:

For all those still looking for the Answer:

对于那些仍在寻找答案的人:

Here is how OLA Cabs and other such apps are doing it.

以下是OLA Cabs和其他类似应用程序是如何做到这一点的。

Add this in your onCreate

在onCreate中添加这个

if (googleApiClient == null) {
    googleApiClient = new GoogleApiClient.Builder(this)
            .addApi(LocationServices.API).addConnectionCallbacks(this)
            .addOnConnectionFailedListener(Login.this).build();
    googleApiClient.connect();
            LocationRequest locationRequest = LocationRequest.create();
    locationRequest.setPriority(LocationRequest.PRIORITY_HIGH_ACCURACY);
    locationRequest.setInterval(30 * 1000);
    locationRequest.setFastestInterval(5 * 1000);
    LocationSettingsRequest.Builder builder = new LocationSettingsRequest.Builder()
            .addLocationRequest(locationRequest);

    // **************************
    builder.setAlwaysShow(true); // this is the key ingredient
    // **************************

    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();
            final LocationSettingsStates state = result
                    .getLocationSettingsStates();
            switch (status.getStatusCode()) {
            case LocationSettingsStatusCodes.SUCCESS:
                // All location settings are satisfied. The client can
                // initialize location
                // requests here.
                break;
            case LocationSettingsStatusCodes.RESOLUTION_REQUIRED:
                // Location settings are not satisfied. But could be
                // fixed by showing the user
                // a dialog.
                try {
                    // Show the dialog by calling
                    // startResolutionForResult(),
                    // and check the result in onActivityResult().
                    status.startResolutionForResult(Login.this, 1000);
                } 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;
            }
        }
    });
}

These are the implmented methods:

这些都是被要求的方法:

@Override
public void onConnected(Bundle arg0) {
    // TODO Auto-generated method stub

}

@Override
public void onConnectionSuspended(int arg0) {
    // TODO Auto-generated method stub

}

@Override
public void onConnectionFailed(ConnectionResult arg0) {
    // TODO Auto-generated method stub

}

Here is the Android Documentation for the same.

这是同样的Android文档。

This is to help other guys if they are still struggling:

这是为了帮助那些还在挣扎的人:

Edit: Adding Irfan Raza's comment for more help.

编辑:添加Irfan Raza的评论以获得更多帮助。

@Override protected void onActivityResult(int requestCode, int resultCode, Intent data) {
     if (requestCode == 1000) {
         if(resultCode == Activity.RESULT_OK){
             String result=data.getStringExtra("result"); 
         } if (resultCode == Activity.RESULT_CANCELED) {
             //Write your code if there's no result 
         } 
    } 
} 

#3


47  

ENABLE GPS:

启用GPS:

Intent intent=new Intent("android.location.GPS_ENABLED_CHANGE");
intent.putExtra("enabled", true);
sendBroadcast(intent);

DISABLE GPS:

禁用GPS:

Intent intent = new Intent("android.location.GPS_ENABLED_CHANGE");
intent.putExtra("enabled", false);
sendBroadcast(intent);

#4


28  

This code works on ROOTED phones if the app is moved to /system/aps, and they have the following permissions in the manifest:

如果将应用程序移动到/system/aps中,则此代码可以在有根的手机上工作,并且在清单中具有以下权限:

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

Code

代码

private void turnGpsOn (Context context) {
    beforeEnable = Settings.Secure.getString (context.getContentResolver(),
                                              Settings.Secure.LOCATION_PROVIDERS_ALLOWED);
    String newSet = String.format ("%s,%s",
                                   beforeEnable,
                                   LocationManager.GPS_PROVIDER);
    try {
        Settings.Secure.putString (context.getContentResolver(),
                                   Settings.Secure.LOCATION_PROVIDERS_ALLOWED,
                                   newSet); 
    } catch(Exception e) {}
}


private void turnGpsOff (Context context) {
    if (null == beforeEnable) {
        String str = Settings.Secure.getString (context.getContentResolver(),
                                                Settings.Secure.LOCATION_PROVIDERS_ALLOWED);
        if (null == str) {
            str = "";
        } else {                
            String[] list = str.split (",");
            str = "";
            int j = 0;
            for (int i = 0; i < list.length; i++) {
                if (!list[i].equals (LocationManager.GPS_PROVIDER)) {
                    if (j > 0) {
                        str += ",";
                    }
                    str += list[i];
                    j++;
                }
            }
            beforeEnable = str;
        }
    }
    try {
        Settings.Secure.putString (context.getContentResolver(),
                                   Settings.Secure.LOCATION_PROVIDERS_ALLOWED,
                                   beforeEnable);
    } catch(Exception e) {}
}

#5


20  

Since Android version 4.4, you can't enable/disable gps programatically. If you try the code proposed on this answer, an exception will be fired.

由于Android版本4.4,您不能按程序启用/禁用gps。如果您尝试在此答案上建议的代码,就会触发异常。

java.lang.SecurityException: Permission Denial: not allowed to send broadcast android.location.GPS_ENABLED_CHANGE

#6


13  

Instead of using intent Settings.ACTION_LOCATION_SOURCE_SETTINGS you can directly able to show pop up in your app like Google Map & on Gps on click of ok button their is no need to redirect to setting simply you need to use my code as

而不是使用意图设置。ACTION_LOCATION_SOURCE_SETTINGS你可以直接显示在你的应用中,比如谷歌Map和Gps上点击ok按钮,你不需要重定向到设置你只需要使用我的代码

Note : This line of code automatic open the dialog box if Location is not on. This piece of line is used in Google Map also

注意:如果位置不在,这行代码自动打开对话框。这条线也用在谷歌地图中

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


LocationRequest mLocationRequest;
GoogleApiClient mGoogleApiClient;
PendingResult<LocationSettingsResult> result;
final static int REQUEST_LOCATION = 199;

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

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

}

@Override
public void onConnected(Bundle bundle) {

    mLocationRequest = LocationRequest.create();
    mLocationRequest.setPriority(LocationRequest.PRIORITY_HIGH_ACCURACY);
    mLocationRequest.setInterval(30 * 1000);
    mLocationRequest.setFastestInterval(5 * 1000);

    LocationSettingsRequest.Builder builder = new LocationSettingsRequest.Builder()
            .addLocationRequest(mLocationRequest);
    builder.setAlwaysShow(true);

    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 state = result.getLocationSettingsStates();
            switch (status.getStatusCode()) {
                case LocationSettingsStatusCodes.SUCCESS:
                    // All location settings are satisfied. The client can initialize location
                    // requests here.
                    //...
                    break;
                case LocationSettingsStatusCodes.RESOLUTION_REQUIRED:
                    // Location settings are not satisfied. But could be fixed by showing the user
                    // a dialog.
                    try {
                        // Show the dialog by calling startResolutionForResult(),
                        // and check the result in onActivityResult().
                        status.startResolutionForResult(
                                MainActivity.this,
                                REQUEST_LOCATION);
                    } catch (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;
            }
        }
    });

}

@Override
public void onActivityResult(int requestCode, int resultCode, Intent data)
{
    Log.d("onActivityResult()", Integer.toString(resultCode));

    //final LocationSettingsStates states = LocationSettingsStates.fromIntent(data);
    switch (requestCode)
    {
        case REQUEST_LOCATION:
            switch (resultCode)
            {
                case Activity.RESULT_OK:
                {
                    // All required changes were successfully made
                    Toast.makeText(MainActivity.this, "Location enabled by user!", Toast.LENGTH_LONG).show();
                    break;
                }
                case Activity.RESULT_CANCELED:
                {
                    // The user was asked to change settings, but chose not to
                    Toast.makeText(MainActivity.this, "Location not enabled, user cancelled.", Toast.LENGTH_LONG).show();
                    break;
                }
                default:
                {
                    break;
                }
            }
            break;
    }
}

@Override
public void onConnectionSuspended(int i) {

}

@Override
public void onConnectionFailed(ConnectionResult connectionResult) {

}

}

}

Note : This line of code automatic open the dialog box if Location is not on. This piece of line is used in Google Map also

注意:如果位置不在,这行代码自动打开对话框。这条线也用在谷歌地图中

#7


6  

To turn GPS on or off programatically you need 'root' access and BusyBox installed. Even with those, the task is not trivial.

要按程序打开或关闭GPS,需要安装“root”访问和BusyBox。即使有了这些,任务也不是微不足道的。

Sample's here: Google Drive, Github, Sourceforge

样品在这里:谷歌驱动器,Github, Sourceforge

Tested with 2.3.5 and 4.1.2 Androids.

使用2.3.5和4.1.2的机器人进行测试。

#8


2  

An answer was developed in another question, but it was closed, and I'd like the community to try it out as well.

一个答案在另一个问题中得到了发展,但是它被关闭了,我希望社区也能尝试一下。

boolean gpsStatus = locmanager.isProviderEnabled(LocationManager.GPS_PROVIDER);
if (!gpsStatus) {
    Settings.Secure.putString(getContentResolver(), Settings.Secure.LOCATION_PROVIDERS_ALLOWED, "network,gps");
}

See this comment

看到这个评论

This solution would require the WRITE_SETTINGS and WRITE_SECURE_SETTINGS permissions.

这个解决方案需要WRITE_SETTINGS和WRITE_SECURE_SETTINGS权限。

#9


2  

Maybe with reflection tricks around the class android.server.LocationManagerService.

也许可以使用android.server.LocationManagerService类的反射技巧。

Also, there is a method (since API 8) android.provider.Settings.Secure.setLocationProviderEnabled

此外,还有一个方法(自API 8以来)android.provider.Settings.Secure.setLocationProviderEnabled

#10


1  

Things have changed since this question was posted, now with new Google Services API, you can prompt users to enable GPS:

这个问题发布后,情况发生了变化,现在有了新的谷歌服务API,您可以提示用户启用GPS:

https://developers.google.com/places/android-api/current-place

https://developers.google.com/places/android-api/current-place

You will need to request ACCESS_FINE_LOCATION permission in your manifest:

您将需要在您的清单中请求ACCESS_FINE_LOCATION权限:

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

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

Also watch this video:

还看这个视频:

https://www.youtube.com/watch?v=F0Kh_RnSM0w

https://www.youtube.com/watch?v=F0Kh_RnSM0w

#11


1  

This code works on ROOTED phones:

这个代码适用于有根的手机:

public class MainActivity extends AppCompatActivity {

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);

        String[] cmds = {"cd /system/bin" ,"settings put secure location_providers_allowed +gps"};
        try {
            Process p = Runtime.getRuntime().exec("su");
            DataOutputStream os = new DataOutputStream(p.getOutputStream());
            for (String tmpCmd : cmds) {
                os.writeBytes(tmpCmd + "\n");
            }
            os.writeBytes("exit\n");
            os.flush();
        }
        catch (IOException e){
            e.printStackTrace();
        }
    }
}

#12


1  

This is the best solution provided by Google Developers. Simply call this method in onResume of onCreate after initializing GoogleApiClient.

这是谷歌开发人员提供的最佳解决方案。在初始化GoogleApiClient之后,只需在onCreate的onResume中调用这个方法。

private void updateMarkers() {
    if (mMap == null) {
        return;
    }

    if (mLocationPermissionGranted) {
        // Get the businesses and other points of interest located
        // nearest to the device's current location.
         mGoogleApiClient = new GoogleApiClient.Builder(this)
                .addApi(LocationServices.API).build();
        mGoogleApiClient.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);


        LocationSettingsRequest.Builder builder = new LocationSettingsRequest
                .Builder()
                .addLocationRequest(mLocationRequest);
        PendingResult<LocationSettingsResult> resultPendingResult = LocationServices
                .SettingsApi
                .checkLocationSettings(mGoogleApiClient, builder.build());

        resultPendingResult.setResultCallback(new ResultCallback<LocationSettingsResult>() {
            @Override
            public void onResult(@NonNull LocationSettingsResult locationSettingsResult) {
                final Status status = locationSettingsResult.getStatus();
                final LocationSettingsStates locationSettingsStates = locationSettingsResult.getLocationSettingsStates();
                switch (status.getStatusCode()) {
                    case LocationSettingsStatusCodes.SUCCESS:
                        // All location settings are satisfied. The client can
                        // initialize location requests here.

                        break;
                    case LocationSettingsStatusCodes.RESOLUTION_REQUIRED:
                        // Location settings are not satisfied, but this can be fixed
                        // by showing the user a dialog.


                        try {
                            // Show the dialog by calling startResolutionForResult(),
                            // and check the result in onActivityResult().
                            status.startResolutionForResult(
                                    MainActivity.this,
                                    PERMISSIONS_REQUEST_ACCESS_FINE_LOCATION);
                        } 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;
                }

            }
        });


        @SuppressWarnings("MissingPermission")
        PendingResult<PlaceLikelihoodBuffer> result = Places.PlaceDetectionApi
                .getCurrentPlace(mGoogleApiClient, null);
        result.setResultCallback(new ResultCallback<PlaceLikelihoodBuffer>() {
            @Override
            public void onResult(@NonNull PlaceLikelihoodBuffer likelyPlaces) {
                for (PlaceLikelihood placeLikelihood : likelyPlaces) {
                    // Add a marker for each place near the device's current location, with an
                    // info window showing place information.
                    String attributions = (String) placeLikelihood.getPlace().getAttributions();
                    String snippet = (String) placeLikelihood.getPlace().getAddress();
                    if (attributions != null) {
                        snippet = snippet + "\n" + attributions;
                    }

                    mMap.addMarker(new MarkerOptions()
                            .position(placeLikelihood.getPlace().getLatLng())
                            .title((String) placeLikelihood.getPlace().getName())
                            .snippet(snippet));
                }
                // Release the place likelihood buffer.
                likelyPlaces.release();
            }
        });
    } else {
        mMap.addMarker(new MarkerOptions()
                .position(mDefaultLocation)
                .title(getString(R.string.default_info_title))
                .snippet(getString(R.string.default_info_snippet)));
    }
}

Note : This line of code automatic open the dialog box if Location is not on. This piece of line is used in Google Map also

注意:如果位置不在,这行代码自动打开对话框。这条线也用在谷歌地图中

 status.startResolutionForResult(
 MainActivity.this,
 PERMISSIONS_REQUEST_ACCESS_FINE_LOCATION);