在回调问题期间创建Lua对象

时间:2013-03-30 11:14:01

标签: api delphi lua

我在Delphi + Lua上创建了一个简单的项目,通过RTTI使用Delphi可视化组件。基于luna.h的主要实现思路。我喜欢Blizzard使用存储在xml中的模板的想法(例如,当您可以在TPanel上放置几个对象并将其用作模板时),所以我几乎也实现了它。

问题是:一切正常,直到我通过Lua回调创建对象,使用与luna.h注入代码几乎相同的代码。如果此对象具有“继承”xml属性,则回调函数调用创建存储在xml中的对象,通过另一次注入创建另一个对象。我收到导致lua51.dll的错误。

当回调函数未返回结果时,可能由回调和Inject使用堆栈引起的问题。那么我可以使用堆栈并通过回调创建对象吗?如果没有 - 是否有任何解决方法来实现它?暴雪真的以某种方式成功了。

更多细节:
1.通过

注册Lua对象(例如TPanel和许多其他对象)的应用程序
  cn := T.ClassName;
  f := @StaticOnCreate;
  lua_pushlightuserdata(L, self); // put offset to self into lightuserdata
  lua_pushcclosure(L, f, 1);
  lua_setglobal(L, PAnsiChar(UTF8Encode(cn))); // T() in lua will make a new instance.

与luna.h的区别 - 应用程序还存储指向对象的指针(Delphi对象是指针)以避免泛型(c模板)
2.现在Lua在全局表中有TPanel 3.使用

p = TPanel("somename")

在脚本中,Lua调用应用程序的StaticOnCreate 4. StaticOnCreate提取对象并调用类的函数

  o := TLuaClassTemplate(lua_topointer(L, lua_upvalueindex(1)));
  result := o.OnCreate(L);

5。 OnCreate函数提取name之类的参数,并创建TPanel类型的精确视觉对象,并使用与luna.h函数相同的代码{/ 1}}

inject

通过堆栈返回Lua对象,所以现在来自 lua_newtable(FL); // create a new table for the class object ('self') obj_index := lua_gettop(FL); lua_pushnumber(FL, 0); a := lua_newuserdata(FL, SizeOf(pointer)); // store a ptr to the ptr a^ := obj; // set the ptr to the ptr to point to the ptr... >.> luaL_newmetatable(FL, PAnsiChar(UTF8Encode(cn))); // get (or create) the classname_metatable lua_pushstring(FL, PAnsiChar(UTF8Encode('__gc'))); lua_pushlightuserdata(FL, self); // put offset to self into lightuserdata lua_pushcclosure(FL, @StaticGc_T, 1); lua_settable(FL, -3); lua_setmetatable(FL, -2); // userdata.metatable = classname_metatable lua_settable(FL, obj_index); // self[0] = obj; f := @StaticThunk; // register the functions for i := 0 to length(ClassApiArray) - 1 do begin lua_pushstring(FL, PAnsiChar(UTF8Encode(ClassApiArray[i].name))); lua_pushlightuserdata(FL, self); // put offset to self into lightuserdata lua_pushnumber(FL, i); // let the thunk know which method we mean lua_pushcclosure(FL, f, 2); lua_settable(FL, obj_index); // self["function"] = thunk("function") end; lua_pushvalue(FL, -1); // dup object on stack top rec.ref := luaL_ref(FL, LUA_REGISTRYINDEX); // store object as ref ... result := 1; 的p是对象isntance。

但如果我尝试实施xml模板和第3步

,则会出现问题
p = TPanel("somename")

并且在p = TPanel("somename", "xmltemplatenodename") 执行步骤5期间,如果我看到OnCreate。因此,在步骤5中,在inherits = xmltemplatenodename之前,应用程序搜索精确inject - 如果找到,则为每个对象创建更多具有xmltemplatenodename的对象。然后只有在继续使用自己的inject执行第5步之后。在从inject创建2-3个对象后,我有错误导致lua51.dll。但是,如果应用程序使用相同的xml作为源并在xmltemplatenodename之外创建相同的xmltemplatenodename对象 - 则没有错误。

OnCreate对于xml对象略有不同,而不是将对象留在堆栈中,而是按对象名称注册它

Inject

0 个答案:

没有答案