转载自【黑米GameDev街区】 原文链接: http://www.himigame.com/lua-game/1259.html
此篇基本【COCOS2DX(2.X)_LUA开发之三】在LUA中使用自定义精灵(LUA脚本与自创建类之间的访问)及LUA基础讲解
在Lua第三篇中介绍了,如何在cocos2dx中使用Lua创建自定义类供Lua脚本调用使用,当时出于Himi对Lua研究不够深入,所以当时使用了笨方法手动添加的方式进行的,那么本篇将介绍利用tolua++快速将我们自定义的c2dx类嵌入,供 lua脚本使用。
首先介绍整个过程:
之前我们的过程: 自定义类->手动到LuaCoco2d.cpp中手动添加binding->lua使用
现在我们的过程是: 自定义类->使用tolua++工具编译到LuaCoco2d.cpp中->lua使用
下面进行详细步骤讲解:
步骤一:首先自定义类(这里Himi自定义类名 “MySprite”)
MySprite.h
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
|
//
// MySprite.h
// mtet
//
// Created by Himi on 13-4-7.
//
//
#ifndef __mtet__MySprite__
#define __mtet__MySprite__
#include "cocos2d.h"
using
namespace
cocos2d
;
class
MySprite
:
public
CCSprite
{
public
:
static
MySprite*
createMS
(
const
char
*
fileName
)
;
}
;
#endif /* defined(__mtet__MySprite__) */
|
MySprite.cpp
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
|
//
// MySprite.cpp
// mtet
//
// Created by Himi on 13-4-7.
//
//
#include "MySprite.h"
MySprite*
MySprite
::
createMS
(
const
char
*
fileName
)
{
MySprite*
sp
=
new
MySprite
(
)
;
if
(
sp
&
amp
;
&
amp
;
sp
-
&
gt
;
initWithFile
(
fileName
)
)
{
sp
-
&
gt
;
setPosition
(
ccp
(
100
,
100
)
)
;
sp
-
&
gt
;
autorelease
(
)
;
return
sp
;
}
CC_SAFE_DELETE
(
sp
)
;
return
NULL
;
}
|
步骤二:利用tolua++编译我们创建的pkg,将自定义类嵌入LuaCocos2d.cpp中
首先我们到cocos2dx引擎目录下找到tools下的tolua++文件夹。
然后你看到很多的pkg文件,你可以使用文本打开,就会发现都是Cocos2dx引擎封装的类、函数定义,如下CCSprite.pkg
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
|
/*
typedef enum {
//! Translate with it's parent
CC_HONOR_PARENT_TRANSFORM_TRANSLATE = 1 << 0,
//! Rotate with it's parent
CC_HONOR_PARENT_TRANSFORM_ROTATE = 1 << 1,
//! Scale with it's parent
CC_HONOR_PARENT_TRANSFORM_SCALE = 1 << 2,
//! Skew with it's parent
CC_HONOR_PARENT_TRANSFORM_SKEW = 1 << 3,
//! All possible transformation enabled. Default value.
CC_HONOR_PARENT_TRANSFORM_ALL = CC_HONOR_PARENT_TRANSFORM_TRANSLATE | CC_HONOR_PARENT_TRANSFORM_ROTATE | CC_HONOR_PARENT_TRANSFORM_SCALE | CC_HONOR_PARENT_TRANSFORM_SKEW,
} ccHonorParentTransform;
*/
class
CCSprite
:
public
CCNode
{
void
setDirty
(
bool
bDirty
)
;
bool
isDirty
(
void
)
;
ccV3F_C4B_T2F_Quad
getQuad
(
void
)
;
CCRect
getTextureRect
(
void
)
;
//bool isUsesBatchNode(void);
bool
isTextureRectRotated
(
void
)
;
void
setAtlasIndex
(
unsigned
int
uAtlasIndex
)
;
unsigned
int
getAtlasIndex
(
void
)
;
//void setUsesSpriteBatchNode(bool bUsesSpriteBatchNode);
void
setTextureAtlas
(
CCTextureAtlas *
pobTextureAtlas
)
;
CCTextureAtlas*
getTextureAtlas
(
void
)
;
//void setSpriteBatchNode(CCSpriteBatchNode *pobSpriteBatchNode);
//CCSpriteBatchNode* getSpriteBatchNode(void);
//void setHonorParentTransform(ccHonorParentTransform eHonorParentTransform);
//ccHonorParentTransform getHonorParentTransform(void);
void
setBlendFunc
(
ccBlendFunc
blendFunc
)
;
ccBlendFunc
getBlendFunc
(
void
)
;
CCPoint
getOffsetPosition
(
void
)
;
void
ignoreAnchorPointForPosition
(
bool
newValue
)
;
void
setFlipX
(
bool
bFlipX
)
;
void
setFlipY
(
bool
bFlipY
)
;
bool
isFlipX
(
void
)
;
bool
isFlipY
(
void
)
;
void
removeChild
(
CCNode*
pChild
,
bool
bCleanUp
)
;
void
removeAllChildrenWithCleanup
(
bool
bCleanup
)
;
void
reorderChild
(
CCNode*
pChild
,
int
zOrder
)
;
void
addChild
(
CCNode*
pChild
)
;
void
addChild
(
CCNode*
pChild
,
int
zOrder
)
;
void
addChild
(
CCNode*
pChild
,
int
zOrder
,
int
tag
)
;
void
sortAllChildren
(
)
;
//void setPosition(CCPoint pos);
void
setRotation
(
float
rotation
)
;
void
setSkewX
(
float
sx
)
;
void
setSkewY
(
float
sy
)
;
void
setScale
(
float
fScale
)
;
void
setScaleX
(
float
fScaleX
)
;
void
setScaleY
(
float
fScaleY
)
;
void
setVertexZ
(
float
fVertexZ
)
;
void
setAnchorPoint
(
const
CCPoint
&
amp
;
anchor
)
;
void
setVisible
(
bool
bVisible
)
;
void
setOpacity
(
GLubyte
opacity
)
;
GLubyte
getOpacity
(
void
)
;
void
setColor
(
ccColor3B
color3
)
;
ccColor3B
getColor
(
void
)
;
void
setOpacityModifyRGB
(
bool
bValue
)
;
bool
isOpacityModifyRGB
(
void
)
;
void
setTexture
(
CCTexture2D *
texture
)
;
CCTexture2D*
getTexture
(
void
)
;
void
updateTransform
(
void
)
;
//void useSelfRender(void);
void
setTextureRect
(
CCRect
rect
)
;
void
setTextureRect
(
CCRect
rect
,
bool
rotated
,
CCSize
size
)
;
void
setVertexRect
(
CCRect
rect
)
;
//void useBatchNode(CCSpriteBatchNode *batchNode);
void
setDisplayFrame
(
CCSpriteFrame *
pNewFrame
)
;
bool
isFrameDisplayed
(
CCSpriteFrame *
pFrame
)
;
CCSpriteFrame*
displayFrame
(
void
)
;
void
setBatchNode
(
CCSpriteBatchNode*
pBatchNode
)
;
CCSpriteBatchNode*
getBatchNode
(
)
;
void
setDisplayFrameWithAnimationName
(
const
char
*
animationName
,
int
frameIndex
)
;
static
CCSprite*
createWithTexture
(
CCTexture2D *
pTexture
)
;
static
CCSprite*
createWithTexture
(
CCTexture2D *
pTexture
,
CCRect
rect
)
;
static
CCSprite*
createWithSpriteFrame
(
CCSpriteFrame *
pSpriteFrame
)
;
static
CCSprite*
createWithSpriteFrameName
(
const
char
*
pszSpriteFrameName
)
;
static
CCSprite*
create
(
const
char
*
pszFileName
,
CCRect
rect
)
;
static
CCSprite*
create
(
const
char
*
pszFileName
)
;
static
CCSprite*
create
(
)
;
}
;
|
没错,我们也会按照类似方式进行创建我们自定义类的pkg文件。
我们自定义一个文件(文本、xcode等都可以),后缀 .pkg ,然后将Himi自定义的MySprite类定义到pkg中,如下:
注意:只要自定义类.h中的内容,至于cpp的实现,binding后lua自动调用你类的函数
MySprite.pkg
1
2
3
|
class
MySprite
:
public
CCSprite
{
static
MySprite*
createMS
(
const
char
*
fileName
)
;
}
;
|
在pkg中我只是定义了创建函数而已,至于更多的函数就交给大家自定义啦,另外我们注意书写pkg时是需要几条规则的,其实在tolua++这个文件夹中我们也能看到有一个名字叫 README 的文件,打开如下:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
|
1.
Generating
the
lua
&
lt
;
--
&
gt
;
C
bindings
with
tolua
++
Build
scripts
for
windows
(
build
.
bat
)
and
unix
(
build
.
sh
)
are
provided
to
generate
the
relevant
files
after
modifying
the
.
pkg
files
.
These
scripts
basically
run
the
following
command
:
tolua
++
.
exe
-
L
basic
.
lua
-
o
LuaCocos2d
.
cpp
Cocos2d
.
pkg
This
will
generate
the
bindings
file
and
patch
it
with
come
cocos2dx
specific
modifications
.
On
POSIX
systems
you
can
also
just
run
"make"
to
build
the
bindings
if
/
when
you
change
.
pkg
files
.
2.
Writing
.
pkg
files
1
)
enum
keeps
the
same
2
)
remove
CC_DLL
for
the
class
defines
,
pay
attention
to
multi
inherites
3
)
remove
inline
keyword
for
declaration
and
implementation
4
)
remove
public
protect
and
private
5
)
remove
the
decalration
of
class
member
variable
6
)
keep
static
keyword
7
)
remove
memeber
functions
that
declared
as
private
or
protected
|
这个文件声明了书写pkg的规则,不多赘述。
书写好我们的pkg之后,将pkg文件放置此tolua++文件夹下即可,然后配置我们tolua++工具。
继续在tolua++文件夹中解压tolua++.Mac.zip 文件,会得到一个tolua++的工具,如下图:
解压出工具之后,我们还要在tolua++文件夹中,配置tolua++路径,打开“build.sh”文件,如下:
这里 TOLUA 是tolua++工具的位置(路径后面要架上 /tolua++ 表示这个工具),最下面配置的是编译后的luaCocos2d.cpp文件导出的位置,Himi这里配置到桌面,配置如下:
最后,我们要将我们定义的pkg文件注册到 tolua++文件夹下的Cocos2d.pkg中,如下:
如上步骤都OK后,我们就可以使用“终端”,先cd到tolua++的文件夹下,然后使用“make”命令执行tolua++工具。
(如果这里终端不能正常执行, 请继续修改tolua++文件夹下的: makefile ,将其路径配置一下即可。)
终端正常执行后,会在一开始指定的目录生成LuaCocos2d.cpp 文件,且其中已经binding好了自定义类,将生成的LuaCocos2d.cpp替换到你项目的/libs/lua/cocos2dx_support下的LuaCocos2d.cpp 文件。
Himi建议生成的LuaCocos2d.cpp 文件路径直接设置你的项目的/libs/lua/cocos2dx_support下很方便
注意:这时候LuaCoco2d.cpp中虽然已经binding了我们的自定义类,但是没有引用我们的头文件,所以我们还需要在LuaCocos2d.h中倒入我们自定义类.h 。
步骤三:Lua测试我们的自定义类
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
|
--
for
CCLuaEngine
traceback
function
__G__TRACKBACK__
(
msg
)
print
(
"----------------------------------------"
)
print
(
"LUA ERROR: "
.
.
tostring
(
msg
)
.
.
"\n"
)
print
(
debug
.
traceback
(
)
)
print
(
"----------------------------------------"
)
end
local
function
main
(
)
--
avoid
memory
leak
collectgarbage
(
"setpause"
,
100
)
collectgarbage
(
"setstepmul"
,
5000
)
local
cclog
=
function
(
.
.
.
)
print
(
string
.
format
(
.
.
.
)
)
end
require
"hello2"
cclog
(
"result is "
.
.
myadd
(
3
,
5
)
)
--
--
--
--
--
--
--
-
--
create
farm
local
function
createLayerFarm
(
)
local
layerFarm
=
CCLayer
:
create
(
)
local
font
=
CCLabelTTF
:
create
(
"Himi 使用tolua++ binding自定义类"
,
"Verdana-BoldItalic"
,
20
)
font
:
setPosition
(
ccp
(
220
,
260
)
)
layerFarm
:
addChild
(
font
)
local
ms
=
MySprite
:
createMS
(
"Icon.png"
)
layerFarm
:
addChild
(
ms
)
return
layerFarm
end
--
run
local
sceneGame
=
CCScene
:
create
(
)
sceneGame
:
addChild
(
createLayerFarm
(
)
)
CCDirector
:
sharedDirector
(
)
:
runWithScene
(
sceneGame
)
end
xpcall
(
main
,
__G__TRACKBACK__
)
|
运行截图如下:
OK,今天就到这,希望大家多多探讨,有问题请及时留言。