Java 3D (Exercício 3)
Professora: Isabel Harb Manssour
 

O objetivo deste exercício é verificar como criar textos (2D e 3D) e colocar backgrounds em aplicações Java 3D.

Inicialmente, crie uma classe chamada Text2DExample para executar um exemplo onde é colocado um texto 2D. Clique duas vezes sobre a caixa e substitua o código que o BlueJ colocou pelo código apresentado abaixo. Depois compile e execute o programa Java 3D.

/*
 *  @(#)HelloUniverse.java 1.55 02/10/21 13:43:36
 *
 * Copyright (c) 1996-2002 Sun Microsystems, Inc. All Rights Reserved.
 *
 * Redistribution and use in source and binary forms, with or without
 * modification, are permitted provided that the following conditions
 * are met:
 *
 * - Redistributions of source code must retain the above copyright
 *   notice, this list of conditions and the following disclaimer.
 *
 * - Redistribution in binary form must reproduce the above copyright
 *   notice, this list of conditions and the following disclaimer in
 *   the documentation and/or other materials provided with the
 *   distribution.
 */

///////////////////////////////////////////////////////////////////////////
// Isabel Harb Manssour
// Junho de 2003
// Text2DExample.java ilustra como criar textos 2D.
// Este código está baseado no demo HelloUniverse.java

import javax.swing.*;
import java.awt.*;
import com.sun.j3d.utils.geometry.*;
import com.sun.j3d.utils.universe.*;
import javax.media.j3d.*;
import javax.vecmath.*;

public class Text2DExample extends JFrame {

    ///////////////////////////////////////////////////////////////////////
    // Atributo da classe Text2DExample
    //
    private SimpleUniverse universe = null;    

    ///////////////////////////////////////////////////////////////////////
    // Construtor da classe Text2DExample
    //
    public Text2DExample() {
        Container container = getContentPane();
        container.setLayout(new BorderLayout());
        GraphicsConfiguration config =
           SimpleUniverse.getPreferredConfiguration();

        Canvas3D canvas = new Canvas3D(config);
        container.add("Center", canvas);

        // Cria um sub-grafo de conteúdo
        BranchGroup scene = criaGrafoDeCena();
        universe = new SimpleUniverse(canvas);

        // O código abaixo faz com que a ViewPlatform seja movida
        // um pouco para trás, para que os objetos possam ser
        // visualizados
        universe.getViewingPlatform().setNominalViewingTransform();

        // Anexa o sub-grafo no universo  virtual
        universe.addBranchGraph(scene);
        
        setSize(350,350);
        setVisible(true);
    }    
    
    ///////////////////////////////////////////////////////////////////////
    // Método responsável pela criação do grafo de cena (ou sub-grafo)
    //    
    public BranchGroup criaGrafoDeCena() {
        
        // Cria o nodo raiz do sub-grafo
        BranchGroup objRaiz = new BranchGroup();

        // Cria o nodo TransformGroup e permite que ele possa
        // ser alterado em tempo de execução (TRANSFORM_WRITE).
        // Depois, adiciona-o na raiz do grafo.
        TransformGroup objTrans = new TransformGroup();
        objTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE);
        objRaiz.addChild(objTrans);

        // Cria um "bounds" para o background 
        BoundingSphere bounds =
           new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0);

        // Especifica um background azul e adiciona-o no grafo
        Color3f bgColor = new Color3f(0.1f, 0.1f, 0.7f);
        Background bg = new Background(bgColor);
        bg.setApplicationBounds(bounds);
        objRaiz.addChild(bg);

        // Especifica as luzes do "ambiente"
        Color3f corLuz = new Color3f(0.9f, 0.9f, 0.9f);
        Vector3f direcaoLuz  = new Vector3f(-1.0f, -1.0f, -1.0f);
        Color3f corAmb = new Color3f(0.2f, 0.2f, 0.2f);

        AmbientLight luzAmb = new AmbientLight(corAmb);
        luzAmb.setInfluencingBounds(bounds);
        DirectionalLight luzDir = new DirectionalLight(corLuz, direcaoLuz);
        luzDir.setInfluencingBounds(bounds);
        objRaiz.addChild(luzAmb);
        objRaiz.addChild(luzDir);
    
        Appearance app = new Appearance();
        Material material = new Material(new Color3f(0.7f,0.1f,0.7f), 
                                         new Color3f(0.0f,0.0f,0.0f), 
                                         new Color3f(0.7f,0.1f,0.7f), 
                                         new Color3f(1.0f,1.0f,1.0f), 60.0f);
        app.setMaterial(material);
          
        Sphere esfera = new Sphere(0.4f, 1, 40);
        esfera.setAppearance(app);
        
        objTrans.addChild(esfera);
 
        // Cria outro nodo TransformGroup node e permite que ele possa
        // ser alterado em tempo de execução (TRANSFORM_WRITE).
        // Depois, adiciona-o na raiz do grafo.
        TransformGroup textTrans = new TransformGroup();
        textTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE);
        objRaiz.addChild(textTrans);
        
        // Cria um novo objeto que irá aplicar as transformações
        // geométricas sobre texto e o adicina no grafo.
        Transform3D trans = new Transform3D();
        trans.setTranslation(new Vector3d(-0.4,0.6,0.0));
        textTrans.setTransform(trans);        
        
        // Text2D (java.lang.String text, Color3f color,
        //        java.lang.String fontName, int fontSize, int fontStyle)         
        Text2D text2D = new Text2D("E S F E R A !!",
                                   new Color3f(0.9f, 0.1f, 0.9f),
                                   "Helvetica", 30, Font.BOLD | Font.ITALIC);
        textTrans.addChild(text2D); 
 
        // Para o Java 3D realizar otimizações no grafo de cena
        objRaiz.compile();

        return objRaiz;
    }


    ///////////////////////////////////////////////////////////////////////
    // Método principal que permite executar a aplicação
    //
    public static void main(String[] args) 
    {
        Text2DExample h = new Text2DExample();
    }

}

Experimente trocar alguns parâmetros para ver o resultado. Por exemplo:

  • "Helvetica" por "Times";
  • Font.BOLD por Font.ITALIC ou Font.PLAIN;
  • 30 por 25 ou 35;
  • "E S F E R A !!" por outro texto qualquer (se necessário altere a posição do início do texto no comando trans.setTranslation(new Vector3d(-0.4,0.6,0.0));), ou aumente o field-of-view acrescentando as duas linhas abaixo no construtor após o comando universe.getViewingPlatform().setNominalViewingTransform():
            View view = universe.getViewer().getView();
            view.setFieldOfView(view.getFieldOfView()*1.4);
    
  • ou simplesmente troque a cor do texto em new Color3f(0.9f, 0.1f, 0.9f).

Para verificar como seria a inclusão de um texto 3D, crie uma nova classe com o nome Text3DExample e substitua o código que o BlueJ colocou pelo código apresentado abaixo.

/*
 *  @(#)HelloUniverse.java 1.55 02/10/21 13:43:36
 *
 * Copyright (c) 1996-2002 Sun Microsystems, Inc. All Rights Reserved.
 *
 * Redistribution and use in source and binary forms, with or without
 * modification, are permitted provided that the following conditions
 * are met:
 *
 * - Redistributions of source code must retain the above copyright
 *   notice, this list of conditions and the following disclaimer.
 *
 * - Redistribution in binary form must reproduce the above copyright
 *   notice, this list of conditions and the following disclaimer in
 *   the documentation and/or other materials provided with the
 *   distribution.
 */

///////////////////////////////////////////////////////////////////////////
// Isabel Harb Manssour
// Junho de 2003
// Text3DExample.java ilustra como criar textos 3D.
// Este código está baseado no demo HelloUniverse.java

import javax.swing.*;
import java.awt.*;
import com.sun.j3d.utils.geometry.*;
import com.sun.j3d.utils.universe.*;
import javax.media.j3d.*;
import javax.vecmath.*;

public class Text3DExample extends JFrame 
{
    ///////////////////////////////////////////////////////////////////////
    // Atributo da classe Text3DExample
    //
    private SimpleUniverse universe = null;
    
    ///////////////////////////////////////////////////////////////////////
    // Construtor da classe Text3DExample
    //
    public Text3DExample() {
        Container container = getContentPane();
        container.setLayout(new BorderLayout());
        GraphicsConfiguration config =
           SimpleUniverse.getPreferredConfiguration();

        Canvas3D canvas = new Canvas3D(config);
        container.add("Center", canvas);

        // Cria um sub-grafo de conteúdo
        BranchGroup scene = criaGrafoDeCena();
        universe = new SimpleUniverse(canvas);

        // O código abaixo faz com que a ViewPlatform seja movida
        // um pouco para trás, para que os objetos possam ser
        // visualizados
        universe.getViewingPlatform().setNominalViewingTransform();

        // Anexa o sub-grafo no universo virtual
        universe.addBranchGraph(scene);
        
        setSize(350,350);
        setVisible(true);
    }
    
    ///////////////////////////////////////////////////////////////////////
    // Método responsável pela criação do grafo de cena (ou sub-grafo)
    //    
    public BranchGroup criaGrafoDeCena() {
        
        // Cria o nodo raiz 
        BranchGroup objRaiz = new BranchGroup();

        // Cria o nodo TransformGroup e permite que ele possa
        // ser alterado em tempo de execução (TRANSFORM_WRITE).
        // Depois, adiciona-o na raiz do grafo de cena.
        TransformGroup objTrans = new TransformGroup();
        objTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE);
        objRaiz.addChild(objTrans);

        // Cria um "bounds" para o background 
        BoundingSphere bounds =
           new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0);

        // Especifica um background azul e adiciona-o no grafo
        Color3f bgColor = new Color3f(0.1f, 0.1f, 0.7f);
        Background bg = new Background(bgColor);
        bg.setApplicationBounds(bounds);
        objRaiz.addChild(bg);

        // Especifica as luzes do "ambiente"
        Color3f corLuz = new Color3f(0.9f, 0.9f, 0.9f);
        Vector3f direcaoLuz  = new Vector3f(-1.0f, -1.0f, -1.0f);
        Color3f corAmb = new Color3f(0.2f, 0.2f, 0.2f);

        AmbientLight luzAmb = new AmbientLight(corAmb);
        luzAmb.setInfluencingBounds(bounds);
        DirectionalLight luzDir = new DirectionalLight(corLuz, direcaoLuz);
        luzDir.setInfluencingBounds(bounds);
        objRaiz.addChild(luzAmb);
        objRaiz.addChild(luzDir);
    
        Appearance app = new Appearance();
        Material material = new Material(new Color3f(0.7f,0.1f,0.7f), 
                                         new Color3f(0.0f,0.0f,0.0f), 
                                         new Color3f(0.7f,0.1f,0.7f), 
                                         new Color3f(1.0f,1.0f,1.0f), 60.0f);
        app.setMaterial(material);
          
        Sphere esfera = new Sphere(0.4f, 1, 40);
        esfera.setAppearance(app);
        
        objTrans.addChild(esfera);
 
        // Cria outro nodo TransformGroup node e permite que ele possa
        // ser alterado em tempo de execução (TRANSFORM_WRITE).
        // Depois, adiciona-o na raiz do grafo.
        TransformGroup textTrans = new TransformGroup();
        textTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE);
        objRaiz.addChild(textTrans);
        
        // Cria um novo objeto que irá aplicar as transformações
        // geométricas sobre texto e o adicina no grafo.
        Transform3D trans = new Transform3D();
        Transform3D t1 = new Transform3D();
        
        t1.rotX(Math.toRadians(-10.0));
        trans.mul(t1);
        trans.setScale(0.3);
        trans.setTranslation(new Vector3d(-0.6,0.6,0.0));
        
        textTrans.setTransform(trans);      
 
        Font3D font3d = new Font3D(new Font("Helvetica", Font.PLAIN, 1),
                                   new FontExtrusion());
        Text3D textGeom = new Text3D(font3d, new String("ESFERA 3D !"),
                                     new Point3f(-1.0f, 0.0f, 0.0f));
        Shape3D textShape = new Shape3D(textGeom);
        textShape.setAppearance(app);

        textTrans.addChild(textShape); 
 
        // Para o Java 3D realizar otimizações no grafo de cena
        objRaiz.compile();

        return objRaiz;
    }

    ///////////////////////////////////////////////////////////////////////
    // Método principal que permite executar a aplicação
    //
    public static void main(String[] args) 
    {
        Text3DExample h = new Text3DExample();
    }
}

Da mesma maneira que no exemplo anterior, altere os parâmetros para verificar os diferentes efeitos que podem ser obtidos. Altere o ângulo e o eixo de rotação (t1.rotX(Math.toRadians(-10.0));), a escala (trans.setScale(0.3);) e a posição (trans.setTranslation(new Vector3d(-0.6,0.6,0.0));), por exemplo. Experimente colocar um valor de escala negativo e veja o que acontece!!! Aproveite também para analisar como se faz para alterar a cor do fundo da imagem (background). Procure colocar uma cor de fundo que você ache que ficaria melhor.

Agora, para ver um exemplo de como colocar uma imagem como background de uma cena, crie uma nova classe com o nome ImageBackgroundApplication e substitua o código que o BlueJ colocou pelo código apresentado abaixo. Também é necessário colocar os arquivos que estão em "imagens.zip" na mesma pasta onde estão os programas Java 3D (arquivos .java). Compile o programa Java 3D e em seguida o execute. Experimente trocar a imagem "parede.png" por "bg.jpg" ou qualquer outra imagem disponível.

/*
 *  @(#)HelloUniverse.java 1.55 02/10/21 13:43:36
 *
 * Copyright (c) 1996-2002 Sun Microsystems, Inc. All Rights Reserved.
 *
 * Redistribution and use in source and binary forms, with or without
 * modification, are permitted provided that the following conditions
 * are met:
 *
 * - Redistributions of source code must retain the above copyright
 *   notice, this list of conditions and the following disclaimer.
 *
 * - Redistribution in binary form must reproduce the above copyright
 *   notice, this list of conditions and the following disclaimer in
 *   the documentation and/or other materials provided with the
 *   distribution.
 */

///////////////////////////////////////////////////////////////////////////
// Isabel Harb Manssour
// Junho de 2003
// ImageBackgroundApplication.java ilustra como criar backgrounds.
// Este código está baseado no demo HelloUniverse.java

import javax.swing.*;
import java.awt.*;
import com.sun.j3d.utils.geometry.*;
import com.sun.j3d.utils.universe.*;
import com.sun.j3d.utils.image.TextureLoader;
import javax.media.j3d.*;
import javax.vecmath.*;

public class ImageBackgroundApplication extends JFrame 
{

    ///////////////////////////////////////////////////////////////////////
    // Atributo da classe ImageBackgroundApplication
    //
    private SimpleUniverse universe = null;
    

    ///////////////////////////////////////////////////////////////////////
    // Construtor da classe ImageBackgroundApplication
    //
    public ImageBackgroundApplication() {
        Container container = getContentPane();
        container.setLayout(new BorderLayout());
        GraphicsConfiguration config =
           SimpleUniverse.getPreferredConfiguration();

        Canvas3D canvas = new Canvas3D(config);
        container.add("Center", canvas);

        // Cria um sub-grafo de conteúdo 
        BranchGroup scene = criaGrafoDeCena();
        universe = new SimpleUniverse(canvas);

        // O código abaixo faz com que a ViewPlatform seja movida
        // um pouco para trás, para que os objetos possam ser
        // visualizados
        universe.getViewingPlatform().setNominalViewingTransform();

        // Anexa o sub-grafo no universo virtual
        universe.addBranchGraph(scene);
        
        setSize(350,350);
        setVisible(true);
    }
    
    
    ///////////////////////////////////////////////////////////////////////
    // Método responsável pela criação do grafo de cena (ou sub-grafo)
    //    
    public BranchGroup criaGrafoDeCena() {
        
        // Cria o nodo raiz 
        BranchGroup objRaiz = new BranchGroup();

        // Cria o nodo TransformGroup e permite que ele possa
        // ser alterado em tempo de execução (TRANSFORM_WRITE).
        // Depois, adiciona-o na raiz do grafo.
        TransformGroup objTrans = new TransformGroup();
        objTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE);
        objRaiz.addChild(objTrans);

        // Cria um "bounds" para o background 
        BoundingSphere bounds =
           new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0);
      
        // objeto para abrir imagens
        Toolkit toolkit = Toolkit.getDefaultToolkit();         
        TextureLoader texturaBg = 
                          new TextureLoader(toolkit.getImage("parede.png"), this);
        Background bg = new Background(texturaBg.getImage());
        bg.setApplicationBounds(bounds);
        bg.setImageScaleMode(Background.SCALE_REPEAT);
        objRaiz.addChild(bg);
        
        // Especifica as luzes do "ambiente"
        Color3f corLuz = new Color3f(0.9f, 0.9f, 0.9f);
        Vector3f direcaoLuz  = new Vector3f(0.0f, -0.8f, -1.0f);
        Color3f corAmb = new Color3f(0.2f, 0.2f, 0.2f);

        AmbientLight luzAmb = new AmbientLight(corAmb);
        luzAmb.setInfluencingBounds(bounds);
        DirectionalLight luzDir = new DirectionalLight(corLuz, direcaoLuz);
        luzDir.setInfluencingBounds(bounds);
        objRaiz.addChild(luzAmb);
        objRaiz.addChild(luzDir);
    
        Appearance app = new Appearance();
        Material material = new Material(new Color3f(0.9f,0.1f,0.1f), 
                                         new Color3f(0.0f,0.0f,0.0f), 
                                         new Color3f(0.9f,0.1f,0.1f), 
                                         new Color3f(1.0f,1.0f,1.0f), 60.0f);
        app.setMaterial(material);
          
        Sphere esfera = new Sphere(0.4f, 1, 40);
        esfera.setAppearance(app);
        
       objTrans.addChild(esfera);
 
        // Cria outro nodo TransformGroup node e permite que ele possa
        // ser alterado em tempo de execução (TRANSFORM_WRITE).
        // Depois, adiciona-o na raiz do grafo.
        TransformGroup textTrans = new TransformGroup();
        textTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE);
        objRaiz.addChild(textTrans);
        
        // Cria um novo objeto que irá aplicar as transformações
        // geométricas sobre texto e o adicina no grafo.
        Transform3D trans = new Transform3D();
        trans.setTranslation(new Vector3d(-0.4,0.6,0.0));
        textTrans.setTransform(trans);        
        
        // Text2D (java.lang.String text, Color3f color,
        //        java.lang.String fontName, int fontSize, int fontStyle)         
        Text2D text2D = new Text2D("E S F E R A !!",
                                   new Color3f(0.9f, 0.1f, 0.1f),
                                   "Helvetica", 30, Font.BOLD);
        textTrans.addChild(text2D); 
                                        
        // Para o Java 3D realizar otimizações no grafo de cena
        objRaiz.compile();

        return objRaiz;
    }

    ///////////////////////////////////////////////////////////////////////
    // Método principal que permite executar a aplicação
    //
    public static void main(String[] args) 
    {
        ImageBackgroundApplication app = new ImageBackgroundApplication();
    }
}

 ../Imagens/emban15.png(1469 bytes)

../Imagens/E-MAIL.JPG (3237 bytes) Comentários, dúvidas, sugestões, envie um mail para [email protected]

../Imagens/emban15.png(1469 bytes)

[Homepage Java 3D]  [Homepage Isabel H. Manssour]

Última alteração em 11 de outubro de 2003.