cocos2d-x内部使用tolua进行lua绑定。可是引擎并没有提供一个通用的接口让我们能够把一个lua函数注冊给C++层面的回调事件。

翻看引擎的lua绑定代码,我们能够仿照引擎中的方法来做。

值得吐槽的是。这套流程在开发中差点儿是不可避免的,而cocos2d-x居然不把它作为一个公用接口暴露给开发人员,而须要我自己动手,真是无奈。

以下以一个简单的消息分发类为样例,演示怎样完毕这一工作。

MessageDispatcher.h

class MessageDispather
{
public:
static MessageDispather* sharedDispather(); public:
void invokeLuaCallbackFunction(int msgId, const char* text);
void registerScriptHandler(int nHandler); private:
int mLuaHandlerId;
};

MessageDispatcher.cpp

#include "CCLuaEngine.h"

MessageDispather* sharedDispather()
{
static MessageDispather* instance = NULL;
if(instance == NULL) instance = new MessageDispather();
return instance;
} void MessageDispather::invokeLuaCallbackFunction(int msgId, const char* text)
{
if(mScriptHandler > 0)
{
CCLuaStack* stack = CCLuaEngine::defaultEngine()->getLuaStack();
stack->pushInt(msgId);
stack->pushString(text);
stack->executeFunctionByHandler(mScriptHandler, 2);
stack->clean();
}
} void MessageDispather::registerScriptHandler(int nHandler)
{
mLuaHandlerId = nHandler;
}

说明

#include "CCLuaEngine.h"

这个头文件来自cocos2d-x\scripting\lua\cocos2dx_support

整个目录里的内容是cocos2d-x引擎做lua绑定时封装的一些工具类。

你须要在你的项目中加入这个文件夹的include搜索路径。

void registerScriptHandler(int nHandler)

这个函数须要暴露给lua。

在lua中调用这个函数。參数nHandler的位置传进去一个lua函数。就行在C++这边得到一个nHandler的整数句柄值。

之后不论什么时间假设想要在C++中调用刚刚注冊的lua回调函数,须要以这个整数值来指代那个函数。

void invokeLuaCallbackFunction(int msgId, const char* text)

在C++用调用此函数,我们期待它会调用到一个在lua中定义的回调函数。

详细这个函数里的实现是什么意思,假设你对lua c api有一定了解的话应该非常easy能看懂,我就不再做解释。

用于tolua的pkg文件

class MessageDispather
{
static MessageDispather* sharedDispather();
void registerScriptHandler(LUA_FUNCTION nHandler);
};

在lua中使用MessageDispatcher

local function onMessage(msgId, text)
print(msgId, text)
end
MessageDispatcher:sharedDispatcher():registerScriptHandler(onMessage)

万事大吉。。。。。才怪!

有没有发现我们的pkg文件里有一个类型是LUA_FUNCTION??

对,由于这个參数在lua中应该传入一个函数。而到了C++这边我们拿到的却是一个int。

这并非tolua的缺省行为,而是cocos2d-x针对这样的情况做的一个特殊处理。

翻看cocos2d-x的tolua绑定流程,我们能够发现build.bat中的内容是这种:

tolua++ -L basic.lua -o "../../scripting/lua/cocos2dx_support/LuaCocos2d.cpp"
Cocos2d.pkg


这里basic.lua是一些额外的逻辑,当中处理LUA_FUNCTION类型的逻辑也在里面。

那么我们能够照猫画虎,请创建这样一个lua文件:

_is_functions = _is_functions or {}
_to_functions = _to_functions or {} -- register LUA_FUNCTION, LUA_TABLE, LUA_HANDLE type
_to_functions["LUA_FUNCTION"] = "toluafix_ref_function"
_is_functions["LUA_FUNCTION"] = "toluafix_isfunction"
_to_functions["LUA_TABLE"] = "toluafix_totable"
_is_functions["LUA_TABLE"] = "toluafix_istable" local toWrite = {}
local currentString = ''
local out
local WRITE, OUTPUT = write, output function output(s)
out = _OUTPUT
output = OUTPUT -- restore
output(s)
end function write(a)
if out == _OUTPUT then
currentString = currentString .. a
if string.sub(currentString,-1) == '\n' then
toWrite[#toWrite+1] = currentString
currentString = ''
end
else
WRITE(a)
end
end function post_output_hook(package)
local result = table.concat(toWrite)
local function replace(pattern, replacement)
local k = 0
local nxt, currentString = 1, ''
repeat
local s, e = string.find(result, pattern, nxt, true)
if e then
currentString = currentString .. string.sub(result, nxt, s-1) .. replacement
nxt = e + 1
k = k + 1
end
until not e
result = currentString..string.sub(result, nxt)
if k == 0 then print('Pattern not replaced', pattern) end
end replace([[*((LUA_FUNCTION*)]], [[(]])
replace([[tolua_usertype(tolua_S,"LUA_FUNCTION");]], [[]]) WRITE(result)
end

然后在你运行tolua++的时候把这个文件作为-L參数传进去就能够了。

应该真的万事大吉了。

cocos2d-x 2.2.0 怎样在lua中注冊回调函数给C++的更多相关文章

  1. cocos2d-x 2.2.0 如何在lua中注册回调函数给C++

    cocos2d-x内部使用tolua进行lua绑定,但是引擎并没有提供一个通用的接口让我们可以把一个lua函数注册给C++层面的回调事件.翻看引擎的lua绑定代码,我们可以仿照引擎中的方法来做.值得吐 ...

  2. 【Cocos2d-x 3.0 基础系列一】 各类回调函数写法汇总

    一.button回调 1. Lambda 表达式,C++11 Lambda 赋予了Cocos2d-x 3.0创建回调函数的灵活性. auto itemNor = Sprite::create(&quo ...

  3. EXTJS4.0 form 表单提交 后 回调函数 不响应的问题

    在提交表单后,应返回一个 JSON 至少要包含{success:true} 否则,EXT 不知道是否成功,没有响应. {success:true,msg:'成功',Url:'http://www.ba ...

  4. Cocos2d-x3.0下一个 Lua与C++打电话给对方

    这里谈下Lua与C++如何实现相互通话 原来的连接:http://blog.csdn.net/qqmcy/article/details/26052771 DJLCData.h 实现类 // // D ...

  5. php7.0支持调用lua脚本

    需求前瞻: 最近因需求,需要支持php调用现有的Lua代码,可以减少php的代码量,同时在维护上也比较方便,不会照成需求变更,需要同时修改两份代码 第一步:安装php7.0及以上版本,此处安装方法就略 ...

  6. Lua中调用C函数

    Lua利用一个虚拟的堆栈来给C传递值或从C获取值.每当Lua调用C函数,都会获得一个新的堆栈,该堆栈初始包含所有的调用C函数所需要的参数值(Lua传给C函数的调用实参),并且C函数执行完毕后,会把返回 ...

  7. lua堆栈操作常用函数学习二

    /* ** basic stack manipulation */ LUA_API int  <strong> (lua_gettop) (lua_State *L);  </str ...

  8. Lua中调用C函数(lua-5.2.3)

    Lua能够调用C函数的能力将极大的提高Lua的可扩展性和可用性. 对于有些和操作系统相关的功能,或者是对效率要求较高的模块,我们全然能够通过C函数来实现,之后再通过Lua调用指定的C函数. 对于那些可 ...

  9. Lua调用C,C++函数案例

    该程序主要是C++与Lua之间的相互调用示例.执行内容:(1)新建一个lua_State(2)打开常用库,如io,os,table,string等(3)注册C函数(4)导入程序所在目录下所有*.lua ...

随机推荐

  1. nginx 子进程 woker process 启动失败的问题

    问题: 重启nginx服务,worker process 子进程启动失败,启动的都是master进程: 负载急速升高(平常都是4-5),占用CPU资源多的前十进程都是nginx : nginx 错误日 ...

  2. Hadoop不同模式下关键配置属性

    Hadoop分为三种模式: 独立(或本地)模式. 伪分布模式. 全分布模式 不同模式下关键配置项及属性内容如下面表格所示 组件名称 配置的文件名 属性名称 独立模式 伪分布模式 全分布模式 Commo ...

  3. 【BZOJ4448】【SCOI2015】情报传递

    这题面错别字真tm多 题意: Description 奈特公司是一个巨大的情报公司,它有着庞大的情报网络.情报网络中共有n名情报员.每名情报员口J-能有若T名(可能没有)下线,除1名大头日外其余n-1 ...

  4. 支持JSONP跨域的对象

    支持JSONP跨域的对象 1:img 2:iframe 3:link 4:script 为什么,JSONP 最终选择是 script 实现呢?度娘来也! 平常我们进行JSONP请求数据,因为 json ...

  5. Windows和Linux的编译理解

    Windows一般编译出来的x86的软件,就是只能在x86的系统上才能运行,同理,在x64系统上也是一样的道理. Linux利用gcc编译器编译,可以在Linux上面运行,但是想要在嵌入式系统上运行的 ...

  6. cin详解(get()、getline()、clear()、sync())

    简述 在C中,输入输出用scanf和printf,在输入数据的同时还需说明数据的类型,如果输入数据较多,那就很麻烦,而C++中也有相似的东西cin和cout,它们来自C++的一个名叫" io ...

  7. codeforces #313(div 2)

    B. Gerald is into Art time limit per test 2 seconds memory limit per test 256 megabytes input standa ...

  8. Windows下mnist数据集caffemodel分类模型训练及测试

    1. MNIST数据集介绍 MNIST是一个手写数字数据库,样本收集的是美国中学生手写样本,比较符合实际情况,大体上样本是这样的: MNIST数据库有以下特性: 包含了60000个训练样本集和1000 ...

  9. Word frequency analysis

    Write a program that reads a file, breaks each line into words, scripts whitespace and punctuation f ...

  10. AngularJs轻松入门源码托管至Github

    Github是全球最大的代码托管平台,笔者玩Github有一段时间了,有很多开源项目的源码都托管在Github上,笔者在上面也发现了不少优秀的开源代码. 每次写完博文想在最后附上文章相关的代码,但是由 ...