View Javadoc

1   /* -------------------------------------------------------------------
2    * Java source file for the class GeometryInfo
3    * 
4    * Copyright (c), 2003, Masahiro Takatsuka.
5    * All Rights Researved.
6    * 
7    * Original Author: Masahiro Takatsuka (masa@jbeans.net)
8    * $Author: takatsukam $
9    * 
10   * $Date: 2004/03/03 11:53:06 $
11   * 
12   * $Id: GeometryInfo.java,v 1.3 2004/03/03 11:53:06 takatsukam Exp $
13   * 
14   * Reference:		Document no:
15   * ___				___
16   * 
17   * To Do:
18   * ___
19   * 
20  ------------------------------------------------------------------- */
21  
22  /* --------------------------- Package ---------------------------- */
23  package net.jbeans.j3d.modeler.geometry.util;
24  
25  /* ------------------ Import classes (packages) ------------------- *//package-summary/html">class="comment"> ------------------ Import classes (packages) ------------------- *//package-summary.html">class="comment">/* ------------------ Import classes (packages) ------------------- *//package-summary.html">class="comment"> ------------------ Import classes (packages) ------------------- */
26  import java.util.*;
27  import javax.media.j3d.*;
28  import javax.vecmath.*;
29  //import com.sun.j3d.utils.geometry.*;
30  
31  import net.jbeans.util.debug.*;
32  
33  /*====================================================================
34                   Implementation of class GeometryInfo                 
35  ====================================================================*/
36  /***
37   * GeometryInfo provides same functionalities as
38   * GeometryInfo(com.sun.j3d.utils.geometry.GeometryInfo).
39   * It is however capable of produceing GeometryArray using either
40   * by-copying or by-reference mode. The default is by-reference mode.
41   * 
42   * @version $Revision: 1.3 $
43   * @author Masahiro Takatsuka (masa@jbeans.net)
44   * @see com.sun.j3d.utils.geometry.GeometryInfo
45   */
46  
47  public class GeometryInfo extends com.sun.j3d.utils.geometry.GeometryInfo {
48  	private static final boolean DEBUG = Debug.getDebugFlag(GeometryInfo.class);
49  
50  	public static final int BY_REFERENCE = GeometryArray.BY_REFERENCE;
51  	public static final int BY_COPY = BY_REFERENCE + 1;
52  	
53      public static final int PRIMITIVE_FIRST = 1;
54      public static final int PRIMITIVE_LAST = 5;	
55  
56  	public static final int COORDINATE = 0x01;
57  	public static final int COLOR = 0x02;
58  	public static final int NORMAL = 0x04;
59  	public static final int TEXTCOORD = 0x08;
60  	
61  	private int mode;
62  	
63      public GeometryInfo(int i) {
64  		super(i);
65  		this.mode = BY_REFERENCE;
66      }
67  
68  	public void setGeometryMode(int mode) {
69  		this.mode = (mode == BY_COPY) ? BY_COPY : BY_REFERENCE;
70  	}
71  	
72      private int getVertexCount() {
73  		Point3f[] coordinates = getCoordinates();		
74          int i = coordinates.length;
75  //  		Object[] colors = getColors();
76  //  		Vector3f[] normals = getNormals();
77  //  		Object[] texCoords = getTextureCoordinates(0);
78  //  		if (colors != null) {
79  //  			if (colors.length > i) {
80  //  				i = colors.length;
81  //  			}
82  //  		}
83  //  		if (normals != null && normals.length > i) {
84  //              i = normals.length;
85  //  		}
86  //  		if (texCoords != null) {
87  //  			if (texCoords.length > i) {
88  //  				i = texCoords.length;
89  //  			}
90  //  		}
91          return i;
92      }
93  
94      private int getVertexFormat() {
95          int i = 1;
96  		Object[] colors = getColors();
97  		Vector3f[] normals = getNormals();
98  		int numTexCoord = getNumTexCoordComponents();
99  		Object[] texCoords = (numTexCoord > 0) ? getTextureCoordinates() : null;
100 		if (colors != null) {
101 			if (colors instanceof Color3f[]) {
102 				i |= GeometryArray.COLOR_3;
103 			} else {
104 				if(colors instanceof Color4f[]) {
105 					i |= GeometryArray.COLOR_4;
106 				}
107 			}
108 		}
109         if (normals != null) {
110             i |= GeometryArray.NORMALS;
111 		}
112         if (texCoords != null) {
113 			if (texCoords instanceof Point2f[]) {
114 				i |= GeometryArray.TEXTURE_COORDINATE_2;
115 			} else if (texCoords instanceof Point3f[]) {
116 				i |= GeometryArray.TEXTURE_COORDINATE_3;
117 			}
118 		}
119         if (this.mode == BY_REFERENCE) {
120             i |= GeometryArray.BY_REFERENCE;
121 		}
122         return i;
123     }
124 
125 	transient private Object[] tmpcolors;
126 	transient private Vector3f[] normals;
127 	private void prepareForRef() {
128 
129 	}
130 
131 	private void setCapabilities(GeometryArray geometryarray) {
132 		// always;
133 		geometryarray.setCapability(GeometryArray.ALLOW_FORMAT_READ);
134 		geometryarray.setCapability(GeometryArray.ALLOW_COORDINATE_READ);
135 		geometryarray.setCapability(GeometryArray.ALLOW_COORDINATE_WRITE);
136 		geometryarray.setCapability(GeometryArray.ALLOW_NORMAL_READ);
137 		geometryarray.setCapability(GeometryArray.ALLOW_NORMAL_WRITE);
138 		geometryarray.setCapability(IndexedGeometryArray.ALLOW_COORDINATE_INDEX_READ);
139 		geometryarray.setCapability(IndexedGeometryArray.ALLOW_COORDINATE_INDEX_WRITE);
140 		geometryarray.setCapability(IndexedGeometryArray.ALLOW_NORMAL_INDEX_READ);
141 		geometryarray.setCapability(IndexedGeometryArray.ALLOW_NORMAL_INDEX_WRITE);
142 	}
143 	
144     private void fillIn(GeometryArray src, GeometryArray geometryarray) {
145 		Point3f[] coordinates = getCoordinates();
146 		Object[] colors = getColors();
147 		Vector3f[] normals = getNormals();
148 		int numTexCoord = getNumTexCoordComponents();
149 		Object[] texCoords = (numTexCoord > 0) ? getTextureCoordinates() : null;
150 		int[] coordinateIndices = getCoordinateIndices();
151 		int[] colorIndices = getColorIndices();
152 		int[] normalIndices = getNormalIndices();
153 		int[] texCoordIndices = (numTexCoord > 0) ? getTextureCoordinateIndices() : null;
154 		TexCoord2f[] texCoords2f = null;
155 		TexCoord3f[] texCoords3f = null;
156 
157 		if (texCoords != null) {
158 			if (texCoords instanceof Point2f[]) {
159 				texCoords2f = new TexCoord2f[texCoords.length];
160 				for (int i = 0; i < texCoords.length; i++) {
161 					texCoords2f[i] = new TexCoord2f((Point2f) texCoords[i]);
162 				}
163 			} else if (texCoords instanceof Point3f[]) {
164 				texCoords3f = new TexCoord3f[texCoords.length];
165 				for (int i = 0; i < texCoords.length; i++) {
166 					texCoords3f[i] = new TexCoord3f((Point3f) texCoords[i]);
167 				}
168 			}
169 		}
170 		
171 		if (this.mode == BY_REFERENCE) {
172 			if (DEBUG) {
173 				System.out.println("vertex count = " + getVertexCount());
174 				System.out.println("num of coords = " + coordinates.length);
175 				System.out.println("num of normals = " + normals.length);
176 				System.out.println("num of normalsindices = " + normalIndices.length);
177 				System.out.println("numtmpcolors; of colors = " + colors.length);				
178 			}
179 			geometryarray.setCapability(GeometryArray.ALLOW_REF_DATA_WRITE);
180 			geometryarray.setCoordRef3f(coordinates);
181 			if (colors != null) {
182 				if (colors instanceof Color3f[]) {
183 					geometryarray.setColorRef3f((Color3f[]) colors);
184 				} else if (colors instanceof Color4f[]) {
185 					geometryarray.setColorRef4f((Color4f[]) colors);
186 				}
187 			}
188 			if (normals != null) {
189 				int vertexcount = getVertexCount();
190 				if (normals.length < vertexcount) {
191 					Vector3f[] oldnormals = normals;
192 					normals = new Vector3f[vertexcount];
193 					//					System.arraycopy(normals, 0, oldnormals, 0, oldnormals.length);
194 					//for (int i = oldnormals.length; i < vertexcount; i++) {
195 					for (int i = 0; i < oldnormals.length; i++) {
196 						if (oldnormals[i] != null) {
197 							normals[i] = oldnormals[i];
198 						} else {
199 							normals[i] = new Vector3f();
200 						}
201 					}
202 					for (int i = oldnormals.length; i < vertexcount; i++) {
203 						normals[i] = new Vector3f();
204 					}
205 				}
206 				geometryarray.setNormalRef3f(normals);
207 			}
208 			if (texCoords2f != null) {
209 				geometryarray.setTexCoordRef2f(0, texCoords2f);
210 			} else if (texCoords3f != null) {
211 				geometryarray.setTexCoordRef3f(0, texCoords3f);
212 			}
213 		} else {
214 			geometryarray.setCoordinates(0, coordinates);
215 			if (colors != null) {
216 				if (colors instanceof Color3f[]) {
217 					geometryarray.setColors(0, (Color3f[]) colors);
218 				} else if (colors instanceof Color4f[]) {
219 					geometryarray.setColors(0, (Color4f[]) colors);
220 				}
221 			}
222 			if (normals != null) {
223 				geometryarray.setNormals(0, normals);
224 			}
225 			if (texCoords2f != null) {
226 				geometryarray.setTextureCoordinates(0, 0, texCoords2f);
227 			} else if (texCoords3f != null) {
228 				geometryarray.setTextureCoordinates(0, 0, texCoords3f);
229 			}
230 		}
231         IndexedGeometryArray indexedgeometryarray = null;
232 		if (coordinateIndices != null) {
233             indexedgeometryarray = (IndexedGeometryArray)geometryarray;
234 			indexedgeometryarray.setCoordinateIndices(0, coordinateIndices);
235         }
236         if (colorIndices != null) {
237             indexedgeometryarray.setColorIndices(0, colorIndices);
238 		}
239         if (normalIndices != null) {
240             indexedgeometryarray.setNormalIndices(0, normalIndices);
241 		}
242         if (texCoordIndices != null) {
243             indexedgeometryarray.setTextureCoordinateIndices(0, 0, texCoordIndices);
244 		}
245 
246 		setCapabilities(geometryarray);		
247     }
248 	
249     public GeometryArray getGeometryArray() {
250         GeometryArray geom = super.getGeometryArray();
251 		int prim = getPrimitive();
252         int i = getVertexFormat();
253         int j = getVertexCount();
254 		int[] stripCounts = getStripCounts();
255         Object obj = null;
256 
257         switch (prim) {
258         case TRIANGLE_ARRAY: // '\001'
259             TriangleArray trianglearray = new TriangleArray(j, i);
260             obj = trianglearray;
261             break;
262 
263         case QUAD_ARRAY: // '\002'
264             QuadArray quadarray = new QuadArray(j, i);
265             obj = quadarray;
266             break;
267 			
268         case TRIANGLE_STRIP_ARRAY: // '\004'
269             TriangleStripArray trianglestriparray = new TriangleStripArray(j, i, stripCounts);
270             obj = trianglestriparray;
271             break;
272 
273         case TRIANGLE_FAN_ARRAY: // '\003'
274             TriangleFanArray trianglefanarray = new TriangleFanArray(j, i, stripCounts);
275             obj = trianglefanarray;
276             break;
277         }
278         fillIn(geom, ((GeometryArray) (obj)));
279         return ((GeometryArray) (obj));
280     }
281 
282     public IndexedGeometryArray getIndexedGeometryArray() {
283         return getIndexedGeometryArray(false);
284     }
285 
286     public IndexedGeometryArray getIndexedGeometryArray(boolean flag) {
287         GeometryArray geom = super.getIndexedGeometryArray(flag);
288 		int prim = getPrimitive();
289         int i = getVertexFormat();
290         int j = getVertexCount();
291 		int[] stripCounts = getStripCounts();
292 		int[] coordinateIndices = getCoordinateIndices();
293         Object obj = null;
294 
295         switch (prim) {
296         case TRIANGLE_ARRAY: // '\001'
297             IndexedTriangleArray indexedtrianglearray = new IndexedTriangleArray(j, i, coordinateIndices.length);
298             obj = indexedtrianglearray;
299             break;
300 
301         case QUAD_ARRAY: // '\002'
302             IndexedQuadArray indexedquadarray = new IndexedQuadArray(j, i, coordinateIndices.length);
303             obj = indexedquadarray;
304             break;
305 
306         case TRIANGLE_STRIP_ARRAY: // '\004'
307             IndexedTriangleStripArray indexedtrianglestriparray = new IndexedTriangleStripArray(j, i, coordinateIndices.length, stripCounts);
308             obj = indexedtrianglestriparray;
309             break;
310 
311         case TRIANGLE_FAN_ARRAY: // '\003'
312             IndexedTriangleFanArray indexedtrianglefanarray = new IndexedTriangleFanArray(j, i, coordinateIndices.length, stripCounts);
313             obj = indexedtrianglefanarray;
314             break;
315         }
316         fillIn(geom, ((GeometryArray) (obj)));
317         return ((IndexedGeometryArray) (obj));
318     }
319 
320     public void recomputeIndices(int flag) {
321         unindexify(flag);
322         indexify(flag);
323     }
324 
325     private void unindexify(int flag) {
326 		if ((flag & COORDINATE) == COORDINATE) {
327 			int[] coordinateIndices = getCoordinateIndices();
328 			Point3f[] coordinates = getCoordinates();
329 			if (coordinateIndices != null) {
330 				Point3f apoint3f[] = new Point3f[coordinateIndices.length];
331 				for (int i = 0; i < coordinateIndices.length; i++) {
332 					apoint3f[i] = coordinates[coordinateIndices[i]];
333 				}
334 				setCoordinates(apoint3f);
335 				setCoordinateIndices(null);
336 			}
337 		}
338 		if ((flag & COLOR) == COLOR) {
339 			int[] colorIndices = getColorIndices();
340 			Object[] colors = getColors();
341 			if (colorIndices != null) {
342 				if (colors != null && colors instanceof Color3f[]) {
343 					Color3f acolor3f[] = new Color3f[colorIndices.length];
344 					for (int j = 0; j < colorIndices.length; j++) {
345 						acolor3f[j] = (Color3f) colors[colorIndices[j]];
346 					}
347 					setColors(acolor3f);
348 				} else {
349 					Color4f acolor4f[] = new Color4f[colorIndices.length];
350 					for (int k = 0; k < colorIndices.length; k++) {
351 						acolor4f[k] = (Color4f) colors[colorIndices[k]];
352 					}
353 					setColors(acolor4f);
354 				}
355 				colorIndices = null;
356 			}
357         }
358 		if ((flag & NORMAL) == NORMAL) {
359 			int[] normalIndices = getNormalIndices();
360 			Vector3f[] normals = getNormals();
361 			if (normalIndices != null) {
362 				Vector3f avector3f[] = new Vector3f[normalIndices.length];
363 				for (int l = 0; l < normalIndices.length; l++) {
364 					avector3f[l] = normals[normalIndices[l]];
365 				}
366 				setNormals(avector3f);
367 				normalIndices = null;
368 			}
369 		}
370 		if ((flag & TEXTCOORD) == TEXTCOORD) {
371 			int[] texCoordIndices = getTextureCoordinateIndices();
372 			Object[] texCoords = getTextureCoordinates();
373 			if (texCoordIndices != null) {
374 				if (texCoords != null && texCoords instanceof Point2f[]) {
375 					Point2f apoint2f[] = new Point2f[texCoordIndices.length];
376 					for (int i1 = 0; i1 < texCoordIndices.length; i1++) {
377 						apoint2f[i1] = (Point2f) texCoords[texCoordIndices[i1]];
378 					}
379 					setTextureCoordinates(apoint2f);
380 				} else {
381 					Point3f apoint3f1[] = new Point3f[texCoordIndices.length];
382 					for (int j1 = 0; j1 < texCoordIndices.length; j1++) {
383 						apoint3f1[j1] = (Point3f) texCoords[texCoordIndices[j1]];
384 					}
385 					setTextureCoordinates(apoint3f1);
386 				}
387 				texCoordIndices = null;
388 			}
389 		}
390     }
391 
392     private void indexify(int flag) {
393 		if ((flag & COORDINATE) == COORDINATE) {
394 			int[] coordinateIndices = getCoordinateIndices();			
395 			if (coordinateIndices != null) {
396 				return;
397 			}
398 			Point3f[] coordinates = getCoordinates();
399 			coordinateIndices = getListIndices(coordinates);
400 			setCoordinateIndices(coordinateIndices);
401 		}
402 		if ((flag & COLOR) == COLOR) {
403 			int[] colorIndices = getColorIndices();
404 			if (colorIndices != null) {
405 				return;
406 			}
407 			Object[] colors = getColors();
408 			if (colors != null) {
409 				colorIndices = getListIndices(colors);
410 				setColorIndices(colorIndices);
411 			}
412 		}
413 		if ((flag & NORMAL) == NORMAL) {
414 			int[] normalIndices = getNormalIndices();
415 			if (normalIndices != null) {
416 				return;
417 			}
418 			Vector3f[] normals = getNormals();
419 			if (normals != null) {
420 				normalIndices = getListIndices(normals);
421 				setNormalIndices(normalIndices);
422 			}
423 		}
424 		if ((flag & TEXTCOORD) == TEXTCOORD) {
425 			int[] texCoordIndices = getTextureCoordinateIndices();
426 			if (texCoordIndices != null) {
427 				return;
428 			}
429 			Object[] texCoords = getTextureCoordinates();
430 			if (texCoords != null) {
431 				texCoordIndices = getListIndices(texCoords);
432 				setTextureCoordinateIndices(texCoordIndices);
433 			}
434 		}
435     }
436 
437     private int[] getListIndices(Object aobj[]) {
438         int ai[] = new int[aobj.length];
439         Hashtable hashtable = new Hashtable(aobj.length, 0.5F);
440 
441 		for (int i = 0; i < aobj.length; i++) {
442             Integer integer = (Integer)hashtable.get(aobj[i]);
443             if (integer == null) {
444                 ai[i] = i;
445                 hashtable.put(aobj[i], new Integer(i));
446             } else {
447                 ai[i] = integer.intValue();
448             }
449         }
450         return ai;
451     }
452 }