Big Bucket Software you like to use
Lua and the Registry
March 15th, 2006

So I’ve got this class; The ActorModel and this class has an inventoryItem accessor/mutator that takes/returns an InventoryItem& (would you believe). Both of these classes have Lua counterparts, that is, there is a Table that wraps up an ActorModel and another that wraps up an InventoryItem. The trick to these tables is that they contain a “ptr” key that contain a pointer to the relevant C++ object. Functions on these tables operate on the pointer contained there.

It is therefore possible to do things like this:

some_actor_model:setInventoryItem(some_inventory_item);

When setInventoryItem is called, the object on the bottom of the stack is the some_actor_model and the object on top of that is some_inventory_item. It is straightforward then, to derive the C++ object by casting the contents of the “ptr” key to the relevant type. Hence, it is possible to move from the Lua wrapper of an object to the C++ object itself. But how about the other way around?

That is, it’s easy to call the mutator, but what about the accessor? The accessor would need to be able to somehow derive the Lua table from the object. My first instinct was simply to let each C++ object hold a pointer to their counterpart Lua table – if only it were possible. The solution: the Lua registry.

The registry is a Table in Lua that is acessible only to C. The thing that makes it really neat is the luaL_ref function. This function “pops a value from the stack, stores it into the registry with a fresh integer key, and returns that key. We call this key a reference.” This means, when you create a table in Lua, you can add it to the registry, hold onto the key that LuaL_ref gives you, and use that key later to retrieve the table! I found that the neatest way to implement this was to put a registryKey accessor/mutator on classes that have Lua wrappers.

Have a nice day.