今天在调试一个fragment时,申请到权限,然后在权限回调里面做相应的dialog提示用户,但是发现一直无弹窗。
话不多说,直接上问题代码
private void testRxPermissions() {
ActivityCompat.requestPermissions(this.getActivity(), new String[]{Manifest.permission.CAMERA}, 100);
}
@Override
public void onRequestPermissionsResult(int requestCode, @androidx.annotation.NonNull String[] permissions, @androidx.annotation.NonNull int[] grantResults) {
super.onRequestPermissionsResult(requestCode, permissions, grantResults);
//TODO:dialog展示相关代码
}
问题现象: dialog展示相关代码一直未执行,最后打了断点,发现onRequestPermissionsResult函数根本没有进来
问题原因:
问题根因在于,我们调用的是ActivityCompat.requestPermissions
,而点进去看一下这个方法的源码
大家知道原因了吧,所以回调会直接到activity的onRequestPermissionsResult方法中。
问题解决方法:
既然知道了原因,那么解决方法就对应的有两个
解决方法1
最直接的方法,就是统一在fragment所属的activity onRequestPermissionsResult
中,处理权限申请回调
解决方法2
既然知道了问题原因,那么我们也可以直接调用fragment中的requestPermissions方法,保证onRequestPermissionsResult回调在fragment中
private void testRxPermissions() {
requestPermissions(this, new String[]{Manifest.permission.CAMERA}, 100);
}
@Override
public void onRequestPermissionsResult(int requestCode, @androidx.annotation.NonNull String[] permissions, @androidx.annotation.NonNull int[] grantResults) {
super.onRequestPermissionsResult(requestCode, permissions, grantResults);
}
解决办法3
仔细看fragment api注释,发现已经requestPermissions废弃,官方建议使用registerForActivityResult
Deprecated
use registerForActivityResult(ActivityResultContract, ActivityResultCallback) passing in a androidx.activity.result.contract.ActivityResultContracts.RequestMultiplePermissions object for the ActivityResultContract and handling the result in the callback.
官方建议使用registerForActivityResult
ActivityResultLauncher activityResultLauncher = registerForActivityResult(new ActivityResultContracts.RequestPermission(), new ActivityResultCallback<Boolean>() {
@Override
public void onActivityResult(Boolean isGranted) {
if (isGranted) {
//做后续操作
} else {
// 权限被拒绝就要提醒
}
}
});
activityResultLauncher.launch(Manifest.permission.CAMERA);
总结
建议使用方法3,毕竟是官方建议的,但是如果简单而且防止出错的话,方法1的确是最简单的。