为什么 Android 8 中的 Settings.canDrawOverlays() 方法返回“false"?当用户授予绘制叠加层的权限并返回应用程序时? [英] Why does Settings.canDrawOverlays() method in Android 8 returns "false" when user grants permission to draw overlays and returns back to the app?

查看:15
本文介绍了为什么 Android 8 中的 Settings.canDrawOverlays() 方法返回“false"?当用户授予绘制叠加层的权限并返回应用程序时?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在为父母开发 MDM 应用程序来控制孩子的设备,它使用权限 SYSTEM_ALERT_WINDOW 在设备上显示警告,如果执行了禁止的操作.在安装过程中使用 SDK 23+ (Android 6.0) 的设备上,应用程序使用以下方法检查权限:

I'm developing the MDM app for parents to control children's devices and it uses permission SYSTEM_ALERT_WINDOW to display warnings on device if forbidden action has performed. On devices with SDK 23+ (Android 6.0) during installation the app checks the permission using this method:

Settings.canDrawOverlays(getApplicationContext()) 

如果此方法返回 false,应用程序将打开系统对话框,用户可以在其中授予权限:

and if this method returns false the app opens system dialog where user can grant the permission:

Intent intent = new Intent(Settings.ACTION_MANAGE_OVERLAY_PERMISSION,
                    Uri.parse("package:" + getPackageName()));
startActivityForResult(intent, REQUEST_CODE);

但是在带有 SDK 26 (Android 8.0) 的设备上,当用户成功授予权限并通过按后退按钮返回应用程序时,方法 canDrawOverlays() 仍然返回 false,直到用户没有关闭应用程序并再次启动它或只是在最近的应用程序对话框中选择它.我在 Android Studio 中使用 Android 8 的最新版本虚拟设备上对其进行了测试,因为我没有真实设备.

But on device with SDK 26 (Android 8.0), when user has successfully granted permission and returned to the app by pressing back button, method canDrawOverlays() still returns false, until user doesn't close the app and starts it again or just chooses it in the recent apps dialog. I tested it on latest version of virtual device with Android 8 in Android Studio because I didn't have real device.

我做了一些研究,并额外检查了 AppOpsManager 的权限:

I've done a little research and additionally check the permission with AppOpsManager:

AppOpsManager appOpsMgr = (AppOpsManager) getSystemService(Context.APP_OPS_SERVICE);
int mode = appOpsMgr.checkOpNoThrow("android:system_alert_window", android.os.Process.myUid(), getPackageName());
Log.d(TAG, "android:system_alert_window: mode=" + mode);

所以:

  • 当应用没有这个权限时,模式为2"(MODE_ERRORED) (canDrawOverlays() 返回 false) 当用户
  • 授予权限并返回应用程序,模式为1"(MODE_IGNORED) (canDrawOverlays() 返回 false)
  • 如果您现在重新启动应用程序,则模式为0"(MODE_ALLOWED)(canDrawOverlays() 返回 true)
  • when the application does not have this permission, the mode is "2" (MODE_ERRORED) (canDrawOverlays() returns false) when the user
  • granted permission and returned to the application, the mode is "1" (MODE_IGNORED) (canDrawOverlays() returns false)
  • and if you now restart the app, the mode is "0" (MODE_ALLOWED) (canDrawOverlays() returns true)

请问,谁能向我解释一下这种行为?我可以依赖操作 "android:system_alert_window"mode == 1 并假设用户已授予权限吗?

Please, can anyone explain this behavior to me? Can I rely on mode == 1 of operation "android:system_alert_window" and assume that the user has granted permission?

推荐答案

我也发现 checkOp 存在这个问题.就我而言,我有一个流程,仅当未设置权限时才允许重定向到设置.并且 AppOps 仅在重定向到设置时设置.

I've found this problems with checkOp too. In my case I have the flow which allows to redirect to settings only when the permission is not set. And the AppOps is set only when redirecting to settings.

假设 AppOps 回调仅在发生更改时调用,并且只有一个开关,可以更改.这意味着,如果调用回调,用户必须授予权限.

Assuming that AppOps callback is called only when something is changed and there is only one switch, which can be changed. That means, if callback is called, user has to grant the permission.

if (VERSION.SDK_INT >= VERSION_CODES.O &&
                (AppOpsManager.OPSTR_SYSTEM_ALERT_WINDOW.equals(op) && 
                     packageName.equals(mContext.getPackageName()))) {
    // proceed to back to your app
}

应用程序恢复后,使用 canDrawOverlays() 检查开始对我有用.我确定我重新启动应用程序并检查是否通过标准方式授予权限.

After the app is restored, checking with canDrawOverlays() starts worked for me. For sure I restart the app and check if permission is granted via standard way.

这绝对不是一个完美的解决方案,但它应该可以工作,直到我们从 Google 了解更多相关信息.

It's definitely not a perfect solution, but it should work, till we know more about this from Google.

我问谷歌:https://issuetracker.google.com/issues/66072795

编辑 2:谷歌修复了这个问题.不过看来Android O版还是会受到影响.

EDIT 2: Google fixes this. But it seem that the Android O version will be affected still.

这篇关于为什么 Android 8 中的 Settings.canDrawOverlays() 方法返回“false"?当用户授予绘制叠加层的权限并返回应用程序时?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
相关文章
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆