How to replace strings resources with Android Gradle

前端 未结 4 941
感动是毒
感动是毒 2020-12-07 23:45

I made a new app with gradle in Android Studio, and now I need to make about 10 versions with different package names and values in resources. I made custom flavors as in ex

相关标签:
4条回答
  • 2020-12-07 23:55

    These links may be helpful:

    • Using Gradle for building Android applications
    • Gradle Plugin User Guide

    And my filter definition using regex to replace something:

    from('res/') {
        include '**/*.xml'
        filter {
            line -> line.replaceAll(/YOUR_REGEX_TO_REPLACE_SOMETHING/, 'REPLACED_RESULT_EXPRESSION')
        }
    }
    into 'build/path/to/your/filtered/resources/'
    
    0 讨论(0)
  • 2020-12-08 00:03

    I was trying to get similar functionality as Maven resource filtering. This is what I came up with. My solution could use some changes to be more robust (i.e. pulling from a properties file, etc).

    My example just shows how to replace a single value, which is all that I needed. The variables follow the ${some.property} convention. This solution also works with product flavors that have their own resource files.

    import org.apache.tools.ant.filters.*
    ...
    android.applicationVariants.all{ variant ->
        // Perform resource filtering
        variant.mergeResources.doLast {
            filterResources(variant)
        }
    }
    
    def filterResources(buildVariant) {
    
        //Setup temp directory to filter the resources
        File resFiltered = file("${buildDir}/res/all/filtered/${buildVariant.dirName}")
        if(resFiltered.exists()){
            resFiltered.delete()
        }
    
        //Copy and filter the resources.
        copy {
            from(buildVariant.processResources.resDir) {
                include '**/*.xml'
    
                //Could be improved upon to pull from a properties file, etc.
                ant.properties['app.version'] = project.version
    
                filter(ExpandProperties, project: ant.project)
    
            }
            from(buildVariant.processResources.resDir) {
                exclude '**/*.xml'
            }
    
            into resFiltered
    
        }
    
        //Delete all the original resource files
        file(buildVariant.processResources.resDir).deleteDir()
        //Replace with the filtered ones.
        resFiltered.renameTo(file(buildVariant.processResources.resDir))
        //Delete the original 'filtered' directory
        file( "${buildDir}/res/all/filtered").deleteDir()
    }
    

    Example in strings.xml

     ...
     <string name="app_version">${app.version}</string>
     ...
    
    0 讨论(0)
  • 2020-12-08 00:10

    In your "src" folder, create "flavor1" and "flavor2" folders with the same hierarchy as your "main" folder. If you have strings.xml in your main/res/values, you can do it in flavor1/res/values as well and have the replacement values in there. It may show errors in the IDE but it should still build and run.

    0 讨论(0)
  • 2020-12-08 00:13

    I had a similar problem. I wanted to add the Jenkins build number to the strings that get merged from strings.xml. Here's my solution as of Android Gradle plugin 0.12.+.

    // Insert the build number into strings.xml
    android.applicationVariants.all{ variant ->
        variant.mergeResources.doLast{
            ext.env = System.getenv()
            def buildNumber = env.BUILD_NUMBER
            if (buildNumber != null) {
                File valuesFile = file("${buildDir}/intermediates/res/${variant.dirName}/values/values.xml")
                println("Replacing revision number in " + valuesFile)
                println("Build number = " + buildNumber)
                String content = valuesFile.getText('UTF-8')
                content = content.replaceAll(/devBuild/, buildNumber)
                valuesFile.write(content, 'UTF-8')
            }
        }
    }
    

    You might want to hook into a different Gradle task depending on what you want to do. Take a look at the tasks that are part of the Android build to figure that out.

    http://tools.android.com/tech-docs/new-build-system/user-guide

    UPDATE: At some point, the Android Gradle plugin changed the way to iterate through application variants keyword from each to all. My answer has been updated to reflect the change, but try switching to each if this code doesn't print anything to the console.

    0 讨论(0)
提交回复
热议问题