多模块Android应用无法直接访问其他模块Strings资源问题
问题本质
当前项目开启了AGP的非传递性R类(non-transitive R class) 配置,这是AGP 4.0版本后新增、新版本默认开启的编译优化特性:
- 开启状态下,每个模块生成的R类只会包含自身模块定义的资源,不会自动聚合所有依赖模块的资源,因此你在Onboarding模块直接调用自身包路径下的
R.string.mystring时,无法检索到shared模块里的资源 - 你之前接触的同类多模块项目,要么使用的是4.0之前的旧版AGP,要么手动关闭了该配置,才会出现依赖模块资源自动合并到当前模块R类的效果。
可选解决方式
根据项目实际需求二选一即可:
方案1:保留非传递R类特性(官方推荐)
该特性可以大幅降低多模块项目的增量编译耗时,同时避免不同模块的同名资源引用冲突,是官方目前推荐的配置方式。
你不需要修改全局配置,跨模块引用资源时直接指向对应模块的R类即可。如果觉得每次写全shared模块完整包名太繁琐,可以在业务模块的导入语句中给shared的R类起别名:
import 你的shared模块完整包名.R as SharedR
后续直接通过SharedR.string.mystring就能访问shared模块的资源,写法简洁也不会出现引用冲突。
方案2:关闭非传递R类,兼容旧版引用逻辑
如果需要统一用当前模块的R类直接访问所有依赖的资源,在项目根目录的gradle.properties文件中添加如下配置,全局关闭非传递R类特性:
android.nonTransitiveRClass=false
添加完成后同步Gradle,所有依赖模块的资源会自动合并到当前模块的R类中,直接调用R.string.mystring即可正常访问。
注意:关闭该特性后,模块的R类会随着依赖的模块数量增加不断膨胀,会明显拖慢多模块项目的编译速度,模块数量越多性能影响越大。
内容的提问来源于stack exchange,提问作者Othmane_lam
相关产品推荐
相关产品推荐

