问题描述
我得到了一个不是单例实例的 GameScene 类.因此,每次用户选择新关卡时,我都会分配和取消分配它,并将静态"/共享"数据保存在不同的单例类(例如 GameManager)中.
I got a GameScene class that is not a singleton instance. Hence I allocate and deallocate it every time the user chooses a new level and keep the "static"/"shared" data in a different singleton class (E.g. GameManager).
我正在使用 ARC.我想了解在内存管理的角度下我的方法是否正确.换句话说,在清理时调用removeUnusedSpriteFrames"就足够了吗?这会删除 game-art-forLevelOne-hd.plist 中的所有精灵吗?我也应该对 CCSpriteBatchNode 做点什么吗?
I am using ARC. I would like to understand if my approach is correct under the memory management point of view. In other words, is it enough to call "removeUnusedSpriteFrames" at cleanup? Will this remove all sprites in game-art-forLevelOne-hd.plist? Should I do something also with the CCSpriteBatchNode?
-(void) loadGameArtFileForLevelOne //I do this in a switch but this is to simplify the reading
{
CCSpriteFrameCache* frameCache = [CCSpriteFrameCache sharedSpriteFrameCache];
[frameCache addSpriteFramesWithFile:@"game-art-forLevelOne-hd.plist"];
CCSpriteBatchNode * sharedSpriteBatchNode = [CCSpriteBatchNode batchNodeWithFile:@"game-art-forLevelOne-hd.png"];
}
//As dealloc is deprecated for ARC code, I prefer to remove unused sprites and texture on cleanup
-(void) cleanup
{
[[CCSpriteFrameCache sharedSpriteFrameCache] removeUnusedSpriteFrames];
}
我在 CCSpriteBatch 节点的 dealloc 方法中添加了一个 CCLOG 调用.当我加载 GameScene 然后返回菜单时,我看到了删除未使用的纹理"的日志,但 我没有看到 CCSpriteFrameCache 的 dealloc 方法的任何日志. *!!警告:请参阅下面的编辑 - 我的错误!*
I added a CCLOG call in the dealloc method of CCSpriteBatch node. When I load the GameScene and then go back to the menu I see the log of "remove unused texture" as expected but I don't see any log of the dealloc method of CCSpriteFrameCache. *!! Warning: See edit below - my mistake!!*
抱歉,我的意思是我没有看到 CCSpriteBatch 的 dealloc 方法的任何日志
这让我有点担心,因为我想释放"并删除与关卡 Sprite 相关的所有内存.
This concerns me slightly as I want to "free" and remove all memory related to the Sprites for the level.
一旦我理解了这一点,我就会优化"这一点(例如,每个级别都有一个精灵表 - 例如世界 1 - 并且每个背景都有一个精灵表).
Once I understood this I will then "optimize" this bit (e.g. have one sprite sheet for each class of level - e.g. world 1 - and one sprite sheet for each background).
有什么建议吗?
推荐答案
我假设您正在某处添加 CCSpriteBatchNode
节点,尽管您发布的代码没有显示它(您还提到,它发生在开关中,所以我认为在完全不同的设置中).如果是这样,它不会被释放,直到您从添加它的位置删除它.
I assume you are adding the CCSpriteBatchNode
node somewhere, although the code you posted does not show it (you also mention, it happens in a switch, so I think in a completely different settings). If so, it will not be deallocated until you remove it from where you added it to.
在这里,也许需要澄清一下.
Here, maybe, a clarification is in order.
CCSpriteFrameCache
是一个缓存:一块存储空间,所有精灵都可以在其中获取以便随时可以重用.
The CCSpriteFrameCache
is a cache: a piece of storage where all the sprites get in order to be readily available for reuse.
CCSpriteBatchNode
是一种在 Open GL 层中提高性能的机制,原则上与缓存完全无关.
The CCSpriteBatchNode
is a mechanism for improving performance in the Open GL layer in principle totally unrelated from the cache.
我了解,如果您通过批处理节点使用的某些精灵仍然存在于某些层/节点/场景中,则它不会被视为未使用"并且不会被您的清理代码删除.实际上,它正在使用中.当您从所有引用它的节点中删除它时,缓存的 sprite 将变为未使用".
I understand that if you have some sprite used through a batch node still present in some layer/node/scene, than it will not be considered "unused" and will not be removed by your cleanup code. Actually, it is in use. The cached sprite will become "unused" when you remove it from all the nodes that refers to it.
关于你的问题:
也就是说,清理时调用removeUnusedSpriteFrames"就够了吗?
In other words, is it enough to call "removeUnusedSpriteFrames" at cleanup?
嗯,我认为这取决于您的应用程序什么可以被认为是好的清理.从缓存中删除未使用的精灵当然可以;但你也可以做其他事情:卸载你加载的音频资源;删除场景中未使用的部分(如果需要,可以重新加载);等等
Well, I think that it depends on your app what could be considered good cleanup. Removing unused sprites from the cache is certainly ok; but you might also do other things: unloading audio resources you loaded; removing parts of the scene that are not used (and could be reloaded if required); etc.
希望这会有所帮助.
我没有看到 CCSpriteFrameCache 的 dealloc 方法的任何日志.
CCSpriteFrameCache
是一个单例,所以它应该在程序的整个生命周期中都存在(它可能会有所不同,但我敢打赌就是这种情况):
CCSpriteFrameCache
is a singleton, so it shall exist for the lifetime of the program (it could be different, but I bet this is the case):
CCSpriteFrameCache* frameCache = [CCSpriteFrameCache sharedSpriteFrameCache];
所以,我不会担心缓存没有被删除;重要的是它的内容被清空了.
So, I would not be worried at the fact that the Cache is not deleted; what matters is that its content is emptied.
这篇关于Cocos2d,iOS:从缓存中删除精灵的正确方法是什么?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持跟版网!