Skip to content

Commit 3008ac5

Browse files
authored
Merge pull request #2403 from tonihele/bugfix/issue-2296
Improved fix for IndexOutOfBoundsException
2 parents 36c4d5a + 8da632a commit 3008ac5

File tree

1 file changed

+23
-27
lines changed

1 file changed

+23
-27
lines changed

jme3-core/src/main/java/com/jme3/scene/BatchNode.java

Lines changed: 23 additions & 27 deletions
Original file line numberDiff line numberDiff line change
@@ -31,15 +31,6 @@
3131
*/
3232
package com.jme3.scene;
3333

34-
import java.nio.Buffer;
35-
import java.nio.FloatBuffer;
36-
import java.util.ArrayList;
37-
import java.util.HashMap;
38-
import java.util.List;
39-
import java.util.Map;
40-
import java.util.logging.Level;
41-
import java.util.logging.Logger;
42-
4334
import com.jme3.collision.Collidable;
4435
import com.jme3.collision.CollisionResults;
4536
import com.jme3.material.Material;
@@ -50,6 +41,14 @@
5041
import com.jme3.util.TempVars;
5142
import com.jme3.util.clone.Cloner;
5243
import com.jme3.util.clone.JmeCloneable;
44+
import java.nio.Buffer;
45+
import java.nio.FloatBuffer;
46+
import java.util.ArrayList;
47+
import java.util.HashMap;
48+
import java.util.List;
49+
import java.util.Map;
50+
import java.util.logging.Level;
51+
import java.util.logging.Logger;
5352

5453
/**
5554
* BatchNode holds geometries that are a batched version of all the geometries that are in its sub scenegraph.
@@ -188,6 +187,11 @@ protected void doBatch() {
188187
Map<Material, List<Geometry>> matMap = new HashMap<>();
189188
int nbGeoms = 0;
190189

190+
// Recalculate the maxVertCount during gatherGeometries() so it's always
191+
// accurate. Keep track of what it used to be so we know if temp arrays need
192+
// to be reallocated.
193+
int oldMaxVertCount = maxVertCount;
194+
maxVertCount = 0;
191195
gatherGeometries(matMap, this, needsFullRebatch);
192196
if (needsFullRebatch) {
193197
for (Batch batch : batches.getArray()) {
@@ -196,10 +200,6 @@ protected void doBatch() {
196200
batches.clear();
197201
batchesByGeom.clear();
198202
}
199-
//only reset maxVertCount if there is something new to batch
200-
if (matMap.size() > 0) {
201-
maxVertCount = 0;
202-
}
203203

204204
for (Map.Entry<Material, List<Geometry>> entry : matMap.entrySet()) {
205205
Mesh m = new Mesh();
@@ -244,8 +244,8 @@ protected void doBatch() {
244244
logger.log(Level.FINE, "Batched {0} geometries in {1} batches.", new Object[]{nbGeoms, batches.size()});
245245
}
246246

247-
//init the temp arrays if something has been batched only.
248-
if (matMap.size() > 0) {
247+
//init the temp arrays if the size has changed
248+
if (oldMaxVertCount != maxVertCount) {
249249
initTempFloatArrays();
250250
}
251251
}
@@ -285,6 +285,13 @@ private void gatherGeometries(Map<Material, List<Geometry>> map, Spatial n, bool
285285

286286
if (!isBatch(n) && n.getBatchHint() != BatchHint.Never) {
287287
Geometry g = (Geometry) n;
288+
289+
// Need to recalculate the max vert count whether we are rebatching this
290+
// particular geometry or not.
291+
if (maxVertCount < g.getVertexCount()) {
292+
maxVertCount = g.getVertexCount();
293+
}
294+
288295
if (!g.isGrouped() || rebatch) {
289296
if (g.getMaterial() == null) {
290297
throw new IllegalStateException("No material is set for Geometry: " + g.getName() + " please set a material before batching");
@@ -385,11 +392,8 @@ private void mergeGeometries(Mesh outMesh, List<Geometry> geometries) {
385392
totalVerts += geom.getVertexCount();
386393
totalTris += geom.getTriangleCount();
387394
totalLodLevels = Math.min(totalLodLevels, geom.getMesh().getNumLodLevels());
388-
if (maxVertCount < geom.getVertexCount()) {
389-
maxVertCount = geom.getVertexCount();
390-
}
395+
391396
Mesh.Mode listMode;
392-
//float listLineWidth = 1f;
393397
int components;
394398
switch (geom.getMesh().getMode()) {
395399
case Points:
@@ -530,7 +534,6 @@ private void doTransforms(FloatBuffer bindBufPos, FloatBuffer bindBufNorm, Float
530534
Vector3f norm = vars.vect2;
531535
Vector3f tan = vars.vect3;
532536

533-
validateTempFloatArrays(end - start);
534537
int length = (end - start) * 3;
535538
int tanLength = (end - start) * 4;
536539

@@ -611,13 +614,6 @@ private void doTransforms(FloatBuffer bindBufPos, FloatBuffer bindBufNorm, Float
611614
}
612615
}
613616

614-
private void validateTempFloatArrays(int vertCount) {
615-
if (maxVertCount < vertCount) {
616-
maxVertCount = vertCount;
617-
initTempFloatArrays();
618-
}
619-
}
620-
621617
private void initTempFloatArrays() {
622618
//TODO these arrays should be allocated by chunk instead to avoid recreating them each time the batch is changed.
623619
tmpFloat = new float[maxVertCount * 3];

0 commit comments

Comments
 (0)