Closed JKremsner closed 2 years ago
I think the main reason for this is because the documentation for Image
class says
/// A class or method that receives an image object must call [dispose] on the
/// handle when it is no longer needed. To create a shareable reference to the
/// underlying image, call [clone]. The method or object that receives
/// the new instance will then be responsible for disposing it, and the
/// underlying image itself will be disposed when all outstanding handles are
/// disposed.
and we never do that. Normally, it's not a problem, because all images are stored in the cache anyways. But if you want to clear something from cache, then that would create a memory leak.
You are completely right @st-pasha! If I adept my code, keep a reference to the SpriteSheetImage within the CowComponent and change the code of the onDetach to
@override
void onDetach() {
super.onDetach();
print("detach");
cows.forEach((cow) {
cow.spriteSheetImage.dispose();
});
Flame.images.clear('cow/spriteSheets/__brown_cow.png');
Flame.images.clear('cow/spriteSheets/__black_and_white_cow.png');
}
it works as intended and I see the memory decreasing by the same amount as it increases when I load cows. This painfully means I kinda have to keep references of all the images that I use in components and dispose them manually before clearing them from the flame cache.
How could we improve on that?
Can you try to depend on this branch to verify that this fix fixes it for you?
dependencies:
flame:
git:
url: https://github.com/flame-engine/flame.git
ref: spydon.dispose-images-when-cleared
path: packages/flame
@spydon Just tested it and you are a hero! Works flawlessly! Thank you!
You don't have to close the issue yet, it will be closed automatically when the PR is merged. :)
Please note that the components used use very big spritesheets.
I for example use a SpriteAnimationGroupComponent.
As you can see aboth I use Flame.images.load to load the spritesheet into the memory. I use Flutter DevTools to inspect the memory. As soon as this code loads I can see the memory usage increasing. My game includes the following code snippet:
Now when I detach the game it will clear the 2 spritesheets from the cache but I don't see the memory reducing at all in Flutter DevTools. Even worse: Flame doesn't find the image in the cache anymore (as it should be) and therefore it gets loaded again into the cache as soon as the component/game gets attached again. This causes the memory to slowly flood as I can always see the memory increasing when I load the component but never see it decrease when I clear something from it. The only way to prevent flooding the memory like this is to never clear it from the cache. Obviously that can't be intended. Am I missing something?
If I go even further and use Flame.images.clearCache() I can see some memory getting freed up but loading everything in again uses much more then previously needed causing the same kind of flood.