在C++中从全局表中调用Lua函数

下面是 Lua 代码:

print("Loading Hook System")
local pairs = pairs;
Hooks = {}
Hooks.Hooks = {}
----------
--  This file defines all the available hooks
----------
Hooks.Hooks.OnScoreboardOpen = {}

function Hooks.Add( Name, Identifier, Function )
    if (Hooks.Hooks[Name] == nil) then
        print("Hook "..Name.." Does Not Exist")
    else
        if (Hooks.Hooks[Name][Identifier] == nil) then
            Hooks.Hooks[Name][Identifier] = Function
        else
            print("Hooks.Add Error: Identifier: "..Identifier.." Already Exists")
        end
    end
end

function Hooks.Remove( Identifier )
    for _,Hook in pairs(Hooks.Hooks) do
        if (Hook[Identifier]) then
            Hook[Identifier] = nil
        end
    end
end

function Hooks.Call( Name, ... )
    local arg = {...}
    for _,v in pairs(Hooks.Hooks[Name]) do
        v(unpack(arg))
    end
end

print("Complete")

用户可以将自己的函数添加到钩子系统中,使用唯一标识符,然后在需要时将其移除。

我需要想出如何从 C++ 中调用 Hooks.Call() 函数,但我只知道如何调用全局函数,而不是在全局作用域中的表中的函数。在 C++ 中完全执行 Hooks.Call() 功能的方式是最有效的路线。

以下代码允许我从 C++ 中调用 Lua 函数:

lua_getglobal(m_Lua, "Hooks");
lua_getfield(m_Lua, -1, "Call");
lua_pushstring(m_Lua, "OnScoreboardOpen");
lua_pushnumber(m_Lua, 5);
lua_pushnumber(m_Lua, 7);
int Error = lua_pcall(m_Lua, 3, 0, 0);
if (Error)
{
    std::cout << lua_tostring(m_Lua, -1) << std::endl;
}

这段代码是否完整?此时堆栈是否清除?

点赞
用户1560821
用户1560821

你的代码看起来还不错。

  • 你在栈上保留了 Hooks 表。你可以在调用 lua_getfield 后立即将其删除。或者,封装一个“table.field”检索的实用函数。例如,getglobal2(m_Lua, "Hooks", "Call")

  • 你还在栈上保留了错误消息。你需要将其弹出。

或者,将你的代码封装在一个 Lua 函数中(在 C 端编写),然后通过 lua_pushcfunctionlua_pcall 调用它。这样,栈将自动为您管理。

顺便说一下,你可以使用 v(...) 代替 v(unpack(arg))

2014-07-22 08:27:52