[Unity热更新]tolua# & LuaFramework(八):更新下载

效果图:

未更新前的:

[Unity热更新]tolua# & LuaFramework(八):更新下载_第1张图片

重新启动后:

[Unity热更新]tolua# & LuaFramework(八):更新下载_第2张图片


更新下载:

1.先成功运行框架中的例子

2.分析GameManager中的IEnumerator OnUpdateResource(),发现它向服务器发送的第一条信息为:http://localhost:6688/files.txt?v=当前时间,这条信息到达服务器后,会由HttpServer中的OnGetRequest进行处理,首先这条信息会被截去http://localhost:6688/和?v=当前时间,剩下files.txt,然后会在Server的同级目录下找Assets/StreamingAssets下找files.txt,如果找到就会发送给客户端。客户端得到这个从服务器下来的最新files.txt,就会进行MD5值的比较,下载变化了的内容

3.将原有的StreamingAssets进行备份,修改项目中的资源,重新生成,在服务器那建一个Assets文件夹,再将新的StreamingAssets放进去,还原旧的StreamingAssets

4.运行例子,如无意外例子是没有变化的,然后设置AppConst.UpdateMode为true,同时修改ResourceManager中的Initialize方法:m_BaseDownloadingURL = "file:///" + Util.DataPath;,然后启动服务器,然后运行例子,就会发现真的更新了!


分析一下框架自带例子,会发现它是先更新资源,然后才进行lua逻辑,展示界面。而很多情况下,我们是先展示主界面(即选择服务器及显示下载进度的那个界面),然后才更新资源的,这里我总结一下:

1.解包

2.更新lua脚本(自动更新)

3.显示主界面

4.更新其他资源(以进度条的方式进行显示)

在游戏中,UI相关的东西最好都由lua负责,当然主界面也是这样的,这样主界面就可以不断地变化了。这里为什么不是显示主界面后再把变更的资源进行统一下载呢?因为如果你要显示主界面,就需要先加载lua的一些核心脚本,那么如果你的这些核心lua脚本发生了变化,当进行更新时,你原来的核心脚本就会被删掉,从服务器那下载最新的,这时因为游戏还是需要依赖于旧的核心lua脚本,但被删除了,就会出错。因此,为了更加灵活,我觉得还是先更新lua脚本比较好。

当然,将第二第三步交换我是测试过的,容易出错。核心脚本一般会封装得很好,不会出现什么变化,而我这里指的是,客户端和服务端的files.txt中,两者的核心lua脚本的MD5值不同而导致核心lua脚本被更新(核心脚本的内容没改,但同样的脚本MD5值不同)。例如,你生成了一份新的StreamingAssets放到了服务器端,然后为了测试客户端能否下载新内容,还原了旧的StreamingAssets,此时核心脚本的MD5值就变了。




一.lua

1.创建lua模板

88-ToLua# Panel Script-Panel.lua.txt

#SCRIPTNAME# = {};
local this = #SCRIPTNAME#;

local gameObject;
local transform;

--由LuaBehaviour自动调用
function #SCRIPTNAME#.Awake(obj)
	gameObject = obj;
	transform = obj.transform;

	--this.gridText = transform:FindChild('ScrollView/Grid'):GetComponent('Text');
	
end

--由LuaBehaviour自动调用
function #SCRIPTNAME#.Start()

end

89-ToLua# Ctrl Script-Ctrl.lua.txt

require "Common/define"

#SCRIPTNAME# = {};
local this = #SCRIPTNAME#;

local gameObject;
local transform;

function #SCRIPTNAME#.New()
	return this;
end

function #SCRIPTNAME#.Awake()
	panelMgr:CreatePanel('Prompt', this.OnCreate);--需修改处
end

function #SCRIPTNAME#.OnCreate(obj)
	gameObject = obj;
	transform = obj.transform;

	--go.transform.localPosition = Vector3.zero;
	
end


2.封装一个事件中心

框架提供了一个events.lua,可以对它进行再一次封装,这样c#发送事件给lua也很方便:

EventType =   
{  
	--这几个是和NotiConst.cs对应的
    UPDATE_PROGRESS = "UpdateProgress", --更新进度
	UPDATE_DOWNLOAD = "UpdateDownload", --更新下载,下载完一个文件就会被发送
	UPDATE_ALLCOUNT = "UpdateAllCount", --更新文件数
}

Event = require 'events'

EventCenter = {};  
local Events = {};

function EventCenter.AddListener(eventType, func)  
	Events[eventType] = true;
    Event.AddListener(eventType, func);  
end  
  
function EventCenter.RemoveListener(eventType, func)  
	Events[eventType] = false;
    Event.RemoveListener(eventType, func);  
end  
  
function EventCenter.Brocast(eventType, ...)  
	if Events[eventType] then
		Event.Brocast(eventType, ...); 
	end
end  



二.c#(主要是对GameManager和AppView进行了变动)

注意点:

AppView

1.一般情况下,c#调用lua使用的是Util.CallMethod,如果这个方法在子线程中被调用,那么就会报get_xxx can only be called from the main thread的错误,那么可以将调用转移到Awake、Start和Update等mono的方法

2.很多时候,我们需要获取下载进度,并把它展示出来,那么通过ThreadManager中的ProgressChanged,它会把消息进行分发,其中AppView会对NotiConst.UPDATE_PROGRESS进行监听,执行对应的方法。

3.由于框架使用的是ThreadManager进行线程下载,所以下载进度、是否下载完成等信息是不能与界面显示同步的。


GameManager
就是上面所说的四个步骤了


工程下载:

http://pan.baidu.com/s/1nvrgM97

你可能感兴趣的:(tolua#,LuaFramework)