Android 给 app默认权限(不弹窗申请权限)

1.系统app

系统app的权限默认开启,大家应该都知道是修改DefaultPermissionGrantPolicy.java。

frameworks/base/services/core/java/com/android/server/pm/DefaultPermissionGrantPolicy.java

在grantDefaultSystemHandlerPermissions中可以看到

// Camera
Intent cameraIntent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);
PackageParser.Package cameraPackage = getDefaultSystemHandlerActivityPackageLPr(
        cameraIntent, userId);
if (cameraPackage != null
        && doesPackageSupportRuntimePermissions(cameraPackage)) {
    grantRuntimePermissionsLPw(cameraPackage, CAMERA_PERMISSIONS, userId);
    grantRuntimePermissionsLPw(cameraPackage, MICROPHONE_PERMISSIONS, userId);
    grantRuntimePermissionsLPw(cameraPackage, STORAGE_PERMISSIONS, userId);
}
从上面这段代码就可以看到Camera中默认打开了CAMERA_PERMISSIONS, MICROPHONE_PERMISSIONS, STORAGE_PERMISSIONS这三个Dangerous Permission。

2.第三方app

手动安装的第三方app的权限默认开启是修改PackageManagerService.java。

frameworks/base/services/core/java/com/android/server/pm/PackageManagerService.java

在grantPermissionsLpw函数中添加如下代码

//Permissions for com.xxx.xxx
 if(pkg.packageName.contains("com.xxx.xxx")) {
          final int permsSize = pkg.requestedPermissions.size();
          for (int i=0; i<permsSize; i++) {
              final String name = pkg.requestedPermissions.get(i);
              final BasePermission bp = mSettings.mPermissions.get(name);
              if(null != bp && permissionsState.grantInstallPermission(bp) != PermissionsState.PERMISSION_OPERATION_FAILURE) {
                  Slog.d(TAG, "zrx--- grant permission " + name + " to package " + pkg.packageName);
                  changedInstallPermission = true;
              }
          }
      }
参考:

https://blog.youkuaiyun.com/u011280717/article/details/51819708

https://blog.youkuaiyun.com/fmc088/article/details/83063198
 

<think>首先,用户的问题是关于Android应用中打开指定默认权限的方法。他们在询问如何实现这个功能。用户提供了几个引用,我需要参考这些引用来回答问题。 回顾引用内容: - 引用[1]:讨论了在Android中使用系统默认应用打开文档的方法。 - 引用[2]:提到Android系统给第三方应用运行时权限默认开启。 - 引用[3]:关于文件权限,特别是读SD卡的权限。 - 引用[4]:提供了一个方法来检查权限是否被授予。 用户的问题是:"我想查找在Android应用中打开指定默认权限的方法 请问Android应用打开指定默认权限的实现方法"。所以,焦点是"打开指定默认权限",可能意味着设置或请求默认权限。 在Android中,"默认权限"可能指的是系统预先授予的权限,或者用户手动授予的权限。引用[2]提到系统应用可能有默认开启的权限,但第三方应用需要请求权限。 从引用[4]中,有一个方法`hasPermissions`来检查权限是否被授予。引用[1]涉及打开文档,这可能涉及到权限。 用户的上一次问题或历史没有提供,所以我只能基于当前信息和引用。 关键点:用户想实现"打开指定默认权限",但这个表述有点模糊。通常,在Android中,应用能"打开"权限;它们请求权限,然后用户授予或拒绝。系统权限是预先定义的。 可能用户误解了。"打开默认权限"可能是指请求权限或确保权限被授予。 参考引用[2],它说:"Android系统 给第三方应用(system/app) 运行时权限默认开启",这似乎是针对系统应用的。对于普通应用,权限默认被授予。 所以,对于第三方应用,需要请求权限。 在回答中,我应该解释如何请求权限。 步骤概述: 1. **添加权限到manifest文件**:如引用[3]所示,在AndroidManifest.xml中声明权限。 2. **在运行时请求权限**:对于API级别23(Android 6.0 Marshmallow)及以上,需要在运行时请求权限。 3. **检查权限状态**:使用类似引用[4]中的方法。 引用[1]是关于打开文档的,这可能涉及到权限;例如,如果要打开外部文件,需要READ_EXTERNAL_STORAGE权限。 所以,结合所有引用,我可以提供一个综合的回答。 结构化回答: - 解释什么是默认权限:对于系统应用,某些权限可能默认开启;对于普通应用,权限默认授予,需要请求。 - 实现方法:如何在应用中请求指定权限。 - 参考提供的引用。 系统级指令: - 使用中文回答。 - 生成相关问题。 - 在行内数学表达式使用$...$,但这个问题没有数学内容,所以可能需要。 - 独立公式使用$$...$$,同样可能需要。 - LaTeX语法正确:如果有公式,但要确保正确。 - 回答结构清晰:一步步解释。 - 在引用的段落末尾添加引用标识,如[^1]。 最后,生成相关问题。 回答结构: 1. **引言**:解释权限Android中的重要性。 2. **步骤实现**: - 第一步:在AndroidManifest.xml中添加权限声明(参考引用[3])。 - 第二步:在运行时检查权限(参考引用[4])。 - 第三步:如果未授予,请求权限。 3. **额外提示**:对于特定场景,如打开文档(参考引用[1]),可能需要权限。 4. **总结**。 然后,生成相关问题。 确保回答真实可靠:基于标准的Android开发实践。 最终回答用中文。 </think>### Android应用中请求指定权限的实现方法 在Android开发中,权限管理是确保应用安全访问设备资源(如文件、位置、相机等)的核心机制。所谓“默认权限”,通常指系统预定义但未自动授予的权限;对于普通第三方应用,权限默认会被开启,需要开发者主动请求(系统应用可能有默认开启的权限,如引用[2]所述)。您的需求是“打开指定默认权限”,这可能是指动态请求和授予指定权限的过程。Android系统遵循“运行时权限”模型(API级别23及以上),即权限需要在代码中显式请求,用户手动批准。下面我将基于您提供的引用内容,结合Android开发最佳实践,逐步解释实现方法。 #### 步骤概述 要请求指定权限(如`READ_EXTERNAL_STORAGE`),请遵循以下步骤: 1. **添加权限声明到AndroidManifest.xml**:在manifest文件中声明所需权限。 2. **在运行时检查权限状态**:使用系统API检查权限是否已被授予。 3. **请求权限(如果需要)**:如果权限未授予,通过系统弹窗请求用户授权。 4. **处理权限结果**:在回调中处理用户的选择(授予或拒绝)。 下面详细说明每个步骤的实现方法,并参考您提供的引用以确保准确性。 #### 步骤一:添加权限声明到AndroidManifest.xml 在项目的`AndroidManifest.xml`文件中,添加您需要的权限声明。例如,请求读取外部存储的权限(如引用[3]中提到的`READ_EXTERNAL_STORAGE`)。权限名称必须与系统定义的常量匹配。 ```xml <manifest xmlns:android="http://schemas.android.com/apk/res/android" package="com.example.myapp"> <!-- 添加权限声明 --> <uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE" /> <!-- 其他权限示例 --> <uses-permission android:name="android.permission.CAMERA" /> <application ...> ... </application> </manifest> ``` - **关键点**:权限声明是静态的,必须在manifest中定义,否则系统会拒绝后续请求。对于API低于23的设备,manifest中声明的权限在安装时自动授予;但对于API 23+的设备,还需运行时请求[^3]。 #### 步骤二:在运行时检查权限状态 在Activity或Fragment中,使用`ContextCompat.checkSelfPermission`方法检查权限是否已授予(参考引用[4]中的代码)。该方法返回`PackageManager.PERMISSION_GRANTED`如果权限已开启。 ```java import android.Manifest; import android.content.pm.PackageManager; import android.os.Build; import android.os.Bundle; import androidx.appcompat.app.AppCompatActivity; import androidx.core.content.ContextCompat; public class MainActivity extends AppCompatActivity { private static final String PERMISSION_READ_STORAGE = Manifest.permission.READ_EXTERNAL_STORAGE; private static final int PERMISSION_REQUEST_CODE = 123; // 请求码,自定义唯一值 @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); // 检查权限状态(API 23+需运行时处理) if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) { if (hasPermissions(this, PERMISSION_READ_STORAGE)) { // 权限已授予,执行相关操作(如打开文档) openDocument(); } else { // 权限未授予,触发请求 requestPermissions(); } } else { // API <23 时,权限在安装时授予,直接执行操作 openDocument(); } } // 检查权限是否授予的通用方法(类似引用[4]的实现) public static boolean hasPermissions(Context context, String... permissions) { if (Build.VERSION.SDK_INT < Build.VERSION_CODES.M) { Log.d("Permission", "API < M, permissions granted by default!"); return true; // 低版本系统默认授予权限[^4] } for (String perm : permissions) { if (ContextCompat.checkSelfPermission(context, perm) != PackageManager.PERMISSION_GRANTED) { return false; } } return true; } private void requestPermissions() { // 请求权限数组(可指定多个) String[] permissionsToRequest = {PERMISSION_READ_STORAGE}; requestPermissions(permissionsToRequest, PERMISSION_REQUEST_CODE); } private void openDocument() { // 实现打开文档的逻辑(参考引用[1]) Intent intent = new Intent(Intent.ACTION_VIEW); intent.setDataAndType(fileUri, "application/pdf"); // 示例:打开PDF startActivity(intent); } } ``` - **关键点**:`hasPermissions`方法封装了权限检查逻辑,确保兼容API 23以下版本(如引用[4]所述)。如果权限已授予,即可执行后续操作(如使用Intent打开默认应用[^1])。 #### 步骤三:请求权限并处理结果 如果权限未授予,调用`requestPermissions`方法触发系统弹窗。用户响应后,在`onRequestPermissionsResult`回调中处理结果。 ```java @Override public void onRequestPermissionsResult(int requestCode, @NonNull String[] permissions, @NonNull int[] grantResults) { super.onRequestPermissionsResult(requestCode, permissions, grantResults); if (requestCode == PERMISSION_REQUEST_CODE) { if (grantResults.length > 0 && grantResults[0] == PackageManager.PERMISSION_GRANTED) { // 权限已授予,执行操作 openDocument(); } else { // 权限被拒绝,可提示用户或降级处理 Toast.makeText(this, "权限被拒绝,无法访问文件", Toast.LENGTH_SHORT).show(); } } } ``` - **最佳实践**:如果用户拒绝权限,提供解释为什么需要该权限(使用`shouldShowRequestPermissionRationale`),并在必要时引导用户到设置页手动开启。 #### 注意事项 - **系统默认权限的限制**:普通第三方应用无法强制“开启”权限;用户始终拥有控制权。系统应用(如预装应用)可能有默认开启的权限(引用[2]中提到的`DefaultPermissionGrantPolicy.java`),但这适用于普通开发[^2]。 - **兼容性**:针对API 23+(Android 6.0及以上)的设备运行时请求是必需的;低版本设备权限在安装时授予。 - **权限组**:Android权限分组(如存储权限组)。请求一组权限中的一个,可能自动授予组内其他权限。 - **调试建议**:使用Android Studio的Logcat监控权限状态,避免忘记处理回调。 通过以上步骤,您可以在应用中实现动态请求和开启指定权限的功能。如果您需要结合特定场景(如打开文档),请确保权限逻辑与Intent操作集成(引用[1])。 ### 相关问题 1. 如何在Android中处理权限被拒绝后的用户引导? 2. Android权限组的分类和作用是什么? 3. 如何为同API版本(低于23和23+)优化权限请求代码?
评论 1
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值