Marshmallow的运行时许可

时间:2016-01-11 08:54:08

标签: android android-alertdialog android-permissions android-6.0-marshmallow

这种新的,令人敬畏的安全功能 RUN-TIME Permission

我正在努力理解它并为此制作一个演示但是当我在DIALOG处理用户许可时,我想到了一个问题。

如何处理" 永远不要再问"

enter image description here

假设我的应用程序必须需要位置/联系人,但是用户拒绝它,并且#34;再也不要问及#34;。

我能为此做些什么。并非所有用户都了解我的字段是必需的。

任何建议?

4 个答案:

答案 0 :(得分:5)

首先,您需要在OnRequestPermissionsResultCallback中实施Listener类的ActivityCompat Activity并覆盖void onRequestPermissionsResult(int requestCode, @NonNull String[] permissions, @NonNull int[] grantResults)方法,以检查用户是否允许或拒绝该权限

你可以这样做。在这里,我检查WRITE_EXTERNAL_STORAGE的权限访问权限:

int REQUEST_STORAGE = 1;

private void checkPermissions() {
    if (hasStoragePermissionGranted()) {
        // you can do whatever you want
    } else {
        requestPermission();
    }
}

public boolean hasPermissionGranted(){
        return  ContextCompat.checkSelfPermission(MainActivity.this, Manifest.permission.WRITE_EXTERNAL_STORAGE) == PackageManager.PERMISSION_GRANTED;
}

public void requestPermission() {
    if(Build.VERSION.SDK_INT >= Build.VERSION_CODES.M){
        ActivityCompat.requestPermissions(MainActivity.this, {Manifest.permission.WRITE_EXTERNAL_STORAGE},
                REQUEST_STORAGE);
    }
}

当用户允许或拒绝来自运行时权限对话框的权限时,将调用onRequestPermissionsResult()方法。

您还可以处理用户已选中从不显示运行时权限对话框的情况,您可以显示Snackbar或按钮以将用户重定向到您的应用程序设置页面,因为在用户选中"Never ask again"后您无法显示权限对话框。

@Override
public void onRequestPermissionsResult(int requestCode, @NonNull String[] permissions,
                                           @NonNull int[] grantResults) {

        if (requestCode == REQUEST_STORAGE) {
            if (grantResults[0] == PackageManager.PERMISSION_GRANTED) {
               //Storage permission is enabled
               canSendAttachments = true;
               systemLogsCheckbox.setEnabled(true);
            } else if (ActivityCompat.shouldShowRequestPermissionRationale(MainActivtity.this, Manifest.permission.WRITE_EXTERNAL_STORAGE)) {
                //User has deny from permission dialog
                Snackbar.make(mainLayout, getResources().getString("Please enable storage permission"),
                        Snackbar.LENGTH_INDEFINITE)
                        .setAction("OK", new View.OnClickListener() {
                            @Override
                            public void onClick(View view) {
                                ActivityCompat.requestPermissions(MainActivity.this, {Manifest.permission.WRITE_EXTERNAL_STORAGE},
                REQUEST_STORAGE);
                            }
                        })
                        .show();
            } else {
                // User has deny permission and checked never show permission dialog so you can redirect to Application settings page
                Snackbar.make(mainLayout, getResources().getString("Please enable permission from settings"),
                        Snackbar.LENGTH_INDEFINITE)
                        .setAction("OK", new View.OnClickListener() {
                            @Override
                            public void onClick(View view) {
                                Intent intent = new Intent();
                                intent.setAction(Settings.ACTION_APPLICATION_DETAILS_SETTINGS);
                                Uri uri = Uri.fromParts("package", MainActivity.this.getPackageName(), null);
                                intent.setData(uri);
                                startActivity(intent);
                            }
                        })
                        .show();
            }
        }
    }

我在这里使用Snackbar向用户显示有关权限的相关消息,mainLayoutActivity's Main Layout的ID。

希望它对你有所帮助。

答案 1 :(得分:2)

我创建了一个library来处理所有permissions。你可以在这里找到它:

PermissionHelper

回答你的问题:

为了让您知道用户checked是否再次展示,如果权限为 declined 且没有 explanation needed 如果这两个返回**true**,则意味着不再可以再次询问权限,处理此案例的唯一解决方案是打开设置屏幕。

P.S:我创建的库为您处理所有这些场景,并为您返回回调以决定下一步做什么!该库有两个实现

  1. 手动实现(这意味着您必须在活动中实现回调并从库中侦听返回的回调)。
  2. 让图书馆为您申请许可,并且还会给您一个回调,让您决定永久拒绝该权限后会发生什么。

答案 2 :(得分:1)

当用户选择&#34时,

打开您的应用设置; Nerver再次询问"

Intent intent = new Intent(Settings.ACTION_APPLICATION_DETAILS_SETTINGS);
Uri uri = Uri.fromParts("package", getPackageName(), null);
intent.setData(uri);
startActivityForResult(intent, REQUEST_PERMISSION_SETTING);

我处理RuntimePermission的例子:
https://github.com/henrychuangtw/RuntimePermission

答案 3 :(得分:0)

使用Dexter

使用PermissionsDispatcher:

步骤1:PermissionsDispatcher使用hotchemi库(该库基于注释,易于使用且记录良好)

第2步:您必须提供4个带注释的方法,其中一个是@OnNeverAskAgain(Manifest.permission。[permission_you_want]),如下所示

@OnNeverAskAgain(Manifest.permission.[permission_you_want])
void showNeverAsk() {  
   // handle here
}  

这是sample