Android 9及以下权限弹窗不显示且请求权限时崩溃问题求助
Hey Jim, let's break down and fix the permission issues you're facing on Android 9 and below. I've gone through your code thoroughly and spotted several key problems that are likely causing the dialog failures and simulator crashes:
1. Critical Logic Error in onRequestPermissionsResult
Your current code only updates permission flags when permissions are denied—it completely ignores the case where users grant permissions. This means even if a user approves a permission, your app will still think it's denied, triggering endless permission requests that can crash your simulator.
Fix this by correctly updating flags for both grant and denial scenarios:
@Override public void onRequestPermissionsResult(int requestCode, @NonNull String[] permissions, @NonNull int[] grantResults) { super.onRequestPermissionsResult(requestCode, permissions, grantResults); if(requestCode == 5){ // Reset flags to true first, then adjust based on results isRecordPermGranted = true; isWritePermGranted = true; for (int i = 0; i < permissions.length; i++){ if(permissions[i].equals(Manifest.permission.RECORD_AUDIO)){ isRecordPermGranted = grantResults[i] == PackageManager.PERMISSION_GRANTED; } else if(permissions[i].equals(Manifest.permission.WRITE_EXTERNAL_STORAGE)){ isWritePermGranted = grantResults[i] == PackageManager.PERMISSION_GRANTED; } } } if(!isWritePermGranted || !isRecordPermGranted){ Log.d("REQUEST PERMISSIONS RESULT", "onPermissionResult"); if(totalCount <3){ finishAffinity(); }else{ Intent intent = new Intent(MainActivity.this, PermissionActivity.class); startActivity(intent); } } }
2. ActivityResultLauncher Compatibility Crash on Older Android Versions
While ActivityResultLauncher is the modern recommended API, it has known edge-case compatibility bugs on Android 9 (API 28) and below. Your version-specific logic might be triggering these crashes.
A reliable fix is to fall back to the universally compatible ActivityCompat.requestPermissions() for all versions. Update your requestPermission() method to remove the version check:
public void requestPermission(){ List<String> permissionRequests = new ArrayList<>(); if(!isRecordPermGranted){ permissionRequests.add(Manifest.permission.RECORD_AUDIO); } if(!isWritePermGranted){ permissionRequests.add(Manifest.permission.WRITE_EXTERNAL_STORAGE); } Log.d("permissionRequests list", permissionRequests.toString()); if(!permissionRequests.isEmpty()){ boolean shouldShowRationale = false; // Check rationale for any required permission for(String perm : permissionRequests){ if(ActivityCompat.shouldShowRequestPermissionRationale(this, perm)){ shouldShowRationale = true; break; } } if(shouldShowRationale){ Toast.makeText(this, "Permissions needed to record and save your audio recordings!", Toast.LENGTH_LONG).show(); } // Use the universally compatible request method ActivityCompat.requestPermissions( MainActivity.this, permissionRequests.toArray(new String[permissionRequests.size()]), 5 ); } }
3. Broken Rationale Handling
Your original code showed a Toast when rationale was needed but didn't proceed to request permissions afterward. The fix above ensures that after explaining why permissions are needed, the app still triggers the permission dialog.
4. Simulator Crash Troubleshooting
If your simulator still crashes after fixing the code:
- Re-download the Android 9 system image (corrupted images can cause unexpected crashes)
- Verify your AndroidX dependencies are up-to-date (use version
1.2.0+forandroidx.activity:activityif you ever want to revisitActivityResultLauncher)
Final Notes
- On Android 9 and below, granting
WRITE_EXTERNAL_STORAGEautomatically grantsREAD_EXTERNAL_STORAGE, so your current manifest setup is fine. - Double-check that your
PermissionActivitycorrectly handles permission redirection (make sure it doesn't loop back toMainActivitywithout resolving permissions).
内容的提问来源于stack exchange,提问作者Jim Ross

