1 /*
2  * $RCSfile: GeometryInfoGenerator.java,v $
3  *
4  * Copyright (c) 2007 Sun Microsystems, Inc. All rights reserved.
5  *
6  * Redistribution and use in source and binary forms, with or without
7  * modification, are permitted provided that the following conditions
8  * are met:
9  *
10  * - Redistribution of source code must retain the above copyright
11  *   notice, this list of conditions and the following disclaimer.
12  *
13  * - Redistribution in binary form must reproduce the above copyright
14  *   notice, this list of conditions and the following disclaimer in
15  *   the documentation and/or other materials provided with the
16  *   distribution.
17  *
18  * Neither the name of Sun Microsystems, Inc. or the names of
19  * contributors may be used to endorse or promote products derived
20  * from this software without specific prior written permission.
21  *
22  * This software is provided "AS IS," without a warranty of any
23  * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND
24  * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY,
25  * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY
26  * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL
27  * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF
28  * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS
29  * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR
30  * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL,
31  * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND
32  * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR
33  * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE
34  * POSSIBILITY OF SUCH DAMAGES.
35  *
36  * You acknowledge that this software is not designed, licensed or
37  * intended for use in the design, construction, operation or
38  * maintenance of any nuclear facility.
39  *
40  * $Revision: 1.4 $
41  * $Date: 2007/02/09 17:20:19 $
42  * $State: Exp $
43  */
44 
45 package com.sun.j3d.utils.geometry;
46 
47 import javax.media.j3d.GeometryArray;
48 import javax.media.j3d.GeometryStripArray;
49 import javax.media.j3d.TriangleFanArray;
50 import javax.media.j3d.TriangleStripArray;
51 import javax.media.j3d.TriangleArray;
52 import javax.media.j3d.QuadArray;
53 import javax.media.j3d.IndexedGeometryArray;
54 import javax.media.j3d.IndexedGeometryStripArray;
55 import javax.media.j3d.IndexedQuadArray;
56 import javax.media.j3d.IndexedTriangleArray;
57 import javax.media.j3d.IndexedTriangleFanArray;
58 import javax.media.j3d.IndexedTriangleStripArray;
59 import javax.vecmath.*;
60 import com.sun.j3d.utils.geometry.GeometryInfo;
61 import com.sun.j3d.internal.J3dUtilsI18N;
62 import com.sun.j3d.internal.BufferWrapper;
63 import com.sun.j3d.internal.ByteBufferWrapper;
64 import com.sun.j3d.internal.FloatBufferWrapper;
65 import com.sun.j3d.internal.DoubleBufferWrapper;
66 import javax.media.j3d.J3DBuffer;
67 
68 
69 
70 /**
71  * Populate a GeometryInfo object from the Geometry provided.  Used
72  * by GeometryInfo.
73  */
74 class GeometryInfoGenerator extends Object {
75 
create(GeometryInfo geomInfo, GeometryArray geomArray)76   public static void create(GeometryInfo geomInfo, GeometryArray geomArray)
77   {
78     if (geomArray instanceof GeometryStripArray)
79       create(geomInfo, (GeometryStripArray)geomArray);
80     else if (geomArray instanceof TriangleArray) {
81       geomInfo.reset(GeometryInfo.TRIANGLE_ARRAY);
82       processGeometryArray(geomInfo, geomArray);
83     } else if (geomArray instanceof QuadArray) {
84       geomInfo.reset(GeometryInfo.QUAD_ARRAY);
85       processGeometryArray(geomInfo, geomArray);
86     } else if (geomArray instanceof IndexedGeometryArray)
87       create(geomInfo, (IndexedGeometryArray)geomArray);
88     else throw new IllegalArgumentException(
89       J3dUtilsI18N.getString("GeometryInfoGenerator0"));
90   } // End of create(GeometryInfo, GeometryArray)
91 
92 
93 
create(GeometryInfo geomInfo, GeometryStripArray geomArray)94   private static void create(GeometryInfo geomInfo,
95 			     GeometryStripArray geomArray)
96   {
97     if (geomArray instanceof TriangleFanArray) {
98       geomInfo.reset(GeometryInfo.TRIANGLE_FAN_ARRAY);
99     } else if (geomArray instanceof TriangleStripArray) {
100       geomInfo.reset(GeometryInfo.TRIANGLE_STRIP_ARRAY);
101     } else throw new IllegalArgumentException(
102       J3dUtilsI18N.getString("GeometryInfoGenerator0"));
103 
104     processGeometryArray(geomInfo, geomArray);
105     processStripArray(geomInfo, geomArray);
106   } // End of create(GeometryInfo, GeometryStripArray)
107 
108 
109 
create(GeometryInfo geomInfo, IndexedGeometryArray geomArray)110   private static void create(GeometryInfo geomInfo,
111 			     IndexedGeometryArray geomArray)
112   {
113     if (geomArray instanceof IndexedQuadArray) {
114       geomInfo.reset(GeometryInfo.QUAD_ARRAY);
115     } else if (geomArray instanceof IndexedTriangleArray) {
116       geomInfo.reset(GeometryInfo.TRIANGLE_ARRAY);
117     } else if (geomArray instanceof IndexedTriangleFanArray) {
118       geomInfo.reset(GeometryInfo.TRIANGLE_FAN_ARRAY);
119       processIndexStripArray(geomInfo, (IndexedGeometryStripArray)geomArray);
120     } else if (geomArray instanceof IndexedTriangleStripArray) {
121       geomInfo.reset(GeometryInfo.TRIANGLE_STRIP_ARRAY);
122       processIndexStripArray(geomInfo, (IndexedGeometryStripArray)geomArray);
123     }
124 
125     processGeometryArray(geomInfo, geomArray);
126     processIndexedArray(geomInfo, geomArray);
127   } // End of create(GeometryInfo, IndexedGeometryArray)
128 
129 
130 
processGeometryArray(GeometryInfo geomInfo, GeometryArray geomArray)131   private static void processGeometryArray(GeometryInfo geomInfo,
132 					   GeometryArray geomArray)
133   {
134     int i, j;
135     int vertexFormat = geomArray.getVertexFormat();
136     int texSets = geomArray.getTexCoordSetCount();
137     int valid;
138 
139     // Calculate validVertexCount
140     if (geomArray instanceof GeometryStripArray) {
141       // Does not include IndexedGeometryStripArray
142       GeometryStripArray gsa = (GeometryStripArray)geomArray;
143       int[] strips = new int[gsa.getNumStrips()];
144       gsa.getStripVertexCounts(strips);
145       valid = 0;
146       for (i = 0 ; i < strips.length ; i++) {
147 	valid += strips[i];
148       }
149     } else if (geomArray instanceof IndexedGeometryArray) {
150       valid = geomArray.getVertexCount();
151     } else valid = geomArray.getValidVertexCount();
152 
153     if ((vertexFormat & GeometryArray.INTERLEAVED) != 0) {
154 
155       // Calculate words_per_vertex (wpv)
156       int wpv = 3;			// Always have coordinate data
157       if ((vertexFormat & GeometryArray.NORMALS) != 0) wpv += 3;
158       if ((vertexFormat & GeometryArray.COLOR_4) == GeometryArray.COLOR_4)
159 	wpv += 4;
160       else if ((vertexFormat & GeometryArray.COLOR_3) != 0) wpv += 3;
161       if ((vertexFormat & GeometryArray.TEXTURE_COORDINATE_2) != 0)
162 	wpv += 2 * texSets;
163       else if ((vertexFormat & GeometryArray.TEXTURE_COORDINATE_3) != 0)
164 	wpv += 3 * texSets;
165       else if ((vertexFormat & GeometryArray.TEXTURE_COORDINATE_4) != 0)
166 	wpv += 4 * texSets;
167 
168       int initial;
169       if (!(geomArray instanceof IndexedGeometryArray)) {
170 	initial = geomArray.getInitialVertexIndex();
171       } else initial = 0;
172 
173       float[] d;
174       if ((vertexFormat & GeometryArray.USE_NIO_BUFFER) != 0) {
175 	J3DBuffer b = geomArray.getInterleavedVertexBuffer();
176 	FloatBufferWrapper w = new FloatBufferWrapper(b);
177 	d = new float[w.limit()];
178 	w.position( 0 );
179 	w.get(d);
180       } else d = geomArray.getInterleavedVertices();
181 
182       int offset = 0;
183       if ((vertexFormat & GeometryArray.TEXTURE_COORDINATE_2) != 0) {
184 	geomInfo.setTextureCoordinateParams(texSets, 2);
185 	int[] map = new int[geomArray.getTexCoordSetMapLength()];
186 	geomArray.getTexCoordSetMap(map);
187 	geomInfo.setTexCoordSetMap(map);
188 	for (i = 0 ; i < texSets ; i++) {
189 	  TexCoord2f[] tex = new TexCoord2f[valid];
190 	  for (j = 0 ; j < valid ; j++) {
191 	    tex[j] = new TexCoord2f(d[wpv * (j + initial) + offset],
192 				    d[wpv * (j + initial) + offset + 1]);
193 	  }
194 	  geomInfo.setTextureCoordinates(i, tex);
195 	  offset += 2;
196 	}
197       } else if ((vertexFormat & GeometryArray.TEXTURE_COORDINATE_3) != 0) {
198 	geomInfo.setTextureCoordinateParams(texSets, 3);
199 	int[] map = new int[geomArray.getTexCoordSetMapLength()];
200 	geomArray.getTexCoordSetMap(map);
201 	geomInfo.setTexCoordSetMap(map);
202 	for (i = 0 ; i < texSets ; i++) {
203 	  TexCoord3f[] tex = new TexCoord3f[valid];
204 	  for (j = 0 ; j < valid ; j++) {
205 	    tex[j] = new TexCoord3f(d[wpv * (j + initial) + offset],
206 				    d[wpv * (j + initial) + offset + 1],
207 				    d[wpv * (j + initial) + offset + 2]);
208 	  }
209 	  geomInfo.setTextureCoordinates(i, tex);
210 	  offset += 3;
211 	}
212       } else if ((vertexFormat & GeometryArray.TEXTURE_COORDINATE_4) != 0) {
213 	geomInfo.setTextureCoordinateParams(texSets, 4);
214 	int[] map = new int[geomArray.getTexCoordSetMapLength()];
215 	geomArray.getTexCoordSetMap(map);
216 	geomInfo.setTexCoordSetMap(map);
217 	for (i = 0 ; i < texSets ; i++) {
218 	  TexCoord4f[] tex = new TexCoord4f[valid];
219 	  for (j = 0 ; j < valid ; j++) {
220 	    tex[j] = new TexCoord4f(d[wpv * (j + initial) + offset],
221 				    d[wpv * (j + initial) + offset + 1],
222 				    d[wpv * (j + initial) + offset + 2],
223 				    d[wpv * (j + initial) + offset + 3]);
224 	  }
225 	  geomInfo.setTextureCoordinates(i, tex);
226 	  offset += 4;
227 	}
228       }
229 
230       if ((vertexFormat & GeometryArray.COLOR_4) == GeometryArray.COLOR_4) {
231 	Color4f[] color = new Color4f[valid];
232 	for (i = 0 ; i < valid ; i++) {
233 	  color[i] = new Color4f(d[wpv * (i + initial) + offset],
234 				 d[wpv * (i + initial) + offset + 1],
235 				 d[wpv * (i + initial) + offset + 2],
236 				 d[wpv * (i + initial) + offset + 3]);
237 	}
238 	geomInfo.setColors(color);
239 	offset += 4;
240       } else if ((vertexFormat & GeometryArray.COLOR_3) != 0) {
241 	Color3f[] color = new Color3f[valid];
242 	for (i = 0 ; i < valid ; i++) {
243 	  color[i] = new Color3f(d[wpv * (i + initial) + offset],
244 				 d[wpv * (i + initial) + offset + 1],
245 				 d[wpv * (i + initial) + offset + 2]);
246 	}
247 	geomInfo.setColors(color);
248 	offset += 3;
249       }
250 
251       if ((vertexFormat & GeometryArray.NORMALS) != 0) {
252 	Vector3f[] normals = new Vector3f[valid];
253 	for (i = 0 ; i < valid ; i++) {
254 	  normals[i] = new Vector3f(d[wpv * (i + initial) + offset],
255 				    d[wpv * (i + initial) + offset + 1],
256 				    d[wpv * (i + initial) + offset + 2]);
257 	}
258 	geomInfo.setNormals(normals);
259 	offset += 3;
260       }
261 
262       Point3f[] coords = new Point3f[valid];
263       for (i = 0 ; i < valid ; i++) {
264 	coords[i] = new Point3f(d[wpv * (i + initial) + offset],
265 				d[wpv * (i + initial) + offset + 1],
266 				d[wpv * (i + initial) + offset + 2]);
267       }
268       geomInfo.setCoordinates(coords);
269     } else {
270       // Data is not INTERLEAVED
271       boolean byRef = ((vertexFormat & GeometryArray.BY_REFERENCE) != 0 );
272       boolean nio = ((vertexFormat & GeometryArray.USE_NIO_BUFFER) != 0 );
273 
274       Point3f[] coords = null;
275       if (byRef) {
276 
277 	int initial;
278 	if (!(geomArray instanceof IndexedGeometryArray)) {
279 	  initial = geomArray.getInitialCoordIndex();
280 	} else initial = 0;
281 
282 	if ( nio ) {
283 	  J3DBuffer buf = geomArray.getCoordRefBuffer();
284 
285 	  switch (BufferWrapper.getBufferType(buf)) {
286 
287 	  case BufferWrapper.TYPE_FLOAT: {
288 	    FloatBufferWrapper bb = new FloatBufferWrapper(buf);
289 	    float[] c = new float[valid * 3];
290 	    bb.position(initial * 3);
291 	    bb.get(c, 0, valid * 3);
292 	    coords = new Point3f[valid];
293 	    for (i = 0 ; i < valid ; i++) {
294 	      coords[i] = new Point3f(c[i * 3 + 0],
295 				      c[i * 3 + 1],
296 				      c[i * 3 + 2]);
297 	    }
298 	  }
299 	  break;
300 
301 	  case BufferWrapper.TYPE_DOUBLE: {
302 	    DoubleBufferWrapper bb = new DoubleBufferWrapper( buf );
303 	    double[] c = new double[valid * 3];
304 	    bb.position(initial * 3);
305 	    bb.get(c, 0, valid * 3);
306 	    coords = new Point3f[valid];
307 	    for (i = 0 ; i < valid ; i++) {
308 	      coords[i] = new Point3f((float)(c[i * 3 + 0]),
309 				      (float)(c[i * 3 + 1]),
310 				      (float)(c[i * 3 + 2]));
311 	    }
312 	  }
313 	  break;
314 	  }
315 	} else if (geomArray.getCoordRef3f() != null) {
316 	  if (initial != 0) {
317 	    Point3f[] c = geomArray.getCoordRef3f();
318 	    coords = new Point3f[valid];
319 	    for (i = 0 ; i < valid ; i++) {
320 	      coords[i] = new Point3f(c[i + initial]);
321 	    }
322 	  } else coords = geomArray.getCoordRef3f();
323 	} else if (geomArray.getCoordRef3d() != null) {
324 	  Point3d[] c = geomArray.getCoordRef3d();
325 	  coords = new Point3f[valid];
326 	  for (i = 0 ; i < valid ; i++) {
327 	    coords[i] = new Point3f(c[i + initial]);
328 	  }
329 	} else if (geomArray.getCoordRefFloat() != null) {
330 	  float[] c = geomArray.getCoordRefFloat();
331 	  coords = new Point3f[valid];
332 	  for (i = 0 ; i < valid ; i++) {
333 	    coords[i] = new Point3f(c[(i + initial) * 3],
334 				    c[(i + initial) * 3 + 1],
335 				    c[(i + initial) * 3 + 2]);
336 	  }
337 	} else if (geomArray.getCoordRefDouble() != null) {
338 	  double[] c = geomArray.getCoordRefDouble();
339 	  coords = new Point3f[valid];
340 	  for (i = 0 ; i < valid ; i++) {
341 	    coords[i] = new Point3f((float)(c[(i + initial) * 3]),
342 				    (float)(c[(i + initial) * 3 + 1]),
343 				    (float)(c[(i + initial) * 3 + 2]));
344 	  }
345 	}
346 	// No coordinate data - let GeometryInfo handle this.
347       } else {
348 	// Not BY_REFERENCE
349 	int initial;
350 	if (!(geomArray instanceof IndexedGeometryArray)) {
351 	  initial = geomArray.getInitialVertexIndex();
352 	} else initial = 0;
353 	coords = new Point3f[valid];
354 	for (i = 0 ; i < valid ; i++) coords[i] = new Point3f();
355 	geomArray.getCoordinates(initial, coords);
356       }
357       geomInfo.setCoordinates(coords);
358 
359       if ((vertexFormat & GeometryArray.NORMALS) != 0) {
360 	Vector3f[] normals = null;
361 	if (byRef) {
362 
363 	  int initial;
364 	  if (!(geomArray instanceof IndexedGeometryArray)) {
365 	    initial = geomArray.getInitialNormalIndex();
366 	  } else initial = 0;
367 
368 	  if ( nio ) {
369 	    J3DBuffer buf = geomArray.getNormalRefBuffer();
370 
371 	    if (BufferWrapper.getBufferType(buf) == BufferWrapper.TYPE_FLOAT) {
372 	      FloatBufferWrapper bb = new FloatBufferWrapper(buf);
373 	      float[] c = new float[valid * 3];
374 	      bb.position(initial * 3);
375 	      bb.get(c, 0, valid * 3);
376 	      normals = new Vector3f[valid];
377 	      for (i = 0 ; i < valid ; i++) {
378 		normals[i] = new Vector3f(c[i * 3 + 0],
379 					  c[i * 3 + 1],
380 					  c[i * 3 + 2]);
381 	      }
382 	    }
383 	    // Normals were set in vertexFormat but none were set - OK
384 	  } else if (geomArray.getNormalRef3f() != null) {
385 	    if (initial != 0) {
386 	      Vector3f[] n = geomArray.getNormalRef3f();
387 	      normals = new Vector3f[valid];
388 	      for (i = 0 ; i < valid ; i++) {
389 		normals[i] = new Vector3f(n[i + initial]);
390 	      }
391 	    } else normals = geomArray.getNormalRef3f();
392 	  } else if (geomArray.getNormalRefFloat() != null) {
393 	    float[] n = geomArray.getNormalRefFloat();
394 	    normals = new Vector3f[valid];
395 	    for (i = 0 ; i < valid ; i++) {
396 	      normals[i] = new Vector3f(n[(i + initial) * 3],
397 					n[(i + initial) * 3 + 1],
398 					n[(i + initial) * 3 + 2]);
399 	    }
400 	  }
401 	  // Normals were set in vertexFormat but none were set - OK
402 	} else {
403 	  // Not BY_REFERENCE
404 	  int initial;
405 	  if (!(geomArray instanceof IndexedGeometryArray)) {
406 	    initial = geomArray.getInitialVertexIndex();
407 	  } else initial = 0;
408 	  normals = new Vector3f[valid];
409 	  for (i = 0 ; i < valid ; i++) normals[i] = new Vector3f();
410 	  geomArray.getNormals(initial, normals);
411 	}
412 	geomInfo.setNormals(normals);
413       }
414 
415       if ((vertexFormat & GeometryArray.COLOR_4) == GeometryArray.COLOR_4) {
416 	Color4f[] colors = null;
417 	if (byRef) {
418 
419 	  int initial;
420 	  if (!(geomArray instanceof IndexedGeometryArray)) {
421 	    initial = geomArray.getInitialColorIndex();
422 	  } else initial = 0;
423 
424 	  if ( nio ) {
425 	    J3DBuffer buf = geomArray.getColorRefBuffer();
426 
427 	    switch (BufferWrapper.getBufferType(buf)) {
428 
429 	    case BufferWrapper.TYPE_FLOAT: {
430 	      FloatBufferWrapper bb = new FloatBufferWrapper(buf);
431 	      float[] c = new float[valid * 4];
432 	      bb.position(initial * 4);
433 	      bb.get(c, 0, valid * 4);
434 	      colors = new Color4f[valid];
435 	      for (i = 0 ; i < valid ; i++) {
436 		colors[i] = new Color4f(c[i * 4 + 0],
437 					c[i * 4 + 1],
438 					c[i * 4 + 2],
439 					c[i * 4 + 3]);
440 	      }
441 	    }
442 	    break;
443 
444 	    case BufferWrapper.TYPE_BYTE: {
445 	      ByteBufferWrapper bb = new ByteBufferWrapper(buf);
446 	      byte[] c = new byte[valid * 4];
447 	      bb.position(initial * 4);
448 	      bb.get(c, 0, valid * 4);
449 	      colors = new Color4f[valid];
450 	      for (i = 0 ; i < valid ; i++) {
451 		colors[i] = new Color4f((float)(c[i * 4 + 0] & 0xff) / 255.0f,
452 					(float)(c[i * 4 + 1] & 0xff) / 255.0f,
453 					(float)(c[i * 4 + 2] & 0xff) / 255.0f,
454 					(float)(c[i * 4 + 3] & 0xff) / 255.0f);
455 	      }
456 	    }
457 	    break;
458 	    }
459 	  } else if (geomArray.getColorRef4f() != null) {
460 	    if (initial != 0) {
461 	      Color4f[] c = geomArray.getColorRef4f();
462 	      colors = new Color4f[valid];
463 	      for (i = 0 ; i < valid ; i++) {
464 		colors[i] = new Color4f(c[i + initial]);
465 	      }
466 	    } else colors = geomArray.getColorRef4f();
467 	  } else if (geomArray.getColorRefFloat() != null) {
468 	    float[] c = geomArray.getColorRefFloat();
469 	    colors = new Color4f[valid];
470 	    for (i = 0 ; i < valid ; i++) {
471 	      colors[i] = new Color4f(c[(i + initial) * 4 + 0],
472 				      c[(i + initial) * 4 + 1],
473 				      c[(i + initial) * 4 + 2],
474 				      c[(i + initial) * 4 + 3]);
475 	    }
476 	  } else if (geomArray.getColorRefByte() != null) {
477 	    byte[] c = geomArray.getColorRefByte();
478 	    colors = new Color4f[valid];
479 	    for (i = 0 ; i < valid ; i++) {
480 	      colors[i] = new Color4f((float)(c[(i + initial) * 4 + 0] & 0xff) / 255.0f,
481 				      (float)(c[(i + initial) * 4 + 1] & 0xff) / 255.0f,
482 				      (float)(c[(i + initial) * 4 + 2] & 0xff) / 255.0f,
483 				      (float)(c[(i + initial) * 4 + 3] & 0xff) / 255.0f);
484 	    }
485 	  } else if (geomArray.getColorRef4b() != null) {
486 	    Color4b[] c = geomArray.getColorRef4b();
487 	    colors = new Color4f[valid];
488 	    for (i = 0 ; i < valid ; i++) {
489 	      colors[i] = new Color4f((float)(c[i + initial].x & 0xff) / 255.0f,
490 				      (float)(c[i + initial].y & 0xff) / 255.0f,
491 				      (float)(c[i + initial].z & 0xff) / 255.0f,
492 				      (float)(c[i + initial].w & 0xff) / 255.0f);
493 	    }
494 	  }
495 	  // Colors4 were set in vertexFormat but none were set - OK
496 	} else {
497 	  // Not BY_REFERENCE
498 	  int initial;
499 	  if (!(geomArray instanceof IndexedGeometryArray)) {
500 	    initial = geomArray.getInitialVertexIndex();
501 	  } else initial = 0;
502 	  colors = new Color4f[valid];
503 	  for (i = 0 ; i < valid ; i++) colors[i] = new Color4f();
504 	  geomArray.getColors(initial, colors);
505 	}
506 	geomInfo.setColors(colors);
507       } else if ((vertexFormat & GeometryArray.COLOR_3) != 0) {
508 	Color3f[] colors = null;
509 	if (byRef) {
510 
511 	  int initial;
512 	  if (!(geomArray instanceof IndexedGeometryArray)) {
513 	    initial = geomArray.getInitialColorIndex();
514 	  } else initial = 0;
515 
516 	  if ( nio ) {
517 	    J3DBuffer buf = geomArray.getColorRefBuffer();
518 
519 	    switch (BufferWrapper.getBufferType(buf)) {
520 
521 	    case BufferWrapper.TYPE_FLOAT: {
522 	      FloatBufferWrapper bb = new FloatBufferWrapper(buf);
523 	      float[] c = new float[valid * 3];
524 	      bb.position(initial * 3);
525 	      bb.get(c, 0, valid * 3);
526 	      colors = new Color3f[valid];
527 	      for (i = 0 ; i < valid ; i++) {
528 		colors[i] = new Color3f(c[i * 3 + 0],
529 					c[i * 3 + 1],
530 					c[i * 3 + 2]);
531 	      }
532 	    }
533 	    break;
534 
535 	    case BufferWrapper.TYPE_BYTE: {
536 	      ByteBufferWrapper bb = new ByteBufferWrapper(buf);
537 	      byte[] c = new byte[valid * 3];
538 	      bb.position(initial * 3);
539 	      bb.get(c, 0, valid * 3);
540 	      colors = new Color3f[valid];
541 	      for (i = 0 ; i < valid ; i++) {
542 		colors[i] = new Color3f((float)(c[i * 3 + 0] & 0xff) / 255.0f,
543 					(float)(c[i * 3 + 1] & 0xff) / 255.0f,
544 					(float)(c[i * 3 + 2] & 0xff) / 255.0f);
545 	      }
546 	    }
547 	    break;
548 	    }
549 	  } else if (geomArray.getColorRef3f() != null) {
550 	    if (initial != 0) {
551 	      Color3f[] c = geomArray.getColorRef3f();
552 	      colors = new Color3f[valid];
553 	      for (i = 0 ; i < valid ; i++) {
554 		colors[i] = new Color3f(c[i + initial]);
555 	      }
556 	    } else colors = geomArray.getColorRef3f();
557 	  } else if (geomArray.getColorRefFloat() != null) {
558 	    float[] c = geomArray.getColorRefFloat();
559 	    colors = new Color3f[valid];
560 	    for (i = 0 ; i < valid ; i++) {
561 	      colors[i] = new Color3f(c[(i + initial) * 3 + 0],
562 				      c[(i + initial) * 3 + 1],
563 				      c[(i + initial) * 3 + 2]);
564 	    }
565 	  } else if (geomArray.getColorRefByte() != null) {
566 	    byte[] c = geomArray.getColorRefByte();
567 	    colors = new Color3f[valid];
568 	    for (i = 0 ; i < valid ; i++) {
569 	      colors[i] = new Color3f((float)(c[(i + initial) * 3 + 0] & 0xff) / 255.0f,
570 				      (float)(c[(i + initial) * 3 + 1] & 0xff) / 255.0f,
571 				      (float)(c[(i + initial) * 3 + 2] & 0xff) / 255.0f);
572 	    }
573 	  } else if (geomArray.getColorRef3b() != null) {
574 	    Color3b[] c = geomArray.getColorRef3b();
575 	    colors = new Color3f[valid];
576 	    for (i = 0 ; i < valid ; i++) {
577 	      colors[i] = new Color3f((float)(c[i + initial].x & 0xff) / 255.0f,
578 				      (float)(c[i + initial].y & 0xff) / 255.0f,
579 				      (float)(c[i + initial].z & 0xff) / 255.0f);
580 	    }
581 	  }
582 	  // Colors3 were set in vertexFormat but none were set - OK
583 	} else {
584 	  // Not BY_REFERENCE
585 	  int initial;
586 	  if (!(geomArray instanceof IndexedGeometryArray)) {
587 	    initial = geomArray.getInitialVertexIndex();
588 	  } else initial = 0;
589 	  colors = new Color3f[valid];
590 	  for (i = 0 ; i < valid ; i++) colors[i] = new Color3f();
591 	  geomArray.getColors(initial, colors);
592 	}
593 	geomInfo.setColors(colors);
594       }
595 
596       if ((vertexFormat & GeometryArray.TEXTURE_COORDINATE_4) != 0) {
597 	geomInfo.setTextureCoordinateParams(texSets, 4);
598 	for (i = 0 ; i < texSets ; i++) {
599 	  TexCoord4f[] tex = null;
600 	  if (byRef) {
601 
602 	    int initial;
603 	    if (!(geomArray instanceof IndexedGeometryArray)) {
604 	      initial = geomArray.getInitialTexCoordIndex(i);
605 	    } else initial = 0;
606 
607 	    if (nio) {
608 	      J3DBuffer buf = geomArray.getTexCoordRefBuffer(i);
609 
610 	      if (BufferWrapper.getBufferType(buf) == BufferWrapper.TYPE_FLOAT) {
611 		FloatBufferWrapper bb = new FloatBufferWrapper(buf);
612 		float[] c = new float[valid * 4];
613 		bb.position(initial * 4);
614 		bb.get(c, 0, valid * 4);
615 		tex = new TexCoord4f[valid];
616 		for (j = 0 ; j < valid ; j++) {
617 		  tex[j] = new TexCoord4f(c[j * 4 + 0],
618 					  c[j * 4 + 1],
619 					  c[j * 4 + 2],
620 					  c[j * 4 + 3]);
621 		}
622 	      }
623 	      // TexCoords4 were set in vertexFormat but none were set - OK
624 	    } else {
625 	      // There if no TexCoordRef4f, so we know it's float
626 	      float[] t = geomArray.getTexCoordRefFloat(i);
627 	      tex = new TexCoord4f[valid];
628 	      for (j = 0 ; j < valid ; j++) {
629 		tex[j] = new TexCoord4f(t[(j + initial) * 4],
630 					t[(j + initial) * 4 + 1],
631 					t[(j + initial) * 4 + 2],
632 					t[(j + initial) * 4 + 3]);
633 	      }
634 	    }
635 	  } else {
636 	    // Not BY_REFERENCE
637 	    int initial;
638 	    if (!(geomArray instanceof IndexedGeometryArray)) {
639 	      initial = geomArray.getInitialVertexIndex();
640 	    } else initial = 0;
641 	    tex = new TexCoord4f[valid];
642 	    for (j = 0 ; j < valid ; j++) tex[j] = new TexCoord4f();
643 	    geomArray.getTextureCoordinates(i, initial, tex);
644 	  }
645 	  geomInfo.setTextureCoordinates(i, tex);
646 	}
647 	int[] map = new int[geomArray.getTexCoordSetMapLength()];
648 	geomArray.getTexCoordSetMap(map);
649 	geomInfo.setTexCoordSetMap(map);
650       } else if ((vertexFormat & GeometryArray.TEXTURE_COORDINATE_3) != 0) {
651 	geomInfo.setTextureCoordinateParams(texSets, 3);
652 	for (i = 0 ; i < texSets ; i++) {
653 	  TexCoord3f[] tex = null;
654 	  if (byRef) {
655 
656 	    int initial;
657 	    if (!(geomArray instanceof IndexedGeometryArray)) {
658 	      initial = geomArray.getInitialTexCoordIndex(i);
659 	    } else initial = 0;
660 
661 	    if (nio) {
662 	      J3DBuffer buf = geomArray.getTexCoordRefBuffer(i);
663 
664 	      if (BufferWrapper.getBufferType(buf) == BufferWrapper.TYPE_FLOAT) {
665 		FloatBufferWrapper bb = new FloatBufferWrapper(buf);
666 		float[] c = new float[valid * 3];
667 		bb.position(initial * 3);
668 		bb.get(c, 0, valid * 3);
669 		tex = new TexCoord3f[valid];
670 		for (j = 0 ; j < valid ; j++) {
671 		  tex[j] = new TexCoord3f(c[j * 3 + 0],
672 					  c[j * 3 + 1],
673 					  c[j * 3 + 2]);
674 		}
675 	      }
676 	      // TexCoords3 were set in vertexFormat but none were set - OK
677 	    } else if (geomArray.getTexCoordRef3f(i) != null) {
678 	      if (initial != 0) {
679 		TexCoord3f[] t = geomArray.getTexCoordRef3f(i);
680 		tex = new TexCoord3f[valid];
681 		for (j = 0 ; j < valid ; j++) {
682 		  tex[j] = new TexCoord3f(t[j + initial]);
683 		}
684 	      } else tex = geomArray.getTexCoordRef3f(i);
685 	    } else if (geomArray.getTexCoordRefFloat(i) != null) {
686 	      float[] t = geomArray.getTexCoordRefFloat(i);
687 	      tex = new TexCoord3f[valid];
688 	      for (j = 0 ; j < valid ; j++) {
689 		tex[j] = new TexCoord3f(t[(j + initial) * 3],
690 					t[(j + initial) * 3 + 1],
691 					t[(j + initial) * 3 + 2]);
692 	      }
693 	    }
694 	    // TexCoords3 were set in vertexFormat but none were set - OK
695 	  } else {
696 	    // Not BY_REFERENCE
697 	    int initial;
698 	    if (!(geomArray instanceof IndexedGeometryArray)) {
699 	      initial = geomArray.getInitialVertexIndex();
700 	    } else initial = 0;
701 	    tex = new TexCoord3f[valid];
702 	    for (j = 0 ; j < valid ; j++) tex[j] = new TexCoord3f();
703 	    geomArray.getTextureCoordinates(i, initial, tex);
704 	  }
705 	  geomInfo.setTextureCoordinates(i, tex);
706 	}
707 	int[] map = new int[geomArray.getTexCoordSetMapLength()];
708 	geomArray.getTexCoordSetMap(map);
709 	geomInfo.setTexCoordSetMap(map);
710       } else if ((vertexFormat & GeometryArray.TEXTURE_COORDINATE_2) != 0 ) {
711 	geomInfo.setTextureCoordinateParams(texSets, 2);
712 	for (i = 0 ; i < texSets ; i++) {
713 	  TexCoord2f[] tex = null;
714 	  if (byRef) {
715 
716 	    int initial;
717 	    if (!(geomArray instanceof IndexedGeometryArray)) {
718 	      initial = geomArray.getInitialTexCoordIndex(i);
719 	    } else initial = 0;
720 
721 	    if (nio) {
722 	      J3DBuffer buf = geomArray.getTexCoordRefBuffer(i);
723 
724 	      if (BufferWrapper.getBufferType(buf) == BufferWrapper.TYPE_FLOAT) {
725 		FloatBufferWrapper bb = new FloatBufferWrapper(buf);
726 		float[] c = new float[valid * 2];
727 		bb.position(initial * 2);
728 		bb.get(c, 0, valid * 2);
729 		tex = new TexCoord2f[valid];
730 		for (j = 0 ; j < valid ; j++) {
731 		  tex[j] = new TexCoord2f(c[j * 2 + 0],
732 					  c[j * 2 + 1]);
733 		}
734 	      }
735 	      // TexCoords2 were set in vertexFormat but none were set - OK
736 	    } else if (geomArray.getTexCoordRefFloat(i) != null) {
737 	      float[] t = geomArray.getTexCoordRefFloat(i);
738 	      tex = new TexCoord2f[valid];
739 	      for (j = 0 ; j < valid ; j++) {
740 		tex[j] = new TexCoord2f(t[(j + initial) * 2 + 0],
741 					t[(j + initial) * 2 + 1]);
742 	      }
743 	    } else if (geomArray.getTexCoordRef2f(i) != null) {
744 	      if (initial != 0) {
745 		TexCoord2f[] t = geomArray.getTexCoordRef2f(i);
746 		tex = new TexCoord2f[valid];
747 		for (j = 0 ; j < valid ; j++) {
748 		  tex[j] = new TexCoord2f(t[j + initial]);
749 		}
750 	      } else tex = geomArray.getTexCoordRef2f(i);
751 	    }
752 	    // TexCoords2 were set in vertexFormat but none were set - OK
753 	  } else {
754 	    // Not BY_REFERENCE
755 	    int initial;
756 	    if (!(geomArray instanceof IndexedGeometryArray)) {
757 	      initial = geomArray.getInitialVertexIndex();
758 	    } else initial = 0;
759 	    tex = new TexCoord2f[valid];
760 	    for (j = 0 ; j < valid ; j++) tex[j] = new TexCoord2f();
761 	    geomArray.getTextureCoordinates(i, initial, tex);
762 	  }
763 	  geomInfo.setTextureCoordinates(i, tex);
764 	}
765 	int[] map = new int[geomArray.getTexCoordSetMapLength()];
766 	geomArray.getTexCoordSetMap(map);
767 	geomInfo.setTexCoordSetMap(map);
768       }
769     }
770   } // End of processGeometryArray
771 
772 
773 
processIndexedArray(GeometryInfo geomInfo, IndexedGeometryArray geomArray)774   private static void processIndexedArray(GeometryInfo geomInfo,
775 					  IndexedGeometryArray geomArray)
776   {
777     int initial = geomArray.getInitialIndexIndex();
778     int vertexFormat = geomArray.getVertexFormat();
779     int texSets = geomArray.getTexCoordSetCount();
780 
781     int valid;
782     if (geomArray instanceof IndexedGeometryStripArray) {
783       IndexedGeometryStripArray igsa = (IndexedGeometryStripArray)geomArray;
784       int[] strips = new int[igsa.getNumStrips()];
785       igsa.getStripIndexCounts(strips);
786       valid = 0;
787       for (int i = 0 ; i < strips.length ; i++) {
788 	valid += strips[i];
789       }
790     } else {
791       valid = geomArray.getValidIndexCount();
792     }
793 
794     int[] coordI = new int[valid];
795     geomArray.getCoordinateIndices(initial, coordI);
796     geomInfo.setCoordinateIndices(coordI);
797 
798     if ((vertexFormat & GeometryArray.USE_COORD_INDEX_ONLY) != 0) {
799       if ((vertexFormat & GeometryArray.NORMALS) != 0)
800 	geomInfo.setNormalIndices(coordI);
801       if (((vertexFormat & GeometryArray.COLOR_3) != 0) ||
802 	  ((vertexFormat & GeometryArray.COLOR_4) != 0))
803 	geomInfo.setColorIndices(coordI);
804       if (((vertexFormat & GeometryArray.TEXTURE_COORDINATE_2) != 0) ||
805 	  ((vertexFormat & GeometryArray.TEXTURE_COORDINATE_3) != 0) ||
806 	  ((vertexFormat & GeometryArray.TEXTURE_COORDINATE_4) != 0)) {
807 	for (int i = 0 ; i < texSets ; i++) {
808 	  geomInfo.setTextureCoordinateIndices(i, coordI);
809 	}
810       }
811     } else {
812       if ((vertexFormat & GeometryArray.NORMALS) != 0) {
813 	int[] normalI = new int[valid];
814 	geomArray.getNormalIndices(initial, normalI);
815 	geomInfo.setNormalIndices(normalI);
816       }
817 
818       if (((vertexFormat & GeometryArray.COLOR_3) != 0) ||
819 	  ((vertexFormat & GeometryArray.COLOR_4) != 0)) {
820 	int[] colorI = new int[valid];
821 	geomArray.getColorIndices(initial, colorI);
822 	geomInfo.setColorIndices(colorI);
823       }
824 
825       if (((vertexFormat & GeometryArray.TEXTURE_COORDINATE_2) != 0) ||
826 	  ((vertexFormat & GeometryArray.TEXTURE_COORDINATE_3) != 0) ||
827 	  ((vertexFormat & GeometryArray.TEXTURE_COORDINATE_4) != 0)) {
828 	for (int i = 0 ; i < texSets ; i++) {
829 	  int[] texI = new int[valid];
830 	  geomArray.getTextureCoordinateIndices(i, initial, texI);
831 	  geomInfo.setTextureCoordinateIndices(i, texI);
832 	}
833       }
834     }
835   } // End of processIndexedArray
836 
837 
838 
processStripArray(GeometryInfo geomInfo, GeometryStripArray geomArray)839   private static void processStripArray(GeometryInfo geomInfo,
840 					GeometryStripArray geomArray)
841   {
842     int[] strips = new int[geomArray.getNumStrips()];
843     geomArray.getStripVertexCounts(strips);
844     geomInfo.setStripCounts(strips);
845   } // End of processStripArray
846 
847 
848 
processIndexStripArray( GeometryInfo geomInfo, IndexedGeometryStripArray geomArray)849   private static void processIndexStripArray(
850     GeometryInfo geomInfo, IndexedGeometryStripArray geomArray)
851   {
852     int[] strips = new int[geomArray.getNumStrips()];
853     geomArray.getStripIndexCounts(strips);
854     geomInfo.setStripCounts(strips);
855   } // End of processIndexStripArray
856 
857 } // End of class GeometryInfoGenerator
858