以下是关于“framework-res.apk覆盖编译方式由rro替换为sro”的完整攻略,包含两个示例。
背景
在Android应用程序中,framework-res.apk
是一个非常重要的文件,它包含了许多系统资源,例如布局、字符串、颜色等。在Android应用程序的开发过程中,我们经常需要修改这些资源,以满足应用程序的需求。为了修改这些资源,我们需要对framework-res.apk
进行覆盖编译。在Android 9之前,我们使用的是RRO(Runtime Resource Overlay)覆盖编译方式。但是,在Android 9及以后的版本中,Google引入了SRO(Static Resource Overlay)覆盖编译方式,以取代RRO。
RRO和SRO的区别
RRO和SRO都是覆盖编译方式,它们的主要区别在于编译时机和编译方式。
- RRO:在应用程序安装时,系统会将
framework-res.apk
中的资源打包成一个Overlay包,然后与应用程序一起安装。在运行时,系统会根据需要加载Overlay包,并将其应用于应用程序中。 - SRO:在编译应用程序时,系统会将
framework-res.apk
中的资源打包成一个Overlay包,并将其与应用程序一起打包成APK文件。在运行时,系统不需要再加载Overlay包,因为所有的资源都已经包含在APK文件中了。
将RRO替换为SRO的步骤
要将RRO替换为SRO,我们需要执行以下步骤:
- 修改
Android.mk
文件,以使用SRO编译方式。 - 修改
AndroidManifest.xml
文件,以声明Overlay包。 - 修改
build.gradle
文件,以启用SRO编译方式。
以下是两个示例:
示例1:使用SRO编译framework-res.apk
在Android.mk
文件中,我们需要将LOCAL_RESOURCE_DIR
变量设置为frameworks/base/core/res
,并将LOCAL_RESOURCE_DIR
变量设置为frameworks/base/core/res/res-overlay
。这将告诉系统使用SRO编译framework-res.apk
。
LOCAL_PATH := $(call my-dir)
include $(CLEAR_VARS)
LOCAL_MODULE := framework-res
LOCAL_SRC_FILES := $(call all-java-files-under, src)
LOCAL_RESOURCE_DIR := $(LOCAL_PATH)/../../core/res
LOCAL_AAPT_FLAGS := --auto-add-overlay
LOCAL_PACKAGE_NAME := framework-res
LOCAL_CERTIFICATE := platform
include $(BUILD_PACKAGE)
在AndroidManifest.xml
文件中,我们需要声明Overlay包。我们可以使用<overlay>
元素来声明Overlay包,如下所示:
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="com.android.framework.res"
android:versionCode="1"
android:versionName="1.0">
<overlay
android:targetPackage="android"
android:priority="1"
android:isStatic="true"
android:requiredSystemPropertyName="ro.build.version.sdk"
android:requiredSystemPropertyValue="31" />
</manifest>
在build.gradle
文件中,我们需要启用SRO编译方式。我们可以在defaultConfig
块中设置resConfigs
属性,如下所示:
android {
compileSdkVersion 31
buildToolsVersion "31.0.0"
defaultConfig {
applicationId "com.example.myapp"
minSdkVersion 21
targetSdkVersion 31
versionCode 1
versionName "1.0"
resConfigs "en", "fr", "de"
}
}
示例2:使用SRO编译自定义应用程序
在自定义应用程序中,我们可以使用SRO编译方式来覆盖framework-res.apk
中的资源。以下是一个示例:
android {
compileSdkVersion 31
buildToolsVersion "31.0.0"
defaultConfig {
applicationId "com.example.myapp"
minSdkVersion 21
targetSdkVersion 31
versionCode 1
versionName "1.0"
resConfigs "en", "fr", "de"
}
sourceSets {
main {
res.srcDirs = [
'src/main/res',
'../../core/res/res-overlay'
]
}
}
}
在这个示例中,我们将res.srcDirs
属性设置为src/main/res
和../../core/res/res-overlay
。这将告诉系统使用SRO编译应用程序,并将Overlay包包含在APK文件中。
结论
将RRO替换为SRO是一个简单的过程,只需要修改Android.mk
、AndroidManifest.xml
和build.gradle
文件即可。使用SRO编译方式可以提高应用程序的性能和稳定性,因为所有的资源都已经包含在APK文件中了。