简体   繁体   English

如何从c ++创建和调用lua函数(即多个文件)

[英]how to create and call lua function, that is in multiple files, from c++

I need to create something like an onSomeEvent function, that'll be in every Lua plugin file. 我需要创建类似onSomeEvent函数的东西,该函数将出现在每个Lua插件文件中。 I have this: 我有这个:

void onSomeEvent(int someParameter) {
    lua_getglobal(L, "onSomeEvent");
    lua_pushnumber(L, someParameter);
    lua_pcall(L, 1, 0, 0);
    lua_pop(L, 1);
}

but it works only for the last Lua file. 但它仅适用于最后一个Lua文件。 However, it calls only the last onSomeEvent function from the recently loaded Lua file. 但是,它仅调用最近加载的Lua文件中的最后一个onSomeEvent函数。 I want to call the onSomeEvent function from every loaded Lua file... 我想从每个加载的Lua文件中调用onSomeEvent函数...

Do you have some ideas on how to do this? 您对此有什么想法吗?

Sorry for my bad English. 对不起,我的英语不好。

onSomeEvent is clearly global. onSomeEvent显然是全局的。 Every script that defines it overwrites the previous definition. 定义它的每个脚本都将覆盖先前的定义。 You could give each script its own environment or Lua state, but it's much cleaner to let your scripts tell you where their event handler is rather than forcing it to be in a particular place by convention (such as being a global named onSomeEvent). 您可以为每个脚本提供自己的环境或Lua状态,但是让脚本告诉其事件处理程序在哪里要干净得多,而不是按照约定将其置于特定的位置(例如,名为onSomeEvent的全局变量)要干净得多。

Your C program just needs to expose a function the script can use to register an event handler. 您的C程序只需要公开一个函数,脚本可以使用该函数来注册事件处理程序。 Here's an example (note lack of error handling or bounds checking, this is just for illustration purposes): 这是一个示例(请注意,没有错误处理或边界检查,这只是出于说明目的):

#include "lua.h"
#include "lauxlib.h"

// list of registered handlers
static int handlers[20];

// number that are current registered
int numHandlers = 0;

// allow scripts to register a new handler
static int addEventHandler (lua_State* L) {
    if (!lua_isfunction(L,1)) {
        luaL_argerror(L, 1, "expected function");
    }
    lua_pushvalue(L, -1);
    handlers[numHandlers++] = luaL_ref(L, LUA_REGISTRYINDEX);
    return 0;
}

// call the registered handlers
static void onEvent (lua_State* L) {
    int i;
    for (i = 0; i < numHandlers; ++i) {
        lua_rawgeti(L, LUA_REGISTRYINDEX, handlers[i]);
        lua_pcall(L, 0, 0, 0);
    }
}

int main()
{    
    lua_State* L = lua_open();
    luaL_openlibs(L);

    // expose function that lets scripts register a callback handler
    lua_register(L, "addEventHandler", addEventHandler);

    // run test script
    luaL_dofile(L, "handlertest.lua");

    // call any callback(s) registered by the test script
    onEvent(L);

    lua_close(L);
    return 0;
}

handlertest.lua handlertest.lua

addEventHandler(function() print("anonymous function called") end)

local function localFunc() print("local function called") end
addEventHandler(localFunc)

function globalFunction() print("global function called") end
addEventHandler(globalFunction)

output 产量

anonymous function called
local function called
global function called

If your scripts all define a global function named onSomeEvent , then you need to give the scripts different environments when you load them. 如果所有脚本都定义了一个名为onSomeEvent的全局函数,那么在加载脚本时,需要为它们提供不同的环境。 When the time comes to handle the event, run through the list of script environment and call the event handler of each script. 当需要处理事件时,请遍历脚本环境列表并调用每个脚本的事件处理程序。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM