前言
在Android 11上有很多的更新都是用来保护隐私的,之前使用的来获取安装的应用列表的方法,在targetSdkVersion 30及以上则会失效,系统会自动过滤这些信息,经测试只能获得自己当前使用的应用包名及系统的一些应用包名(系统会自动让部分应用可见,以便我们的应用可与其交互),想要了解具体的信息,可以到下方的地址去查看:
As of Android 11, this method no longer returns information about all apps; see https://g.co/dev/packagevisibility
image.png
先看看如何获取安装的应用列表
List<ApplicationInfo> infos = getPackageManager().getInstalledApplications(0);
for (ApplicationInfo info : infos) {
Log.e("yzt", info.packageName);
}
再看看Android 11.0及以上如何适配,其实有3种方法可以查询别的应用包名
如果已经知道想交互的应用包名,可以这么做:
在Android的AndroidManifest.xml的<manifest>之下加入<queries>标签,并且在其中使用<package>来声明想要交互的应用包名,比如这里写的是微信和QQ的包名,也就是遍历时能找到微信和QQ
<queries>
<package android:name="com.tencent.mm" />
<package android:name="com.tencent.mobileqq" />
</queries>
如果已经知道能相应特定Intent的应用,可以这么做:
同样的,在Android的AndroidManifest.xml的<manifest>之下加入<queries>标签,并且在其中使用<package>来声明有对应Intent功能的应用,比如在这里写的是具有图片分享功能的Intent,遍历时找到了飞猪等包名。需要注意的是<intent>中只能有一个<action>元素,并且<data>中也只能有mimeType,scheme和host这些属性。
<queries>
<intent>
<action android:name="android.intent.action.SEND" />
<data android:mimeType="image/png" />
</intent>
</queries>
看到有作者提到直接使用android.intent.action.MAIN这个action就可以获取安装的应用列表,经测试确实可以,真是机智,几乎所有的应用都有这个action吧。
<queries>
<intent>
<action android:name="android.intent.action.MAIN" />
</intent>
</queries>
最后是希望查询所有应用,那就需要申请权限了:
<uses-permission
android:name="android.permission.QUERY_ALL_PACKAGES"
tools:ignore="QueryAllPackagesPermission" />
结尾
当然也可以选择维持在targetSdkVersion在30以下,这样就暂时不用适配,具体还是看项目的要求。
网友评论