Android 多渠道打包(二)--动态多渠道资源替换技巧

Android多渠道打包最佳实践中介绍了几种快速进行Android渠道包构建的方式,嫌弃多渠道速度慢的同学可以先去看一下,一定会有所收获。
<br /> 有时多渠道打包时不仅仅需要进行渠道号的设置,还需要对不同版本进行资源的替换或者在代码中对于某些渠道的用户进行一些特殊设置(运营的同学也不容易)。这时仅仅依靠前边的方法就不灵了,除非你想手动打包。
<br /> 这里有两种思路:

  • 利用gradle Product flavors 进行打包, 使用 gradle打包在 速度上没有优势,每个flavors都要进行编译,混淆等操作(这里想写篇文章具体介绍下)。
  • 使用apktool 对资源进行替换,这种方式会需要重新打包资源,进行签名,速度要快一些,但是在某些机器上有莫名其妙的crash,你懂的……
    所以基本也就剩下了第一种方式。

流程分析

这里我们明确自己的目标:动态资源替换多渠道打包,同时过程要快速、自动化。基本流程如下:

  • 首发渠道号配置
    一般来说不是每个渠道都需要进行首发的,正常每个版本会有1~2个渠道进行首发,首发的渠道包一方面要进行替换资源,另一方面在代码上也有需求(比如有些渠道要求首发闪屏保持2s以上,心疼为app做启动优化的同学……)。因此这部分要进行动态配置。
  • gradle打包时获取渠道号
    我们要利用gradle进行首发渠道包的打包,因此需要根据每次的需求动态获取需要首发渠道号,并进行打包
  • 普通多渠道打包时对首发渠道的处理
    Android多渠道打包最佳实践中直接在 defaultRelease 包的基础进行了多渠道打包,这次gradle打包完成后会编译出所有的首发渠道包,我们需要把渠道号写入到对应的渠道包中。
    + 代码中对首发渠道号的处理
    这里主要是根据需求在代码中判断自己是否是首发包。

《Android 多渠道打包(二)--动态多渠道资源替换技巧》 Paste_Image.png

代码实现

  • 首发渠道号配置
    这里三个地方要获取首发渠道号,gradle、渠道号写入、代码中读取,考虑到方便行,我们把首发渠道号单独写在文件中,方便各步的读取。

  • gradle中读取
    android中gradle实际使用groovy,groovy与java语法非常像,很容易上手。
    这里利用groovy读取配置文件,获取到首发渠道号

//读取首发渠道号
ArrayList channelList = new File("xxx").readLines()
java.lang.StringBuffer channels = new StringBuffer()
channelList.each {    
       channel -> channels.append(channel + ","
)}
//在这里进行渠道号到配置
productFlavors {  
    //自动打包每个渠道号,需要包各个渠道的资源放置在相应的目录下 
    //这里可以参考利用gradle进行多渠道打包,方法是一样的,网上资源也比较多 
     channelList.each {       
            flavorName -> "$flavorName" {}    
     }    
     //首发渠道号到Androidmanifest,这样代码中可以读取到
     productFlavors.all { 
             flavor ->  flavor.manifestPlaceholders = [Channel: channels]   
     }
}
  • 渠道号写入
    非首发渠道可以通过在default包中写入渠道号,首发包的渠道写入相应的渠道包中。
    这里可以使用shell或则python脚本写入。
    shell命令参见Android多渠道打包最佳实践

  • 代码中读取
    在打包时已经把所有的首发渠道号写入到了AndroidManifest中,读取即可

try {    
    ApplicationInfo ai = getPackageManager().getApplicationInfo( getPackageName(), PackageManager.GET_META_DATA);    
    if (null != ai) {        
         metaData = ai.metaData;   
     }    
    if (null != metaData) {        
        metaValue = metaData.getString(metaKey);    
     }
} catch (PackageManager.NameNotFoundException e) {
}
return metaValue;

至此,基本动态多渠道资源替换完成。

Other

贴个不定期更新的公众号,欢迎交流:

《Android 多渠道打包(二)--动态多渠道资源替换技巧》 wutongke

    原文作者:wutongke
    原文地址: https://www.jianshu.com/p/3104650d3bac
    本文转自网络文章,转载此文章仅为分享知识,如有侵权,请联系博主进行删除。
点赞