Bootstrap

CocosCreator 微信小游戏显示加载远程包进度

前言:关于 CocosCreator 微信小游戏使用远程包这里不做过多的阐述了,不清楚的同学可以去官网看一下。(该文章目前只做为笔记使用,后期会补全补详细)


前言

目前实现的方式有两种


提示:以下是本篇文章正文内容,下面案例可供参考

一、使用 cc.assetManager.loadBundle()

这种方法对分包我是按场景分的,其他方式分包应该也可以(由于项目时间紧,没能去尝试)

项目结构:

  • update
  • hall
    在这里插入图片描述
    在这里插入图片描述

hall 文件夹设置为远程包
在这里插入图片描述

接下来就是代码了,如果加载远程包并且显示进度的代码如下(加载远程包引擎已经做了,我们只需要使用即可)

// An highlighted block
cc.assetManager.loadBundle("hall", {onFileProgress: function (arg0) {
                    cc.log("正在加载场景 sceneId: " + sceneId + "arg0: " + JSON.stringify(arg0);
                    //arg0 = {"totalBytesWritten":31707,"totalBytesExpectedToWrite":32850,"progress":96,"cookies":[]}
                }}, (err, bundle) => {
                bundle.loadScene(sceneId, function (err, scene) {
                    cc.director.runScene(scene);
                });
            });

由于我的分包是把整个 hall 场景分出去了,所以用 cc.assetManager.loadBundle() 加载资源后完成后就直接加载场景运行了。远端资源下载过程就在使用 cc.assetManager.loadBundle() 的时候执行的,上面代码可以看到打印的log为:

// An highlighted block
正在加载场景 sceneId:{"totalBytesWritten":31707,"totalBytesExpectedToWrite":32850,"progress":96,"cookies":[]}

根据上面log可以看出有下载进度等数据,只需要显示到界面上就可以了。

注:1、上传到远端服务器上的资源包(remote)上传完成后如果更新是 totalBytesExpectedToWrite 和 progress 为 null 话,注意上传的文件的 http头(header)的 Content-Type 和 Content-Encoding 有没有设置合理的字段,这里设置一下就不会为 null了。目前我只设置了每个 ab 中的包中的 config.xxx.json 文件的 header(Content-Type: application/json, Content-Encoding: Content-Length),就可以正常了。

2、配置 bundle 包压缩类型为“默认”时正常使用上述的方式直接加载远端数据可以正常下载到本地(并无失败的报错),但是下载完成后再次使用 cc.assetManager.loadBundle() 方法进行场景跳转时在某些情况下会重新冲远端下载并且大面积提示超过连接数(有的时候正常),导致场景跳转很慢(重新载入小游戏或删除重试也会同样的出现上述的问)(真机更容易出现)。最终将所有的 bundle 包的压缩类型改为“zip”后就没有上面的问题出来现了。

二、使用微信小游戏的下载功能

cocos 中可以直接使用微信小游戏的 wx.downloadFile()

  • 按照步骤一的方式分包
  • 构建发布界面的“资源服务器地址”配置成“http://usr”(该地址为小游戏内用户数据位置 wx.env.USER_DATA_PATH)。模拟器的这个地址是"http://usr", 真机运行则是"wxfile://usr".这里一定要注意
    在这里插入图片描述
  • 构建发布后把构建好的微信小游戏工程中的远程包“remote”压缩成zip,然后上传到你的资源服务器上
  • 在使用 cc.assetManager.loadBundle 前先下载 remote.zip 并解压。代码如下:
let downloader = wx.downloadFile({
            url: url,
            success: function (res) {
                // 下载成功
                logDebug("下载成功", res);
                // 解压
                let unzipTargerPath = wx.env.USER_DATA_PATH;
                    let fileManager = wx.getFileSystemManager();
                    fileManager.unzip({
                        zipFilePath: res.tempFilePath, // 下载路径
                        targetPath: unzipTargerPath, // 解压资源存放路径
                        success: function (zRes) {
                            // 解压成功,在此调用 cc.assetManager.loadBundle()
                        },
                        fail: function (zRes) {
                            // 解压失败
                        }
                    });
            },
            fail: function (res) {
                // 下载失败
            }
        });
        // 下载进度
        downloader.onProgressUpdate((res) => {
            cc.log("下载进度: " + res.progress);
        });
  • 在下载并且解压完成后使用 cc.assetManager.loadBundle 加载资源,此时资源已经被下载到“http://usr”中,加载路径也是从该目录加载,所以就不会再有下载资源的过程了。

总结

以上两种方式我目前还没有详细的对比优劣以下只是简单目测谈下。

  • 第一种是在官方的基础上显示进度优势是可以用于更新资源,引擎会自动帮我们判断资源是否需要重新下载更新,缺点就是都是单个文件下载,如果远端资源过多的话下载连接数需要注意。
  • 第二中方式需要自己写是否下载远端资源的逻辑,有点是只下载一个zip,可以比较自由的做更新逻辑。
;