Una clase Loader lee ficheros de escenas 3D (no ficheros Java 3D) y crea representaciones Java 3D de sus contenidos que pueden ser a�adidos selectivamente a un mundo Java 3D y argumentados por otro c�digo Java 3D. El paquete com.sun.j3d.loaders proporciona el contenido principal para convertir los ficheros creados en otras aplicaciones en aplicaciones Java 3D. Las clases cargadoras implementan el interface Loader definido en el paquete com.sun.j3d.loaders.
Como hay una gran variedad de formatos de ficheros para porp�sitos de representaci�n de escenas 3D (por ejemplo, .obj, .vrml, etc.) y siempre habr� m�s formatos de ficheros, el c�digo real para cargar un fichero no forma parte de Java 3D o del paquete loaders; s�lo se incluye el interface para el mecanismo de carga. Con la definici�n del interface, el usuario de Java 3D puede desarrollar clases cargadoras de ficheros con el mismo interface que las otras clases cargadoras.
�Ejemplo de Usos de un Loader
Sin una clase que realmente lea el fichero, no es posible cargar su contenido. Con una clase Loader es sencillo. La siguiente lista presenta la receta para usar un cargador.
- encontrar un cargador (si no hay ninguno disponible, los escribimos)
- importar la clase cargador para nuestro formato de fichero
- importar otras clases necesarias
- declarar una variable Scene (no usar el constructor)
- crear un objeto loader
- cargar el fichero en un bloque try, asignar el resultado a la variable Scene
- insertar el Scene dentro del escenariog gr�fico
Con el JDK 1.2 se distribuye una clase basada en este ejemplo, se encuentra en jdk1.2/demo/java3d/ObjLoad. El Fragmento de C�digo 3-1 presenta un extracto del c�digo de esta demo.
La clase ObjectFile se distribuye con el paquete com.sun.j3d.loaders como ejemplo. La Tabla 3-1 muestra algunos otros ejemplos de cargadores disponibles.
Clase ObjectFile Paquete: com.sun.j3d.loaders Implementa: Loader La clase ObjectFile implementa el interface Loader para el formato de fichero de Wavefront ".obj", un formato de ficheros de objetos 3D est�ndard creado por el uso de Wavefront's Advanced Visualizer _. Los ficheros Object est�n basados en texto soportanto tanto geometr�a poligonal como de forma libre (curvas y superficies). El cargador de ficheros .obj de Java 3D soporta un subconjunto de formatos de ficheros, pero es completamente suficiente para cargar casi todos los ficheros Object disponibles. La geometr�a de forma libre no est� soportada. |
1. import com.sun.j3d.loaders.objectfile.ObjectFile; 2. import com.sun.j3d.loaders.ParsingErrorException; 3. import com.sun.j3d.loaders.IncorrectFormatException; 4. import com.sun.j3d.loaders.Scene; 5. import java.applet.Applet; 6. import javax.media.j3d.*; 7. import javax.vecmath.*; 8. import java.io.*; 9. 10. public class ObjLoad extends Applet { 11. 12. private String filename = null; 13. 14. public BranchGroup createSceneGraph() { 15. // Create the root of the branch graph 16. BranchGroup objRoot = new BranchGroup(); 17. 18. ObjectFile f = new ObjectFile(); 19. Scene s = null; 20. try { 21. s = f.load(filename); 22. } 23. catch (FileNotFoundException e) { 24. System.err.println(e); 25. System.exit(1); 26. } 27. catch (ParsingErrorException e) { 28. System.err.println(e); 29. System.exit(1); 30. } 31. catch (IncorrectFormatException e) { 32. System.err.println(e); 33. System.exit(1); 34. } 35. 36. objRoot.addChild(s.getSceneGroup()); 37. }
Este programa trata sobre a�adir comportamientos (el efecto por defecto, o la interacci�n con el rat�n - cubierto en el Cap�tulo 4) y luces (Cap�tulo 6) para proporcionar una renderizaci�n sombreada del modelo del objeto. Por supuesto, podemos hacer muchas otras cosas con el modelo en un programa Java 3D como a�adir animaciones, a�adir otras geom�trias, cambiar el color del modelo, etc.
Dentro de la distribuci�n del JDK 1.2 tenemos un ejemplo de loader en jdk1.2/demos/java3d/lightwave/Viewer.java. Este cargador carga las luces y animaciones espacificadas en un fichero .lws de Lightwave.
�Cargadores Disponibles P�blicamente
En Java 3D existen varias clases cargadoras. La siguiente tabla lista los formatos de ficheros cuyos cargadores est�n disponibles p�blicamente. En el momento de escribir esto, al menos hay disponible una clase cargador por cada uno de estos formatos de fichero:
Formato de Fichero | Descripci�n |
---|---|
3DS | 3D-Studio |
COB | Caligari trueSpace |
DEM | Digital Elevation Map |
DXF | AutoCAD Drawing Interchange File |
IOB | Imagine |
LWS | Lightwave Scene Format |
NFF | WorldToolKit NFF format |
OBJ | Wavefront |
PDB | Protein Data Bank |
PLAY | PLAY |
SLD | Solid Works (prt and asm files) |
VRT | Superscape VRT |
VTK | Visual Toolkit |
WRL | Virtual Reality Modeling Language |
Tabla 3-1, Cargadores Java 3D disponibles P�blicamente
Puedes localizar estos cargadores desde la p�gina principal de Java 3D: http://java.sun.con/products/java-media/3d.
�Interfaces y Clases Base del Paquete Loader
Esta gran varidad de cargadores existe para hacer m�s sencilla la escritura de cargadores para los dise�adores Java 3D. Las clases Loader son implementaciones del interface Loader que baja el nivel de dificultad para escribir un cargador. Como en el ejemplo, un programa que carga un fichero 3D realmente usa un cargador y un objeto escena. El cargador lee, analiza y crea la representaci�n Java 3D de los contenidos del fichero. El objeto escena almacena el escenario grafico creado por el cargador. Es posible cargar escenas desde m�s de un fichero (del mismo formato) usando el mismo objeto cargador y crear m�ltiples objetos escena. Los ficheros de diferentes formatos pueden combinarse en un programa Java 3D usando las clases cargadoras apropiadas.
El siguiente bloque de referencia lista los interface del paquete com.sun.j3d.loaders. Un loader implementa el interface loader y usa una clase que implementa el interface scene.
Sumario de Interfaces de com.sun.j3d.loaders
|
Adem�s de estos interfaces, el paquete com.sun.j3d.loaders proporciona implementaciones b�sicas de los interfaces.
Sumario de Clases de com.sun.j3d.loaders
|
Sumario de M�todos del Interface Loader Paquete: com.sun.j3d.loaders El interface Loader se usa para especificar la localizaci�n y los elementos de un formato de fichero a cargar. Este interface se utiliza para darle a los cargadores de varios formatos de ficheros un interface p�blico com�n. Idealmente el interface Scene ser� implementado para darle al usuario un interface consistente para extraer los datos. Scene load(java.io.Reader reader) Este m�todo carga el Reader y devuelve el objeto Scene que contiene la escena. Scene load(java.lang.String fileName) Este m�todo carga el fichero nombrado y devuelve el objeto Scene que contiene la escena. Scene load(java.net.URL url) Este m�todo carga el fichero nombrado y devuelve el objeto Scene que contiene la escena. void setBasePath(java.lang.String pathName) Este m�todo selecciona el nombre del path base para los ficheros de datos asociados con el fichero pasado en el m�todo load(String). void setBaseUrl(java.net.URL url) Este m�todo selecciona el nombre de la URL base para los ficheros de datos asociados con el fichero pasado en el m�todo load(String). void setFlags(int flags) Este m�todo selecciona las banderas de carga para el fichero.
|
La clase LoaderBase proporciona una implementaci�n para cada uno de los tres m�todos load() del interface Loader. LoaderBase tambi�n implementa dos constructores. Observa que los tres m�todos cargadores devuelven un objeto Scene.
Sumario de Constructores de la Clase LoaderBase Paquete: com.sun.j3d.loaders Implementa: Loader Esta clase implementa el interface Loader. El autor de un cargador de ficheros deber�a extender esta clase. El usuario de un cargador de ficheros deber�a usar estos m�todos. LoaderBase() Construye un Loader con los valores por defecto para todas las variables. LoaderBase(int flags) Construye un loader con las banderas especificadas. |
Lista Parcial (m�todos usados por usuarios) de la Clase SceneBase Background[] getBackgroundNodes() Behavior[] getBehaviorNodes() java.lang.String getDescription() Fog[] getFogNodes() float[] getHorizontalFOVs() Light[] getLightNodes() java.util.Hashtable getNamedObjects() BranchGroup getSceneGroup() Sound[] getSoundNodes() TransformGroup[] getViewGroups() |
�Escribir un Loader
Como se mencion� arriba, la caracter�stica m�s importante de los cargadores es que podemos escribir el nuestro propio, lo que significa que todos los usuarios de Java 3D tambi�n pueden hacerlo!
Para escribir un cargador, debemos extender la clase LoaderBase definida en el paquete com.sun.j3d.loaders. El nuevo cargador usar� la clase Scene del mismo paquete.
Los futuros cargadores deber�an tener poca necesitad de subclasificar SceneBase, o de implementar directamente Scene, ya que la funcionalidad de SceneBase es bastante correcta. Esta clase es responsable del almacenamiento y recuperaci�n de datos creados por un cargador mientras lee un fichero. Los m�todos de almacenamiento (usados s�lo por los autores del Loader) son todas las rutinas add*. Los m�todos recuperadores (usados principalmente por los usuarios de Loader) son todas las rutinas get*.
Escribir un cargador de ficheros puede ser bastante complejo dependiendo de la complejidad del formato del fichero. La parte m�s dura es analizar el fichero. Por supuesto, tenemos que empezar con la documentaci�n del formato de fichero para el que queremos escribir la clase Loader. Una vez que se entiende el formato, empezamos leyendo las clase bases de loader y scene. La nueva clase loader extender� la clase base loader y usar� la clase base scene.
En la extensi�n del clase loader base, la mayor�a del trabajo ser� escribir m�todos que reconozcan los distintos tipos de contenidos que se pueden representar en el formato del fichero. Cada uno de esos m�todos crea el correspondiente componente Java 3D del escenario gr�fico y lo almacena en un objeto scene.
Sumario de Constructores de la Clase SceneBase Paquete: com.sun.j3d.loaders Implementa: Scene Esta clase implementa el interface Scene y lo ampl�a para incorporar utilidades que podr�an usars los cargadores. Esta clase es responsable del almacenamiento y recuperaci�n de los datos de la escena. SceneBase() Crea un objeto SceneBase - no deber�a haber ninguna raz�n para usar este constructor excepto en la implementaci�n de una nueva clase de loader. |
�GeometryInfo
Si no tenemos acceso a los ficheros de modelos geom�tricos o a software de modelado geom�trico, tenemos que crear nuestra geometr�a a mano. Como se mencion� en cap�tulos anteriores, esta codificaci�n de geometr�a a mano requiere mucho tiempo y es una actividad muy propensa a errores. Como sabemos, cuando especifamos geometr�as a trav�s de las clases coraz�n, estamos limitados a tri�ngulos y cuadrados. Usando las clase de utilidad GeometryInfo se puede mejorar el tiempo empleado y el trabajo tedioso de la creacci�n de geometr�as. En lugar de especificar cada tri�ngulo, podemos especificar pol�gonos arbitrarios, que pueden ser c�ncavos, pol�gonos no planos, e incluso con agujeros. El objeto GeometryInfo, y otras clases de utilidad, convierten esta geometr�a en geometr�a tirangular que Java 3D puede renderizar.
Por ejemplo, si queremos crear un coche en Java 3D, en vez de especificar tri�ngulos, podemos espcificar el perfil del coche como un pol�gono en un objeto GeometryInfo. Luego, usando un objeto Triangulator, el pol�gono puede subdividirse en tri�ngulos. La imagen de la izquierda de la figura 3-2 muestra el perfil de un coche como un pol�gono. El imagen de la derecha es el pol�gonos subdividido en tri�ngulos.
Si estamos interesados en el rendimiento, �y qui�n no?, usamos un objeto Stripifier para convertir los tri�ngulos en franjas de tri�ngulos. Si queremos sombrear el objeto visual, usamos el NormalGenerator para calcular las superficies y la geometr�a.
El programa GeomInfoApp.java, usa las clases GeometryInfo, Triangulator, Stripifier, y NormalGeneration para crear un coche. La Figura 3-3 muestra dos renderizaciones podrucidas por GeomInfoApp.java. En ambas, las l�neas azules muestran los contornos especificados en el objeto GeometryInfo. Los tri�ngulos rojos (rellenos y sombreados a la ziquierda y enmarcados a la derecha) fueron calculados autom�ticamente por el objeto GeometryInfo con Triangulation, NormalGeneration, y Stripification.
Un sencillo pol�gono plano, similar al de la figura 3-2, especifica el perfil de un coche (cada lado) en el ejemplo GeomInfoApp.
�Sencillo Ejemplo de GeometryInfo
Usar un objeto GeometryInfo es tan sencillo como usar las clases coraz�n GeomertryArray si no m�s sencillo. En la creacci�n de un objeto GeomertyInfo, simplemente especificamos el tipo de geometr�a que vamos a necesitar. Las opciones son POLYGON_ARRAY, QUAD_ARRAY, TRIANGLE_ARRAY, TRIANGLE_FAN_ARRAY, y TRIANGLE_STRIP_ARRAY. Entonces seleccionamos las coordenadas y el contador de franjas. No tenemos que decirle al objeto GeometryInfo cu�ntas coordenadas hay en los datos; se calcular�n autom�ticamente.
El Fragmento de C�digo 3-2 muestra un ejemplo de aplicaci�n GeometryInfo. Las l�neas 1-3 muestran la creacci�n de un objeto GeometryInfo y la especificaci�n de la geometr�a inicial.
Despu�s de haber creado el objeto GeometryInfo, podr�an usarse las otras clases. Si queremos usar el NormalGenerator, por ejemplo, primero creamos un objeto NormalGenerator, luego le pasamos el objeto GeometryInfo. Las l�neas 8 y 9 hacen exactamente esto.
1. GeometryInfo gi = new GeometryInfo(GeometryInfo.POLYGON_ARRAY); 2. gi.setCoordinates(coordinateData); 3. gi.setStripCounts(stripCounts); 4. 5. Triangulator tr = new Triangulator(); 6. tr.triangulate(gi); 7. 8. NormalGenerator ng = new NormalGenerator(); 9. ng.generateNormals(gi); 10. 11. Stripifier st = new Stripifier(); 12. st.stripify(gi); 13. 14. Shape3D part = new Shape3D(); 15. part.setAppearance(appearance); 16. part.setGeometry(gi.getGeometryArray());
�Clases para GeometryInfo
La clase GeometryInfo y sus clases relacionadas son miembros del paquete com.sun.j3d.util.geometry y son subclases de Object. La Figura 3-4 muestra el �rbol de estas clases.
La clase GeometryInfo s�lo tiene un constructor y en �l especificamos el tipo de geometr�a a especificar por las coordenadas.
Sumario de Constrcutores de la Clase GeometryInfo Paquete: com.sun.j3d.utils.geometry Extiende: java.lang.Object El objeto GeometryInfo es donde ponemos nuestra geometr�a si queremos usar las librer�as de utilidades de Java 3D. Una vez que tenemos los datos en el objeto GeometryInfo, podemos enviarlo a cualquiera (o a todas) las clases de utilidades para realizar operaciones sobre ellas, como generar superficies o convertirlo en franjas largas para una renderizaci�n m�s eficiente. La geometr�a se carga tal como es en el objeto GeometryArray de Java 3D, pero hay unas pocas opciones para obtener datos del objeto. La propia GeometryInfo contiene algunas sencillas utilidades, como el c�lculo de �ndices para datos no indexados y obtener datos no usados en nuestra informaci�n de geometr�a indexada ("compactaci�n"). GeometryInfo(int primitive) Construye y un objeto GeometryInfo, donde "primitive" es uno de
|
La clase GeometryInfo tiene muchos m�todos. Muchos de ellos son para seleccionar (u obtener) datos de coordenadas, colores, �ndices, superficies o de coordenadas de textura. La mayor�a de las aplicaciones s�lo usar�n unos pocos de estos m�todos. Sin embargo, es conveniente poder especificar la geometr�a a cualquier nivel de detalle y deja el resto calculado.
Lista Parcial de M�todos de la Clase GeometryInfo void recomputeIndices() Reconstruye los �ndices para garantizar la informaci�n de conexi�n. void reverse() Invierte el orden de todas las listas. void setColorIndices(int[] colorIndices) Selecciona el array de �ndices en un array Color. void setColors(Color3f[] colors) Selecciona el array de colores. void setColors(Color4f[] colors) Selecciona el array de colores, Hay otros m�todos setColors. void setContourCounts(int[] contourCounts) Selecciona la lista del contador de contornos. void setCoordinateIndices(int[] coordinateIndices) Selecciona el array de �ndices en el array de coordenadas. void setCoordinates(Point3f[] coordinates) Selecciona el array de coordenadas. void setCoordinates(Point3d[] coordinates) Selecciona el array de coordenadas. Hay otros m�todos setCoordinates. void setNormalIndices(int[] normalIndices) Selecciona el array de �ndices en el array de superficies normales. void setNormals(Vector3f[] normals) Selecciona el array de superficies normales. void setNormals(float[] normals) Selecciona el array de superficies normales. void setStripCounts(int[] stripCounts) Selecciona el array del contador de franjas. void setTextureCoordinateIndices(int[] texCoordIndices) Selecciona el array de �ndices en el array de coordenadas de textura. void setTextureCoordinates(Point2f[] texCoords) Selecciona el array de coordenadas de textura. Hay otros m�todos setTextureCoordinates. |
Todas las clases de 'ayuda' de GeometryInfo se usan de forma similar. Los siguientes bloques de referencia muestran los constructoes y m�todos para Triangulator, Stripifier, y NormalGenerator, en este orden, que es el orden en que se usar�an para un POLYGON_ARRAY.
La utilidad Triangulator s�lo se usa con geometr�a POLYGON_ARRAY. Otros objetos GeometryInfo con otras geometr�as primitivas s�lo usar�an Stripifier y NormalGenerator.
El constructor por defecto para la clase Triangulator simplemente crea un objeto Triangulation.
Sumario de Constructores de la Clase Triangulator Paquete: com.sun.j3d.utils.geometry Extiende: java.lang.Object Triangulator es una utilidad para convertir pol�gonos arbitrar�os en tri�ngulos para que puedan ser renderizados por Java 3D. Los pol�gonos pueden ser c�ncavos, no planos, y pueden contener agujeros. Triangulator() Creata un uevo ejemplar de Triangulator. |
El �nico m�todo de la clase Triangulator es para triangular un objeto GeometryInfo.
Sumario de M�todos de la Clase Triangulator void triangulate(GeometryInfo gi) Esta rutina convierte el objeto GeometryInfo desde el tipo primitivo POLYGON_ARRAY al tipo primitivo TRIANGLE_ARRAY usando t�cnicas de descomposici�n de pol�gonos. |
El �nico constructor de la clase Stripifier crea un objeto stripification.
Sumario de Constructores de la Clase Stripifier Paquete: com.sun.j3d.utils.geometry Extiende: java.lang.Object La utilidad Stripifier cambia el tipo primitivo del objeto GeometryInfo a una franja de tri�ngulos. Las franjas se hacen analizando los tri�ngulos en los datos originales y conect�ndolos juntos. Para obtener un mejor resultado se debe realizar antes un NormalGeneration sobre el objeto GeometryInfo. Stripifier() Crea el objeto Stripifier. |
El �nico m�todo de la clase Stripifier es para convertir la geometr�a de un objeto GeometryInfo.
Sumario de M�todos de la Clase Stripifier void stripify(GeometryInfo gi) Cambia la geometr�a contenida en el objeto GeometryInfo en un array de franjas de tri�ngulos. |
La clase NormalGenerator tiene dos constructores. El primero construye un NormalGenerator con un valor por defecto para el �ngulo de pliegue. El segundo constructor permite la especificaci�n del �ngulo de pliegue.
Sumario de Constructores de la Clase NormalGenerator Paquete: com.sun.j3d.utils.geometry Extiende: java.lang.Object La utilidad NormalGenerator calcula y rellena en las superficies de un objeto GeometryInfo. Las superficies normales se estiman bas�ndose en el an�lisis de la informaci�n de coordenadas indexadas. Si nuestros datos no est�n indexados, se creara una lista de �ndices. Si dos (o m�s) tri�ngulos del modelo comparten el mismo �ndice de coordenadas el normalgenerator intentar� generar una superficie para el v�rtice, resultando en una superficie pulida. Si dos coordenadas no tienen el mismo �ndice entonces tendr�n dos superficies separadas, incluso si tienen la misma posici�n. Esto resultar� en un "pliegue" en nuestro objeto. Si sospechamos que nuestros datos no est�n indexados apropiadamente, debemos llamar a GeometryInfo.recomputeIndexes(). Por supuesto, algunas veces, nuestro modelo tiene un pliegue. Si dos superficies triangulares difieren por m�s de creaseAngle, entonces el v�rtice obtendr� dos superficies separadas, creando un pliegue discontin�o en el modelo. Esto es perfecto para el borde de un tabla o la esquina de un cubo, por ejemplo. NormalGenerator() Construye un NormalGenerator con el �ngulo de pliegue por defecto (0.76794 radianes, o 44�). NormalGenerator(double radians) Construye un NormalGenerator con el �ngulo de pliegue especificado en radianes. |
Entre los m�todos de la clase NormalGenerator se incluyen algunos para seleccionar u obtener el �ngulo de pliegue, y c�lculo de superficies para la geometr�a de un objeto GeometryInfo.
Sumario de M�todos de la Clase NormalGenerator void generateNormals(GeometryInfo geom) Genera superficies para el objeto GeometryInfo. double getCreaseAngle() Devuelve el valor actual para el �ngulo de pliegue, en radianes. void setCreaseAngle(double radians) Selecciona el �ngulo de pliegue en radianes. |
�Texto 2D
Hay dos formas de a�adir texto a una escena Java 3D. Una forma es usar la clase Text2D y otra es usar la clase Text3D. Obviamente, la diferencia es que los objetos Text2D tienen dos dimensiones y los objetos Text3D tienen tres dimensiones. Otra diferencia significante es la forma en que se crean estos objetos.
Los objetos Text2D son pol�gonos rectangulares con el texto aplicado como una textura. Los objetos Text3D son objetos 3D geom�tricos creados como un extrusi�n del texto.
Como una subclase de Shape3D, los ejemplares de Text2D pueden ser hijos de objetos group. Para situar un objeto Text2D en una escena Java 3D, simplemente creamos el objeto Text2D y lo a�adimos al escenario gr�fico. Aqu� tenemos una sencilla receta.
- Crer un objeto Text2D
- A�adirlo al escenario gr�fico
Los objetos Text2D se implementan usando un pol�gono y una textura. El pol�gono es transparente para que s�lo sea visible la textura. La textura es la cadena de texto seleccionada con los par�metros de fuente y tipo especifiados. Los tipos de letras disponibles dependen de nuestro sistema. Normalmente, est�n disponibles Courier, Helvetica, TimesRoman, entre otros. Cualquier fuente disponible en el AWT tambi�n est� disponible para aplicaciones Text2D (y Text3D).
�Ejemplo de Text2D
El Fragmento de C�digo 3-3 muestra un ejemplo de adici�n de texto 2D a una escena. El objeto Text2D se crea en las l�neas 21 a 23. En este constructor, se especifican la cadena de texto, el color, el tipo, el tama�o y el estilo de la fuente. El objeto Text2D se a�ade a la escena en la l�nea 24. Observa la sentencia import para Font (l�nea 5) usada para las constantes de estilos de fuente.
1. import java.applet.Applet; 2. import java.awt.BorderLayout; 3. import java.awt.Frame; 4. import java.awt.event.*; 5. import java.awt.Font; 6. import com.sun.j3d.utils.applet.MainFrame; 7. import com.sun.j3d.utils.geometry.Text2D; 8. import com.sun.j3d.utils.universe.*; 9. import javax.media.j3d.*; 10. import javax.vecmath.*; 11. 12. // Text2DApp renders a single Text2D object. 13. 14. public class Text2DApp extends Applet { 15. 16. public BranchGroup createSceneGraph() { 17. // Create the root of the branch graph 18. BranchGroup objRoot = new BranchGroup(); 19. 20. // Create a Text2D leaf node, add it to the scene graph. 21. Text2D text2D = new Text2D("2D text is a textured polygon", 22. new Color3f(0.9f, 1.0f, 1.0f), 23. "Helvetica", 18, Font.ITALIC)); 24. objRoot.addChild(text2D);
Text2DApp.java es un programa completo que incluye el fragmento de c�digo anterior. En este ejemplo, el objeto Text2D rota sobre el origen de la escena. Cuando se ejecuta la aplicaci�n podemos ver, por defecto, que el pol�gono texturado no es visible cuando se ve desde atr�s.
Algunos atributos de un objeto Text2D se pueden modificar variando le paquete de apariencia referenciado y/o el NodeComponent. El Fragmento de C�digo 3-4 muestra el c�digo que modifica el objeto text2d, creado en el Fragmento de C�digo 3-3.
25. Appearance textAppear = text2d.getAppearance(); 26. 27. // The following 4 lines of code make the Text2D object 2-sided. 28. PolygonAttributes polyAttrib = new PolygonAttributes(); 29. polyAttrib.setCullFace(PolygonAttributes.CULL_NONE); 30. polyAttrib.setBackFaceNormalFlip(true); 31. textAppear.setPolygonAttributes(polyAttrib);
La textura creada por un objeto Text2D tambi�n puede aplicarse a otros objetos visuales. Ya que la aplicaci�n de texturas a objetos visuales es el objetivo del Cap�tulo 7 lo dejaremos aqu�.
�Clases Usadas para Crear Objetos Text2D
La �nica clase necesaria es la clase Text2D. Como podemos ver de la Figura 3-7, Text2D es una clase de utilidad que desciende de Shape3D.
Sumario de Constructores de la Clase Text2D Paquete: com.sun.j3d.utils.geometry Esta clase crea un rect�ngulo de textura mapeado que muestra la cadena de texto enviada por el usuario, d�ndole la apariencia suministrada en los par�metros de usuario. El tama�o del rect�ngulo (y su mapa de textura) est� determinado por los par�metros de la fuente pasados al constructor. El objeto Shape3D resultante es un rect�ngulo transparente (excepto el texto) localizado en (0, 0, 0). Text2D(java.lang.String text, Color3f color, java.lang.String fontName, int fontSize, int fontStyle) Constructor. |
Con el constructor Text2D, hay un m�todo. Este m�todo selecciona el factor de escala para crear objetos Text2D mayores o menores que el tama�o de punto especificado. Este m�todo no es �til en la versi�n 1.1.x del API, ya que s�lo se utiliza cuando se especifica el texto. En la versi�n 1.2 se ha introducido un m�todo setText() haciendo �til el setRectangleScaleFactor().
Sumario de M�todos de la Clase Text2D void setRectangleScaleFactor(float newScaleFactor) Selecciona el factor de escala usado para convertir la anchura/altura de la imagen. |
�Texto 3D
Otra forma de a�adir texto a un mundo virtual Java 3D es crear un objeto Text3D para texto. Mientras que Text2D crea el texto con un textura, Text3D crea texto usando geometr�a. La geometr�a textual de un objeto Text3D es una extrusi�n de la fuente.
Crear un objeto Text3D es un poco m�s complicado que crear un objeto Text2D. El primer paso es crear un objeto Font3D con el tipo de fuente, el tama�o y el estilo seleccionado. Luego se crea un objeto Text3D para una cadena particular usando el objeto Font3D. Como la clase Text3D es una subclase de Geometry, el objeto Text3D es un NodeComponent que es referenciado por uno o m�s objetos Shape3D:
- Crear un objeto Font3D desde una fuente AWT
- Crear un objeto Text3D para un string usando el objeto Font3D, opcionalmente especificando un punto de referencia
- Referenciar el objeto desde un objeto Shape3D a�adido al escenario gr�fico
�Ejemplo de Text3D
El Fragmento de C�digo 3-5 muestra la construcci�n b�sica de un objeto Text3D. El objeto Font3D se crea en las l�neas 19 y 20. El tipo usado es "Helvetica". Igual que en Text2D, cualquier tipo disponible en el AWT puede ser usado para Font3D y por lo tanto en el objeto Text3D. Este constructor de Font3D (l�neas 19 y 20) tambi�n selecciona el tama�o de la fuente a 10 puntos y usa la extrusi�n por defecto.
La sentencia de las l�neas 21 y 22 crea un objeto Text3D usando el objeto Font3D recientemente creado para la cadena "3DText" mientras especifica un punto de referencia para el objeto. Las �ltimas dos sentencias crean un objeto Shape3D para el objeto Text3D y lo a�aden al escenario gr�fico. Observa que la sentencia import de la l�nea 5 es necesaria porque se usa un objeto Font para la creacci�n de Font3D.
1. import java.applet.Applet; 2. import java.awt.BorderLayout; 3. import java.awt.Frame; 4. import java.awt.event.*; 5. import java.awt.Font; 6. import com.sun.j3d.utils.applet.MainFrame; 7. import com.sun.j3d.utils.universe.*; 8. import javax.media.j3d.*; 9. import javax.vecmath.*; 10. 11. // Text3DApp renders a single Text3D object. 12. 13. public class Text3DApp extends Applet { 14. 15. public BranchGroup createSceneGraph() { 16. // Create the root of the branch graph 17. BranchGroup objRoot = new BranchGroup(); 18. 19. Font3D font3d = new Font3D(new Font("Helvetica", Font.PLAIN, 10), 20. new FontExtrusion()); 21. Text3D textGeom = new Text3D(font3d, new String("3DText"), 22. new Point3f(-2.0f, 0.0f, 0.0f)); 23. Shape3D textShape = new Shape3D(textGeom); 24. objRoot.addChild(textShape);
La Figura 3-9 muestra un objeto Text3D que ilustra la extrusi�n del tipo. En la figura, la extrusi�n se muestra en gris mientras que el tipo se muestra en negro. Para recrear esta figura en Java 3D, son necesarios un objeto Material y otro DirectionalLight. No podemos seleccionar el color de los v�rtices individuales en el objeto Text3D porque no tenemos acceso a la geometr�a del objeto Text3D.
El texto de un objeto Text3D puede orientarse de una gran cantidad de formas. La orientaci�n se especifica como el camino de direcci�n. Las direcciones son right, left, up, y down.
Cada objeto Text3D tiene un punto de referencia. El punto de referencia para un objeto Text3D es el origen del objeto. El punto de referencia de cada objeto se define por la combinaci�n del camino y la alineaci�n del texto. La Tabla 3-2 muestra los efectos de las especificaciones del camino y la alineaci�n sobre la orientaci�n del texto y la situaci�n del punto de referencia.
La situaci�n del punto de referencia puede definirse expl�citamente sobreescribiendo el camino y la alineaci�n.
Los objetos Text3D tienen superficies. La adicci�n de un paquete de apariencia que incluye un objeto Material a un objeto Shape3D referenciando la geometr�a Text3D permitir� la iluminaci�n del objeto Text3D.
�Clases Usadas en la Creaci�n de Objetos Text3D
Esta secci�n presenta el material de referencia para tres clases usadas en la creacci�n de objetos Text3D: Text3D, Font3D, y FontExtrusion, en este orden. La Figura 3-10 muestra el �rbol de clases de Text3D.
La clase Text3D define varios constructores. Cada uno permite especificar ninguno, uno o todos los atributos de un objeto Text3D.
Sumario de Constructores de la Clase Text3D Un objeto Text3D es una cadena de texto que se ha convertido en una geometr�a 3D. El objeto Font3D determina la apariencia del objeto NodeComponent. Cada objeto Text3D tiene una posici�n - un punto de referencia que sit�a el objeto Text3D. El texto 3D puede situarse alrededor de su posici�n usando diferentes alineamientos y caminos. Text3D() Crea un objeto Text3D vac�o. Los valores por defecto usados para este y otros constructores son:
Text3D(Font3D font3D) Crea un objeto Text3D con el objeto Font3D dado. Text3D(Font3D font3D, String string) Crea un objeto Text3D dando un objeto Font3D y una cadena de texto. Text3D(Font3D font3D, String string, Point3f position) Crea un objeto Text3D dando un objeto Font3D y una cadena de texto. El punto de posici�n define un punto de referencia para el objeto Text3D. Su posici�n se define en relaci�n a la esquina inferior iquierda frontal de la geometr�a. Text3D(Font3D font3D, String string, Point3f position, int alignment, int path) Crea un objeto Text3D dando un objeto Font3D y una cadena de texto.
|
La clase Text3D tambi�n define varios m�todos. Cada uno de ellos nos permite modificar (seleccionar) los atributos del objeto Text3D. Esta clase tambi�n define los correspondientes m�todos get*.
Sumario de M�todos de la Clase Text3D void setAlignment(int alignment) Selecciona la pol�tica de alineamiento para este objeto Text3D NodeComponent. void setCharacterSpacing(float characterSpacing) Selecciona el espaciado entre caracteres cuando se construye la cadena Text3D. void setFont3D(Font3D font3d) Selecciona el objeto Font3D usado para este objeto Text3D NodeComponent. void setPath(int path) Selecciona la direcci�n del camino del nodo. void setPosition(Point3f position) Selecciona el punto de referencia del nodo. void setString(java.lang.String string) Copia la cadena de caracteres desde el par�metro suministrado dentro del nodo Text3D. |
Sumario de Capacidades de la Clase Text3D
|
Cada objeto Text3D se crea desde un objeto Font3D. Un s�lo objeto Font3D puede usarse para crear un n�mero ilimitado de objetos Text3D. Un objeto Font3D contiene la extrusi�n geom�trica de cada caracter en el tipo de letra. Un objeto Text3D copia las geometr�as para formar la cadena especificada. Los objetos Font3D pueden ser recolectados por el recolector de basura sin afectar a los objetos Text3D creados a partir de �l.
Sumario de Constructores de la Clase Font3D Extiende: java.lang.Object Una fuente 3D consiste en una fuente Java 2D y un camino de extrusi�n. Este camino de extrusi�n describe c�mo var�a el flanco de una letra en el eje Z. El objeto Font3D se usa para almacenar letras 2D extrusionadas. Estas letras 3D pueden usarse para construir objetos Text3D NodeComponent. Las fuentes 3D personalizadas as� como el almacenamiento de fuentes 3D en disco se cubriran en una futura versi�n de Java 3D. Tambi�n puedes ver : java.awt.Font, FontExtrusion, Text3D Font3D(java.awt.Font font, FontExtrusion extrudePath) Crea un objeto Font3D desde el objeto Font especificado. |
Sumario de M�todos de Font3D void getBoundingBox(int glyphCode, BoundingBox bounds) Devuelve la caja 3D que rodea el c�digo de letra espec�ficado. java.awt.Font getFont() Devuelve la fuente Java 2D usada para crear este objeto Font3D. void getFontExtrusion(FontExtrusion extrudePath) Copia el objeto FontExtrusion usado para crear este objeto Font3D dentro del par�metro especificado. |
La clase Font se usa en la creacci�n de un objeto Font3D.
Lista Parcial de M�todos de la Clase Font Paquete: java.awt Una clase AWT que crea una representaci�n interna de las fuentas. Font desciende de java.lang.Object. public Font(String name, int style, int size) Crea un nuevo Font desde el nombre, estilo y tama�o de punto especificados. Par�metros:
|
Sumario de Constructores de la Clase FontExtrusion Extiende: java.lang.Object El objeto FontExtrusion se usa para describir el camino de extrusi�n de un objeto Font3D. Este camino de extrusi�n se usa en conjunci�n con un objeto Font2D. El camino de extrusi�n define el fondo del contorno del texto 3D. Este contorno es perpendicular a la cara del texto. La extrusi�n tiene su origen en el lateral de la letra siendo 1.0 la altura de la letra m�s alta. El contorno debe ser monot�nico en el eje X. El usuario es responsable de la sanidad de los datos y debe asegurarse de que esta extrusionShape no causa intersecciones en letras adyacentes o dentro de una sola letra. No est� definida la salida para extrusiones que causan intersecciones. FontExtrusion() Construye un objeto FontExtrusion con los par�metros por defecto. FontExtrusion(java.awt.Shape extrusionShape) Construye un objeto FontExtrusion con la forma especificada. |
Sumario de M�todos de la Clase FontExtrusion java.awt.Shape getExtrusionShape() Obtiene el par�metro shape de FontExtrusion. void setExtrusionShape(java.awt.Shape extrusionShape) Selecciona el par�metro shape de FontExtrusion. |
�Fondo
Por defecto, el fondo de un universo virtual Java 3D es negro s�lido. Sin embargo, podemos especificar otros fondos para nuestros mundos virtuales. El API Java 3D proporciona una forma f�cil de especificar un color s�lido, una imagen, una geometr�a o una combinaci�n de �stos como fondo.
Cuando especificamos una imagen para el fondo, se sobreescribie la especificaci�n del color de fondo, si existe. Cuando se especifica una geometr�a, se dibuja sobre el color de fondo o la imagen.
La �nica parte espinosa es la especificaci�n de un fondo geom�trico. Toda la geometr�a de fondo se especifica como puntos en una esfera. Si nuestra geometr�a es un PointArray, que podr�a representar estrellas a a�os luz, o un TriangleArray, que podr�a representar monta�as en la distancia. La geometria de fondo se proyecta sobre el infinito cuando se renderiza.
Los objetos Background tienen l�mites de aplicaci�n, lo que nos permite que se puedan especificar diferentes fondos para diferentes regiones del mundo virtual. Un nodo Background est� activo cuando su regi�n de aplicaci�n intersecciona con el volumen de activaci�n del ViewPlatform.
Si est�n activos varios nodos Background,el nodo que est� m�s "cercano" al ojo ser� el utilizado. Si no hay ning�n nodo Background activo, la ventana se mostrar� en negro. Sin embargo, la definici�n de "m�s cercano" no est� especificada. Por cercano, se elige el fondo con los l�mites de aplicaci�n m�s internos que encierra la ViewPlatform.
Es improbable que nuestra aplicaci�n necesite iluminar la geometr�a del fondo -- en realidad el sistema visual humano no puede percibir los detalles visuales a grandes distancias. Sin embargo, una geometr�a de fondo si puede ser sombreada. La geometr�a del fondo podr�a no contener luces, pero las luces definidas en el escenario gr�fico pueden influenciar en la geometr�a del fondo.
Para crear un fondo seguimos esta sencilla receta:
- Crear un objeto Background especificando un color o una imagen.
- A�adir geometr�a (opcional).
- Proporcionar un l�mite de Aplicaci�n o BoundingLeaf.
- A�adir el objeto Background al escenario gr�fico.
�Ejemplos de fondos
Como se explic� en la secci�n anterior, un fondo puede tener un color o una imagen. La Geometr�a puede aparecer en el fondo con el color o la imagen. Esta secci�n proporciona un ejemplo de un fondo blanco s�lido. Un segundo ejemplo muestra la adicci�n de geom�tria al fondo.
Ejemplo de Fondo Coloreado
Las l�neas de c�digo del Fragmento de C�digo 3-6 corresponden con los pasos de la receta anterior. Junto a la personalizaci�n del color, el �nico posible ajuste es para definir unos l�mites de aplicaci�n m�s apropiados para el fondo (o usar un BoundingLeaf).
1. Background backg = new Background(1.0f, 1.0f, 1.0f); 2. // 3. backg.setApplicationBounds(BoundingSphere()); 4. contentRoot.addChild(backg);
Ejemplo de Geometr�a de Fondo
De nuevo, las l�neas de c�digo en el Fragmento de C�digo 3-7 corresponden con lo pasos de la receta de creacci�n de un fondo. En este fragmento, se llama al m�todo createBackGraph() para crear la geometr�a del fondo. Este m�todo devuelve un objeto BranchGroup. Para un ejemplo m�s completo puedes ver el fichero BackgroundApp.java.
1. Background backg = new Background(); //black background 2. backg.setGeometry(createBackGraph()); // add BranchGroup of background 3. backg.setApplicationBounds(new BoundingSphere(new Point3d(), 100.0)); 4. objRoot.addChild(backg);
BackgroundApp.java
Para apreciar un fondo, necesitamos experimentarlo. BackgroundApp.java es una aplicaci�n completa con un fondo geom�trico. Esta aplicaci�n nos permite movernos por un mundo virtual Java 3D. Mientras nos movemos, podemos ver el movimiento relativo entre la geometr�a local y la del fondo.
BackgroundApp.java usa la clase KeyNavigatorBehavior proprocionada por la librer�a de utilidades para visores de movimiento.
KeyNavigatorBehavior responde a las teclas de flechas, PgUp, y PgDn para el movimiento. La tecla Alt tambi�n juega un papel (para m�s detalles puedes ver el Cap�tulo 4. Cuando ejecutes BackgroundApp, no te olvides de rotar para ver la _constellation_, as� como viajar lejos en la distancia.
La clase Background
La Figura 3-13 muestra el �rbol de clase de la clase Background. Como una extensi�n de la clase Leaf, un ejemplar de la clase Background puede ser un hijo de un objeto Group.
Background tiene varios constructores. Los constructores con par�metros nos permiten especificar un color o una imagen para el fondo. La geometr�a del fondo s�lo se puede aplicar a trav�s del m�todo apropiado.
Sumario de Constructores de la Clase Background El nodo hoja Background define un color s�lido o una imagen para el fondo que se usa para rellenar la ventana al principio de cada nuevo marco. Opcionalmente permite referenciar geometr�as de fondo. La geometr�a de fondo debe representarse dentro de una esfera y es dibujada hacia el infinito. Tambi�n especifica una regi�n de aplicaci�n en la que este fondo est� activo. Background() Construye un nodo Background con un color por defecto (negro). Background(Color3f color) Construye un nodo Background con el color especificado. Background(float r, float g, float b) Construye un nodo Background con el color especificado. Background(ImageComponent2D image) Construye un nodo Background con la imagen especificada. |
Cualquier atributo de un fondo puede seleccionarse a trav�s de sus m�todos.
Sumario de M�todos de la Clase Background void setApplicationBoundingLeaf(BoundingLeaf region) Selecciona la regi�n de aplicaci�n del Background a la hoja especificada. void setApplicationBounds(Bounds region) Selecciona la regi�n de aplicaci�n del Background a los l�mites especificados. void setColor(Color3f color) Selecciona el color del fondo. void setColor(float r, float g, float b) Selecciona el color del fondo. void setGeometry(BranchGroup branch) Selecciona la geometr�a del fondo al nodo BranchGroup especificado. void setImage(ImageComponent2D image) Selecciona la imagen del fondo. |
Sumario de Capacidades de la Clase Background
|
BoundingLeaf
Los Bounds (l�mites) se usan con luces, comportamientos, fondos y una gran variedad de otras aplicaciones en Java 3D. Los Bounds permiten al programador variar la acci�n, la apariencia, y/o el sonido sobre el campo virtual. La especificaci�n de Bounds tambi�n permite al sistema de renderizado de Java 3D mejorar la ejecuci�n del recortado y por lo tanto mejorar el rendimiento.
La especificaci�n t�pica de l�mites utiliza un objeto Bounds para limitar una regi�n. En el escenario gr�fico resultante, los objetos Bounds se mueven con los objetos que lo referencian. Esto esta bi�n para muchas aplicaciones; sin embargo, podr�a haber situaciones en las que fuera deseable tener la regi�n l�mite que se moviera independientemente de los objetos que usan los l�mites.
Por ejemplo, si un mundo incluye una fuente de luz estacionaria que ilumina unos objetos en movimiento, los l�mites de la luz deber�an incluir el objeto en movimiento. Una forma de manejar esto podr�a ser crear los l�mites lo suficientemente grandes como para incluir todos los lugares donde se mueve el objeto. Esta no es la mejor respuesta en muchos casos. Una mejor soluci�n es usar un BoundingLeaf. Situado en el escenario gr�fico con el objeto visual, el BoundingLeaf se mueve con el objeto visual independientemente de la fuente de luz. La Figura 3-14 muestra un escenario gr�fico con un una luz que usa un nodo BoundingLeaf.
Una aplicaci�n interesante de un objeto BoundingLeaf sit�a un BoundingLeaf en la viewPlatform. Este BoundingLeaf puede usarse para un l�mite "siempre sobre" para un comportamiento, o para unos l�mites de aplicaci�n "aplica siempre" para fondos o nieblas. El Fragmento de C�digo 3-8 presenta un ejemplo de la aplicaci�n BoundingLeaf usada con un Background.
El Fragmento de C�digo 3-8 presenta un ejemplo de c�mo a�adir un BoundingLeaf como un hijo de PlatformGeometry para proporcionar un l�mite de "aplica siempre" para un fondo. En este c�digo se ha modificado el m�todo est�ndard createSceneGraph() para que tome un s�lo par�metro, que es el objeto SimpleUniverse. Esto es necesario para crear el objeto PlatformGeometry.
Las l�neas 2, 3 y 4 crean el objeto BoundingLeaf, el objeto PlatformGeometry y hace del objeto BoundingLeaf un hijo de PlatformGeometry, en este orden. Si tuviera que haber m�s objeto PlatformGeometry, se a�adir�an en este punto. El objeto PlatformGeometry se a�ade la rama de vista gr�fica en la l�nea 6.
El objeto BoundingLeaf se selecciona como los limites de aplicaci�n para el objeto background en la l�nea 11. El mismo objeto BoundingLeaf puede usarse para otros prop�sitos en este programa. Por ejemplo, puede usarse para los comportamientos. Observa que usando el BoundingLeaf en este programa como el InfluencingBoundingLeaf de una luz hace que esta luz no influya en todos los objetos del mundo virtual.
1. void createSceneGraph (SimpleUniverse su) { 2. BoundingLeaf boundingLeaf = new BoundingLeaf(); 3. PlatformGeometry platformGeom = new PlatformGeometry(); 4. platformGeom.addChild(boundingLeaf); 5. platformGeom.compile(); 6. simpleUniv.getViewingPlatform().setPlatformGeometry(platformGeom); 7. 8. BranchGroup contentRoot = new BranchGroup(); 9. 10. Background backg = new Background(1.0f, 1.0f, 1.0f); 11. backg.setApplicationBoundingLeaf(boundingLeaf); 12. contentRoot.addChild(backg);
�La Clase BoundingLeaf
La clase BoundingLeaf extiende la clase Leaf. La Figura 3-15 representa el �rbol de clases de BoundingLeaf.
El constructor sin par�metros de BoundingLeaf crea l�mites para una esfera. El otro constructor permite la especificaci�n de l�mites para el objeto BoundingLeaf.
Sumario de Constructores de la Clase BoundingLeaf El nodo BoundingLeaf define una regi�n de l�mites que puede ser referenciada por otros nodos para definir un regi�n de influencia, o una regi�n programada. BoundingLeaf() Construye un nodo BoundingLeaf con un objeto esfera. BoundingLeaf(Bounds region) Construye un nodo BoundingLeaf con la regi�n de l�mites especificada. |
Sumario de M�todos de la Clase BoundingLeaf Bounds getRegion() Recupera la regi�n de l�mites de este BoundingLeaf void setRegion(Bounds region) Selecciona la regi�n de l�mites de este nodo BoundungLeaf |
�Datos de Usuario
Cualquier SceneGraphObject puede referenciar cualquier otro objeto como datos de usuario. Primero, deber�amos habernos dado cuenta de que casi cualquier clase del coraz�n del API Java 3D es un descendiente de SceneGraphObject. La lista de descendientes de SceneGraphObject incluye Appearance, Background, Behavior, BranchGroup, Geometry, Lights, Shape3D, y TransformGroup.
Las aplicaci�n para el campo UserData, s�lo est� limitado por nuestra imaginaci�n. Por ejemplo, una aplicaci�n podr�a tener varios objetos recolectables. Cada uno de estos objetos podr�a tener alg�n texto informativo almacenado en el objeto de datos de usuario. Cuando el usuario recoge un objeto, se puede mostrar la informaci�n de los datos de usuario.
Otra aplicaci�n podr�a almacenar alg�n valor calculado para un objeto de escenario gr�fico como su posici�n en las coordenadas del mundo virtual. Y otra aplicaci�n podr�a almacenar alguna informaci�n especifica de comportamiento que podr�a controlar el comportamiento aplicado a varios objetos.
Lista Parcial de M�todos de Datos de Usuario de SceneGraphObject SceneGraphObject es una superclase com�n para todos los objetos componentes de un escenario gr�fico. Estos incluyen Node, Geometry, Appearance, etc. java.lang.Object getUserData() Recupera el campo userData desde este objeto del escenario gr�fico. void setUserData(java.lang.Object userData) Selecciona el campo userData asociado con este objeto del escenario gr�fico. |