I have 40 lightmaps at 1024x1024. Each one is compressed to pvr 4, without mip maps, which results in there being exactly 20 mb of lightmap data.
However once I load it on the iPad, I found including all of these lightmaps adds 40 mb of memory usage to my app! Regularly its 36 mb in use, I add all the lightmaps, it then is 76 mb in usage. Seems like the lightmaps are being stored twice or something?
are they marked for get pixel - set pixel? (shouldn’t be but who knows?) cause in that case they are twice in RAM, once in RAM and once in VRAM which on mobiles is the same basically from the “losing ram” PoV
Also is calculating the lightmap the only thing you did?
so all the rest including settings for static batching and alike are equal?
The setting is only exposed for advanced textures
Unsure to what it defaults for the rest, but a simple usage of SetPixel + Apply will tell you if they are not marked for it by throwing an error
@eem: In that case you pretty surely forgot the 33% overhead of mipmaps thats present whenever a texture is not set to not use them
I replaced all my commandline generated .pvr’s with the original PNG files and let unity handle the pvr conversion with the ‘lightmap’ flag checked in the advanced settings. And it comes in now with an expected 20 mb of memory usage… So maybe get/set wasn’t turned off.
What would be the best way to turn get/set off on .pvr files you drop into unity? Is there somewhere to disable that before Unity even loads the scene?
Also, are you sure about this 33% overhead without using mip maps? Because I started out with all my lightmaps having mip maps, checked memory usage and it was around like 65. Then I disabled all mip maps for my lightmaps and then checked memory usage and its now at 56. So disabling mip maps for sure reduced memory usage.
Well for .pvr files you drop into unity, you don’t get an advanced tab. You don’t get any settings to set… So I assume you do it through code but, whats the best place to do that?
My first thought would be do it under Start() but that seems like a bad idea because youd prolly want to disable this before the app even loads…
@ eem
How detailed are your lightmaps, how big is your scenes?? My scenes are a good size and I average about 1-3 MB total (compressed and Max size set to 512) per scene ( 4-8 lightmaps) and the quality is still very good. Are you overdoing it??
I disabled all of the isReadable flags and the .pvr files that I dropped into Unity still are using twice as much memory as they should.
Im running a script in Awake that does this:
Texture2D tx2d;
for (int i = 0; i < lightmapMaterials.Length; i++)
{
tx2d = (Texture2D)lightmapMaterials[i].mainTexture;
tx2d.Apply(false,true);
}
for (int i = 0; i < LightmapSettings.lightmaps.Length; i++)
{
if (LightmapSettings.lightmaps[i].lightmapNear != null)
LightmapSettings.lightmaps[i].lightmapNear.Apply(false,true);
if (LightmapSettings.lightmaps[i].lightmapFar != null)
LightmapSettings.lightmaps[i].lightmapFar.Apply(false,true);
}
and I tried running a script from the editor that does this:
The only other function I knew of to disable the isreadable flag is via Texture2D.Apply but that doesn’t seem to work? Am I doing something wrong? Is there another reason why textures would be stored in memory twice?
Ok after disabling the isReadable flag every which way I could possibly found, I discovered doing so in the OnPostProcessTexture function makes it actually result in using the proper memory amount on the ipad. Here is the code:
using UnityEngine;
using UnityEditor;
public class TextureProcessor : AssetPostprocessor
{
void OnPostprocessTexture(Texture2D texture)
{
if (assetPath.IndexOf ("PVR") == -1)
return;
Debug.Log("disabling isReadable on " + assetPath);
texture.Apply(false, true);
}
}
what that does is look for the capitalized letters PVR in your asset path. So put all of your PVR compressed textures into a folder suffixed by PVR, Assets/TexturesPVR/texture, and then it will automatically disable the isreadable on all PVR files coming into unity from that folder
Just adding a small detail:
The script has to be placed inside the ‘Editor’ folder in the Assets.
Then, it will work only when assets are imported. So, if you already have your pvr textures in the project, re-import them once and watch the console for the results
You shouldn’t need to mark them as not readable cause they are never writable on the device anyway (texture compression is only available on desktop and only available for DXT within the client)
Theoretically.
Practically there is only one setting and thats ‘Get / Set Pixel’ or basically ‘is changeable’ and for PVR this is force defined as false, independent if you want that or not.
Thats also why it has an own asset importer, why the asset importer is not accessable (as there is nothing you can change if you use pvr - see the different threads on why mipmap stuff and other things are ignored when you use pvr images) and why it has an own texture import inspector that does not even expose the readable flag inside of unity if you check it.
In 3.4 the inspector was slightly bugged and pretended that you can change stuff, 3.5 b6 (dev preview) finally shows you a blank inspector beside the preview
Basically if you use PVR then the PVR is what you have and what you will use, point.
Its the only format where Unity does not give you the possibility to change anything. (the only other limited format is PSD where you get no activation / deactivation control over the layers upon flat baking on import inside of unity)