参考链接:
http://blog.sina.com.cn/s/blog_6788cd880102wbc0.html
1.c#层
LuaComponent.cs
1 using LuaInterface; 2 using UnityEngine; 3 4 public class LuaComponent : MonoBehaviour 5 { 6 private LuaTable table; 7 8 private LuaFunction funcAwake; 9 private LuaFunction funcStart; 10 private LuaFunction funcUpdate; 11 12 [SerializeField] 13 private string tableName; 14 15 public static LuaTable Add(GameObject go, LuaTable tableClass) 16 { 17 LuaFunction func = tableClass.GetLuaFunction("New"); 18 if (func == null) 19 { 20 return null; 21 } 22 23 LuaComponent cmp = go.AddComponent<LuaComponent>(); 24 cmp.table = func.Invoke<LuaTable, LuaTable>(tableClass); 25 26 cmp.funcAwake = tableClass.GetLuaFunction("Awake"); 27 cmp.funcStart = tableClass.GetLuaFunction("Start"); 28 cmp.funcUpdate = tableClass.GetLuaFunction("Update"); 29 30 string name = cmp.table.GetStringField("tableName"); 31 if (name != null) 32 { 33 cmp.tableName = name; 34 } 35 36 cmp.CallAwake(); 37 38 return cmp.table; 39 } 40 41 public static LuaTable Get(GameObject go, LuaTable table) 42 { 43 LuaComponent[] cmps = go.GetComponents<LuaComponent>(); 44 for (int i = 0; i < cmps.Length; i++) 45 { 46 if (table == cmps[i].table.GetMetaTable()) 47 { 48 return cmps[i].table; 49 } 50 } 51 return null; 52 } 53 54 void CallAwake() 55 { 56 if (funcAwake != null) 57 { 58 funcAwake.Call(table, gameObject); 59 } 60 } 61 62 void Start() 63 { 64 if (funcStart != null) 65 { 66 funcStart.Call(table, gameObject); 67 } 68 } 69 70 void Update() 71 { 72 if (funcUpdate != null) 73 { 74 funcUpdate.Call(table); 75 } 76 } 77 }
在CustomSettings.cs中添加这个类,并重新生成wrap文件
2.lua层
TestLuaComponent.lua
1 --测试LuaComponent 2 3 TestLuaComponent = 4 { 5 tableName = "TestLuaComponent", 6 property1 = 100, 7 } 8 9 function TestLuaComponent:New() 10 local o = {}; 11 setmetatable(o, self); 12 self.__index = self; 13 return o; 14 end 15 16 function TestLuaComponent:Awake(go) 17 self.go = go; 18 logWarn("TestLuaComponent Awake:" .. go.name .. "_" .. self.property1); 19 end 20 21 function TestLuaComponent:Start(go) 22 logWarn("TestLuaComponent Start:" .. go.name .. "_" .. self.property1); 23 end 24 25 function TestLuaComponent:Update() 26 logWarn("TestLuaComponent Update:" .. self.go.name); 27 end
Game.lua
3.输出
4.分析(配合例子)
LuaComponent.Add:TestLuaComponent这个table作为参数传到c#时,会转化为LuaTable类,这时会获取table的New方法,即TestLuaComponent.New,然后传入参数TestLuaComponent,来创建一个TestLuaComponent的实例,赋值给LuaComponent中的table,因此,LuaComponent中的table是一个实例。创建过程可以表示为TestLuaComponent.New(TestLuaComponent),简写为TestLuaComponent:New()。其余的回调方法同理。
LuaComponent.Get:该方法传入的是一个TestLuaComponent,而LuaComponent中的table是一个实例,其metatable是TestLuaComponent,因为是引用类型,所以直接比较即可,找到则返回实例。
LuaComponent.CallAwake:funcAwake表示TestLuaComponent.Awake,LuaFunction.Call和LuaFunction.Invoke相比,前者没有返回值,后者有。通过调用TestLuaComponent.Awake(table, gameObject),就可以执行lua中对应的Awake方法。另外说明一下,因为添加了LuaComponent组件后c#中的Awake会立即被执行,会导致lua中的Awake无法执行,因此使用CallAwake手动触发,保证在Start前即可。
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· AI与.NET技术实操系列(二):开始使用ML.NET
· 记一次.NET内存居高不下排查解决与启示
· 探究高空视频全景AR技术的实现原理
· 理解Rust引用及其生命周期标识(上)
· 浏览器原生「磁吸」效果!Anchor Positioning 锚点定位神器解析
· DeepSeek 开源周回顾「GitHub 热点速览」
· 物流快递公司核心技术能力-地址解析分单基础技术分享
· .NET 10首个预览版发布:重大改进与新特性概览!
· AI与.NET技术实操系列(二):开始使用ML.NET
· 单线程的Redis速度为什么快?