changed terrain to use a ShortBuffer if the index count is less than 65535 so it can work on more android devices

git-svn-id: https://jmonkeyengine.googlecode.com/svn/trunk@10065 75d07b2b-3a1a-0410-a2c5-0572b91ccdca
3.0
bre..om 12 years ago
parent 4f02b407cf
commit 4bbbf7dbe8
  1. 76
      engine/src/terrain/com/jme3/terrain/geomipmap/LODGeomap.java
  2. 26
      engine/src/terrain/com/jme3/terrain/geomipmap/TerrainPatch.java
  3. 11
      engine/src/terrain/com/jme3/terrain/geomipmap/UpdatedTerrainPatch.java
  4. 10
      engine/src/terrain/com/jme3/terrain/geomipmap/lodcalc/util/EntropyComputeUtil.java

@ -40,14 +40,18 @@ import com.jme3.math.Vector3f;
import com.jme3.scene.Mesh; import com.jme3.scene.Mesh;
import com.jme3.scene.Mesh.Mode; import com.jme3.scene.Mesh.Mode;
import com.jme3.scene.VertexBuffer.Type; import com.jme3.scene.VertexBuffer.Type;
import com.jme3.scene.mesh.IndexBuffer;
import com.jme3.terrain.GeoMap; import com.jme3.terrain.GeoMap;
import com.jme3.util.BufferUtils; import com.jme3.util.BufferUtils;
import com.jme3.util.TempVars; import com.jme3.util.TempVars;
import java.io.IOException; import java.io.IOException;
import java.nio.Buffer;
import java.nio.BufferOverflowException; import java.nio.BufferOverflowException;
import java.nio.BufferUnderflowException; import java.nio.BufferUnderflowException;
import java.nio.FloatBuffer; import java.nio.FloatBuffer;
import java.nio.IntBuffer; import java.nio.IntBuffer;
import java.nio.ShortBuffer;
import org.bushe.swing.event.Logger;
/** /**
* Produces the mesh for the TerrainPatch. * Produces the mesh for the TerrainPatch.
@ -84,7 +88,12 @@ public class LODGeomap extends GeoMap {
FloatBuffer pb = writeVertexArray(null, scale, center); FloatBuffer pb = writeVertexArray(null, scale, center);
FloatBuffer texb = writeTexCoordArray(null, tcOffset, tcScale, offsetAmount, totalSize); FloatBuffer texb = writeTexCoordArray(null, tcOffset, tcScale, offsetAmount, totalSize);
FloatBuffer nb = writeNormalArray(null, scale); FloatBuffer nb = writeNormalArray(null, scale);
IntBuffer ib = writeIndexArrayLodDiff(null, lod, rightLod, topLod, leftLod, bottomLod); Buffer ib;
IndexBuffer idxB = writeIndexArrayLodDiff(lod, rightLod, topLod, leftLod, bottomLod, totalSize);
if (idxB.getBuffer() instanceof IntBuffer)
ib = (IntBuffer)idxB.getBuffer();
else
ib = (ShortBuffer)idxB.getBuffer();
FloatBuffer bb = BufferUtils.createFloatBuffer(getWidth() * getHeight() * 3); FloatBuffer bb = BufferUtils.createFloatBuffer(getWidth() * getHeight() * 3);
FloatBuffer tanb = BufferUtils.createFloatBuffer(getWidth() * getHeight() * 3); FloatBuffer tanb = BufferUtils.createFloatBuffer(getWidth() * getHeight() * 3);
writeTangentArray(nb, tanb, bb, texb, scale); writeTangentArray(nb, tanb, bb, texb, scale);
@ -95,7 +104,10 @@ public class LODGeomap extends GeoMap {
m.setBuffer(Type.Tangent, 3, tanb); m.setBuffer(Type.Tangent, 3, tanb);
m.setBuffer(Type.Binormal, 3, bb); m.setBuffer(Type.Binormal, 3, bb);
m.setBuffer(Type.TexCoord, 2, texb); m.setBuffer(Type.TexCoord, 2, texb);
m.setBuffer(Type.Index, 3, ib); if (ib instanceof IntBuffer)
m.setBuffer(Type.Index, 3, (IntBuffer)ib);
else if (ib instanceof ShortBuffer)
m.setBuffer(Type.Index, 3, (ShortBuffer)ib);
m.setStatic(); m.setStatic();
m.updateBound(); m.updateBound();
return m; return m;
@ -151,17 +163,13 @@ public class LODGeomap extends GeoMap {
* @param bottomLod LOD of the bottom neighbour * @param bottomLod LOD of the bottom neighbour
* @return the LOD-ified index buffer * @return the LOD-ified index buffer
*/ */
public IntBuffer writeIndexArrayLodDiff(IntBuffer store, int lod, boolean rightLod, boolean topLod, boolean leftLod, boolean bottomLod) { public IndexBuffer writeIndexArrayLodDiff(int lod, boolean rightLod, boolean topLod, boolean leftLod, boolean bottomLod, int totalSize) {
//if (true)
//return writeIndexArrayLodVariable(store, lod, height, lod, lod, lod);
IntBuffer buffer2 = store;
int numIndexes = calculateNumIndexesLodDiff(lod); int numIndexes = calculateNumIndexesLodDiff(lod);
if (store == null) {
buffer2 = BufferUtils.createIntBuffer(numIndexes); IndexBuffer ib = IndexBuffer.createIndexBuffer(numIndexes, numIndexes);
} VerboseBuffer buffer = new VerboseBuffer(ib);
VerboseIntBuffer buffer = new VerboseIntBuffer(buffer2);
// generate center squares minus the edges // generate center squares minus the edges
@ -357,14 +365,12 @@ public class LODGeomap extends GeoMap {
return buffer.delegate; return buffer.delegate;
} }
public IntBuffer writeIndexArrayLodVariable(IntBuffer store, int lod, int rightLod, int topLod, int leftLod, int bottomLod) { public IndexBuffer writeIndexArrayLodVariable(int lod, int rightLod, int topLod, int leftLod, int bottomLod, int totalSize) {
IntBuffer buffer2 = store;
int numIndexes = calculateNumIndexesLodDiff(lod); int numIndexes = calculateNumIndexesLodDiff(lod);
if (store == null) {
buffer2 = BufferUtils.createIntBuffer(numIndexes); IndexBuffer ib = IndexBuffer.createIndexBuffer(numIndexes, numIndexes);
} VerboseBuffer buffer = new VerboseBuffer(ib);
VerboseIntBuffer buffer = new VerboseIntBuffer(buffer2);
// generate center squares minus the edges // generate center squares minus the edges
@ -908,25 +914,47 @@ public class LODGeomap extends GeoMap {
/** /**
* Keeps a count of the number of indexes, good for debugging * Keeps a count of the number of indexes, good for debugging
*/ */
public class VerboseIntBuffer { public class VerboseBuffer {
private IntBuffer delegate; private IndexBuffer delegate;
//private IntBuffer delegateInt;
//private ShortBuffer delegateShort;
int count = 0; int count = 0;
//private boolean intb = true;
public VerboseIntBuffer(IntBuffer d) { public VerboseBuffer(IndexBuffer d) {
delegate = d; this.delegate = d;
} }
/*public VerboseBuffer(Buffer d) {
if (d instanceof IntBuffer)
delegateInt = (IntBuffer)d;
else if (d instanceof ShortBuffer) {
delegateShort = (ShortBuffer)d;
intb = false;
}
}*/
public void put(int value) { public void put(int value) {
delegate.put(count, value);
count++;
}
/*public void put(int value) {
try { try {
count++; count++;
if (count > delegate.limit()) int limit = intb? delegateInt.limit() : delegateShort.limit();
if (count > limit)
throw new BufferOverflowException(); throw new BufferOverflowException();
delegate.put(value); if (intb)
} catch (BufferOverflowException e) { delegateInt.put(value);
System.out.println("err buffer size: "+delegate.capacity()); else {
System.out.println(Integer.toString(value)+" "+Short.toString((short)value));
delegateShort.put((short)value);
} }
} catch (BufferOverflowException e) {
Logger.getLogger(this.getClass().getName()).log(Logger.Level.ERROR, "err buffer size: "+delegateInt.capacity());
} }
}*/
public int getCount() { public int getCount() {
return count; return count;

@ -46,12 +46,15 @@ import com.jme3.scene.Geometry;
import com.jme3.scene.Mesh; import com.jme3.scene.Mesh;
import com.jme3.scene.VertexBuffer; import com.jme3.scene.VertexBuffer;
import com.jme3.scene.VertexBuffer.Type; import com.jme3.scene.VertexBuffer.Type;
import com.jme3.scene.mesh.IndexBuffer;
import com.jme3.terrain.geomipmap.TerrainQuad.LocationHeight; import com.jme3.terrain.geomipmap.TerrainQuad.LocationHeight;
import com.jme3.terrain.geomipmap.lodcalc.util.EntropyComputeUtil; import com.jme3.terrain.geomipmap.lodcalc.util.EntropyComputeUtil;
import com.jme3.util.BufferUtils; import com.jme3.util.BufferUtils;
import java.io.IOException; import java.io.IOException;
import java.nio.Buffer;
import java.nio.FloatBuffer; import java.nio.FloatBuffer;
import java.nio.IntBuffer; import java.nio.IntBuffer;
import java.nio.ShortBuffer;
import java.util.HashMap; import java.util.HashMap;
import java.util.List; import java.util.List;
@ -195,8 +198,13 @@ public class TerrainPatch extends Geometry {
float[] entropies = new float[getMaxLod()+1]; float[] entropies = new float[getMaxLod()+1];
for (int i = 0; i <= getMaxLod(); i++){ for (int i = 0; i <= getMaxLod(); i++){
int curLod = (int) Math.pow(2, i); int curLod = (int) Math.pow(2, i);
IntBuffer buf = geomap.writeIndexArrayLodDiff(null, curLod, false, false, false, false); IndexBuffer idxB = geomap.writeIndexArrayLodDiff(curLod, false, false, false, false, totalSize);
entropies[i] = EntropyComputeUtil.computeLodEntropy(mesh, buf); Buffer ib;
if (idxB.getBuffer() instanceof IntBuffer)
ib = (IntBuffer)idxB.getBuffer();
else
ib = (ShortBuffer)idxB.getBuffer();
entropies[i] = EntropyComputeUtil.computeLodEntropy(mesh, ib);
} }
lodEntropy = entropies; lodEntropy = entropies;
@ -243,12 +251,18 @@ public class TerrainPatch extends Geometry {
boolean right = utp.getRightLod() > utp.getNewLod(); boolean right = utp.getRightLod() > utp.getNewLod();
boolean bottom = utp.getBottomLod() > utp.getNewLod(); boolean bottom = utp.getBottomLod() > utp.getNewLod();
IntBuffer ib = null; IndexBuffer idxB;
if (useVariableLod) if (useVariableLod)
ib = geomap.writeIndexArrayLodVariable(null, pow, (int) Math.pow(2, utp.getRightLod()), (int) Math.pow(2, utp.getTopLod()), (int) Math.pow(2, utp.getLeftLod()), (int) Math.pow(2, utp.getBottomLod())); idxB = geomap.writeIndexArrayLodVariable(pow, (int) Math.pow(2, utp.getRightLod()), (int) Math.pow(2, utp.getTopLod()), (int) Math.pow(2, utp.getLeftLod()), (int) Math.pow(2, utp.getBottomLod()), totalSize);
else
idxB = geomap.writeIndexArrayLodDiff(pow, right, top, left, bottom, totalSize);
Buffer b;
if (idxB.getBuffer() instanceof IntBuffer)
b = (IntBuffer)idxB.getBuffer();
else else
ib = geomap.writeIndexArrayLodDiff(null, pow, right, top, left, bottom); b = (ShortBuffer)idxB.getBuffer();
utp.setNewIndexBuffer(ib); utp.setNewIndexBuffer(b);
} }
} }

@ -32,7 +32,9 @@
package com.jme3.terrain.geomipmap; package com.jme3.terrain.geomipmap;
import com.jme3.scene.VertexBuffer.Type; import com.jme3.scene.VertexBuffer.Type;
import java.nio.Buffer;
import java.nio.IntBuffer; import java.nio.IntBuffer;
import java.nio.ShortBuffer;
/** /**
* Stores a terrain patch's details so the LOD background thread can update * Stores a terrain patch's details so the LOD background thread can update
@ -47,7 +49,7 @@ public class UpdatedTerrainPatch {
private int newLod; private int newLod;
private int previousLod; private int previousLod;
private int rightLod,topLod,leftLod,bottomLod; private int rightLod,topLod,leftLod,bottomLod;
private IntBuffer newIndexBuffer; private Buffer newIndexBuffer;
//private boolean reIndexNeeded = false; //private boolean reIndexNeeded = false;
private boolean fixEdges = false; private boolean fixEdges = false;
@ -93,7 +95,7 @@ public class UpdatedTerrainPatch {
return newIndexBuffer; return newIndexBuffer;
}*/ }*/
protected void setNewIndexBuffer(IntBuffer newIndexBuffer) { protected void setNewIndexBuffer(Buffer newIndexBuffer) {
this.newIndexBuffer = newIndexBuffer; this.newIndexBuffer = newIndexBuffer;
} }
@ -174,7 +176,10 @@ public class UpdatedTerrainPatch {
if (newIndexBuffer != null && isReIndexNeeded()) { if (newIndexBuffer != null && isReIndexNeeded()) {
updatedPatch.setPreviousLod(previousLod); updatedPatch.setPreviousLod(previousLod);
updatedPatch.getMesh().clearBuffer(Type.Index); updatedPatch.getMesh().clearBuffer(Type.Index);
updatedPatch.getMesh().setBuffer(Type.Index, 3, newIndexBuffer); if (newIndexBuffer instanceof IntBuffer)
updatedPatch.getMesh().setBuffer(Type.Index, 3, (IntBuffer)newIndexBuffer);
else if (newIndexBuffer instanceof ShortBuffer)
updatedPatch.getMesh().setBuffer(Type.Index, 3, (ShortBuffer)newIndexBuffer);
} }
} }

@ -40,8 +40,10 @@ import com.jme3.scene.Mesh;
import com.jme3.scene.VertexBuffer; import com.jme3.scene.VertexBuffer;
import com.jme3.scene.VertexBuffer.Type; import com.jme3.scene.VertexBuffer.Type;
import com.jme3.util.BufferUtils; import com.jme3.util.BufferUtils;
import java.nio.Buffer;
import java.nio.FloatBuffer; import java.nio.FloatBuffer;
import java.nio.IntBuffer; import java.nio.IntBuffer;
import java.nio.ShortBuffer;
/** /**
* Computes the entropy value δ (delta) for a given terrain block and * Computes the entropy value δ (delta) for a given terrain block and
@ -53,7 +55,7 @@ import java.nio.IntBuffer;
*/ */
public class EntropyComputeUtil { public class EntropyComputeUtil {
public static float computeLodEntropy(Mesh terrainBlock, IntBuffer lodIndices){ public static float computeLodEntropy(Mesh terrainBlock, Buffer lodIndices){
// Bounding box for the terrain block // Bounding box for the terrain block
BoundingBox bbox = (BoundingBox) terrainBlock.getBound(); BoundingBox bbox = (BoundingBox) terrainBlock.getBound();
@ -72,7 +74,11 @@ public class EntropyComputeUtil {
VertexBuffer originalIndices = terrainBlock.getBuffer(Type.Index); VertexBuffer originalIndices = terrainBlock.getBuffer(Type.Index);
terrainBlock.clearBuffer(Type.Index); terrainBlock.clearBuffer(Type.Index);
terrainBlock.setBuffer(Type.Index, 3, lodIndices); if (lodIndices instanceof IntBuffer)
terrainBlock.setBuffer(Type.Index, 3, (IntBuffer)lodIndices);
else if (lodIndices instanceof ShortBuffer) {
terrainBlock.setBuffer(Type.Index, 3, (ShortBuffer) lodIndices);
}
// Recalculate collision mesh // Recalculate collision mesh
terrainBlock.createCollisionData(); terrainBlock.createCollisionData();

Loading…
Cancel
Save