xlua 原理
基于版本 104
可以直接在lua访问c#函数原理:
CS 是一个table,设置了一个__index函数,如果访问不存在的成员的时候,会走__index函数,调用import_type从C#中找到具体函数设置到CS中。以便下一次访问的时候直接使用
xlua在生产wrap时,会生成一个partial ObjectTranslator类,对该类添加了成员变量XLua_Gen_Initer_Register__ s_gen_reg_dumb_obj,在类的构造函数中会提交一个函数(AddIniter),执行该函数时会注册已经生成了wrap的wrap类和__Register方法到ObjectTranslator.delayWrap中。
没有生产类的wrap时,就不会有上面的过程,delayWrap就为空
在lua访问cs中不存在的类的时候,会触发ImportType,ImportType走方法TryDelayWrapLoader注册该类的wrap类和方法。
public bool TryDelayWrapLoader(RealStatePtr L, Type type)
{
.....
if (delayWrap.TryGetValue(type, out loader))
{
delayWrap.Remove(type);
loader(L);
}
else
{
.....
if (!DelegateBridge.Gen_Flag && !type.IsEnum() && !typeof(Delegate).IsAssignableFrom(type) && Utils.IsPublic(type))
{
Type wrap = ce.EmitTypeWrap(type);
MethodInfo method = wrap.GetMethod("__Register", BindingFlags.Static | BindingFlags.Public);
method.Invoke(null, new object[] { L });
}
else
{
Utils.ReflectionWrap(L, type, privateAccessibleFlags.Contains(type));
}
..... return true;
}
从方法中可以看到,如果delayWrap存在对于的wrap和Register函数,那么就走生成好的wrap代码;如果没有,非生成wrap模式就会走EmitTypeWrap方法,动态生成该类的wrap代码和Rigister函数。调用Register函数注册该wrap。如果采用生成wrap模式,DelegateBridge.Gen_Flag就会被生成的代码设置为true,那么凡是没有生成wrap的类代码,都会走Utils.ReflectionWrap
在ReflectionWrap中,对于方法会调用PushFixCSFunction把方法放入fix_cs_functions中,把把函数名,对应的索引和FixCSFunctionWraper注册到lua
internal void PushFixCSFunction(RealStatePtr L, LuaCSFunction func)
{
.....
LuaAPI.xlua_pushinteger(L, fix_cs_functions.Count);
fix_cs_functions.Add(func);
LuaAPI.lua_pushstdcallcfunction(L, metaFunctions.FixCSFunctionWraper, );
.....
}
在lua中调用该函数时,会走FixCSFunction,根据索引定位到具体的函数执行
static int FixCSFunction(RealStatePtr L)
{
try
{
ObjectTranslator translator = ObjectTranslatorPool.Instance.Find(L);
int idx = LuaAPI.xlua_tointeger(L, LuaAPI.xlua_upvalueindex());
LuaCSFunction func = (LuaCSFunction)translator.GetFixCSFunction(idx);
return func(L);
}
catch (Exception e)
{
return LuaAPI.luaL_error(L, "c# exception in FixCSFunction:" + e);
}
}
Hotfix原理
以08_Hotfix中HotfixTest为列
修改HotfixTest的方法Update
xlua.hotfix(CS.HotfixTest, 'Update', function(self)
self.tick = self.tick +
if (self.tick % ) == then
print('<<<<<<<<Update in lua, tick = ' .. self.tick)
end
end
hotfix函数实现
xlua.hotfix = function(cs, field, func)
if func == nil then func = false end
local tbl = (type(field) == 'table') and field or {[field] = func}
for k, v in pairs(tbl) do
local cflag = ''
if k == '.ctor' then
cflag = '_c'
k = 'ctor'
end
local f = type(v) == 'function' and v or nil
xlua.access(cs, cflag .. '__Hotfix0_'..k, f) -- at least one
pcall(function()
for i = , do
xlua.access(cs, cflag .. '__Hotfix'..i..'_'..k, f)
end
end)
end
xlua.private_accessible(cs)
end
经过xlua注入生成的Update代码如下
private static DelegateBridge __Hotfix0_Update;
private void Update()
{
DelegateBridge _Hotfix0_Update = __Hotfix0_Update;
if (_Hotfix0_Update != null)
{
_Hotfix0_Update.__Gen_Delegate_Imp18(this);
}
else if (++tick % == )
{
Debug.Log((object)(">>>>>>>>Update in C#, tick = " + tick));
}
}
xlua.access 对应方法 StaticLuaCallbacks.XLuaAccess
public static int XLuaAccess(RealStatePtr L)
{
......
Type type = getType(L, translator, );//HotfixTest
......
string fieldName = LuaAPI.lua_tostring(L, );// _Hotfix0_Update
...... if (LuaAPI.lua_gettop(L) > ) // set
{
var field = type.GetField(fieldName, bindingFlags);
if (field != null)
{
field.SetValue(obj, translator.GetObject(L, , field.FieldType));
return ;
}
var prop = type.GetProperty(fieldName, bindingFlags);
if (prop != null)
{
prop.SetValue(obj, translator.GetObject(L, , prop.PropertyType), null);
return ;
.......
}
在该方法中,设置方法对应的hotfix属性为lua函数。该例子中设置_Hotfix0_Update
xlua 原理的更多相关文章
- 深入理解xLua热更新原理
热更新简介 热更新是指在不需要重新编译打包游戏的情况下,在线更新游戏中的一些非核心代码和资源,比如活动运营和打补丁.热更新分为资源热更新和代码热更新两种,代码热更新实际上也是把代码当成资源的一种热更新 ...
- 深入xLua实现原理之Lua如何调用C#
xLua是腾讯的一个开源项目,为Unity. .Net. Mono等C#环境增加Lua脚本编程的能力.本文主要是探讨xLua下Lua调用C#的实现原理. Lua与C#数据通信机制 无论是Lua调用C# ...
- 深入xLua实现原理之C#如何调用Lua
本文主要是探讨xLua下C#调用Lua的实现原理,有关Lua如何调用C#的介绍可以查看深入xLua实现原理之Lua如何调用C# C#与Lua数据通信机制 无论是Lua调用C#,还是C#调用Lua,都需 ...
- 深入理解xLua基于IL代码注入的热更新原理
目前大部分手游都会采用热更新来解决应用商店审核周期长,无法满足快节奏迭代的问题.另外热更新能够有效降低版本升级所需的资源大小,节省玩家的时间和流量,这也使其成为移动游戏的主流更新方式之一. 热更新可以 ...
- Unity3D游戏xlua轻量级热修复框架
这是什么东西 前阵子刚刚集成xlua到项目,目的只有一个:对线上游戏C#逻辑有Bug的地方执行修复,通过考察了xlua和tolua,最终选择了xlua,原因如下: 1)项目已经到了后期,线上版本迭代了 ...
- lua热更框架之XLua
框架介绍 xLua是当下最流行的unity热更方案之一,作者是腾讯的车雄生前辈,自2016年初推出以来,已经在腾讯的多款游戏项目上应用,目前xLua已经开源到了GitHub.xLua最大的特色是不仅支 ...
- Unity下XLua方案的各值类型GC优化深度剖析
转自:http://gad.qq.com/article/detail/25645 前言 Unity下的C#GC Alloc(下面简称gc)是个大问题,而嵌入一个动态类型的Lua后,它们之间的交互很容 ...
- Unity3D游戏轻量级xlua热修复框架
Unity3D游戏轻量级xlua热修复框架 一 这是什么东西 前阵子刚刚集成xlua到项目,目的只有一个:对线上游戏C#逻辑有Bug的地方执行修复,通过考察xlua和tolua,最终选择了xlua ...
- ulua、tolua原理解析
在聊ulua.tolua之前,我们先来看看Unity热更新相关知识. 什么是热更新 举例来说: 游戏上线后,玩家下载第一个版本(70M左右或者更大),在运营的过程中,如果需要更换UI显示,或者修改游戏 ...
随机推荐
- Redis Cluster 4.0.9 集群安装搭建
Redis Cluster 4.0.9集群搭建步骤:yum install -y gcc g++ gcc-c++ make openssl cd redis-4.0.9 make mkdir -p / ...
- 009、Java中超过了int的最大值或最小值的结果
01.代码如下: package TIANPAN; /** * 此处为文档注释 * * @author 田攀 微信382477247 */ public class TestDemo { public ...
- 005.CI4框架CodeIgniter, 通过带路径的view视图访问
01. 我们在app目录的Views文件夹中新建一个Login文件,再创建一个login.php文件,在里面我们写上如下代码: <!doctype html> <html> & ...
- 002、创建第一个Java程序HelloWord
代码如下: package TIANPAN; public class TestDemo { public static void main(String args[]) { System.out.p ...
- Spring MVC RedirectAttributes取值方法
RedirectAttributes是Spring mvc 3.1版本之后出来的一个功能,专门用于重定向之后还能带参数跳转的他有两种带参的方式:第一种: attr.addAttribute(" ...
- UVA - 10382 Watering Grass(几何)
题意:有一个矩形,n个圆.已知矩形的长宽和圆的半径,问最少需多少个圆将矩形完全覆盖. 分析: 1.首先求圆与矩形的长的交点,若无交点,则一定不能对用最少的圆覆盖矩形有贡献. 2.如果两个圆与矩形相交所 ...
- Exchange 2003 群集迁移 & SPS 2003 迁移、SQL Server 2000群集
哈哈,本人自己写的文档,内容太多了,有195页,上传到Blog里面,应该是很难看的,排版也不太好. 记得下载时后改名字,用WinRAR解压合并. 第1章 迁移环境介绍 第2章 共享磁盘柜配置 第3章 ...
- 虚拟 DOM 到底是什么?
虚拟 DOM 到底是什么? 作者:wangshengliang 注意:由于文章太长,对文章有删减,但是不会影响整体阅读 是什么? 虚拟 DOM (Virtual DOM )这个概念相信大家都不陌生,从 ...
- 开源DDD设计模式框架YMNNetCoreFrameWork第四篇-增加YMNSession,增加异常处理,增加策略授权
1.增加YMNSession,可以获取当前登录的用户信息 2.增加异常处理,不要使用过滤器,过滤器只能获取到mvc异常 3.增加策略授权,策略授权支持用户角色.用户名授权,初步实现 代码地址:http ...
- flink初识及安装flink standalone集群
flink architecture 1.可以看出,flink可以运行在本地,也可以类似spark一样on yarn或者standalone模式(与spark standalone也很相似),此外fl ...