什么是精灵(Sprite)?游戏中的主角、敌人都可能是一个精灵,但并不是所有的图形对象都是一个精灵,只有你能控制它,它才是一个精灵,如果无法控制,那就只能是一个节点。准确来说,精灵是一个能通过改变自身属性:位置、旋转、缩放、倾斜、颜色和透明度等,变成可控制的 2D 图像。
1.精灵的创建方法
可以使用一张图片来创建一个精灵,除此之外还可以使用图集或者精灵缓存来创建。
1.1通过指定图片创建精灵
auto sprite = Sprite::create("sprite.png");
1.2通过指定图片指定区域创建精灵
auto sprite = Sprite::create("sprite.png", Rect(0, 0, 20, 20));
1.3通过指定纹理创建精灵
Texture2D *cache = Director::getInstance()->getTextureCache()->addImage("Spriet.png");
auto sprite = Sprite::createWithTexture(cache);
1.4通过指定纹理指定区域创建精灵,第三个参数设置是否旋转纹理
auto sprite = Sprite::createWithTexture(TextureCache::getInstance()->addImage("Sprite.png", Rect(0, 0, 20, 20), true);
1.5通过精灵帧创建精灵
SpriteFrameCache *frameCache = SpriteFrameCache::getInstance();
frameCache->addSpriteFrameWithFile("SpriteSheet.plist") //SpriteFrame 只加载一次,后续一直保存在 SpriteFrameCache 中
SpriteFrame *spriteFrame = frameCache->getSpriteFrameByName("sprite.png");
auto sprite = Sprite::createWithSpriteFrame(spriteFrame);
1.6通过精灵帧缓存创建精灵
SpriteFrameCache *frameCache = SpriteFrameCache::getInstance();
frameCache->addSpriteFrameWithFile("SpriteSheet.plist") //SpriteFrame 只加载一次,后续一直保存在 SpriteFrameCache 中
auto sprite = Sprite::createWithSpriteFrameName("sprite.png");
ps:精灵帧不再使用后要及时清除,否则如果再有相同名称精灵帧时会产生冲突:
void removeSpriteFrameByName(const std::string &name):移除指定名字的精灵帧
void removeSprites():移除指定精灵帧
void removeSpriteFramesFromFile(const std::string &plist):移除指定坐标文件的精灵帧
void removeUnusedFrames():移除没有使用的精灵帧
2.精灵的控制
成功创建精灵后,现在可以通过修改精灵的属性去控制精灵了。
2.1锚点
锚点确定了精灵对象在计算坐标位置的一个基准点,这个点是精灵内部的点,锚点影响精灵的缩放,旋转,倾斜,但不影响颜色和透明度。锚点使用的坐标系以左下角为原点 (0, 0)。默认情况下,所有的节点对象锚点是 (0.5, 0.5)。 通过 setAnchorPoint() 方法可以设置精灵的锚点:
sprite->setAnchorPoint(0, 1); //锚点的取值范围为 0~1
锚点设置为(0,1)时的效果(红点为锚点所在的位置):
2.2位置
位置表示精灵所在父节点中的位置,当需要设置一个精灵的位置时,需要用到 setPosition() 方法:
sprite->setPosition(Vec2(100,100));
2.3旋转
通过 setRotation() 方法,旋转用来设置精灵以锚点为基准点的旋转,顺时针旋转为正,逆时针旋转为负,默认情况下,旋转角度为 0.0。
sprite->setRotation(20.0f);
顺时针旋转 20° 的效果:
2.4缩放
通过 setScale() 方法控制精灵的缩放。可以控制精灵水平缩放,垂直缩放,也可以整体缩放。默认水平和竖直的缩放值都是 1.0。
sprite->setScale(2.0); //控制整体缩放
sprite->setScaleX(2.0); //控制 X 轴缩放
sprite->setScaleY(2.0); //控制 Y 轴缩放
效果:
2.5倾斜
通过 setSkewX() 控制精灵的倾斜度,可以控制精灵水平倾斜,竖直倾斜,或者水平竖直同时倾斜,默认水平和竖直的倾斜值都是 0.0。
sprite->setSkewX(20.0f); //控制 X 轴倾斜
sprite->setSkewY(20.f); //控制 Y 轴倾斜
效果:
2.6颜色
通过 setColor() 控制精灵的颜色。将一个 RGB 值设置到 Color3B 对象,调用精灵的 setColor() ,就能完成精灵颜色的设置。RGB 是三个从 0-255 的值,三个值分别代表红绿蓝的颜色深度,数值越大,颜色越深。特别的 RGB(255, 255, 255) 是白色。如果你不想自己指定 RGB 的三个值,也可以使用 Cocos2d-x 提供的预定义颜色,比如: Color3B::White,Color3B::Red。
sprite->setColor(Color3B::WHITE);
sprite->setColor(Color3B(255, 255, 255))
效果:
2.7透明度
精灵的透明度可以通过 setOpacity() 传入一个特定的值来设置,这个值的范围是 0-255,数值越大透明度越低,255 代表完全不透明,0 代表完全透明。
sprite->setOpacity(30);
效果:
3.性能优化
可以通过使用纹理图集、精灵帧缓存或者多边形精灵进行精灵的性能优化。
3.1使用纹理图集
纹理图集(Texture)也称为精灵表(Sprite Sheet)
使用纹理图集的优点:
1.减少文件读取次数,读取一张图片比读取一推小文件要快。
2.减少 OpenGL ES 绘制调用并且加速渲染
OpenGL ES 1.1仅仅能够使用2的n次幂大小的图片(即宽度或者高度是2、4、8、64…)。
如果采用小图片OpenGL ES1.1会分配给每个图片2的n次幂大小的内存空间,即使这张图片达不到这样的宽度和高度也会分配大于此图片的2的n次幂大小的空间。那么运用这种图片集的方式将会减少内存碎片。
虽然在Cocos2d-x v2.0后使用OpenGL ES2.0,它不会再分配2的几次幂的内存块了,但是减少读取次数和绘制的优势依然存在。
3.减少内存消耗。
4.Cocos2d-x全面支持Zwoptex和TexturePacker,所以创建和使用纹理图集是很容易的。
具体实现方法在精灵的创建方法中已做说明,这里不再重复。
3.2使用精灵帧缓存
精灵帧缓存是缓存的一种,缓存有如下几种:
1.纹理缓存(TextureCache)
使用纹理缓存可以创建纹理对象。
2.精灵帧缓存(SpriteFrameCache)
和纹理图集相对应,把plist文件读到内存,到文件里面创建精灵帧缓存,然后再从精灵帧缓存中获得精灵对象,反复使用精灵对象时候,使用精灵帧缓存可以节省内存消耗。
将一个图读到精灵帧缓存中,同时也会加载到纹理缓存中。
3.动画缓存(AnimationCache)
动画缓存主要用于精灵动画,精灵动画中的每一帧是从动画缓存中获取的。
具体实现方法在精灵的创建方法中已做说明,这里不再重复。
3.3多边形精灵
首先观察下面这张图:
注意左右两种情况的不同。
左侧,是一个典型的精灵绘制时的处理,精灵被处理成一个有两个三角形组成的矩形。
右侧,是一个多边形精灵绘制时的处理,精灵被处理成一系列小的三角形。
显然可以看到,右侧多边形精灵需要绘制的像素数量比左侧精灵需要的像素数量更小,但是由于划分了多个三角形出现了更多的顶点,由于在现代的图形处理中,一般绘制定点比绘制像素消耗的性能少。所以多边形精灵的性能更好。
可以通过 AutoPolygon 工具类方法来生成多边形精灵:
auto pinfo = AutoPolygon::generatePolygon("filename.png");
auto sprite = Sprite::create(pinfo);
我是「Super于」,立志做一个每天都有正反馈的人!欢迎大家关注我的公众号「游戏开发小白变怪兽」,一起进步!