展会信息港展会大全

根据CocosBuilder文件自动生成代码
来源:互联网   发布日期:2015-09-27 15:02:08   浏览:2294次  

导读: 本文主要讲述怎样根据Cocosbuilder生成的ccb文件自动生成相应的代码,主要以生成cocos2dx对应的C++文件为例子来说明。 cocosbuilder是一个非常好用的开源...

本文主要讲述怎样根据Cocosbuilder生成的ccb文件自动生成相应的代码,主要以生成cocos2dx对应的C++文件为例子来说明。

cocosbuilder是一个非常好用的开源工具,可以用来编辑ui布局,粒子系统,简单的帧动画等。在编辑器中可以设置UI回调函数名,绑定编辑对象到Owner或者Doc root上以及为自定义的对象设置自定义的属性。以上三点都需要相应的代码来支持。因此在编辑完成游戏场景后,一定要写相应的代码。但是写相关的代码是比较繁琐的,很容易出现错误。

如果在场景编辑完成后,能根据场景文件自动生成代码框架将会节省不少工作量,并且减少出错的概率。下面分三个部分来一一说明如何实现自动生成代码,第一部分将会大体描述如何绑定代码,第二部分分析如何自动生成代码,第三部分给出代码实现

一 场景编辑器中控件与代码绑定

1.菜单回调函数,如下图设置,可以指定一个Selector和Target,在编辑器中设置后,将对应的target对象的某一个拥有特定签名的函数与selector指定的字符串绑定起来后,当菜单按下时,就会回调的相应的函数。

我们先来研究一下,在Cocos2dx中是如何将MenuItem的回调绑定到相应代码中的。

a.假设Document root对应的类为TestAutoGenLayer,为了实现绑定TestAutoGenLayer必须继承一个

cocos2d::extension::CCBSelectorResolver,然后实现 函数

virtual cocos2d::SEL_MenuHandler onResolveCCBCCMenuItemSelector(cocos2d::CCObject * pTarget, cocos2d::CCString * pSelectorName);

在该函数中完成代码绑定。

b.绑定代码如下:

[cpp]

SEL_MenuHandler TestAutoGenLayer::onResolveCCBCCMenuItemSelector(cocos2d::CCObject *pTarget, cocos2d::CCString *pSelectorName)

{

CCB_SELECTORRESOLVER_CCMENUITEM_GLUE(this,"BackPressed",TestAutoGenLayer::BackPressed);

return false;

}

SEL_MenuHandler TestAutoGenLayer::onResolveCCBCCMenuItemSelector(cocos2d::CCObject *pTarget, cocos2d::CCString *pSelectorName)

{

CCB_SELECTORRESOLVER_CCMENUITEM_GLUE(this,"BackPressed",TestAutoGenLayer::BackPressed);

return false;

}

上面代码将selector指定的值”BackPressed“与TestAutoGenLayer::的BackPressed函数绑定起来。(注:Selector的值可以函数名不相同)

c. BackPressed的代码框架如下

[cpp]

void TestAutoGenLayer::BackPressed(cocos2d::CCObject * pSender)

{

//在这里实现回调功能

}

void TestAutoGenLayer::BackPressed(cocos2d::CCObject * pSender)

{

//在这里实现回调功能

}

2.ControlButton回调

假设一个ControlButton在cocosbuild中有如下设置,

Document root还是TestAutoGenLayer类,在该类中实现CCBSelectorResolver的onResolveCCBCCControlSelector函数,假设代码如下

[cpp]

SEL_CCControlHandler TestAutoGenLayer::onResolveCCBCCControlSelector(cocos2d::CCObject *pTarget, cocos2d::CCString *pSelectorName)

{

CCB_SELECTORRESOLVER_CCCONTROL_GLUE(this,"DoNotPress",TestAutoGenLayer::DoNotPress);

return false;

}

SEL_CCControlHandler TestAutoGenLayer::onResolveCCBCCControlSelector(cocos2d::CCObject *pTarget, cocos2d::CCString *pSelectorName)

{

CCB_SELECTORRESOLVER_CCCONTROL_GLUE(this,"DoNotPress",TestAutoGenLayer::DoNotPress);

return false;

}

DonotPressMe的代码框架如下

[cpp]

void TestAutoGenLayer::DoNotPress(CCObject * pSender, cocos2d::extension::CCControlEvent pCCControlEvent)

{

//在这里实现控件回调功能

}

void TestAutoGenLayer::DoNotPress(CCObject * pSender, cocos2d::extension::CCControlEvent pCCControlEvent)

{

//在这里实现控件回调功能

}

3.将场景中的对象赋值给指定的对象,选择一个对象后,修改code connection属性,如下图

可以选择将一个对象赋值给 Document root或者是owner,指定一个绑定名字即可,下面绑定到Document root为例,假设root是TestAutoGenLayer类,被绑定的对象为CClabelTTF,为了实现绑定,a.TestAutoGenLayer必须承继于cocos2d::extension::CCBMemberVariableAssigner,并且实现方法onAssignCCBMemberVariable,b.TestAutoGenLayer 必须定一个类型为CCLabelTTF的成员变量

绑定代码段如下

[cpp]

bool TestAutoGenLayer::onAssignCCBMemberVariable(cocos2d::CCObject *pTarget, cocos2d::CCString *pMemberVariableName, cocos2d::CCNode *pNode)

{CCB_MEMBERVARIABLEASSIGNER_GLUE(this,"m_String2",CCLabelTTF*,this->m_String2);

return false;

}

bool TestAutoGenLayer::onAssignCCBMemberVariable(cocos2d::CCObject *pTarget, cocos2d::CCString *pMemberVariableName, cocos2d::CCNode *pNode)

{ CCB_MEMBERVARIABLEASSIGNER_GLUE(this,"m_String2",CCLabelTTF*,this->m_String2);

return false;

}

4.为自定义类型设置custom properties,具体在编辑中如何设置custom propertyies就不在些描述了,下面只专主如何将自定义属性绑定到代码中,cocosbuilder支持的自定义类型有4种:int,float,string,bool。假设在cocosbuilder中设置了4个自定义类型的变量,分别是

int 类型的m_intVal;

float类型的m_floatVal;

string类型的m_stringVal;

bool类型的m_boolVar;

为了实现绑定到类TestAutoGenLayer,

a.该类必须实现类cocos2d::extension::CCBMemberVariableAssigner的接口onAssignCCBCustomProperty

b.定义与自定义类型相关的变量

绑定代码如下:

[cpp]

bool TestAutoGenLayer::onAssignCCBCustomProperty(cocos2d::CCObject *pTarget, const char *pMemberVariableName, cocos2d::extension::CCBValue *pCCBValue)

{

if (pTarget == this)

{

if (0 == strcmp(pMemberVariableName, "m_intvar")){

m_intvar = pCCBValue->getIntValue();

return true;

}

if (0 == strcmp(pMemberVariableName, "m_floatVar")){

m_floatVar = pCCBValue->getFloatValue();

return true;

}

if (0 == strcmp(pMemberVariableName, "m_stringVar")){

m_stringVar = pCCBValue->getStringValue();

return true;

}

if (0 == strcmp(pMemberVariableName, "m_bool")){

m_bool = pCCBValue->getBoolValue();

return true;

}

}

return false;

}

bool TestAutoGenLayer::onAssignCCBCustomProperty(cocos2d::CCObject *pTarget, const char *pMemberVariableName, cocos2d::extension::CCBValue *pCCBValue)

{

if (pTarget == this)

{

if (0 == strcmp(pMemberVariableName, "m_intvar")){

m_intvar = pCCBValue->getIntValue();

return true;

}

if (0 == strcmp(pMemberVariableName, "m_floatVar")){

m_floatVar = pCCBValue->getFloatValue();

return true;

}

if (0 == strcmp(pMemberVariableName, "m_stringVar")){

m_stringVar = pCCBValue->getStringValue();

return true;

}

if (0 == strcmp(pMemberVariableName, "m_bool")){

m_bool = pCCBValue->getBoolValue();

return true;

}

}

return false;

}

二. 如何实现自动生成代码

根据上面的分析,我们知道一共有四种类型的绑定代码需要生成,每种类型的绑定都需要生成声明和实现(.h文件与.cpp文件),另外还要生成类的定义、构造函数及文件的尾部。下面来一一分析需要生成代码。

1.MenuItem回调

a)头文件:生成Selector对应的函数声明

b)cpp文件,生成空的Selector函数体,

c)cpp文件 生成绑定代码

2.ControlButton回调

a)头文件:生成Selector对应的函数声明

b)cpp文件,生成空的Selector函数体,

c)cpp文件 生成绑定代码

3.场景对象赋值到宿主

a)头文件,生成变量声明

b)cpp文件,生成绑定代码

c)构造函数,变量赋初值

4.自定义变量赋值到宿主

a)头文件,生成变量声明

b)cpp文件,生成绑定代码

c)构造函数,变量赋初值

5.杂项

a)类定义生成

b)构造函数生成

c)头文件尾部生成

要生成这些代码需要些什么信息呢,为了方便说明,直接上代码

[cpp]

struct TypeName {

TypeName(const std::string& t="",const std::string& n="")

:type(t),name(n){}

std::string type;

std::string name;

};

std::stringm_className;//要生成的类名

std::string m_baseClass;//生成类的父类

std::vector<TypeName>m_listAssignMember;//需要赋值的场景对象

std::vector<TypeName>m_listCutomProperty;//需要赋值的自定义变量

std::vector<std::string>m_listCContorlCallBack;//menu回调函数名

std::vector<std::string>m_listMenuCallBack;//control回调函数名

struct TypeName {

TypeName(const std::string& t="",const std::string& n="")

:type(t),name(n){}

std::string type;

std::string name;

};

std::stringm_className;//要生成的类名

std::string m_baseClass;//生成类的父类

std::vector<TypeName>m_listAssignMember;//需要赋值的场景对象

std::vector<TypeName>m_listCutomProperty;//需要赋值的自定义变量

std::vector<std::string>m_listCContorlCallBack;//menu回调函数名

std::vector<std::string>m_listMenuCallBack;//control回调函数名

这些信息从什么地方可以获取呢,只用解析cocosbuilder生成的ccb文件就可以得到了。

有了上述的信息,我们再定义一些代码模板,替换和复制代码模板就可以生成相关代码了。 以类的定义生成来说明。类的代码模板如下

[cpp]

//%class_name%.h

//

//

//this code is auto generate by the toolcreated by neo. Email andsonliang@gmail.com

//

//

#ifndef __autogen_ccbuilder__%class_name%__

#define__autogen_ccbuilder__%class_name%__

#include"cocos2d.h"

#include"cocos-ext.h"

class %class_name%

:publiccocos2d::%base_class%

, publiccocos2d::extension::CCBSelectorResolver

, publiccocos2d::extension::CCBMemberVariableAssigner

, publiccocos2d::extension::CCNodeLoaderListener

{

public:

%class_name%()

:%base_class%()

//%class_name%.h

//

//

//this code is auto generate by the toolcreated by neo. Email andsonliang@gmail.com

//

//

#ifndef __autogen_ccbuilder__%class_name%__

#define__autogen_ccbuilder__%class_name%__

#include"cocos2d.h"

#include"cocos-ext.h"

class %class_name%

:publiccocos2d::%base_class%

, publiccocos2d::extension::CCBSelectorResolver

, publiccocos2d::extension::CCBMemberVariableAssigner

, publiccocos2d::extension::CCNodeLoaderListener

{

public:

%class_name%()

:%base_class%()

在生成代码时,读入代码模板,将%class_name%替换为m_className,%base_class%替换为m_baseClass就可以了。

赞助本站

人工智能实验室
AiLab云推荐
推荐内容
展开

热门栏目HotCates

Copyright © 2010-2024 AiLab Team. 人工智能实验室 版权所有    关于我们 | 联系我们 | 广告服务 | 公司动态 | 免责声明 | 隐私条款 | 工作机会 | 展会港