jmonkeyengine
jmonkeyengine copied to clipboard
BinaryExporter resets buffer positions to 0 when writing them.
When a buffer or buffer arraylist is written using BinaryExporter, the buffer's position gets reset to zero. XMLExporter handles this by restoring the old position after writing. This seems easy enough to fix. It does however bring up another issue currently masked by the position clobbering: shouldn't the position also be serialized? If a buffer with a non-zero position is serialized and the position is preserved, the deserialized buffer will not equals() the original because it will have a zero position. I can easily fix this for XMLExporter with an additional attribute, but from my brief look at BinaryOutputCapsule, it looks like this can't be changed because only one int (length) is expected before the start of the contents.
BinaryExportBufferPositionMRE.java
package com.mygame;
import com.jme3.export.JmeExporter;
import com.jme3.export.JmeImporter;
import com.jme3.export.OutputCapsule;
import com.jme3.export.Savable;
import com.jme3.export.binary.BinaryExporter;
import java.io.IOException;
import java.io.OutputStream;
import java.nio.ByteBuffer;
import org.lwjgl.BufferUtils;
public class BinaryExportBufferPositionMRE
{
static class SavableWithBuffer implements Savable
{
@Override
public void write(JmeExporter je) throws IOException
{
ByteBuffer bb = BufferUtils.createByteBuffer(16);
bb.position(4);
OutputCapsule capsule = je.getCapsule(this);
capsule.write(bb, "buffer", null);
if(bb.position() != 4)
{
throw new IOException("Expected buffer position 4, got position: " + bb.position());
}
}
@Override
public void read(JmeImporter ji) throws IOException
{
}
}
public static void main(String[] args)
{
BinaryExporter be = BinaryExporter.getInstance();
try
{
be.save(new SavableWithBuffer(), OutputStream.nullOutputStream());
} catch(IOException e)
{
System.err.println(e);
}
}
}
JMonkeyEngine is often selective about which attributes it serializes. Buffer position is ignored in many contexts, so I think it's acceptable to skip serializing it. In contexts where the position is significant, developers can serialize it explicitly.
Similar arguments could be made about serializing a buffer's mark, limit, byte order, and whether it's read-only and/or direct.
It would be good to document (in the javadoc) which attributes of a buffer are automatically serialized.
Gotcha. I have changed the behavior for XMLExporter to save the position in the referenced PR, so I'll need to revise that.