API23设备用ImageVector加载矢量图报PNG资源未找到异常
问题原因
- 报错路径中
drawable-xxhdpi-v4的-v4后缀不是指系统要检索API 4版本的资源,这是Android资源系统的标准限定符规则:密度类资源限定符从API 4开始生效,AGP(Android Gradle插件)在执行矢量图自动转各密度PNG的兼容逻辑时,会按规则给生成的密度目录拼接-v4后缀,这个逻辑和AndroidX是否废弃旧版本标签没有关联。 ImageVector.vectorResource()是Compose提供的加载接口,走系统原生Resources的资源查找逻辑,会优先匹配构建时生成的PNG兼容产物,而当前构建流程实际没有生成带-v4后缀的对应密度目录,因此抛出Resources$NotFoundException。AppCompatResources.getDrawable()可正常加载,是因为AppCompat实现了独立的矢量图解析加载逻辑,不会依赖系统原生的资源查找路径匹配自动生成的PNG,而是直接解析矢量XML内容渲染,因此绕过了路径不匹配的问题。
可行解决方案
按推荐优先级排序:
- 方案1:关闭矢量图自动生成PNG的兼容逻辑。项目minSdk为23,Android从API 21开始已原生支持矢量图,无需生成PNG做低版本兼容。在模块级
build.gradle的android.defaultConfig块中添加以下配置:
android { defaultConfig { // 原有配置项,如minSdk 23、compileSdk 31等 vectorDrawables.useSupportLibrary = true // 禁止AGP为矢量图生成各密度PNG产物 generatedDensities = [] } }
配置完成后清理构建缓存重新编译,构建目录不会再生成各密度的PNG转换产物,ImageVector.vectorResource()即可正常加载矢量资源。
- 方案2:沿用已验证可行的
AppCompatResources.getDrawable()接口加载资源,拿到Drawable对象后自行转换为Compose可用的Painter/ImageVector即可,该方案无需修改构建配置。 - 方案3:纯Compose场景下,可替换为Compose自带的
painterResource(id = R.drawable.vectorID)接口加载,新版本Compose中该接口已适配矢量图兼容加载逻辑,不会触发原生资源查找的路径问题。
内容的提问来源于stack exchange,提问作者Kyle
相关产品推荐
相关产品推荐

