原地址:http://crazylights.cnblogs.com/

下载在这个时代实在是太平常了,每个人都深刻的理解着下载到底是什么。

这一篇文字只是把下载的代码分享并介绍,而已。

首先,下载系统担负着几个使命。

第一、是保持客户端版本库的最新。

第二、是下载要能够比对并最少下载

第三、是要尽量快一些。

其实我们并没有写一个下载系统,因为实在没有几行代码。我们这里介绍的是一个

Http下载并保存缓存,首包从StreamingAssets读取,加载资源,三个功能在一起的模块

源码位置https://github.com/lightszero/easydown

保持最新

为了解决第一第二的问题,我们要尽量让下载的资源零散一些。

这样就可以以文件单位进行下载,本地已经有的文件就不下载。

为了实现这个目标我们得在下载之前就决定一个文件是否要更新,因为下载之后流量已经浪费了。

需要知道一个文件是否应该更新,一种简单的办法就是给每个文件提供一个简单的特征信息,先将特征信息下载,然后决定是否下载整个文件。

去一个大文件的特征信息,这是摘要算法的工作,Hash、CRC32、MD5、Sha1,我们这里选择最优秀的Sha1算法来做我们文件的特征信息。

首先我们得为我们打算下载的文件生成特征信息,这些测试文件和工具源码你都可以从GITHUB上下载到。

点击检查,会显示出如上的情况,告诉你版本和你上次的版本发生了什么变化。

请勿删除生成的allver.ver.txt文件,他会记录总的版本,每次检查都会基于上一个版本

然后点击生成版本,会更新所有的版本文件

这里我们加了个group的设计

版本生成工具会把自己路径下的文件夹作为group

在客户端下载时是以group为单位的,方便处理

比如我可以 把高分辨率资源和低分辨率资源分别放在两个group里

只要客户端简单的切换group名字,就可以实现资源切换。

比如这里就生成了两个Group,每个Group有自己的Ver文件

我们看看Ver文件

文件名,中间怪怪的就是sha1特征串,哪怕文件只改了一个字节,生成的特征串就会不一样。最后是文件尺寸,这样我们只要取得了ver文件,下载之前就知道文件有多大了。

这样我们就有了让文件版本保持最新的机制了

只要先下载ver文件,然后再判断每个group的文件有没有变化,有变化的有多少,然后下载他们。

把这些测试文件找个Http服务器放上去,然后我们继续

客户端下载

客户端如何下载?直接看代码说明

先一行代码初始化资源管理系统

第一个参数是下载服务器地址,就是对应allver.ver.txt文件的http地址

第二个参数是一个回调函数,由于初始化资源系统会去网络下载ver文件,需要时间,所以是用回调函数来通知的

第三个参数是一个List<string>,用来告知资源管理器,要检查哪几个Group。

你也许会疑问,怎么会有不检查的Group呢?比如我们的游戏要做好几个平台,有一些平台不通用的资源,我们把他们放在不同平台,这样在一个平台就不会去检查别的平台的资源。

注意Resmgr需要一直Update,因为不管是下载还是加载都不是立即完成的,Resmgr要一直监控情况

利用宏你就可以取到每个平台一个特殊的字符串,把他们混到group名字,就可以自动选取平台专用group下载了

还有第四个默认参数:并发下载数,默认1,要想充分利用下载带宽,你可以改成2,改更多的并发意义并不大,3并发和2并发效果不会有很大差异。

taskState是资源管理器提供的一个简单统计工具,用来得到有几个任务在执行,完成了几个。

GetNeedDownloadRes 就是比对出那些需要下载的资源

然后循环,下载,下载每个资源都可以提供一个独立的通知回调,但我们这里演示的是一个开始批量下载的用法,就不单独处理了。

最后WaitForTaskFinish函数,会一直等到所有任务完成再回调给我们,

这就完成了整个下载过程

下载进度

关于下载进度,我们可以利用taskState做简单的文件数量统计,也可以把downlist里面的每个文件的长度取出来自己计算。

演示个简单的

注意Resmgr需要一直Update,因为不管是下载还是加载都不是立即完成的,Resmgr要一直监控情况

加载使用

无论文件是本地最新还是刚刚下载完,无论是首包资源还是更新资源,我们的加载方式都是一样的

从Resmgr的 verLocal,本地版本管理 中取得对应的Group,然后从Group中取出File,然后调用File的BeginLoadXXX方法即可

我们提供了四种Load接口,其实一种Bytes就够了,其他资源全部都从Bytes中来,这个我们在加载篇中讲过。

但是考虑到常用性,我们对String Texture2D AssetBundle统一作了封装。

还有以下其他的资源是符合加载的,需要多个文件联合才能加载出来,我们把这种文件放到加载篇里去研究。

好了,你现在已经拥有热更新最重要的更新模块了,而且他完全For Free。

Unity3D热更新的更多相关文章

  1. Unity3D热更新全书-重头再来

    之前写了Unity3D热更新全书系列Blog 提出了下载.加载.脚本三个方面的开源类库 下载方面有EasyDown加载方面有GameObjParser脚本方面有C#Light另外有一个没有独立成库,但 ...

  2. Unity3D热更新全书FAQ

    只要有程序员朋友们问过两次的问题 就会收录在此FAQ中 1.C#Light对比LUA有什么好处 C#Light是静态类型脚本语言,语法同C#,Lua是动态类型脚本语言,这两种都有人喜欢. 我更喜欢静态 ...

  3. Unity3D热更新全书-PageZero

    由于深刻的认识到自己是个思维跳跃的人,深入浅出是个我还要努力很久的目标,为了让大家不至于在我乱七八糟的文字中迷失,特整理目录一份 无分类 <Unity3D热更新全书-何谓热更新,为何热更新,如何 ...

  4. Unity3D热更新全书-何谓热更新,为何热更新,如何热更新

    首先来赞叹一下中文,何谓为何如何,写完才发现这三个词是如此的有规律. 为何赞叹中文?因为这是一篇针对新手程序员的文字,是一节语文课. 然后来做一下说文解字,也就是 何谓热更新 热更新,每个程序员一听就 ...

  5. Unity3D 热更新方案(集合各位专家的汇总)

    http://blog.csdn.net/guofeng526/article/details/52662994 热更新”这个词,在Unity3D的应用下,是有些语义错误的,但是作为大家都熟知的一项技 ...

  6. Unity3D热更新之LuaFramework篇[03]--prefab加载和Button事件

    在上一篇文章 Unity3D热更新之LuaFramework篇[02]--用Lua创建自己的面板 中,我介绍了LuaFramework加载面板的方法,但这个方法并不适用于其它Prefab资源,在这套框 ...

  7. Unity3D热更新之LuaFramework篇[02]--用Lua创建自己的面板

    在上篇文章 Unity3D热更新之LuaFramework篇[01]--从零开始 中,我们了解了怎么获得一个可用的LuaFramework框架. 本篇将我会先介绍一下如何配置Lua开发环境,然后分析在 ...

  8. Unity3D热更新之LuaFramework篇[07]--怎么让unity对象绑定Lua脚本

    前言 在上一篇文章 Unity3D热更新之LuaFramework篇[06]--Lua中是怎么实现脚本生命周期的 中,我分析了由LuaBehaviour来实现lua脚本生命周期的方法. 但在实际使用中 ...

  9. Unity3D热更新之LuaFramework篇[09]--资源热更新与代码热更新的具体实现

    前言 在上一篇文章 Unity3D热更新之LuaFramework篇[08]--热更新原理及热更服务器搭建 中,我介绍了热更新的基本原理,并且着手搭建一台服务器. 本篇就做一个实战练习,真正的来实现热 ...

  10. Unity3D热更新之LuaFramework篇[10]--总结篇

    背景 19年年初的时候,进到一家新单位,公司正准备将现有的游戏做成支持热更的版本.于是寻找热更方案的任务就落在了我头上. 经过搜索了解,能做Unity热更的方案是有好几种,但是要么不够成熟,要么不支持 ...

随机推荐

  1. yii下使用oracle中文都变成问号乱码的解决方法

    在配置文件中,一般会用以下配置: 'db_oracle'=>array( 'class' => 'CDbConnection', 'connectionString'=>'oci:d ...

  2. 议:如何将树形菜单形式的数据转化成HTML的二维表(相同内容需合并单元格)

    一般做OA类管理系统,经常涉及到“组织架构”的概念,那么像这种有上下层级关系的数据一般会做成树形菜单的方式显示,底层代码必定会用到递归算法.这篇随笔的目的就是要谈谈除了用树形菜单来显示这种上下层级关系 ...

  3. Java .Net C++ RSA 加密

    原文:http://www.codeproject.com/Articles/25487/Cryptographic-Interoperability-Keys DEMO: JAVA .Net C++

  4. extjs类的生命周期

    只要extjs对应的类文件加载了,那么该类就可以构造对象或者用来继承了.

  5. 编译gd-2.0.35.tar.gz时报错:gd_png.c:16:53: error: png.h: No such file or directory

    编译gd-2.0.35.tar.gz时报错: gcc -DHAVE_CONFIG_H -I. -I. -I. -I/usr/local/freetype/include/freetype2 -I/us ...

  6. iOS对textField进行字符长度限制的办法

    在项目开发过程中,遇到这么一个需求,编辑标签时,输入的最大长度需要限制为24个字节. 查阅了一些材料,并参考了之前项目的相关处理办法,今天在这里总结一下解决方案. 1.写一个截取字符串的方法,将超长的 ...

  7. JavaScript学习笔记(2)——JavaScript和DOM的关系

    文档对象模型(Document Object Model,简称DOM),是W3C组织推荐的处理可扩展标志语言的标准编程接口.DOM实际上是以面向对象方式描述的文档模型.DOM定义了表示和修改文档所需的 ...

  8. Dorado浏览器调试

    通常在项目中我们对js脚本进行调试有以下2种方式: alert调试法 首先是最原始也是最简单的使用alert,在页面中需要输出需要的变量的地方加上alert函数,将变量弹出显示:alert方式虽然简单 ...

  9. C语言 宏/macor/#define/

    C语言 宏/macor/#define 高级技巧 1.在进行调试的时候,需要进行打印/PRINT,可以通过define进行自定义.例如,自己最常用的DEBUG_PRINT() #define DEBU ...

  10. time 函数

    1.Python Time 2.C++ Time Example: #include <iostream> #include <chrono> //C++的`计时`库 #inc ...