edit: [DECISION IN RESPONSE 2]
I am new to LUA and am having trouble trying to do what I want. I have a C ++ object that looks like this:
C ++ Object Definitions
struct TLimit
{
bool enabled;
double value;
TLimit() : enabled(false), value(0.0) {}
~TLimit() {}
};
class TMeaurement
{
public:
TMeasurement() : meas(0.0) {}
~TMeasurement() {}
TLimit min;
TLimit max;
double meas;
};
I want to be able in LUA to access an object of type TMeasurement in the following form:
LUA desired use
-- objmeas is an instance of TMeasurement
objmeas.min.enabled = true
print(objmeas.min.value);
... etc.
Another thing, I do not want LUA to allocate memory for an instance of an object of type TMeasurement. This will be done in my C ++ code. I tried many different things, all to no avail. I will send now the last of my attempts.
In my C ++ code, I defined the following:
TLimit - Get function that will be mapped to __index
#define LUA_MEAS_LIMIT "itse.measurement.limit"
extern int llim_get(lua_State* L)
{
TLimit* lim = (TLimit*)lua_chekuserdata(L, 1, LUA_MEAS_LIMIT);
std::string key = std::string(luaL_checkstring(L, 2));
std::cout << "lim.get: " << key << std::endl;
if(key.find("enabled") == 0)
lua_pushboolean(L, lim->enabled);
else if(key.find("value") == 0)
lua_pushnumber(L, lim->value);
else
return 0;
return 1;
}
TLimit - Set the function to be displayed in __newindex
extern int llim_set(lua_State* L)
{
TLimit* lim = (TLimit*)lua_chekuserdata(L, 1, LUA_MEAS_LIMIT);
std::string key = std::string(luaL_checkstring(L, 2));
std::cout << "limit.set: " << key << " <-" << std::endl;
if(key.find("enabled") == 0)
lim->enabled = lua_toboolean(L, 3);
else if(key.find("value") == 0)
lim->value = lua_tonumber(L, 3);
return 0;
}
TMeasurement. ( set "meas" ).
TMeasurement - Get __index
#define LUA_MEASUREMENT "itse.measurement"
extern int lmeas_get(lua_State* L)
{
TMeasurement* test = (TMeasurement*)lua_checkuserdata(L, 1, LUA_MEASUREMENT);
std::string key = std::string(luaL_checkstring(L, 2));
std::cout << "meas." << key << " ->" << std::endl;
if(key.find("meas") == 0)
lua_pushinteger(L, test->meas);
else if(key.find("min") == 0)
{
lua_pushlightuserdata(L, &test->min);
luaL_getmetatable(L, LUA_MEAS_LIMIT);
lua_setmetatable(L, -2);
}
else if(key.find("max") == 0)
{
lua_pushlightuserdata(L, &test->max);
luaL_getmetatable(L, LUA_MEAS_LIMIT);
lua_setmetatable(L, -2);
}
else
return 0;
return 1;
}
, , mettatables :
++ -
( nsLUA:: safeFunction <... > , , < > " "... MessaegBox )
static const luaL_Reg lmeas_limit_f[] = { { NULL, NULL} };
static const luaL_Reg lmeas_limit[] =
{
{ "__index", nsLUA::safeFunction<llim_get> },
{ "__newindex", nsLUA::safeFunction<lllim_set> },
{ NULL, NULL }
};
static const luaL_Reg lmeas_f[] = { { NULL, NULL} };
static const luaL_Reg lmeas[] =
{
{ "__index", nsLUA::safeFunction<lmeas_get> },
{ NULL, NULL }
};
int luaopen_meas(lua_State* L)
{
luaL_newmetatable(L, LUA_MEAS_LIMIT);
luaL_setfuncs(L, lmeas_limit, 0);
luaL_newlib(L, lmeas_limit_f);
luaL_newmetatable(L, LUA_MEASUREMENT);
luaL_setfuncs(L, lmeas, 0);
luaL_newlib(L, lmeas_f);
return 1;
}
, ++ LUA, TMeasurement, LUA lua script. LEngine:
++ -
int main(int argc, char* argv[])
{
if(argc < 2)
return show_help();
nsLUA::LEngine eng;
eng.runScript(std::string(argv[1]));
return 0;
}
int LEngine::runScript(std::string scrName)
{
luaInit();
if(m_lua)
{
LMeasurement measurement;
measurement.value = 4.5;
lua_pushlightuserdata(m_lua, &tst);
luaL_getmetatable(m_lua, LUA_MEASUREMENT);
lua_setmetatable(m_lua, -2);
lua_setglobal(m_lua, "step");
if(luaL_loadfile(m_lua, scrName.c_str()) || lua_pcall(m_lua, 0, 0, 0))
processLuaError();
}
return 0;
}
, , . lua script, , memebr "min" "max" ... .
LUA -
print(step.meas); -- Ok
print(step.min.enabled); -- Ok
print(step.min.enabled); -- Error: attempt to index field 'min' (a nil value)
, script:
first script line: print(step.meas);
meas.meas -> this comes from lmeas_get function
4.5 this is the actual print from lua sentence
second script line: print(step.min.enabled)
meas.min -> accessing step.min, call to function lmeas_get
limit.get: enabled -> accessing min.enabled, call to function llim_get
false actual print from script sentence
third script line: print(step.min.enabled)
limit.get: min -> accessing min from limit object, call to llim_get ???????
. "min" ( "max", ), " ...". , __index ( e = step.min.enabled) __newindex (step.min.enabled = true).
, LUA min metatble . - "" " " LUA_MEASUREMENT metatable LUA_MEAS_LIMIT... .
, ... , ?
... , .