cocos2d-x在2.x版本里就是用toLua++和.pkg文件这么把自己注册进Lua环境里的,然而从cocos2d-x 3.x开始,用bindings-generator脚本代替了toLua++。
3、虽然不再调用tolua++命令了,但是底层仍然使用toLua++的库函数,比如tolua_function,bindings-generator脚本生成的代码就跟使用toLua++工具生成的几乎一样
frameworks/runtime-src/Classes/MyClass.h
#include "cocos2d.h" using namespace cocos2d; class MyClass : public Ref { public: MyClass() {}; ~MyClass() {}; bool init() { return true; }; CREATE_FUNC(MyClass); int foo(int i); };frameworks/runtime-src/Classes/MyClass.cpp
#include "MyClass.h" int MyClass::foo(int i) { return i + 100; }然后编写.ini文件。在frameworks/cocos2d-x/tools/tolua/目录下能看到genbindings.py脚本和一大堆.ini文件,这些就是bindings-generator的实际执行环境了。随便找一个内容比较少的.ini文件,复制一份,重新命名为MyClass.ini。大部分内容都可以凑合不需要改,这里仅列出必须要改的重要部分:
[MyClass] prefix = MineClass # 添中前缀名XX,注册文件头及注册函数名以前缀名(XX)组合命名 target_namespace = my # 空间命名,调用时,以my.xxx, xxx为自定义类的方法 headers = %(cocosdir)s/../runtime-src/Classes/MyClass.h # 获取自定义类的文件头 classes = MyClass # 需要注册类YY(方法),同时注册函数名以前缀名(XX)_YY组合命名frameworks/cocos2d-x/tools/tolua/genbindings.py
cmd_args = {'cocos2dx.ini' : ('cocos2d-x', 'lua_cocos2dx_auto'), \ 'MyClass.ini' : ('MyClass', 'lua_MyClass_auto'), \ ...(其实这一步本来是可以省略的,只要让genbindings.py脚本自动搜寻当前目录下的所有ini文件就行了,不知道将来cocos2d-x团队会不会这样优化)
python genbindings.py成功执行genbindings.py脚本后,会在frameworks/cocos2d-x/cocos/scripting/lua-bindings/auto/目录下看到新生成的文件:
注:若python报错,看下是否缺少yaml、Cheetah包,若是,安装包就行了。
简单解释下编译成后lua_MyClass_auto.cpp
TOLUA_API int register_all_MineClass(lua_State* tolua_S) { //入口点,它创建管理的内部变量 tolua_open(tolua_S); //创建新模块 tolua_module(tolua_S,"my",0); //注册一个模块或类 tolua_beginmodule(tolua_S,"my"); // 类的注册 lua_register_MineClass_MyClass(tolua_S); tolua_endmodule(tolua_S); return 1; }注册类:
int lua_register_MineClass_MyClass(lua_State* tolua_S) { tolua_usertype(tolua_S,"MyClass"); //注册用户类型 tolua_cclass(tolua_S,"MyClass","MyClass","cc.Ref",nullptr); //注册类 tolua_beginmodule(tolua_S,"MyClass"); //注册模块 tolua_function(tolua_S,"new",lua_MineClass_MyClass_constructor); //绑定函数(将Lua里面MyClass对象的”new”绑定到你的lua_MineClass_MyClass_constructor()函数中去.) tolua_function(tolua_S,"init",lua_MineClass_MyClass_init); tolua_function(tolua_S,"foo",lua_MineClass_MyClass_foo); tolua_function(tolua_S,"create", lua_MineClass_MyClass_create); tolua_endmodule(tolua_S); std::string typeName = typeid(MyClass).name(); //保存注册类 g_luaType[typeName] = "MyClass"; g_typeCast["MyClass"] = "MyClass"; return 1; }绑定函数,要注意下:
cobj = (MyClass*)tolua_tousertype(tolua_S,1,0); //是将数据栈下的对象以(CTest* )的指针形式弹出来。从栈中弹出对象(其实是自定类的对象),接着把对象引用方法(包括含参数及handle)返回结果压栈,实现c、lua之间互相调用了。
打开Classes/lua_module_register.h文件,添加头文件
#include "tolua++/lua_MyClass_auto.hpp"在static int lua_module_register(lua_State* L)添加注册函数
register_all_MineClass(L);若vs2012编译错误,估计都是没把源文件及生成的文件加入工程; 若有特殊处理,比如更换genbindings.py脚本生成文件路径,注意在vs2012环境->属性->c/c++->附加包含目录,添加路径。
lua代码:
function myadd(x, y) -- 自定义 local test = my.MyClass:create() print("lua bind: " .. test:foo(99)) return x + y end编译运行:
引用博客:http://segmentfault.com/a/1190000000631630
引用文章:http://cn.cocos2d-x.org/tutorial/show?id=2496