了解精灵表内存消耗

Posted

技术标签:

【中文标题】了解精灵表内存消耗【英文标题】:understanding sprite sheet memory consumption 【发布时间】:2013-07-04 18:15:21 【问题描述】:

我想知道每行标记的代码如何影响内存消耗。鉴于我的精灵表占用了 4MB 的内存。

CCSpriteBatchNode *spritesBgNode;      // Line 1
spritesBgNode = [CCSpriteBatchNode batchNodeWithFile:@"sprites.pvr.ccz"]; // Line 2
[self addChild:spritesBgNode];    // Line 3
[[CCSpriteFrameCache sharedSpriteFrameCache] addSpriteFramesWithFile:@"sprites.plist"]; // Line 4

sprite1 = [CCSprite spriteWithSpriteFrameName:@"sprite1"];  // Line 5
[spritesBgNode addChild:sprite1]; // Line 6 

[spritesBgNode addChild:sprite1]; // Line 7 

[spritesBgNode addChild:sprite1];  // Line 8

[spritesBgNode removeChild:sprite1]; // Line 9

[spritesBgNode removeSpriteFramesFromFile:@"sprites.plist"]; // line 10

[self removeChild: spritesBgNode]; // Line 11

i) 4MB sprite sheet 从哪一行开始消耗内存?

ii) 第 5 行是否会导致任何额外的内存消耗?

iii) 在第 8 行的情况下会发生什么(第 7 行再次添加),它如何影响内存?

iv) 第 9 行和第 10 行如何影响内存消耗?他们释放内存吗?

v) 如果暂时不使用批处理节点,是否建议使用第 11 行?以后再添加有什么影响。

【问题讨论】:

如果你想知道精确的行和字节,你应该使用 Instruments。纹理使用了 99% 的内存,其他行最多增加了几百个字节。 【参考方案1】:

i) Spritesheet 在加载到内存时会消耗内存。由于 coco2d 是一个开源框架,你可以查看代码,你会看到,在batchNodeWithFile: 调用之后,spritesheet 被添加到了内存中。 in 会将其添加到此方法内的缓存中。

ii)您的第 5 行返回简单的自动释放对象。这是objective-c中的常见做法。对象将在滴答开始时由释放池自动释放。这意味着如果您不保留该对象,它将被销毁,例如,通过将其作为子节点添加到某个其他节点。

iii) 您不能添加孩子两次。如果您尝试添加的节点的父节点不是nil,它将导致断言。前面说了,你可以在CCNode类的代码中看到。

iv) 纹理加载到内存后,所有精灵都非常​​轻量级,因为任何精灵只需使用链接到纹理的某个部分来绘制它。所以你会释放一点内存,但你仍然会看到你的 4MB+。

v) 从父节点移除任何节点后,它的纹理仍会加载到内存中,即使对象被销毁。您可以通过调用卸载此纹理

[[CCSpriteFrameCache sharedSpriteFrameCache] removeUnusedSpriteFrames];
[[CCTextureCache sharedTextureCache] removeUnusedTextures];

此外,如果您使用一些动画,您可以将它们从 CCAnimationCache 中移除。无论如何,如果您对内存没有问题,我可以建议不要从内存中卸载纹理。加载纹理是最漫长的过程,因此在从未加载的纹理中绘制 spriteframe 之前会有延迟,因为它将再次加载。

【讨论】:

可能是这样的情况,以嘲笑提问者编程能力的评论开始答案并没有受到好评?

以上是关于了解精灵表内存消耗的主要内容,如果未能解决你的问题,请参考以下文章

在 iphone 上使用大型精灵表

逆向工程:从 apk 中提取图像/精灵表 [关闭]

精灵表精灵添加

从精灵表中以 sfml 动画精灵

我应该如何为精灵表中的精灵分配名称?

纹理包装动画图像/精灵表有效-Libgdx