Model optimization study

!!!!!!!!!!!!!!!!! Article to be reformated with the new site css. !!!!!!!!!!!!!!!!!

  •  Barbarian model: Optimization study

  •  The Model

The model comes in a MS3D format with TGA textures. It has a two LOD definition: low poly and high poly.
It has diffuse, opacity, normal and specular maps.

Here is the file list, size and some informations:

  • barbarian_high.ms3d   3058 ko

  • barbarian_low.ms3d    2332 ko

  • barbarian_d.tga      14126 ko  (2048 x 2048)

  • barbarian_a.tga       4097 ko  (2048 x 2048)

  • barbarian_n.tga      14478 ko  (2048 x 2048)

  • barbarian_s.tga      13974 ko  (2048 x 2048)

  • armor_d.tga          16155 ko  (2048 x 2048)

  • armor_a.tga          12289 ko  (2048 x 2048)

  • armor_n.tga          15707 ko  (2048 x 2048)

  • armor_s.tga          15764 ko  (2048 x 2048)

  •  Memory optimization

If you load the low / high poly models and save it straight away without any optimizations enabled, you'll get a JMF file of size 7629 ko / 7886 ko with the build 1.1.3-28-08-2010 and prior. If you use the build released this september, which contains various internal memory structures optimizations, you'll get an approximative 2 mo reduction: 5334 ko / 5594 ko !

You can expect that the model takes at least this much of memory inside the JVM, non compressed JMF files are close to memory dump (java object serialization).
This 2 mo improvement is great, but still 5 mo usage inside the JVM is big. We'll see how this can be improved.


For those of you reading this article, some of you may have read this Archived forum (retired). We'll see the results of using the Optimizer introduced there.
With the build 1.1.3-28-08-2010 and prior, you'll get the same memory usage than the non optimized model, meaning 7629 ko / 7886 ko. Using the build release this september, you'll benefit of some new memory optimizations that will reduce the 5334 ko / 5594 ko of the orignal model to just 2462 ko / 2722 ko !!


You've now saved an additional 3 mo (5 mo in total). You can still save a little more memory by using the new 'destructive' animation compression. This optimization will detect unecessary animation keys that could be interpolated very closely (closely is not exactly hence the name 'destructive'). Default settings are not very destructive, instead of using floating point equality, it will use compare the float value differences by a small equsilon value to get rid-off of interpolation foating point imprecision of the exporter of the format conversion.

Using the default setup, which results to a not so destructive optimization as you'll not see any differences, the model is sized down of 20%: 1981 ko / 2240 ko. If you want to reduce even more the animation, you can choose an heavy destructive which currently results to some slight skeleton vibration, you can size it down to 1676 ko / 1417 ko (and more with higher destructive setup).


In summary, you've seen how important is to use the engine optimizer. You can save a huge amount of memory, this sill allow to load more models, to fit in smaller hardware, or just to use less memory that could be used by the OS or other applications.


Note: All optimizations presented here applies mostly to skinning animation info. Geometry (vertex) data has already been hugely optimized before, and takes 700ko for the high poly models (all the remaining size are for the bigger part skinning animation info).
 

  •  File-System storage

All size show in the previous paragraph are non compressed JMF model, just stay close to that actual JVM usage.
Now will see the same values with a model compressed using LZMA, for each of the two builds of the engine.

Using this compressing, the 7629 ko / 7886 ko are compressed to respectively 701 ko / 816 ko. With the lastest optimized build, 1981 ko / 2240 ko are compressed to 574 ko / 690 ko.
We'll also, in a smaller ratio, save some space with the compressed format.
 

  •  Texture optimization

The high definition textures (2048 x 2048) takes just too much memory: 104 mo !

We'll see how to using the tool provide with the engine. It could be possible to do the same thing using some external tool such as ATI The Compressonator, but we'll stick here with the all-in-one optimizer of the engine. It can be easily used in a batch convert, in a multiplatform ecosystem.

So let's use the setTextureWriterOptions introduced in Archived forum (retired). We'll use here dds format, maximum texture size of 1024 x 1024 and merging of diffuse and opacity textures.
After running this tool, you'll getthose textures (to be compared to the tga listed on start of this article):

  • armor_d_da.dds      1024 ko (DXT5)

  • armor_n.dds         1024 ko (ATI2/RGTC2)

  • armor_s.dds          512 ko (DXT1)

  • barbarian_d_da.dds  1024 ko (DXT5)

  • barbarian_n.dds     1024 ko (ATI2/RGTC2)

  • barbarian_s.dds      512 ko (DXT1)

The 104 mo TGA has been reduce to a 5 mo, which is a much more acceptable size.
Using 512x512 textures, the size could be reduce by 4 to a small 1.25mo.
 

Another interesting texture format is TEX, which has been specifically designed for the engine. This format is derived of DDS, and support similar features: non-compressed (byte/float) and compressed (S3TC(DXTx) / 3Dc / RGTC / LATC) texture, with mipmap and cubemap support.
In addition, TEX format support an optional file compression (using LZMA) and optional encryption for protection. TEX format is a binary format independent of the runtime class of the engine. Its design is finished, and forward and backward compatibility is guaranteed.

Let's see the result for this file format using both compression and encryption:

  • armor_d_da.tex       412 ko (DXT5)

  • armor_n.tex          966 ko (ATI2/RGTC2)

  • armor_s.tex          368 ko (DXT1)

  • barbarian_d_da.tex   332 ko (DXT5)

  • barbarian_n.tex      898 ko (ATI2/RGTC2)

  • barbarian_s.tex      293 ko (DXT1)

This results to 3.77 mo (25% smaller for this set of texture).
For 512x512 textures, the size is reduced to 845 ko.
 

  •  Loading speed optimizations

Previous paragraph was oriented around memory improvements. We'll see here the amount of time you'll saved in the different steps.

I've runned a benchmark to measure the time to load the different model and texture format (times after JVM and hard-drive warm-up). MS3D and TGA are the input files listed at start and are exported in JMF/DDS/TEX.
Here are the results:

  • MS3D + Optimization              2.80 s

  • JMF (Optimized)                  0.12 s

  • JMF (LZMA+Encryption+Optimized)  0.39 s

and for the textures:

  • TGA 2048                    6.04 s

  • DDS  512                    0.07 s

  • DDS 1024                    0.14 s

  • TEX  512 (LZMA+Encryption)  0.48 s

  • TEX 1024 (LZMA+Encryption)  1.67 s

JMF loads notably faster than MS3D, even with lzma and encryption enabled.
TEX are slower to load than DDS due to the additional lzma compression and encryption. Without that, they loads at the same speed than DDS. Both DDS/TEX loads notably faster than original TGA files.
 

  •  Temporary memory loading

In addition to loading speed, it may also be interesting to have some indication to memory and garbage collection usage.
Each test are runned separatly with a new VM without warm-up. Garbage collection is requested before running the test code and memory is in this state: total memory is 15.5 mo (Runtime.totalMemory()) and used memory is 0.16 mo (Runtime.totalMemory() - Runtime.freeMemory()).

For each tests, measurements are:
 1) Memory used before GC
 2) Memory used after GC
 3) the new total memory used by the JVM. This value may be different to the initial value if the VM has expanded (occures when the heap has been fully allocated).
MS3D and TGA are the input files listed at start and are exported in JMF/DDS/TEX.

Here are the result for each tests:    1)  /  2)  /   3)

  • MS3D + Optimization              22.37 / 0.49 / 28.29

  • JMF (Optimized)                   4.38 / 0.38 / 15.56

  • JMF (LZMA+Encryption+Optimized)   5.32 / 0.43 / 15.56

  • TGA 2048                         48.22 / 0.21 / 62.47

  • DDS  512                          1.20 / 0.21 / 15.56

  • DDS 1024                          5.08 / 0.71 / 15.56

  • TEX  512 (LZMA+Encryption)        1.29 / 0.29 / 15.56

  • TEX 1024 (LZMA+Encryption)        5.93 / 0.29 / 15.56

As expected MS3D (and tga) uses a high amount of temporary memory, which result to resize of the JVM heap in the test conditions.
It is probably not a big issue in nowadays computer, but on mobiles devices (or on applet with limited JVM heap) this can be the cause some serious issues (out of memory).