本系列学习教程使用的是cocos2d-x-2.1.4(最新版为3.0alpha0-pre) ,PC开发环境Windows7,C++开发环境VS2010
一、文本渲染类
在游戏中,文字占有很重要的位置,游戏的介绍、游戏中的提示和对话等都需要用到文字。Cocos2D-X在文字渲染
方面提供了非常灵活的机制,既可以直接使用系统文字,也可以直接渲染字体,文本渲染类的继承关系如下图所示。
该图展示了引擎用于处理文字的三个类:CCLabelAtlas、CCLabelBMFont、CCLabelTTF。这三个类都是通过不
同的方式来显示文字的。从图中可以看出,它们都继承于CCLabelProtocol协议。从类的名字中,能够发现一个共同
的单词“CCLabel”。在Cocos2D-X引擎中,CCLabel表示了一个文字标签的概念。我们可以将其看作是专门用于显示
文字的对象。
另外,因为它们都有一个共同的父类CCNode,所以如果从绘制组成来说这三个类都是引擎绘制框架中的一员。
文字标签与之前介绍的图层或者精灵等都属于显示游戏内容的对象。在实际的游戏开发中,我们可以按照需要来选择
一种或多种方式显示文字。
二、TTF类型标签(CCLabelTTF)
TTF字体格式算得上是使用最为广泛的文字显示格式了,引擎中提供了对此格式字体的支持。TTF(True Type
Fonts)格式,比如在Windows操作系统当中,文字的显示就是通过TTF格式的字体。这是一种在计算机领域中通用
的字体格式。
CCLabelTTF就是Cocos2D-X引擎中使用TTF字体的文字标签。下图展示了它的继承关系。
通过此图可以看到,此类的另一个父类就是CCSprite。这说明我们完全可以将CCLabelTTF的对象当作精灵对象
来使用。它可以执行各种动作以及变化效果。此类标签对象的优缺点有以下几点。
<1> 任何一种TTF字体都包含了某种语言当中所有的字母以及符号,我们可以随意调整字体的大小、颜色以及样式。
<2> 因为TTF标准得到了普及,所以在很多的操作系统中已经提供了多种字体,我们无需任何的编辑,就可以直接使用。
<3> 创建和更新的过程将会比较缓慢。这是由于字体包含的内容较多,并且初始化时需要创建纹理图片。
1、项目示例
首先新建Cocos2D-X项目,在HelloWorldScene.cppc文件的init函数中修改如下所示代码。
bool HelloWorld::init() { bool bRet = false; do { CC_BREAK_IF(! CCLayer::init()); // Create a "close" menu item with close icon, it's an auto release object. CCMenuItemImage *pCloseItem = CCMenuItemImage::create( "CloseNormal.png", "CloseSelected.png", this, menu_selector(HelloWorld::menuCloseCallback)); CC_BREAK_IF(! pCloseItem); // Place the menu item bottom-right conner. pCloseItem->setPosition(ccp(CCDirector::sharedDirector()->getWinSize().width - 20, 20)); // Create a menu with the "close" menu item, it's an auto release object. CCMenu* pMenu = CCMenu::create(pCloseItem, NULL); pMenu->setPosition(CCPointZero); CC_BREAK_IF(! pMenu); // Add the menu to HelloWorld layer as a child layer. this->addChild(pMenu, 1); CCSize s = CCDirector::sharedDirector()->getWinSize(); CCSize blockSize = CCSizeMake(s.width/3, 200); float fontSize = 26; //创建文字标签对象 CCLabelTTF *left = CCLabelTTF::create("alignment left", "A Damn Mess.ttf", fontSize, blockSize, kCCTextAlignmentLeft, kCCVerticalTextAlignmentCenter); CCLabelTTF *center = CCLabelTTF::create("alignment center", "Abberancy.ttf", fontSize, blockSize, kCCTextAlignmentCenter, kCCVerticalTextAlignmentCenter); CCLabelTTF *right = CCLabelTTF::create("alignment right", "Abduction.ttf", fontSize, blockSize, kCCTextAlignmentRight, kCCVerticalTextAlignmentCenter); CCLayerColor *leftColor = CCLayerColor::create(ccc4(100, 100, 100, 255), blockSize.width, blockSize.height); CCLayerColor *centerColor = CCLayerColor::create(ccc4(200, 100, 100, 255), blockSize.width, blockSize.height); CCLayerColor *rightColor = CCLayerColor::create(ccc4(100, 100, 200, 255), blockSize.width, blockSize.height); //设置标签锚点属性 leftColor->ignoreAnchorPointForPosition(false); centerColor->ignoreAnchorPointForPosition(false); rightColor->ignoreAnchorPointForPosition(false); //设置标签锚点 left->setAnchorPoint(ccp(0,0.5)); leftColor->setAnchorPoint(ccp(0,0.5)); center->setAnchorPoint(ccp(0,0.5)); centerColor->setAnchorPoint(ccp(0,0.5)); right->setAnchorPoint(ccp(0,0.5)); rightColor->setAnchorPoint(ccp(0,0.5)); //设置标签位置 left->setPosition(ccp(0,s.height/2)); leftColor->setPosition(left->getPosition()); center->setPosition(ccp(blockSize.width, s.height/2)); centerColor->setPosition(center->getPosition()); right->setPosition(ccp(blockSize.width*2, s.height/2)); rightColor->setPosition(right->getPosition()); //添加至显示 this->addChild(leftColor, -1); this->addChild(left, 0); this->addChild(rightColor, -1); this->addChild(right, 0); this->addChild(centerColor, -1); this->addChild(center, 0); bRet = true; } while (0); return bRet; }
我们先来看看创建函数中参数最多的一个,下面来介绍其中每个参数的含义。
第一个参数是将要显示的文字内容,它是一个字符串对象指针。第二个参数则是所用字体的名称。第三个参数为
字体的大小,然后是字体显示标签的尺寸。我们需要为当前将要显示的文字内容选择一个合适的尺寸大小。过大就会
浪费内存空间,过小则不能显示完整的内容。最后的两个参数,表示了文字绘制时的对齐方式。不同的对齐方式,将
会导致绘制的文字内容产生位置的变化。这一点,我们可以从实力项目的运行结果中看出。引擎当中,总共存在三种
字体对齐的方式,分别为左对齐、居中对齐、右对齐。示例代码中展示了三种对齐方式。
2、示例效果图
三、Atlas标签类(CCLabelAtlas)
Atlas标签类的父类是CCAtlasNode,这是一个纹理图集的类。此与之前介绍的CCLabelTTF类相比,它有了更大
的灵活性,同时,还占用了更少的资源。下图展示了此类的继承关系。
从继承关系来看,Atlas标签类是CCAtlasNode的子类。这是一个纹理图集类。它可以将纹理图片按照矩形区域分
隔显示。Atlas标签类的创建速度是要远远超过TTF标签类。这两种字体的技术原理十分类似。只不过TTF标签会创建
一张绘制着文字的图片,而Atlas则不会创建任何的纹理图片。从这一点就能体现出它们之间运行效率的差异。Atlas标
签类只会使用源纹理图片进行绘制。
另外,CCLabelAtlas类中的每一个字母或者符号都是独特的。它们可以有灵活可变的样式以及尺寸。这是因为用
于显示文字的纹理图片是由美术人员制作完成的。
最后一点,就是CCLabelAtlas类中的字母或者符号也是可以由开发者定制的。就拿英文举例,并不是每一个CCLabelAtlas类的对象都必须包含26个英文字母。按照开发者的意愿,也可以是只有10个字母的字体。
1、项目示例
首先新建Cocos2D-X项目,在HelloWorldScene.cppc文件的init函数中修改如下所示代码。
bool HelloWorld::init() { bool bRet = false; do { CC_BREAK_IF(! CCLayer::init()); // Create a "close" menu item with close icon, it's an auto release object. CCMenuItemImage *pCloseItem = CCMenuItemImage::create( "CloseNormal.png", "CloseSelected.png", this, menu_selector(HelloWorld::menuCloseCallback)); CC_BREAK_IF(! pCloseItem); // Place the menu item bottom-right conner. pCloseItem->setPosition(ccp(CCDirector::sharedDirector()->getWinSize().width - 20, 20)); // Create a menu with the "close" menu item, it's an auto release object. CCMenu* pMenu = CCMenu::create(pCloseItem, NULL); pMenu->setPosition(CCPointZero); CC_BREAK_IF(! pMenu); // Add the menu to HelloWorld layer as a child layer. this->addChild(pMenu, 1); //创建Atlas标签对象 CCLabelAtlas* label1 = CCLabelAtlas::create("123 Test", "fonts/tuffy_bold_italic-charmap.plist"); //添加显示 addChild(label1, 0); //设置位置 label1->setPosition(ccp(10,100)); //设置透明度 label1->setOpacity(200); CCLabelAtlas *label2 = CCLabelAtlas::create("0123456789", "fonts/tuffy_bold_italic-charmap.plist"); addChild(label2, 0); label2->setPosition(ccp(10,200)); label2->setOpacity(32); label2->setColor( ccRED ); bRet = true; } while (0); return bRet; }
注意:很多时候会报plist,png文件路径的的错误,当报这样的错误的时候就把这两个个文件在Resources下面增一个路径。比如fonts/tuffy_bold_italic-charmap.plist,一定要记得用反斜杠。
2、示例效果图
四、BMFont标签类(CCLabelBMFont)
BMFont标签类是引擎当中最快速最自由的字体类。不过,这也意味着它是使用起来最麻烦的字体。想在游戏中使
用CCLabelBMFont类来绘制文字,开发者至少要有一个编辑器。下图展示了此类的继承关系。
图中展示了BMFont标签类继承自类CCSpriteBatchNode。让我们来看看BMFont标签类的特点。
<1> 需要一个图片编辑器,用于编辑字体的纹理图集。
<2> 具备了很快的创建以及更新速度。
<3> 自由度非常高,每一个字母或者符号都是单独的精灵。
<4> 自制的字体方式,开发者可以自定义其中的字母以及符号,甚至可以包含阴影、外框以及花纹。
1、项目示例
首先新建Cocos2D-X项目,在HelloWorldScene.cppc文件的init函数中修改如下所示代码。
bool HelloWorld::init() { bool bRet = false; do { CC_BREAK_IF(! CCLayer::init()); // Create a "close" menu item with close icon, it's an auto release object. CCMenuItemImage *pCloseItem = CCMenuItemImage::create( "CloseNormal.png", "CloseSelected.png", this, menu_selector(HelloWorld::menuCloseCallback)); CC_BREAK_IF(! pCloseItem); // Place the menu item bottom-right conner. pCloseItem->setPosition(ccp(CCDirector::sharedDirector()->getWinSize().width - 20, 20)); // Create a menu with the "close" menu item, it's an auto release object. CCMenu* pMenu = CCMenu::create(pCloseItem, NULL); pMenu->setPosition(CCPointZero); CC_BREAK_IF(! pMenu); // Add the menu to HelloWorld layer as a child layer. this->addChild(pMenu, 1); //创建一个颜色图层 CCLayerColor* col = CCLayerColor::create( ccc4(128,128,128,255) ); addChild(col, -10); //使用字体资源文件,来创建一个CCLabelBMFont对象 CCLabelBMFont* label1 = CCLabelBMFont::create("Test", "bitmapFontTest2.fnt"); //设置字体锚点并添加至显示 label1->setAnchorPoint( ccp(0,0) ); addChild(label1, 0); CCLabelBMFont *label2 = CCLabelBMFont::create("Test", "bitmapFontTest2.fnt"); // testing anchors label2->setAnchorPoint( ccp(0.5f, 0.5f) ); label2->setColor( ccRED ); addChild(label2, 0); CCLabelBMFont* label3 = CCLabelBMFont::create("Test", "bitmapFontTest2.fnt"); // testing anchors label3->setAnchorPoint( ccp(1,1) ); addChild(label3, 0); CCSize s = CCDirector::sharedDirector()->getWinSize(); //设置位置 label1->setPosition( ccp(s.width/2 - 50, s.height/2) ); label2->setPosition(ccp(s.width/2, s.height/2) ); label3->setPosition(ccp(s.width/2 + 50, s.height/2) ); bRet = true; } while (0); return bRet; }
创建的函数只有两个参数,用法非常简单。第一个参数为将要绘制的文字内容,第二个就是通过编辑器之多的字
体资源文件。因为引擎为BMFont标签类提供了最大的灵活度,BMFont类的对象中每一个字母或者符号都是一个独立
的精灵对象。所以我们可以轻易地就让一个字母跳动、旋转、变形、变色以及改变透明度。
另外,得益于父类精灵图集的特性,BMFont标签类还是速度最快的。
2、示例效果图
源码下载地址