[讨论]基于AssetBundle的大厅子游戏实现思路
2.4.0 发布了 assetbundle 功能,
###通过分析官方实现的功能,发现:
- 如果bundle 为远程包, 第一次加载时必须下载才能使用
- 如果bundle 为非远程包, 虽然无需下载,但是只能用传统的热更新方式进行更新
###希望实现
- bundle可内置,也可以远程.
- 发布新包时,希望旧版本也能同步更新bundle.
- 不管内置还是远程包都可以进行更新.
###如何将远程包放入到apk内加载?
这里要分两种情况.注意,构建打包时都勾选md5cache.版本号指构建后的bundle version
1. bundle在同一个工程内.
* 设置bundle为远程包,记录版本号V1.
* 设置bundle为非远程包.打入apk1 (iOS也一样适用)内. 此时apk1 内本地版本为V1
* 生成远程包V2.
* apk1运行时,通过服务端下发判断需要更新V2,则加载远程包V2.
* 更新apk2时将V2版本号写入,加载本地版本V2.
加载方式
* 加载apk内的bundle `loadbundle(bundleName,{version:V1},(err,bundle)=>{...})`
* 加载远程的bundle `loadbundle('http://yourdomain/'+bundleName),{version:V2},(err,bundle)=>{...})`
弊端
* 需要两次打包.
* 第一次加载远程包时为完整下载.
* 对于加载本地和远程版本是两个不同的方法
如果不想打包两次
* 需要修改main.js ,在cc.assetManager.init ,去掉需要本地加载的bundle数组.
* 构建完毕拷贝需要本地加载的bundle 到 build/assets/目录下
cc.assetManager.init({
bundleVers: settings.bundleVers,
//remoteBundles: settings.remoteBundles,
remoteBundles: [],//所有远程包都去掉了.
server: settings.server
});
2. bundle在另外的项目
- 拷贝外部bundle到 build/assets/ 目录
- 修改 main.js 添加外部bundle 到 bundleVers.
cc.assetManager.init({
bundleVers: Object.assign(settings.bundleVers,{bundleA:"bundleAVer",bundleB:"bundleBVer}),
remoteBundles: settings.remoteBundles,
server: settings.server
});
期望的效果
上面的方法的一大弊端就是
第一次更新远程包时需要完整下载无法增量更新.
最好的效果是可以将bundle 放入到apk内,并且也可以跟其他远程包一样进行增量更新.
分析远程包下载目录 data/data/packname/files/gamecaches
cacheList.json 该文件记录了远程bundle所需的文件下载缓存列表.它通过cc.assetManager.cacheManager 进行缓存管理和文件的写入
* 在第一次启动时,将apk内的bundle zip 解压到gamechaches目录;
* 将bundle内文件添加进入cacheList缓存.
这样操作后, 直接使用 加载远程的bundle 的方法 进行加载即可.
优点:
* 可控的包体减小(zip压缩).
* 核心体验无需下载
* 修改文件较多时, 可实现远程整包zip下载.
缺点
- 首次启动需要解压,如果文件较多,需要比较长的等待时间.

