I have a ARGB float texture that contains data. One of the data entries is an index that points to another pixel in the texture.
This is the code decoding the index into a UV coordinate, which can be used with a texelfetch to read the pixel it points to:
ivec2 getTexelfetchCoord_TEXTURE(float index)
{
return ivec2( mod(index, TEXTURE_WIDTH), int(index / TEXTURE_WIDTH) );
}
This works fine as long as the texture is no larger than 4096x4096. Any larger than that, and the floating point index value becomes inaccurate due to float precision issues.
The problem is that the 32 bit floating point only uses 24 bit for the integer part, which means the U and V components only have 12 bits each. 2^12=4096, alas the max range is 4096. Using the sign I could extend this to 8192, but that is still not enough for my purpose.
The obvious solution would be to store the index as two separate entries, U and V coordinates. However, for reasons that are too complex to get into here, this option is not available to me.
So, I wonder, is there a way to pack a signed 32 bit integer into a float, and unpack it back into an int that has the full 32 bit precision? Actually, I am not even sure if int's in OpenGL are really 32 bit, or if they are in fact internally stored as floats with the same 24 bit range...
Basically I would like to pack UV coordinates into a single float, and unpack to an UV coordinate again, with an accurate range beyond 4096x4096. Is this possible in GLSL?