viniciusgerevini / godot-aseprite-wizard

Godot Editor plugin to help import Aseprite animations to AnimationPlayers, AnimatedSprites and SpriteFrames.
MIT License
879 stars 42 forks source link

Imported .res is too big #13

Closed cstrlcs closed 3 years ago

cstrlcs commented 3 years ago

Hello! First of all, I'd like to thank you for developing this amazing tool!

I installed the plugin and everything works fine. I had no issues so far. But when I went to check my resources folder, I saw that each ".res" files weights about 180 mb. It is weird, since my .aseprite file are all less than 160kb.

I tested this on the last Godot release on WIndows and Linux. It works the same.

Is this the expected behaviour or is it an issue? If it is an issue, I'd like to help solve this. Thank you!

viniciusgerevini commented 3 years ago

Hello @castroclucas. Thank you!

Wow, 180mb? It's definitely an issue. I don't know how I haven't noticed this before. I can see some of my files are also bigger than they should be. Good catch!

The first thing that comes to my head is how it creates new image resources for each frame: https://github.com/viniciusgerevini/godot-aseprite-wizard/blob/master/addons/AsepriteWizard/aseprite_cmd.gd#L312-L316

Back then I though it used the file already stored on disk, but I believe it embeds the image in the resource, duplicating it for each frame. :(

We can move this logic to the export step, lines 95 and 155, and we can use it's reference in the AtlasTexture.

Give it a try if you have time and let me know what you find. I'll try it myself tonight.

Thanks for the help and for finding this issue. :)

viniciusgerevini commented 3 years ago

A simpler fix could be using imagetexture.load(...) instead of imagetexture.create_from_image(). However, this one may not work, as the spritesheet is imported on the background. Worth it a try, though.

cstrlcs commented 3 years ago

Hello!

I changed the line from "texture.create_from_image(i,0)" to "texture.load(image)". Since the method 'load' requires a string, I used the image's path. I deleted all import folders and tried again. Nothing changed.

One thing that I noticed is that two different spritesheets will have a big difference in size, they are not proportional.

Example: Spritesheet 1 with 90 frames -> 180mb Spritesheet 2 with 49 frames -> 11mb

So, the .res file is not only duplicated but the growth is exponential, right?

I'm quite new to GDScript and Godot's API but I'll keep searching and if I find something, I'll update here :)

Again, thank you for your work on this project. It is being extremely useful on my game. If you have any means of donation, I'd like to support this project. I don't have much but I would be happy to help

viniciusgerevini commented 3 years ago

Thanks! I really appreciate your help. I was also able to confirm that the image is causing the issue. I've run a few tests with an animation 48x64 with 38 frames. The .png file generated has 3.2kb. Here are the results: Screenshot from 2021-01-07 19-31-04

I'll start looking into how to make ResourceLoader.load() work, maybe finding a way to trigger the image import without having to leave Godot. The fallback option is to change the logic to use ImageTexture.load() until we find a better way.

Again, thank you for your work on this project. It is being extremely useful on my game.

I'm glad to hear it. I also benefit a lot from the community, so I try to find ways to also contribute back :D

If you have any means of donation, I'd like to support this project. I don't have much but I would be happy to help

It's really nice of you, but it's not necessary. You are already contributing a lot by taking time to help me find and fix this issue. Without your heads up, I don't know when (or whether) I would have noticed this. Thanks!

viniciusgerevini commented 3 years ago

I've managed to use the resource imported by Godot. It won't work in the importer though, so I'll still use a fallback for that. I have tested on Linux only. Tomorrow, I'll validate against Windows and MacOS. I also want validate with more diverse files before merging it.

The spritesheet I used for testing was the same as before, 48x64 with 38 frames. Here are my latest results: Screenshot from 2021-01-08 00-14-30 The first and second files were imported using the fallback method (Image.load()). The last two files use the resources imported by Godot (ResourceLoader.load()).

For some reason, the fallback method is still quite big. Compared to the source file, it is more than 100 times the original size. However, it's not even close to the initial 21mb.

Maybe there is something else we can do for it, but it's already a good improvement.

You can find my changes in the fix_resource_size branch.

I'll open a PR soon to explain with more details the changes and workarounds.

cstrlcs commented 3 years ago

Woah, incredible!

I wrote a comment on your pull request showing my results. It had an imense drop on size (180mb -> 1.5mb). Works really nice! I'll keep testing with other files and bringing more feedback.

Thank you!

viniciusgerevini commented 3 years ago

I've already submitted version 1.2.2 to Godot's Asset Library. It usually takes a few days to land. Thanks again for finding this issue and helping me to debug it. I had files going from 12mb to 3.5kb in my game. :))