美文网首页
ToLua的Example示例学习笔记03_CallLuaFun

ToLua的Example示例学习笔记03_CallLuaFun

作者: 凌枫望星月 | 来源:发表于2020-05-10 21:19 被阅读0次

展示了C#如何调用Lua的函数。

1」代码

操作代码如下:

        private string script =
        @"  function luaFunc(num)                        
                return num + 1
            end

            test = {}
            test.luaFunc = luaFunc
        ";

    LuaFunction luaFunc = null;
    LuaState lua = null;
    
    void Start () 
    {
        new LuaResLoader();
        lua = new LuaState();
        lua.Start();
        DelegateFactory.Init();
        lua.DoString(script);

        //Get the function object
        luaFunc = lua.GetFunction("test.luaFunc");

        if (func != null)
        {
            int num = luaFunc.Invoke<int, int>(123456);
            Debugger.Log("generic call return: {0}", num);

            num = CallFunc();
            Debugger.Log("expansion call return: {0}", num);

            Func<int, int> Func = luaFunc.ToDelegate<Func<int, int>>();
            num = Func(123456);
            Debugger.Log("Delegate call return: {0}", num);
            
            num = lua.Invoke<int, int>("test.luaFunc", 123456, true);
            Debugger.Log("luastate call return: {0}", num);
        }
                
        lua.CheckTop();
    }

    void OnDestroy()
    {
        if (luaFunc != null)
        {
            luaFunc.Dispose();
            luaFunc = null;
        }

        lua.Dispose();
        lua = null;
    }

    int CallFunc()
    {        
        luaFunc.BeginPCall();                
        luaFunc.Push(123456);
        luaFunc.PCall();        
        int num = (int)luaFunc.CheckNumber();                    
        luaFunc.EndPCall();
        return num;                
    }

2」需要了解的部分

  • ToLua通过LuaFunction封装并缓存一个函数,并提供各种操作。建议频繁调用的函数使用无GC方式调用。

3」值得注意的方法

  • LuaState.GetLuaFunction用来获取并缓存一个lua函数, 此函数支持串式操作, 如"test.luaFunc"代表test表中的luaFunc函数。
  • LuaState.Invoke<T1(,T2,...T6),R1>(string name, T1 arg1(,T2 arg2...), bool logMiss) 临时调用一个lua function并返回一个值,这个操作并不缓存lua function,适合频率非常低的函数调用。
  • LuaFunction.Call() 不需要返回值的函数调用操作,可以在括号里加参数。
  • LuaFunction.Invoke() 有一个返回值的函数调用操作

  • 以下几条要一起使用,通常放在一个函数里一起调用。
  • LuaFunction.BeginPCall() 开始函数调用
  • LuaFunction.Push() 压入函数调用需要的参数,通过众多的重载函数来解决参数转换gc问题
  • LuaFunction.PCall() 调用lua函数
  • LuaFunction.CheckNumber() 提取函数返回值, 并检查返回值为lua number类型,注意这个CheckT(),顺序要按照Lua的返回值顺序来,适合多返回值的luaFunction。
  • LuaFunction.EndPCall() 结束lua函数调用, 清楚函数调用造成的堆栈变化

  • LuaFunction.Dispose() 释放LuaFunction, 递减引用计数,如果引用计数为0, 则从_R表删除该函数

  • 还有一点需要注意:
    无论Call还是PCall只相当于lua中的函数'.'调用。
    请注意':'这种语法糖 self:call(...) == self.call(self, ...)
    c# 中需要按后面方式调用, 即必须主动传入第一个参数self
    还有,以后Lua带冒号的调用,都可以写成a:call(...) == a.call(a, ...)

最后再多说几句,这个代码中的

        new LuaResLoader();
        lua = new LuaState();

new LuaResLoader();放在lua = new LuaState();之前,可能会有人想问它是做什么用的。
这个LuaResLoader实际上是继承了我们之前曾提到的LuaFileUtils,并重写和增加了一些函数,由于是单例模式,单例初始化由lua = new LuaState();完成,但是率先 new 一个 LuaResLoader(),就让单例是LuaResLoader()而不是new 一个 LuaFileUtils()。

相关文章

网友评论

      本文标题:ToLua的Example示例学习笔记03_CallLuaFun

      本文链接:https://www.haomeiwen.com/subject/wmssnhtx.html