kapser
kapser

Reputation: 619

How to expose properties to Lua Library from C++

I want to how we can expose properties to lua library.

luaL_openlib( L, kName, kVTable, 1 ); // leave "library" on top of stack

With this, I am able to expose only functions as kVTable refers to luaL_Reg

typedef struct luaL_Reg {
  const char *name;
  lua_CFunction func;
} luaL_Reg;

Eg: With the above code. I can do following.

local myLib = require "plugin.myLib"
myLib.newFunc();

However, I want to expose Lua Table to the library as CONSTANTS variable.

myLib.CONSTANTS.SOME_CONST_1
myLib.CONSTANTS.SOME_CONST_2

etc. Please let me know how can I expose lua Table from my library as property.

Upvotes: 3

Views: 1705

Answers (3)

mpeterv
mpeterv

Reputation: 463

As luaL_openlib leaves the library table on top on the stack, you can use regular C API to add new fields and subtables to it:

luaL_openlib( L, kName, kVTable, 1 ); // leaves "library" on top of stack
lua_pushstring(L, "CONSTANTS"); 
lua_newtable(L); // this will be CONSTANTS subtable

lua_pushstring(L, "SOME_CONST_1");
lua_pushnumber(L, 42); // SOME_CONST_1 value
lua_settable(L, -3); // sets SOME_CONST_1

lua_pushstring(L, "SOME_CONST_2");
lua_pushnumber(L, 12345); // SOME_CONST_2 value
lua_settable(L, -3); // sets SOME_CONST_2

lua_settable(L, -3); // sets CONSTANTS table as field of the library table
return 1;

Upvotes: 3

Bartek Banachewicz
Bartek Banachewicz

Reputation: 39380

Caveat, lector, because Lua C API is, well, C API.

The whole burden with loadlib and friends was because functions are much harder to pass using C (C funcions aren't first class values). So my best bet would be to set all those constants using regular stack API.

In general, it is supposed to be used to exchange runtime data, of course, but there's no inherent reason why you shouldn't be able to fill your tables with that when loading the module.

Upvotes: 0

Dmitry Ledentsov
Dmitry Ledentsov

Reputation: 3660

If you use C++, you can use a binding library, such as the header-only luabridge to bind some data to named tables in Lua. Transforming your example into LuaBridge, call this function after you initialize your Lua state:

void register_constants (lua_State* L) {

    luabridge::getGlobalNamespace(L)
        .beginNamespace("myLib")
            .beginNamespace("CONSTANTS")
                .addVariable("SOME_CONST_1",&some_const_1,false/*read-only*/)
                .addVariable("SOME_CONST_2",&some_const_2,false/*read-only*/)
            .endNamespace()
        .endNamespace()
    ;
}

...

lua_State* L=lua_open();
register_constants(L);
...

you can access the constants as your last code snippet

Upvotes: 0

Related Questions