diff options
author | phil <[email protected]> | 2016-11-06 17:03:11 +1300 |
---|---|---|
committer | phil <[email protected]> | 2016-11-06 17:03:11 +1300 |
commit | b519162cc27f380d36c5d2f779189628a42b3800 (patch) | |
tree | 05da9b1cb5045da85665cee0b0484257552dbe73 /src/main/java/org/jdesktop/j3d/examples | |
parent | 7d153738e397b6f9e7b51ea2d127fc55cdff6032 (diff) |
move java into maven standard src/main/java and resources into
src/main/resources
Diffstat (limited to 'src/main/java/org/jdesktop/j3d/examples')
282 files changed, 54955 insertions, 0 deletions
diff --git a/src/main/java/org/jdesktop/j3d/examples/Resources.java b/src/main/java/org/jdesktop/j3d/examples/Resources.java new file mode 100644 index 0000000..a50a188 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/Resources.java @@ -0,0 +1,90 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples; + +import java.io.File; +import java.net.MalformedURLException; +import java.net.URL; + +/** + * + */ +public class Resources +{ + + /** + * Do not construct an instance of this class. + */ + private Resources() + { + + } + + /** + * Return the URL of the filename under the resources directory + */ + public static URL getResource(String filename) + { + URL url = Resources.class.getClassLoader().getResource(filename); + + if (url == null) + { + try + { + File f = new File(System.getProperty("user.dir") + "/src/" + filename); + if (!f.exists()) + f = new File(System.getProperty("user.dir") + "/src/classes/org/jdesktop/j3d/examples/" + filename); + + url = f.toURL(); + } + catch (MalformedURLException e) + { + e.printStackTrace(); + } + } + return url; + } + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/alternate_appearance/AlternateAppearanceBoundsTest.java b/src/main/java/org/jdesktop/j3d/examples/alternate_appearance/AlternateAppearanceBoundsTest.java new file mode 100644 index 0000000..7bd3d23 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/alternate_appearance/AlternateAppearanceBoundsTest.java @@ -0,0 +1,328 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.alternate_appearance; + +import java.awt.Container; +import java.awt.Frame; +import java.awt.event.ActionEvent; +import java.awt.event.ActionListener; + +import javax.swing.BoxLayout; +import javax.swing.JApplet; +import javax.swing.JCheckBox; +import javax.swing.JComboBox; +import javax.swing.JLabel; +import javax.swing.JPanel; +import javax.swing.border.TitledBorder; + +import org.jogamp.java3d.AlternateAppearance; +import org.jogamp.java3d.AmbientLight; +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.BoundingLeaf; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.Bounds; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.DirectionalLight; +import org.jogamp.java3d.Group; +import org.jogamp.java3d.Material; +import org.jogamp.java3d.Shape3D; +import org.jogamp.java3d.utils.applet.MainFrame; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Vector3f; + +public class AlternateAppearanceBoundsTest extends JApplet +implements ActionListener { + + + Material mat1, altMat; + Appearance app, otherApp; + JComboBox altAppMaterialColor; + JComboBox appMaterialColor; + JCheckBox useBoundingLeaf; + JCheckBox override; + JComboBox boundsType; + private Group content1 = null; + AlternateAppearance altApp; + Shape3D[] shapes1; + boolean boundingLeafOn = false; + // Globally used colors + Color3f white = new Color3f(1.0f, 1.0f, 1.0f); + Color3f red = new Color3f(1.0f, 0.0f, 0.0f); + Color3f green = new Color3f(0.0f, 1.0f, 0.0f); + Color3f blue = new Color3f(0.0f, 0.0f, 1.0f); + Color3f[] colors = {white, red, green, blue}; + + private Bounds worldBounds = new BoundingSphere( + new Point3d( 0.0, 0.0, 0.0 ), // Center + 1000.0 ); // Extent + private Bounds smallBounds = new BoundingSphere( + new Point3d( 0.0, 0.0, 0.0 ), // Center + 0.25 ); // Extent + private Bounds tinyBounds = new BoundingSphere( + new Point3d( 0.0, 0.0, 0.0 ), // Center + 0.05 ); // Extent + private BoundingLeaf leafBounds = null; + private int currentBounds = 2; + + private Bounds[] allBounds = {tinyBounds, smallBounds, worldBounds}; + + DirectionalLight light1 = null; + + // Get the current bounding leaf position + private int currentPosition = 0; + // Point3f pos = (Point3f)positions[currentPosition].value; + + private SimpleUniverse u = null; + + public AlternateAppearanceBoundsTest() { + } + + public void init() {System.setProperty("sun.awt.noerasebackground", "true"); + Container contentPane = getContentPane(); + + Canvas3D c = new Canvas3D(SimpleUniverse.getPreferredConfiguration()); + contentPane.add("Center", c); + + BranchGroup scene = createSceneGraph(); + // SimpleUniverse is a Convenience Utility class + u = new SimpleUniverse(c); + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + u.getViewingPlatform().setNominalViewingTransform(); + u.addBranchGraph(scene); + + + // Create GUI + JPanel p = new JPanel(); + BoxLayout boxlayout = new BoxLayout(p, + BoxLayout.Y_AXIS); + p.add(createBoundsPanel()); + p.add(createMaterialPanel()); + p.setLayout(boxlayout); + + contentPane.add("South", p); + } + + public void destroy() { + u.cleanup(); + } + + BranchGroup createSceneGraph() { + BranchGroup objRoot = new BranchGroup(); + + // Create an alternate appearance + otherApp = new Appearance(); + altMat = new Material(); + altMat.setCapability(Material.ALLOW_COMPONENT_WRITE); + altMat.setDiffuseColor( new Color3f( 0.0f, 1.0f, 0.0f ) ); + otherApp.setMaterial(altMat); + + altApp = new AlternateAppearance(); + altApp.setAppearance(otherApp); + altApp.setCapability(AlternateAppearance.ALLOW_BOUNDS_WRITE); + altApp.setCapability(AlternateAppearance.ALLOW_INFLUENCING_BOUNDS_WRITE); + altApp.setInfluencingBounds( worldBounds ); + objRoot.addChild(altApp); + + // Build foreground geometry + Appearance app1 = new Appearance(); + mat1 = new Material(); + mat1.setCapability(Material.ALLOW_COMPONENT_WRITE); + mat1.setDiffuseColor( new Color3f( 1.0f, 0.0f, 0.0f ) ); + app1.setMaterial(mat1); + content1 = new SphereGroup( + 0.05f, // radius of spheres + 0.15f, // x spacing + 0.15f, // y spacing + 5, // number of spheres in X + 5, // number of spheres in Y + app1, // appearance + true); // alt app override = true + objRoot.addChild( content1 ); + shapes1 = ((SphereGroup)content1).getShapes(); + + + + // Add lights + light1 = new DirectionalLight( ); + light1.setEnable( true ); + light1.setColor( new Color3f(0.2f, 0.2f, 0.2f) ); + light1.setDirection( new Vector3f( 1.0f, 0.0f, -1.0f ) ); + light1.setInfluencingBounds( worldBounds ); + light1.setCapability( + DirectionalLight.ALLOW_INFLUENCING_BOUNDS_WRITE ); + light1.setCapability( + DirectionalLight.ALLOW_BOUNDS_WRITE ); + objRoot.addChild( light1 ); + + // Add an ambient light to dimly illuminate the rest of + // the shapes in the scene to help illustrate that the + // directional lights are being scoped... otherwise it looks + // like we're just removing shapes from the scene + AmbientLight ambient = new AmbientLight( ); + ambient.setEnable( true ); + ambient.setColor( new Color3f(1.0f, 1.0f, 1.0f) ); + ambient.setInfluencingBounds( worldBounds ); + objRoot.addChild( ambient ); + + + // Define a bounding leaf + leafBounds = new BoundingLeaf( allBounds[currentBounds] ); + leafBounds.setCapability( BoundingLeaf.ALLOW_REGION_WRITE ); + objRoot.addChild( leafBounds ); + if (boundingLeafOn) { + altApp.setInfluencingBoundingLeaf(leafBounds); + } + else { + altApp.setInfluencingBounds(allBounds[currentBounds]); + } + + + + return objRoot; + } + JPanel createBoundsPanel() { + JPanel panel = new JPanel(); + panel.setBorder(new TitledBorder("Scopes")); + + + String boundsValues[] = { "Tiny Bounds", "Small Bounds", "Big Bounds"}; + + boundsType = new JComboBox(boundsValues); + boundsType.addActionListener(this); + boundsType.setSelectedIndex(2); + panel.add(new JLabel("Bounds")); + panel.add(boundsType); + + useBoundingLeaf = new JCheckBox("Enable BoundingLeaf", + boundingLeafOn); + useBoundingLeaf.addActionListener(this); + panel.add(useBoundingLeaf); + + override = new JCheckBox("Enable App Override", + false); + override.addActionListener(this); + panel.add(override); + + return panel; + + } + + JPanel createMaterialPanel() { + JPanel panel = new JPanel(); + panel.setBorder(new TitledBorder("Appearance Attributes")); + + String colorVals[] = { "WHITE", "RED", "GREEN", "BLUE"}; + + altAppMaterialColor = new JComboBox(colorVals); + altAppMaterialColor.addActionListener(this); + altAppMaterialColor.setSelectedIndex(2); + panel.add(new JLabel("Alternate Appearance MaterialColor")); + panel.add(altAppMaterialColor); + + + + appMaterialColor = new JComboBox(colorVals); + appMaterialColor.addActionListener(this); + appMaterialColor.setSelectedIndex(1); + panel.add(new JLabel("Normal Appearance MaterialColor")); + panel.add(appMaterialColor); + + return panel; + + + } + + public void actionPerformed(ActionEvent e) { + int i; + + Object target = e.getSource(); + if (target == altAppMaterialColor) { + altMat.setDiffuseColor(colors[altAppMaterialColor.getSelectedIndex()]); + } + else if (target == useBoundingLeaf) { + boundingLeafOn = useBoundingLeaf.isSelected(); + if (boundingLeafOn) { + leafBounds.setRegion(allBounds[currentBounds]); + altApp.setInfluencingBoundingLeaf( leafBounds ); + } + else { + altApp.setInfluencingBoundingLeaf( null ); + altApp.setInfluencingBounds(allBounds[currentBounds]); + } + + } + else if (target == boundsType) { + currentBounds = boundsType.getSelectedIndex(); + if (boundingLeafOn) { + leafBounds.setRegion(allBounds[currentBounds]); + altApp.setInfluencingBoundingLeaf( leafBounds ); + } + else { + altApp.setInfluencingBoundingLeaf( null ); + altApp.setInfluencingBounds(allBounds[currentBounds]); + } + + } + else if (target == override) { + for (i = 0; i < shapes1.length; i++) + shapes1[i].setAppearanceOverrideEnable(override.isSelected()); + } + else if (target == appMaterialColor) { + mat1.setDiffuseColor(colors[appMaterialColor.getSelectedIndex()]); + } + + } + + + public static void main(String[] args) {System.setProperty("sun.awt.noerasebackground", "true"); + Frame frame = new MainFrame(new AlternateAppearanceBoundsTest(), 800, 800); + } + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/alternate_appearance/AlternateAppearanceBoundsTestGL2ES2.java b/src/main/java/org/jdesktop/j3d/examples/alternate_appearance/AlternateAppearanceBoundsTestGL2ES2.java new file mode 100644 index 0000000..c24b79a --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/alternate_appearance/AlternateAppearanceBoundsTestGL2ES2.java @@ -0,0 +1,314 @@ +/* + * Copyright (c) 2016 JogAmp Community. All rights reserved. + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * This code is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 only, as + * published by the Free Software Foundation. Sun designates this + * particular file as subject to the "Classpath" exception as provided + * by Sun in the LICENSE file that accompanied this code. + * + * This code is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + * version 2 for more details (a copy is included in the LICENSE file that + * accompanied this code). + * + * You should have received a copy of the GNU General Public License version + * 2 along with this work; if not, write to the Free Software Foundation, + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. + * + */ + +package org.jdesktop.j3d.examples.alternate_appearance; + +import java.awt.Container; +import java.awt.event.ActionEvent; +import java.awt.event.ActionListener; + +import javax.swing.BoxLayout; +import javax.swing.JApplet; +import javax.swing.JCheckBox; +import javax.swing.JComboBox; +import javax.swing.JLabel; +import javax.swing.JPanel; +import javax.swing.border.TitledBorder; + +import org.jdesktop.j3d.examples.gl2es2pipeline.SimpleShaderAppearance; +import org.jogamp.java3d.AlternateAppearance; +import org.jogamp.java3d.AmbientLight; +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.BoundingLeaf; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.Bounds; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.DirectionalLight; +import org.jogamp.java3d.Group; +import org.jogamp.java3d.Material; +import org.jogamp.java3d.Shape3D; +import org.jogamp.java3d.utils.applet.MainFrame; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Vector3f; + +public class AlternateAppearanceBoundsTestGL2ES2 extends JApplet implements ActionListener +{ + + Material mat1, altMat; + Appearance app, otherApp; + JComboBox<?> altAppMaterialColor; + JComboBox<?> appMaterialColor; + JCheckBox useBoundingLeaf; + JCheckBox override; + JComboBox<?> boundsType; + private Group content1 = null; + AlternateAppearance altApp; + Shape3D[] shapes1; + boolean boundingLeafOn = false; + // Globally used colors + Color3f white = new Color3f(1.0f, 1.0f, 1.0f); + Color3f red = new Color3f(1.0f, 0.0f, 0.0f); + Color3f green = new Color3f(0.0f, 1.0f, 0.0f); + Color3f blue = new Color3f(0.0f, 0.0f, 1.0f); + Color3f[] colors = { white, red, green, blue }; + + private Bounds worldBounds = new BoundingSphere(new Point3d(0.0, 0.0, 0.0), // Center + 1000.0); // Extent + private Bounds smallBounds = new BoundingSphere(new Point3d(0.0, 0.0, 0.0), // Center + 0.25); // Extent + private Bounds tinyBounds = new BoundingSphere(new Point3d(0.0, 0.0, 0.0), // Center + 0.05); // Extent + private BoundingLeaf leafBounds = null; + private int currentBounds = 2; + + private Bounds[] allBounds = { tinyBounds, smallBounds, worldBounds }; + + DirectionalLight light1 = null; + + // Get the current bounding leaf position + //private int currentPosition = 0; + // Point3f pos = (Point3f)positions[currentPosition].value; + + private SimpleUniverse u = null; + + public AlternateAppearanceBoundsTestGL2ES2() + { + } + + @Override + public void init() + { + System.setProperty("sun.awt.noerasebackground", "true"); + Container contentPane = getContentPane(); + + Canvas3D c = new Canvas3D(SimpleUniverse.getPreferredConfiguration()); + contentPane.add("Center", c); + + BranchGroup scene = createSceneGraph(); + // SimpleUniverse is a Convenience Utility class + u = new SimpleUniverse(c); + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + u.getViewingPlatform().setNominalViewingTransform(); + u.addBranchGraph(scene); + + // Create GUI + JPanel p = new JPanel(); + BoxLayout boxlayout = new BoxLayout(p, BoxLayout.Y_AXIS); + p.add(createBoundsPanel()); + p.add(createMaterialPanel()); + p.setLayout(boxlayout); + + contentPane.add("South", p); + } + + @Override + public void destroy() + { + u.cleanup(); + } + + BranchGroup createSceneGraph() + { + BranchGroup objRoot = new BranchGroup(); + + // Create an alternate appearance + otherApp = new SimpleShaderAppearance(true, false); + //otherApp = new Appearance(); + altMat = new Material(); + altMat.setCapability(Material.ALLOW_COMPONENT_WRITE); + altMat.setDiffuseColor(new Color3f(0.0f, 1.0f, 0.0f)); + otherApp.setMaterial(altMat); + + altApp = new AlternateAppearance(); + altApp.setAppearance(otherApp); + altApp.setCapability(AlternateAppearance.ALLOW_BOUNDS_WRITE); + altApp.setCapability(AlternateAppearance.ALLOW_INFLUENCING_BOUNDS_WRITE); + altApp.setInfluencingBounds(worldBounds); + objRoot.addChild(altApp); + + // Build foreground geometry + Appearance app1 = new SimpleShaderAppearance(true, false); + //Appearance app1 = new Appearance(); + mat1 = new Material(); + mat1.setCapability(Material.ALLOW_COMPONENT_WRITE); + mat1.setDiffuseColor(new Color3f(1.0f, 0.0f, 0.0f)); + app1.setMaterial(mat1); + content1 = new SphereGroup(0.05f, // radius of spheres + 0.15f, // x spacing + 0.15f, // y spacing + 5, // number of spheres in X + 5, // number of spheres in Y + app1, // appearance + true); // alt app override = true + objRoot.addChild(content1); + shapes1 = ((SphereGroup) content1).getShapes(); + + // Add lights + light1 = new DirectionalLight(); + light1.setEnable(true); + light1.setColor(new Color3f(0.2f, 0.2f, 0.2f)); + light1.setDirection(new Vector3f(1.0f, 0.0f, -1.0f)); + light1.setInfluencingBounds(worldBounds); + light1.setCapability(DirectionalLight.ALLOW_INFLUENCING_BOUNDS_WRITE); + light1.setCapability(DirectionalLight.ALLOW_BOUNDS_WRITE); + objRoot.addChild(light1); + + // Add an ambient light to dimly illuminate the rest of + // the shapes in the scene to help illustrate that the + // directional lights are being scoped... otherwise it looks + // like we're just removing shapes from the scene + AmbientLight ambient = new AmbientLight(); + ambient.setEnable(true); + ambient.setColor(new Color3f(1.0f, 1.0f, 1.0f)); + ambient.setInfluencingBounds(worldBounds); + objRoot.addChild(ambient); + + // Define a bounding leaf + leafBounds = new BoundingLeaf(allBounds[currentBounds]); + leafBounds.setCapability(BoundingLeaf.ALLOW_REGION_WRITE); + objRoot.addChild(leafBounds); + if (boundingLeafOn) + { + altApp.setInfluencingBoundingLeaf(leafBounds); + } + else + { + altApp.setInfluencingBounds(allBounds[currentBounds]); + } + + return objRoot; + } + + JPanel createBoundsPanel() + { + JPanel panel = new JPanel(); + panel.setBorder(new TitledBorder("Scopes")); + + String boundsValues[] = { "Tiny Bounds", "Small Bounds", "Big Bounds" }; + + boundsType = new JComboBox<Object>(boundsValues); + boundsType.addActionListener(this); + boundsType.setSelectedIndex(2); + panel.add(new JLabel("Bounds")); + panel.add(boundsType); + + useBoundingLeaf = new JCheckBox("Enable BoundingLeaf", boundingLeafOn); + useBoundingLeaf.addActionListener(this); + panel.add(useBoundingLeaf); + + override = new JCheckBox("Enable App Override", false); + override.addActionListener(this); + panel.add(override); + + return panel; + + } + + JPanel createMaterialPanel() + { + JPanel panel = new JPanel(); + panel.setBorder(new TitledBorder("Appearance Attributes")); + + String colorVals[] = { "WHITE", "RED", "GREEN", "BLUE" }; + + altAppMaterialColor = new JComboBox<Object>(colorVals); + altAppMaterialColor.addActionListener(this); + altAppMaterialColor.setSelectedIndex(2); + panel.add(new JLabel("Alternate Appearance MaterialColor")); + panel.add(altAppMaterialColor); + + appMaterialColor = new JComboBox<Object>(colorVals); + appMaterialColor.addActionListener(this); + appMaterialColor.setSelectedIndex(1); + panel.add(new JLabel("Normal Appearance MaterialColor")); + panel.add(appMaterialColor); + + return panel; + + } + + @Override + public void actionPerformed(ActionEvent e) + { + int i; + + Object target = e.getSource(); + if (target == altAppMaterialColor) + { + altMat.setDiffuseColor(colors[altAppMaterialColor.getSelectedIndex()]); + } + else if (target == useBoundingLeaf) + { + boundingLeafOn = useBoundingLeaf.isSelected(); + if (boundingLeafOn) + { + leafBounds.setRegion(allBounds[currentBounds]); + altApp.setInfluencingBoundingLeaf(leafBounds); + } + else + { + altApp.setInfluencingBoundingLeaf(null); + altApp.setInfluencingBounds(allBounds[currentBounds]); + } + + } + else if (target == boundsType) + { + currentBounds = boundsType.getSelectedIndex(); + if (boundingLeafOn) + { + leafBounds.setRegion(allBounds[currentBounds]); + altApp.setInfluencingBoundingLeaf(leafBounds); + } + else + { + altApp.setInfluencingBoundingLeaf(null); + altApp.setInfluencingBounds(allBounds[currentBounds]); + } + + } + else if (target == override) + { + for (i = 0; i < shapes1.length; i++) + shapes1[i].setAppearanceOverrideEnable(override.isSelected()); + } + else if (target == appMaterialColor) + { + mat1.setDiffuseColor(colors[appMaterialColor.getSelectedIndex()]); + } + + } + + public static void main(String[] args) + { + System.setProperty("sun.awt.noerasebackground", "true"); + System.setProperty("j3d.rend", "jogl2es2"); + System.setProperty("j3d.displaylist", "false"); + new MainFrame(new AlternateAppearanceBoundsTestGL2ES2(), 800, 800); + } + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/alternate_appearance/AlternateAppearanceScopeTest.java b/src/main/java/org/jdesktop/j3d/examples/alternate_appearance/AlternateAppearanceScopeTest.java new file mode 100644 index 0000000..bddbee8 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/alternate_appearance/AlternateAppearanceScopeTest.java @@ -0,0 +1,375 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.alternate_appearance; + +import java.awt.Container; +import java.awt.Frame; +import java.awt.event.ActionEvent; +import java.awt.event.ActionListener; + +import javax.swing.BoxLayout; +import javax.swing.JApplet; +import javax.swing.JComboBox; +import javax.swing.JLabel; +import javax.swing.JPanel; +import javax.swing.border.TitledBorder; + +import org.jogamp.java3d.AlternateAppearance; +import org.jogamp.java3d.AmbientLight; +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.DirectionalLight; +import org.jogamp.java3d.Group; +import org.jogamp.java3d.Material; +import org.jogamp.java3d.Shape3D; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.utils.applet.MainFrame; +import org.jogamp.java3d.utils.behaviors.vp.OrbitBehavior; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.java3d.utils.universe.ViewingPlatform; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Vector3f; + +public class AlternateAppearanceScopeTest extends JApplet +implements ActionListener { + + + Material mat1, altMat; + Appearance app, otherApp; + JComboBox altAppMaterialColor; + JComboBox appMaterialColor; + JComboBox altAppScoping; + JComboBox override; + private Group content1 = null; + private Group content2 = null; + BoundingSphere worldBounds; + AlternateAppearance altApp; + Shape3D[] shapes1, shapes2; + boolean shape1Enabled = false, shape2Enabled = false; + // Globally used colors + Color3f white = new Color3f(1.0f, 1.0f, 1.0f); + Color3f red = new Color3f(1.0f, 0.0f, 0.0f); + Color3f green = new Color3f(0.0f, 1.0f, 0.0f); + Color3f blue = new Color3f(0.0f, 0.0f, 1.0f); + Color3f[] colors = {white, red, green, blue}; + + private SimpleUniverse u; + + public AlternateAppearanceScopeTest() { + } + + public void init() {System.setProperty("sun.awt.noerasebackground", "true"); + Container contentPane = getContentPane(); + + Canvas3D c = new Canvas3D(SimpleUniverse.getPreferredConfiguration()); + contentPane.add("Center", c); + + BranchGroup scene = createSceneGraph(); + // SimpleUniverse is a Convenience Utility class + u = new SimpleUniverse(c); + + // add mouse behaviors to the viewingPlatform + ViewingPlatform viewingPlatform = u.getViewingPlatform(); + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + viewingPlatform.setNominalViewingTransform(); + + OrbitBehavior orbit = new OrbitBehavior(c, + OrbitBehavior.REVERSE_ALL); + BoundingSphere bounds = new BoundingSphere(new Point3d(0.0, 0.0, 0.0), + 100.0); + orbit.setSchedulingBounds(bounds); + viewingPlatform.setViewPlatformBehavior(orbit); + + u.addBranchGraph(scene); + + + // Create GUI + JPanel p = new JPanel(); + BoxLayout boxlayout = new BoxLayout(p, + BoxLayout.Y_AXIS); + p.add(createScopingPanel()); + p.add(createMaterialPanel()); + p.setLayout(boxlayout); + + contentPane.add("South", p); + } + + public void destroy() { + u.cleanup(); + } + + BranchGroup createSceneGraph() { + BranchGroup objRoot = new BranchGroup(); + + // Create influencing bounds + worldBounds = new BoundingSphere( + new Point3d( 0.0, 0.0, 0.0 ), // Center + 1000.0 ); // Extent + + Transform3D t = new Transform3D(); + // move the object upwards + t.set(new Vector3f(0.0f, 0.1f, 0.0f)); + // Shrink the object + t.setScale(0.8); + + TransformGroup trans = new TransformGroup(t); + trans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + trans.setCapability(TransformGroup.ALLOW_TRANSFORM_READ); + + + otherApp = new Appearance(); + altMat = new Material(); + altMat.setCapability(Material.ALLOW_COMPONENT_WRITE); + altMat.setDiffuseColor( new Color3f( 0.0f, 1.0f, 0.0f ) ); + otherApp.setMaterial(altMat); + + altApp = new AlternateAppearance(); + altApp.setAppearance(otherApp); + altApp.setCapability(AlternateAppearance.ALLOW_SCOPE_WRITE); + altApp.setCapability(AlternateAppearance.ALLOW_SCOPE_READ); + altApp.setInfluencingBounds( worldBounds ); + objRoot.addChild(altApp); + + // Build foreground geometry into two groups. We'll + // create three directional lights below, one each with + // scope to cover the first geometry group only, the + // second geometry group only, or both geometry groups. + Appearance app1 = new Appearance(); + mat1 = new Material(); + mat1.setCapability(Material.ALLOW_COMPONENT_WRITE); + mat1.setDiffuseColor( new Color3f( 1.0f, 0.0f, 0.0f ) ); + app1.setMaterial(mat1); + content1 = new SphereGroup( + 0.05f, // radius of spheres + 0.4f, // x spacing + 0.2f, // y spacing + 3, // number of spheres in X + 5, // number of spheres in Y + app1, // appearance + true); // alt app override = true + trans.addChild( content1 ); + shapes1 = ((SphereGroup)content1).getShapes(); + + content2 = new SphereGroup( + 0.05f, // radius of spheres + .4f, // x spacing + 0.2f, // y spacing + 2, // number of spheres in X + 5, // number of spheres in Y + app1, // appearance + true); // alt app override = true + trans.addChild( content2 ); + shapes2 = ((SphereGroup)content2).getShapes(); + + + // Add lights + DirectionalLight light1 = null; + light1 = new DirectionalLight( ); + light1.setEnable( true ); + light1.setColor( new Color3f(0.2f, 0.2f, 0.2f) ); + light1.setDirection( new Vector3f( 1.0f, 0.0f, -1.0f ) ); + light1.setInfluencingBounds( worldBounds ); + objRoot.addChild( light1 ); + + DirectionalLight light2 = new DirectionalLight(); + light2.setEnable(true); + light2.setColor(new Color3f(0.2f, 0.2f, 0.2f)); + light2.setDirection(new Vector3f(-1.0f, 0.0f, 1.0f)); + light2.setInfluencingBounds(worldBounds); + objRoot.addChild(light2); + + // Add an ambient light to dimly illuminate the rest of + // the shapes in the scene to help illustrate that the + // directional lights are being scoped... otherwise it looks + // like we're just removing shapes from the scene + AmbientLight ambient = new AmbientLight( ); + ambient.setEnable( true ); + ambient.setColor( new Color3f(1.0f, 1.0f, 1.0f) ); + ambient.setInfluencingBounds( worldBounds ); + objRoot.addChild( ambient ); + + + objRoot.addChild(trans); + + return objRoot; + } + JPanel createScopingPanel() { + JPanel panel = new JPanel(); + panel.setBorder(new TitledBorder("Scopes")); + + String values[] = {"Scoped Set1", "Scoped Set2", "Universal Scope"}; + altAppScoping = new JComboBox(values); + altAppScoping.addActionListener(this); + altAppScoping.setSelectedIndex(2); + panel.add(new JLabel("Scoping")); + panel.add(altAppScoping); + + + String enables[] = { "Enabled Set1", "Enabled Set2", "Enabled set1&2", "Disabled set1&2"}; + + override = new JComboBox(enables); + override.addActionListener(this); + override.setSelectedIndex(3); + panel.add(new JLabel("Alternate Appearance Override")); + panel.add(override); + + return panel; + + } + + JPanel createMaterialPanel() { + JPanel panel = new JPanel(); + panel.setBorder(new TitledBorder("Appearance Attributes")); + + String colorVals[] = { "WHITE", "RED", "GREEN", "BLUE"}; + + altAppMaterialColor = new JComboBox(colorVals); + altAppMaterialColor.addActionListener(this); + altAppMaterialColor.setSelectedIndex(2); + panel.add(new JLabel("Alternate Appearance MaterialColor")); + panel.add(altAppMaterialColor); + + + + appMaterialColor = new JComboBox(colorVals); + appMaterialColor.addActionListener(this); + appMaterialColor.setSelectedIndex(1); + panel.add(new JLabel("Normal Appearance MaterialColor")); + panel.add(appMaterialColor); + + return panel; + + + } + + public void actionPerformed(ActionEvent e) { + Object target = e.getSource(); + if (target == altAppMaterialColor) { + altMat.setDiffuseColor(colors[altAppMaterialColor.getSelectedIndex()]); + } + else if (target == altAppScoping) { + for (int i = 0; i < altApp.numScopes(); i++) { + altApp.removeScope(0); + } + if (altAppScoping.getSelectedIndex() == 0) { + altApp.addScope(content1); + } + else if (altAppScoping.getSelectedIndex() == 1) { + altApp.addScope(content2); + } + } + else if (target == override) { + int i; + if (override.getSelectedIndex()== 0) { + if (!shape1Enabled) { + for (i = 0; i < shapes1.length; i++) + shapes1[i].setAppearanceOverrideEnable(true); + shape1Enabled = true; + } + + if (shape2Enabled) { + for (i = 0; i < shapes2.length; i++) + shapes2[i].setAppearanceOverrideEnable(false); + shape2Enabled = false; + } + } + else if (override.getSelectedIndex() == 1) { + if (!shape2Enabled) { + for (i = 0; i < shapes2.length; i++) + shapes2[i].setAppearanceOverrideEnable(true); + shape2Enabled = true; + } + + if (shape1Enabled) { + for (i = 0; i < shapes1.length; i++) + shapes1[i].setAppearanceOverrideEnable(false); + shape1Enabled = false; + } + } + else if (override.getSelectedIndex() == 2) { + if (!shape1Enabled) { + for (i = 0; i < shapes1.length; i++) + shapes1[i].setAppearanceOverrideEnable(true); + shape1Enabled = true; + } + if (!shape2Enabled) { + for (i = 0; i < shapes2.length; i++) + shapes2[i].setAppearanceOverrideEnable(true); + shape2Enabled = true; + } + } + else { + if (shape1Enabled) { + for (i = 0; i < shapes1.length; i++) + shapes1[i].setAppearanceOverrideEnable(false); + shape1Enabled = false; + } + + if (shape2Enabled) { + for (i = 0; i < shapes2.length; i++) + shapes2[i].setAppearanceOverrideEnable(false); + shape2Enabled = false; + } + } + + } + else if (target == appMaterialColor) { + mat1.setDiffuseColor(colors[appMaterialColor.getSelectedIndex()]); + } + + } + + + public static void main(String[] args) {System.setProperty("sun.awt.noerasebackground", "true"); + Frame frame = new MainFrame(new AlternateAppearanceScopeTest(), 800, 800); + } + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/alternate_appearance/SphereGroup.java b/src/main/java/org/jdesktop/j3d/examples/alternate_appearance/SphereGroup.java new file mode 100644 index 0000000..22f8553 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/alternate_appearance/SphereGroup.java @@ -0,0 +1,132 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.alternate_appearance; + +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.Group; +import org.jogamp.java3d.Material; +import org.jogamp.java3d.Shape3D; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.utils.geometry.Primitive; +import org.jogamp.java3d.utils.geometry.Sphere; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Vector3d; + +public class SphereGroup + extends Group +{ + Shape3D[] shapes; + int numShapes = 0; + // Constructors + public SphereGroup( ) + { + // radius x,y spacing x,y count appearance + this( 0.25f, 0.75f, 0.75f, 5, 5, null, false ); + } + + public SphereGroup( Appearance app ) + { + // radius x,y spacing x,y count appearance + this( 0.25f, 0.75f, 0.75f, 5, 5, app, false ); + } + + public SphereGroup( float radius, float xSpacing, float ySpacing, + int xCount, int yCount, boolean overrideflag ) + { + this( radius, xSpacing, ySpacing, xCount, yCount, null, overrideflag ); + } + + public SphereGroup( float radius, float xSpacing, float ySpacing, + int xCount, int yCount, Appearance app, boolean overrideflag ) + { + if ( app == null ) + { + app = new Appearance( ); + Material material = new Material( ); + material.setDiffuseColor( new Color3f( 0.8f, 0.8f, 0.8f ) ); + material.setSpecularColor( new Color3f( 0.0f, 0.0f, 0.0f ) ); + material.setShininess( 0.0f ); + app.setMaterial( material ); + } + + double xStart = -xSpacing * (double)(xCount-1) / 2.0; + double yStart = -ySpacing * (double)(yCount-1) / 2.0; + + Sphere sphere = null; + TransformGroup trans = null; + Transform3D t3d = new Transform3D( ); + Vector3d vec = new Vector3d( ); + double x, y = yStart, z = 0.0; + shapes = new Shape3D[xCount * yCount]; + for ( int i = 0; i < yCount; i++ ) + { + x = xStart; + for ( int j = 0; j < xCount; j++ ) { + vec.set( x, y, z ); + t3d.setTranslation( vec ); + trans = new TransformGroup( t3d ); + addChild( trans ); + + sphere = new Sphere( + radius, // sphere radius + Primitive.GENERATE_NORMALS, // generate normals + 16, // 16 divisions radially + app ); // it's appearance + trans.addChild( sphere ); + x += xSpacing; + shapes[numShapes] = sphere.getShape(); + if (overrideflag) + shapes[numShapes].setCapability(Shape3D.ALLOW_APPEARANCE_OVERRIDE_WRITE); + numShapes++; + } + y += ySpacing; + } + } + Shape3D[] getShapes() { + return shapes; + } + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/appearance/AppearanceMixed.form b/src/main/java/org/jdesktop/j3d/examples/appearance/AppearanceMixed.form new file mode 100644 index 0000000..2440a43 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/appearance/AppearanceMixed.form @@ -0,0 +1,36 @@ +<?xml version="1.0" encoding="UTF-8" ?> + +<Form version="1.0" type="org.netbeans.modules.form.forminfo.JFrameFormInfo"> + <Properties> + <Property name="defaultCloseOperation" type="int" value="3"/> + <Property name="title" type="java.lang.String" value="AppearanceMixed"/> + </Properties> + <SyntheticProperties> + <SyntheticProperty name="formSizePolicy" type="int" value="1"/> + </SyntheticProperties> + <AuxValues> + <AuxValue name="FormSettings_generateMnemonicsCode" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_listenerGenerationStyle" type="java.lang.Integer" value="0"/> + <AuxValue name="FormSettings_variablesLocal" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_variablesModifier" type="java.lang.Integer" value="2"/> + <AuxValue name="designerSize" type="java.awt.Dimension" value="-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,1,44,0,0,1,-112"/> + </AuxValues> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + <SubComponents> + <Container class="javax.swing.JPanel" name="drawingPanel"> + <Properties> + <Property name="preferredSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor"> + <Dimension value="[700, 700]"/> + </Property> + </Properties> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout" value="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription"> + <BorderConstraints direction="Center"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + </Container> + </SubComponents> +</Form> diff --git a/src/main/java/org/jdesktop/j3d/examples/appearance/AppearanceMixed.java b/src/main/java/org/jdesktop/j3d/examples/appearance/AppearanceMixed.java new file mode 100644 index 0000000..943d387 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/appearance/AppearanceMixed.java @@ -0,0 +1,549 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.appearance; + +import java.awt.GraphicsConfiguration; + +import org.jdesktop.j3d.examples.Resources; +import org.jogamp.java3d.Alpha; +import org.jogamp.java3d.AmbientLight; +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.Background; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.ColoringAttributes; +import org.jogamp.java3d.DirectionalLight; +import org.jogamp.java3d.GraphicsContext3D; +import org.jogamp.java3d.Group; +import org.jogamp.java3d.IndexedTriangleArray; +import org.jogamp.java3d.Material; +import org.jogamp.java3d.PointAttributes; +import org.jogamp.java3d.PolygonAttributes; +import org.jogamp.java3d.RotationInterpolator; +import org.jogamp.java3d.Shape3D; +import org.jogamp.java3d.TextureAttributes; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.TransparencyAttributes; +import org.jogamp.java3d.utils.image.TextureLoader; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Point3f; +import org.jogamp.vecmath.Vector3d; +import org.jogamp.vecmath.Vector3f; + +public class AppearanceMixed extends javax.swing.JFrame { + + private java.net.URL texImage = null; + private java.net.URL bgImage = null; + private SimpleUniverse univ = null; + private BranchGroup scene = null; + + static class MyCanvas3D extends Canvas3D { + private GraphicsContext3D gc; + + private static final int vertIndices[] = { 0, 1, 2, 0, 2, 3 }; + private static final int normalIndices[] = { 0, 0, 0, 1, 1, 1 }; + private IndexedTriangleArray tri = + new IndexedTriangleArray(4, IndexedTriangleArray.COORDINATES | + IndexedTriangleArray.NORMALS, 6); + + private Point3f vert[] = { + new Point3f(-0.12f, -0.12f, 0.0f), + new Point3f( 0.12f, -0.12f, 0.0f), + new Point3f( 0.12f, 0.12f, 0.0f), + new Point3f(-0.12f, 0.12f, 0.0f), + }; + + private Point3f min[] = { + new Point3f(-0.24f, -0.24f, -0.20f), + new Point3f( 0.04f, -0.28f, -0.24f), + new Point3f( 0.00f, 0.00f, -0.24f), + new Point3f(-0.32f, 0.08f, -0.20f), + }; + + private Point3f max[] = { + new Point3f(-0.04f, -0.04f, 0.12f), + new Point3f( 0.32f, -0.04f, 0.16f), + new Point3f( 0.36f, 0.28f, 0.20f), + new Point3f(-0.04f, 0.24f, 0.16f), + }; + + private Point3f delta[] = { + new Point3f(-0.0021f, -0.0017f, 0.0014f), + new Point3f( 0.0025f, -0.0013f, -0.0018f), + new Point3f( 0.0021f, 0.0017f, 0.0018f), + new Point3f(-0.0025f, 0.0013f, -0.0014f), + }; + + private Vector3f normals[]; + private Vector3f v01 = new Vector3f(); + private Vector3f v02 = new Vector3f(); + private Vector3f v03 = new Vector3f(); + + public void renderField(int fieldDesc) { + computeVert(); + computeNormals(); + gc.draw(tri); + } + + private void computeVert() { + for (int i = 0; i < 4; i++) { + vert[i].add(delta[i]); + if (vert[i].x > max[i].x) { + vert[i].x = max[i].x; + delta[i].x *= -1.0f; + } + if (vert[i].x < min[i].x) { + vert[i].x = min[i].x; + delta[i].x *= -1.0f; + } + if (vert[i].y > max[i].y) { + vert[i].y = max[i].y; + delta[i].y *= -1.0f; + } + if (vert[i].y < min[i].y) { + vert[i].y = min[i].y; + delta[i].y *= -1.0f; + } + if (vert[i].z > max[i].z) { + vert[i].z = max[i].z; + delta[i].z *= -1.0f; + } + if (vert[i].z < min[i].z) { + vert[i].z = min[i].z; + delta[i].z *= -1.0f; + } + } + tri.setCoordinates(0, vert); + } + + private void computeNormals() { + v01.sub(vert[1], vert[0]); + v02.sub(vert[2], vert[0]); + v03.sub(vert[3], vert[0]); + normals[0].cross(v01, v02); + normals[0].normalize(); + normals[1].cross(v02, v03); + normals[1].normalize(); + tri.setNormals(0, normals); + } + + public MyCanvas3D(GraphicsConfiguration gcfg) { + super(gcfg); + + // Allocate memory for normals + normals = new Vector3f[2]; + normals[0] = new Vector3f(); + normals[1] = new Vector3f(); + + // Set up the indices + tri.setCoordinateIndices(0, vertIndices); + tri.setNormalIndices(0, normalIndices); + + // Set up the graphics context + gc = getGraphicsContext3D(); + + // Create the appearance for the triangle fan + Appearance app = new Appearance(); + Color3f black = new Color3f(0.0f, 0.0f, 0.0f); + Color3f white = new Color3f(1.0f, 1.0f, 1.0f); + Color3f objColor = new Color3f(0.0f, 0.0f, 0.8f); + app.setMaterial(new Material(objColor, black, objColor, + white, 80.0f)); + gc.setAppearance(app); + + // Set up the global lights + Color3f lColor1 = new Color3f(0.7f, 0.7f, 0.7f); + Vector3f lDir1 = new Vector3f(-1.0f, -1.0f, -1.0f); + Color3f alColor = new Color3f(0.2f, 0.2f, 0.2f); + gc.addLight(new AmbientLight(alColor)); + gc.addLight(new DirectionalLight(lColor1, lDir1)); + } + } + + + private BranchGroup createSceneGraph() { + // Create the root of the branch graph + BranchGroup objRoot = new BranchGroup(); + + // Create a bounds for the background and lights + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + + // Set up the background + TextureLoader bgTexture = new TextureLoader(bgImage, this); + Background bg = new Background(bgTexture.getImage()); + bg.setApplicationBounds(bounds); + objRoot.addChild(bg); + + // Set up the global lights + Color3f lColor1 = new Color3f(0.7f, 0.7f, 0.7f); + Vector3f lDir1 = new Vector3f(-1.0f, -1.0f, -1.0f); + Color3f alColor = new Color3f(0.2f, 0.2f, 0.2f); + + AmbientLight aLgt = new AmbientLight(alColor); + aLgt.setInfluencingBounds(bounds); + DirectionalLight lgt1 = new DirectionalLight(lColor1, lDir1); + lgt1.setInfluencingBounds(bounds); + objRoot.addChild(aLgt); + objRoot.addChild(lgt1); + + // Create a bunch of objects with a behavior and add them + // into the scene graph. + + int row, col; + Appearance[][] app = new Appearance[3][3]; + + for (row = 0; row < 3; row++) + for (col = 0; col < 3; col++) + app[row][col] = createAppearance(row * 3 + col); + + for (int i = 0; i < 3; i++) { + double ypos = (double)(i - 1) * 0.6; + for (int j = 0; j < 3; j++) { + double xpos = (double)(j - 1) * 0.6; + objRoot.addChild(createObject(app[i][j], 0.12, xpos, ypos)); + } + } + + // Let Java 3D perform optimizations on this scene graph. + objRoot.compile(); + + return objRoot; + } + + + private Appearance createAppearance(int idx) { + Appearance app = new Appearance(); + + // Globally used colors + Color3f black = new Color3f(0.0f, 0.0f, 0.0f); + Color3f white = new Color3f(1.0f, 1.0f, 1.0f); + + switch (idx) { + // Unlit solid + case 0: + { + // Set up the coloring properties + Color3f objColor = new Color3f(1.0f, 0.2f, 0.4f); + ColoringAttributes ca = new ColoringAttributes(); + ca.setColor(objColor); + app.setColoringAttributes(ca); + break; + } + + + // Unlit wire frame + case 1: + { + // Set up the coloring properties + Color3f objColor = new Color3f(0.5f, 0.0f, 0.2f); + ColoringAttributes ca = new ColoringAttributes(); + ca.setColor(objColor); + app.setColoringAttributes(ca); + + // Set up the polygon attributes + PolygonAttributes pa = new PolygonAttributes(); + pa.setPolygonMode(pa.POLYGON_LINE); + pa.setCullFace(pa.CULL_NONE); + app.setPolygonAttributes(pa); + break; + } + + // Unlit points + case 2: + { + // Set up the coloring properties + Color3f objColor = new Color3f(0.2f, 0.2f, 1.0f); + ColoringAttributes ca = new ColoringAttributes(); + ca.setColor(objColor); + app.setColoringAttributes(ca); + + // Set up the polygon attributes + PolygonAttributes pa = new PolygonAttributes(); + pa.setPolygonMode(pa.POLYGON_POINT); + pa.setCullFace(pa.CULL_NONE); + app.setPolygonAttributes(pa); + + // Set up point attributes + PointAttributes pta = new PointAttributes(); + pta.setPointSize(5.0f); + app.setPointAttributes(pta); + break; + } + + // Lit solid + case 3: + { + // Set up the material properties + Color3f objColor = new Color3f(0.8f, 0.0f, 0.0f); + app.setMaterial(new Material(objColor, black, objColor, + white, 80.0f)); + break; + } + + // Texture mapped, lit solid + case 4: + { + // Set up the texture map + TextureLoader tex = new TextureLoader(texImage, this); + app.setTexture(tex.getTexture()); + + TextureAttributes texAttr = new TextureAttributes(); + texAttr.setTextureMode(TextureAttributes.MODULATE); + app.setTextureAttributes(texAttr); + + + // Set up the material properties + app.setMaterial(new Material(white, black, white, black, 1.0f)); + break; + } + + // Transparent, lit solid + case 5: + { + // Set up the transparency properties + TransparencyAttributes ta = new TransparencyAttributes(); + ta.setTransparencyMode(ta.BLENDED); + ta.setTransparency(0.6f); + app.setTransparencyAttributes(ta); + + // Set up the polygon attributes + PolygonAttributes pa = new PolygonAttributes(); + pa.setCullFace(pa.CULL_NONE); + app.setPolygonAttributes(pa); + + // Set up the material properties + Color3f objColor = new Color3f(0.7f, 0.8f, 1.0f); + app.setMaterial(new Material(objColor, black, objColor, + black, 1.0f)); + break; + } + + // Lit solid, no specular + case 6: + { + // Set up the material properties + Color3f objColor = new Color3f(0.8f, 0.0f, 0.0f); + app.setMaterial(new Material(objColor, black, objColor, + black, 80.0f)); + break; + } + + // Lit solid, specular only + case 7: + { + // Set up the material properties + Color3f objColor = new Color3f(0.8f, 0.0f, 0.0f); + app.setMaterial(new Material(black, black, black, + white, 80.0f)); + break; + } + + // Another lit solid with a different color + case 8: + { + // Set up the material properties + Color3f objColor = new Color3f(0.8f, 0.8f, 0.0f); + app.setMaterial(new Material(objColor, black, objColor, + white, 80.0f)); + break; + } + + default: + { + ColoringAttributes ca = new ColoringAttributes(); + ca.setColor(new Color3f(0.0f, 1.0f, 0.0f)); + app.setColoringAttributes(ca); + } + } + + return app; + } + + + private Group createObject(Appearance app, double scale, + double xpos, double ypos) { + + // Create a transform group node to scale and position the object. + Transform3D t = new Transform3D(); + t.set(scale, new Vector3d(xpos, ypos, 0.0)); + TransformGroup objTrans = new TransformGroup(t); + + // Create a second transform group node and initialize it to the + // identity. Enable the TRANSFORM_WRITE capability so that + // our behavior code can modify it at runtime. + TransformGroup spinTg = new TransformGroup(); + spinTg.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + + // Create a simple shape leaf node and set the appearance + Shape3D shape = new Tetrahedron(); + shape.setAppearance(app); + + // add it to the scene graph. + spinTg.addChild(shape); + + // Create a new Behavior object that will perform the desired + // operation on the specified transform object and add it into + // the scene graph. + Transform3D yAxis = new Transform3D(); + Alpha rotationAlpha = new Alpha(-1, Alpha.INCREASING_ENABLE, + 0, 0, + 5000, 0, 0, + 0, 0, 0); + + RotationInterpolator rotator = + new RotationInterpolator(rotationAlpha, spinTg, yAxis, + 0.0f, (float) Math.PI*2.0f); + + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + + rotator.setSchedulingBounds(bounds); + + // Add the behavior and the transform group to the object + objTrans.addChild(rotator); + objTrans.addChild(spinTg); + + return objTrans; + } + + + private Canvas3D createUniverse() { + // Get the preferred graphics configuration for the default screen + GraphicsConfiguration config = + SimpleUniverse.getPreferredConfiguration(); + + // Create a MyCanvas3D using the preferred configuration + MyCanvas3D c = new MyCanvas3D(config); + + // Create simple universe with view branch + univ = new SimpleUniverse(c); + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + univ.getViewingPlatform().setNominalViewingTransform(); + + // Ensure at least 5 msec per frame (i.e., < 200Hz) + univ.getViewer().getView().setMinimumFrameCycleTime(5); + + return c; + } + + /** + * Creates new form AppearanceMixed + */ + public AppearanceMixed() { + + if (bgImage == null) { + // the path to the image for an applet + bgImage = Resources.getResource("resources/images/bg.jpg"); + if (bgImage == null) { + System.err.println("resources/images/bg.jpg not found"); + System.exit(1); + } + } + + if (texImage == null) { + // the path to the image for an applet + texImage = Resources.getResource("resources/images/stone.jpg"); + if (texImage == null) { + System.err.println("resources/images/stone.jpg not found"); + System.exit(1); + } + } + + // Initialize the GUI components + initComponents(); + + // Create Canvas3D and SimpleUniverse; add canvas to drawing panel + Canvas3D c = createUniverse(); + drawingPanel.add(c, java.awt.BorderLayout.CENTER); + + // Create the content branch and add it to the universe + scene = createSceneGraph(); + univ.addBranchGraph(scene); + } + + // ---------------------------------------------------------------- + + /** This method is called from within the constructor to + * initialize the form. + * WARNING: Do NOT modify this code. The content of this method is + * always regenerated by the Form Editor. + */ + // <editor-fold defaultstate="collapsed" desc=" Generated Code ">//GEN-BEGIN:initComponents + private void initComponents() { + drawingPanel = new javax.swing.JPanel(); + + setDefaultCloseOperation(javax.swing.WindowConstants.EXIT_ON_CLOSE); + setTitle("AppearanceMixed"); + drawingPanel.setLayout(new java.awt.BorderLayout()); + + drawingPanel.setPreferredSize(new java.awt.Dimension(700, 700)); + getContentPane().add(drawingPanel, java.awt.BorderLayout.CENTER); + + pack(); + }// </editor-fold>//GEN-END:initComponents + + /** + * @param args the command line arguments + */ + public static void main(String args[]) {System.setProperty("sun.awt.noerasebackground", "true"); + java.awt.EventQueue.invokeLater(new Runnable() { + public void run() { + new AppearanceMixed().setVisible(true); + } + }); + } + + // Variables declaration - do not modify//GEN-BEGIN:variables + private javax.swing.JPanel drawingPanel; + // End of variables declaration//GEN-END:variables + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/appearance/AppearanceMixedGL2ES2.java b/src/main/java/org/jdesktop/j3d/examples/appearance/AppearanceMixedGL2ES2.java new file mode 100644 index 0000000..e3ec631 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/appearance/AppearanceMixedGL2ES2.java @@ -0,0 +1,530 @@ +/* + * Copyright (c) 2016 JogAmp Community. All rights reserved. + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * This code is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 only, as + * published by the Free Software Foundation. Sun designates this + * particular file as subject to the "Classpath" exception as provided + * by Sun in the LICENSE file that accompanied this code. + * + * This code is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + * version 2 for more details (a copy is included in the LICENSE file that + * accompanied this code). + * + * You should have received a copy of the GNU General Public License version + * 2 along with this work; if not, write to the Free Software Foundation, + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. + * + */ + +package org.jdesktop.j3d.examples.appearance; + +import java.awt.GraphicsConfiguration; + +import org.jdesktop.j3d.examples.Resources; +import org.jdesktop.j3d.examples.gl2es2pipeline.SimpleShaderAppearance; +import org.jogamp.java3d.Alpha; +import org.jogamp.java3d.AmbientLight; +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.Background; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.ColoringAttributes; +import org.jogamp.java3d.DirectionalLight; +import org.jogamp.java3d.GraphicsContext3D; +import org.jogamp.java3d.Group; +import org.jogamp.java3d.IndexedTriangleArray; +import org.jogamp.java3d.Material; +import org.jogamp.java3d.PointAttributes; +import org.jogamp.java3d.PolygonAttributes; +import org.jogamp.java3d.RotationInterpolator; +import org.jogamp.java3d.Shape3D; +import org.jogamp.java3d.TextureAttributes; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.TransparencyAttributes; +import org.jogamp.java3d.utils.image.TextureLoader; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Point3f; +import org.jogamp.vecmath.Vector3d; +import org.jogamp.vecmath.Vector3f; + +public class AppearanceMixedGL2ES2 extends javax.swing.JFrame { + + private java.net.URL texImage = null; + private java.net.URL bgImage = null; + private SimpleUniverse univ = null; + private BranchGroup scene = null; + + static class MyCanvas3D extends Canvas3D { + private GraphicsContext3D gc; + + private static final int vertIndices[] = { 0, 1, 2, 0, 2, 3 }; + private static final int normalIndices[] = { 0, 0, 0, 1, 1, 1 }; + private IndexedTriangleArray tri = + new IndexedTriangleArray(4, IndexedTriangleArray.COORDINATES | + IndexedTriangleArray.NORMALS, 6); + + private Point3f vert[] = { + new Point3f(-0.12f, -0.12f, 0.0f), + new Point3f( 0.12f, -0.12f, 0.0f), + new Point3f( 0.12f, 0.12f, 0.0f), + new Point3f(-0.12f, 0.12f, 0.0f), + }; + + private Point3f min[] = { + new Point3f(-0.24f, -0.24f, -0.20f), + new Point3f( 0.04f, -0.28f, -0.24f), + new Point3f( 0.00f, 0.00f, -0.24f), + new Point3f(-0.32f, 0.08f, -0.20f), + }; + + private Point3f max[] = { + new Point3f(-0.04f, -0.04f, 0.12f), + new Point3f( 0.32f, -0.04f, 0.16f), + new Point3f( 0.36f, 0.28f, 0.20f), + new Point3f(-0.04f, 0.24f, 0.16f), + }; + + private Point3f delta[] = { + new Point3f(-0.0021f, -0.0017f, 0.0014f), + new Point3f( 0.0025f, -0.0013f, -0.0018f), + new Point3f( 0.0021f, 0.0017f, 0.0018f), + new Point3f(-0.0025f, 0.0013f, -0.0014f), + }; + + private Vector3f normals[]; + private Vector3f v01 = new Vector3f(); + private Vector3f v02 = new Vector3f(); + private Vector3f v03 = new Vector3f(); + + public void renderField(int fieldDesc) { + computeVert(); + computeNormals(); + gc.draw(tri); + } + + private void computeVert() { + for (int i = 0; i < 4; i++) { + vert[i].add(delta[i]); + if (vert[i].x > max[i].x) { + vert[i].x = max[i].x; + delta[i].x *= -1.0f; + } + if (vert[i].x < min[i].x) { + vert[i].x = min[i].x; + delta[i].x *= -1.0f; + } + if (vert[i].y > max[i].y) { + vert[i].y = max[i].y; + delta[i].y *= -1.0f; + } + if (vert[i].y < min[i].y) { + vert[i].y = min[i].y; + delta[i].y *= -1.0f; + } + if (vert[i].z > max[i].z) { + vert[i].z = max[i].z; + delta[i].z *= -1.0f; + } + if (vert[i].z < min[i].z) { + vert[i].z = min[i].z; + delta[i].z *= -1.0f; + } + } + tri.setCoordinates(0, vert); + } + + private void computeNormals() { + v01.sub(vert[1], vert[0]); + v02.sub(vert[2], vert[0]); + v03.sub(vert[3], vert[0]); + normals[0].cross(v01, v02); + normals[0].normalize(); + normals[1].cross(v02, v03); + normals[1].normalize(); + tri.setNormals(0, normals); + } + + public MyCanvas3D(GraphicsConfiguration gcfg) { + super(gcfg); + + // Allocate memory for normals + normals = new Vector3f[2]; + normals[0] = new Vector3f(); + normals[1] = new Vector3f(); + + // Set up the indices + tri.setCoordinateIndices(0, vertIndices); + tri.setNormalIndices(0, normalIndices); + + // Set up the graphics context + gc = getGraphicsContext3D(); + + // Create the appearance for the triangle fan + Appearance app = new SimpleShaderAppearance(true, false); + Color3f black = new Color3f(0.0f, 0.0f, 0.0f); + Color3f white = new Color3f(1.0f, 1.0f, 1.0f); + Color3f objColor = new Color3f(0.0f, 0.0f, 0.8f); + app.setMaterial(new Material(objColor, black, objColor, + white, 80.0f)); + gc.setAppearance(app); + + // Set up the global lights + Color3f lColor1 = new Color3f(0.7f, 0.7f, 0.7f); + Vector3f lDir1 = new Vector3f(-1.0f, -1.0f, -1.0f); + Color3f alColor = new Color3f(0.2f, 0.2f, 0.2f); + gc.addLight(new AmbientLight(alColor)); + gc.addLight(new DirectionalLight(lColor1, lDir1)); + } + } + + + private BranchGroup createSceneGraph() { + // Create the root of the branch graph + BranchGroup objRoot = new BranchGroup(); + + // Create a bounds for the background and lights + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + + // Set up the background + //TextureLoader bgTexture = new TextureLoader(bgImage, this); + //Background bg = new Background(bgTexture.getImage()); + //bg.setApplicationBounds(bounds); + //objRoot.addChild(bg); + + // Set up the global lights + Color3f lColor1 = new Color3f(0.7f, 0.7f, 0.7f); + Vector3f lDir1 = new Vector3f(-1.0f, -1.0f, -1.0f); + Color3f alColor = new Color3f(0.2f, 0.2f, 0.2f); + + AmbientLight aLgt = new AmbientLight(alColor); + aLgt.setInfluencingBounds(bounds); + DirectionalLight lgt1 = new DirectionalLight(lColor1, lDir1); + lgt1.setInfluencingBounds(bounds); + objRoot.addChild(aLgt); + objRoot.addChild(lgt1); + + // Create a bunch of objects with a behavior and add them + // into the scene graph. + + int row, col; + Appearance[][] app = new SimpleShaderAppearance [3][3]; + + for (row = 0; row < 3; row++) + for (col = 0; col < 3; col++) + app[row][col] = createAppearance(row * 3 + col); + + for (int i = 0; i < 3; i++) { + double ypos = (double)(i - 1) * 0.6; + for (int j = 0; j < 3; j++) { + double xpos = (double)(j - 1) * 0.6; + objRoot.addChild(createObject(app[i][j], 0.12, xpos, ypos)); + } + } + + // Let Java 3D perform optimizations on this scene graph. + objRoot.compile(); + + return objRoot; + } + + + private Appearance createAppearance(int idx) { + Appearance app = new SimpleShaderAppearance(true, false);; + + // Globally used colors + Color3f black = new Color3f(0.0f, 0.0f, 0.0f); + Color3f white = new Color3f(1.0f, 1.0f, 1.0f); + + switch (idx) { + // Unlit solid + case 0: + { + // Set up the coloring properties + Color3f objColor = new Color3f(1.0f, 0.2f, 0.4f); + ColoringAttributes ca = new ColoringAttributes(); + ca.setColor(objColor); + app.setColoringAttributes(ca); + break; + } + + + // Unlit wire frame + case 1: + { + // Set up the coloring properties + Color3f objColor = new Color3f(0.5f, 0.0f, 0.2f); + ColoringAttributes ca = new ColoringAttributes(); + ca.setColor(objColor); + app.setColoringAttributes(ca); + + // Set up the polygon attributes + PolygonAttributes pa = new PolygonAttributes(); + pa.setPolygonMode(pa.POLYGON_LINE); + pa.setCullFace(pa.CULL_NONE); + app.setPolygonAttributes(pa); + break; + } + + // Unlit points + case 2: + { + // Set up the coloring properties + Color3f objColor = new Color3f(0.2f, 0.2f, 1.0f); + ColoringAttributes ca = new ColoringAttributes(); + ca.setColor(objColor); + app.setColoringAttributes(ca); + + // Set up the polygon attributes + PolygonAttributes pa = new PolygonAttributes(); + pa.setPolygonMode(pa.POLYGON_POINT); + pa.setCullFace(pa.CULL_NONE); + app.setPolygonAttributes(pa); + + // Set up point attributes + PointAttributes pta = new PointAttributes(); + pta.setPointSize(5.0f); + app.setPointAttributes(pta); + break; + } + + // Lit solid + case 3: + { + // Set up the material properties + Color3f objColor = new Color3f(0.8f, 0.0f, 0.0f); + app.setMaterial(new Material(objColor, black, objColor, + white, 80.0f)); + break; + } + + // Texture mapped, lit solid + case 4: + {app = new SimpleShaderAppearance(true, true);; + // Set up the texture map + TextureLoader tex = new TextureLoader(texImage, this); + app.setTexture(tex.getTexture()); + + TextureAttributes texAttr = new TextureAttributes(); + texAttr.setTextureMode(TextureAttributes.MODULATE); + app.setTextureAttributes(texAttr); + + + // Set up the material properties + app.setMaterial(new Material(white, black, white, black, 1.0f)); + break; + } + + // Transparent, lit solid + case 5: + { + // Set up the transparency properties + TransparencyAttributes ta = new TransparencyAttributes(); + ta.setTransparencyMode(ta.BLENDED); + ta.setTransparency(0.6f); + app.setTransparencyAttributes(ta); + + // Set up the polygon attributes + PolygonAttributes pa = new PolygonAttributes(); + pa.setCullFace(pa.CULL_NONE); + app.setPolygonAttributes(pa); + + // Set up the material properties + Color3f objColor = new Color3f(0.7f, 0.8f, 1.0f); + app.setMaterial(new Material(objColor, black, objColor, + black, 1.0f)); + break; + } + + // Lit solid, no specular + case 6: + { + // Set up the material properties + Color3f objColor = new Color3f(0.8f, 0.0f, 0.0f); + app.setMaterial(new Material(objColor, black, objColor, + black, 80.0f)); + break; + } + + // Lit solid, specular only + case 7: + { + + // Set up the material properties + Color3f objColor = new Color3f(0.8f, 0.0f, 0.0f); + app.setMaterial(new Material(black, black, black, + white, 80.0f)); + break; + } + + // Another lit solid with a different color + case 8: + { + // Set up the material properties + Color3f objColor = new Color3f(0.8f, 0.8f, 0.0f); + app.setMaterial(new Material(objColor, black, objColor, + white, 80.0f)); + break; + } + + default: + { + ColoringAttributes ca = new ColoringAttributes(); + ca.setColor(new Color3f(0.0f, 1.0f, 0.0f)); + app.setColoringAttributes(ca); + } + } + + return app; + } + + + private Group createObject(Appearance app, double scale, + double xpos, double ypos) { + + // Create a transform group node to scale and position the object. + Transform3D t = new Transform3D(); + t.set(scale, new Vector3d(xpos, ypos, 0.0)); + TransformGroup objTrans = new TransformGroup(t); + + // Create a second transform group node and initialize it to the + // identity. Enable the TRANSFORM_WRITE capability so that + // our behavior code can modify it at runtime. + TransformGroup spinTg = new TransformGroup(); + spinTg.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + + // Create a simple shape leaf node and set the appearance + Shape3D shape = new Tetrahedron(); + shape.setAppearance(app); + + // add it to the scene graph. + spinTg.addChild(shape); + + // Create a new Behavior object that will perform the desired + // operation on the specified transform object and add it into + // the scene graph. + Transform3D yAxis = new Transform3D(); + Alpha rotationAlpha = new Alpha(-1, Alpha.INCREASING_ENABLE, + 0, 0, + 5000, 0, 0, + 0, 0, 0); + + RotationInterpolator rotator = + new RotationInterpolator(rotationAlpha, spinTg, yAxis, + 0.0f, (float) Math.PI*2.0f); + + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + + rotator.setSchedulingBounds(bounds); + + // Add the behavior and the transform group to the object + objTrans.addChild(rotator); + objTrans.addChild(spinTg); + + return objTrans; + } + + + private Canvas3D createUniverse() { + // Get the preferred graphics configuration for the default screen + GraphicsConfiguration config = + SimpleUniverse.getPreferredConfiguration(); + + // Create a MyCanvas3D using the preferred configuration + MyCanvas3D c = new MyCanvas3D(config); + + // Create simple universe with view branch + univ = new SimpleUniverse(c); + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + univ.getViewingPlatform().setNominalViewingTransform(); + + // Ensure at least 5 msec per frame (i.e., < 200Hz) + univ.getViewer().getView().setMinimumFrameCycleTime(5); + + return c; + } + + /** + * Creates new form AppearanceMixed + */ + public AppearanceMixedGL2ES2() { + + if (bgImage == null) { + // the path to the image for an applet + bgImage = Resources.getResource("resources/images/bg.jpg"); + if (bgImage == null) { + System.err.println("resources/images/bg.jpg not found"); + System.exit(1); + } + } + + if (texImage == null) { + // the path to the image for an applet + texImage = Resources.getResource("resources/images/stone.jpg"); + if (texImage == null) { + System.err.println("resources/images/stone.jpg not found"); + System.exit(1); + } + } + + // Initialize the GUI components + initComponents(); + + // Create Canvas3D and SimpleUniverse; add canvas to drawing panel + Canvas3D c = createUniverse(); + drawingPanel.add(c, java.awt.BorderLayout.CENTER); + + // Create the content branch and add it to the universe + scene = createSceneGraph(); + univ.addBranchGraph(scene); + } + + // ---------------------------------------------------------------- + + /** This method is called from within the constructor to + * initialize the form. + * WARNING: Do NOT modify this code. The content of this method is + * always regenerated by the Form Editor. + */ + // <editor-fold defaultstate="collapsed" desc=" Generated Code ">//GEN-BEGIN:initComponents + private void initComponents() { + drawingPanel = new javax.swing.JPanel(); + + setDefaultCloseOperation(javax.swing.WindowConstants.EXIT_ON_CLOSE); + setTitle("AppearanceMixed"); + drawingPanel.setLayout(new java.awt.BorderLayout()); + + drawingPanel.setPreferredSize(new java.awt.Dimension(700, 700)); + getContentPane().add(drawingPanel, java.awt.BorderLayout.CENTER); + + pack(); + }// </editor-fold>//GEN-END:initComponents + + /** + * @param args the command line arguments + */ + public static void main(String args[]) {System.setProperty("sun.awt.noerasebackground", "true"); + System.setProperty("j3d.rend", "jogl2es2");System.setProperty("j3d.displaylist", "false"); + java.awt.EventQueue.invokeLater(new Runnable() { + public void run() { + new AppearanceMixedGL2ES2().setVisible(true); + } + }); + } + + // Variables declaration - do not modify//GEN-BEGIN:variables + private javax.swing.JPanel drawingPanel; + // End of variables declaration//GEN-END:variables + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/appearance/AppearanceTest.form b/src/main/java/org/jdesktop/j3d/examples/appearance/AppearanceTest.form new file mode 100644 index 0000000..43cd90f --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/appearance/AppearanceTest.form @@ -0,0 +1,36 @@ +<?xml version="1.0" encoding="UTF-8" ?> + +<Form version="1.0" type="org.netbeans.modules.form.forminfo.JFrameFormInfo"> + <Properties> + <Property name="defaultCloseOperation" type="int" value="3"/> + <Property name="title" type="java.lang.String" value="AppearanceTest"/> + </Properties> + <SyntheticProperties> + <SyntheticProperty name="formSizePolicy" type="int" value="1"/> + </SyntheticProperties> + <AuxValues> + <AuxValue name="FormSettings_generateMnemonicsCode" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_listenerGenerationStyle" type="java.lang.Integer" value="0"/> + <AuxValue name="FormSettings_variablesLocal" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_variablesModifier" type="java.lang.Integer" value="2"/> + <AuxValue name="designerSize" type="java.awt.Dimension" value="-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,1,44,0,0,1,-112"/> + </AuxValues> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + <SubComponents> + <Container class="javax.swing.JPanel" name="drawingPanel"> + <Properties> + <Property name="preferredSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor"> + <Dimension value="[700, 700]"/> + </Property> + </Properties> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout" value="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription"> + <BorderConstraints direction="Center"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + </Container> + </SubComponents> +</Form> diff --git a/src/main/java/org/jdesktop/j3d/examples/appearance/AppearanceTest.java b/src/main/java/org/jdesktop/j3d/examples/appearance/AppearanceTest.java new file mode 100644 index 0000000..0f0315a --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/appearance/AppearanceTest.java @@ -0,0 +1,419 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.appearance; + +import java.awt.GraphicsConfiguration; + +import org.jdesktop.j3d.examples.Resources; +import org.jogamp.java3d.Alpha; +import org.jogamp.java3d.AmbientLight; +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.Background; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.ColoringAttributes; +import org.jogamp.java3d.DirectionalLight; +import org.jogamp.java3d.Group; +import org.jogamp.java3d.Material; +import org.jogamp.java3d.PointAttributes; +import org.jogamp.java3d.PolygonAttributes; +import org.jogamp.java3d.RotationInterpolator; +import org.jogamp.java3d.Shape3D; +import org.jogamp.java3d.TextureAttributes; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.TransparencyAttributes; +import org.jogamp.java3d.utils.image.TextureLoader; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Vector3d; +import org.jogamp.vecmath.Vector3f; + +public class AppearanceTest extends javax.swing.JFrame { + + private java.net.URL texImage = null; + private java.net.URL bgImage = null; + private SimpleUniverse univ = null; + private BranchGroup scene = null; + + private BranchGroup createSceneGraph() { + // Create the root of the branch graph + BranchGroup objRoot = new BranchGroup(); + + // Create a bounds for the background and lights + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + + // Set up the background + TextureLoader bgTexture = new TextureLoader(bgImage, this); + Background bg = new Background(bgTexture.getImage()); + bg.setApplicationBounds(bounds); + objRoot.addChild(bg); + + // Set up the global lights + Color3f lColor1 = new Color3f(0.7f, 0.7f, 0.7f); + Vector3f lDir1 = new Vector3f(-1.0f, -1.0f, -1.0f); + Color3f alColor = new Color3f(0.2f, 0.2f, 0.2f); + + AmbientLight aLgt = new AmbientLight(alColor); + aLgt.setInfluencingBounds(bounds); + DirectionalLight lgt1 = new DirectionalLight(lColor1, lDir1); + lgt1.setInfluencingBounds(bounds); + objRoot.addChild(aLgt); + objRoot.addChild(lgt1); + + // Create a bunch of objects with a behavior and add them + // into the scene graph. + + int row, col; + Appearance[][] app = new Appearance[3][3]; + + for (row = 0; row < 3; row++) + for (col = 0; col < 3; col++) + app[row][col] = createAppearance(row * 3 + col); + + for (int i = 0; i < 3; i++) { + double ypos = (double)(i - 1) * 0.6; + for (int j = 0; j < 3; j++) { + double xpos = (double)(j - 1) * 0.6; + objRoot.addChild(createObject(app[i][j], 0.12, xpos, ypos)); + } + } + + // Let Java 3D perform optimizations on this scene graph. + objRoot.compile(); + + return objRoot; + } + + private Appearance createAppearance(int idx) { + Appearance app = new Appearance(); + + // Globally used colors + Color3f black = new Color3f(0.0f, 0.0f, 0.0f); + Color3f white = new Color3f(1.0f, 1.0f, 1.0f); + + switch (idx) { + // Unlit solid + case 0: + { + // Set up the coloring properties + Color3f objColor = new Color3f(1.0f, 0.2f, 0.4f); + ColoringAttributes ca = new ColoringAttributes(); + ca.setColor(objColor); + app.setColoringAttributes(ca); + break; + } + + + // Unlit wire frame + case 1: + { + // Set up the coloring properties + Color3f objColor = new Color3f(0.5f, 0.0f, 0.2f); + ColoringAttributes ca = new ColoringAttributes(); + ca.setColor(objColor); + app.setColoringAttributes(ca); + + // Set up the polygon attributes + PolygonAttributes pa = new PolygonAttributes(); + pa.setPolygonMode(pa.POLYGON_LINE); + pa.setCullFace(pa.CULL_NONE); + app.setPolygonAttributes(pa); + break; + } + + // Unlit points + case 2: + { + // Set up the coloring properties + Color3f objColor = new Color3f(0.2f, 0.2f, 1.0f); + ColoringAttributes ca = new ColoringAttributes(); + ca.setColor(objColor); + app.setColoringAttributes(ca); + + // Set up the polygon attributes + PolygonAttributes pa = new PolygonAttributes(); + pa.setPolygonMode(pa.POLYGON_POINT); + pa.setCullFace(pa.CULL_NONE); + app.setPolygonAttributes(pa); + + // Set up point attributes + PointAttributes pta = new PointAttributes(); + pta.setPointSize(5.0f); + app.setPointAttributes(pta); + break; + } + + // Lit solid + case 3: + { + // Set up the material properties + Color3f objColor = new Color3f(0.8f, 0.0f, 0.0f); + app.setMaterial(new Material(objColor, black, objColor, + white, 80.0f)); + break; + } + + // Texture mapped, lit solid + case 4: + { + // Set up the texture map + TextureLoader tex = new TextureLoader(texImage, this); + app.setTexture(tex.getTexture()); + + TextureAttributes texAttr = new TextureAttributes(); + texAttr.setTextureMode(TextureAttributes.MODULATE); + app.setTextureAttributes(texAttr); + + // Set up the material properties + app.setMaterial(new Material(white, black, white, black, 1.0f)); + break; + } + + // Transparent, lit solid + case 5: + { + // Set up the transparency properties + TransparencyAttributes ta = new TransparencyAttributes(); + ta.setTransparencyMode(ta.BLENDED); + ta.setTransparency(0.6f); + app.setTransparencyAttributes(ta); + + // Set up the polygon attributes + PolygonAttributes pa = new PolygonAttributes(); + pa.setCullFace(pa.CULL_NONE); + app.setPolygonAttributes(pa); + + // Set up the material properties + Color3f objColor = new Color3f(0.7f, 0.8f, 1.0f); + app.setMaterial(new Material(objColor, black, objColor, + black, 1.0f)); + break; + } + + // Lit solid, no specular + case 6: + { + // Set up the material properties + Color3f objColor = new Color3f(0.8f, 0.0f, 0.0f); + app.setMaterial(new Material(objColor, black, objColor, + black, 80.0f)); + break; + } + + // Lit solid, specular only + case 7: + { + // Set up the material properties + Color3f objColor = new Color3f(0.8f, 0.0f, 0.0f); + app.setMaterial(new Material(black, black, black, + white, 80.0f)); + break; + } + + // Another lit solid with a different color + case 8: + { + // Set up the material properties + Color3f objColor = new Color3f(0.8f, 0.8f, 0.0f); + app.setMaterial(new Material(objColor, black, objColor, + white, 80.0f)); + break; + } + + default: + { + ColoringAttributes ca = new ColoringAttributes(); + ca.setColor(new Color3f(0.0f, 1.0f, 0.0f)); + app.setColoringAttributes(ca); + } + } + + return app; + } + + + private Group createObject(Appearance app, double scale, + double xpos, double ypos) { + + // Create a transform group node to scale and position the object. + Transform3D t = new Transform3D(); + t.set(scale, new Vector3d(xpos, ypos, 0.0)); + TransformGroup objTrans = new TransformGroup(t); + + // Create a second transform group node and initialize it to the + // identity. Enable the TRANSFORM_WRITE capability so that + // our behavior code can modify it at runtime. + TransformGroup spinTg = new TransformGroup(); + spinTg.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + + // Create a simple shape leaf node and set the appearance + Shape3D shape = new Tetrahedron(); + shape.setAppearance(app); + + // add it to the scene graph. + spinTg.addChild(shape); + + // Create a new Behavior object that will perform the desired + // operation on the specified transform object and add it into + // the scene graph. + Transform3D yAxis = new Transform3D(); + Alpha rotationAlpha = new Alpha(-1, Alpha.INCREASING_ENABLE, + 0, 0, + 5000, 0, 0, + 0, 0, 0); + + RotationInterpolator rotator = + new RotationInterpolator(rotationAlpha, spinTg, yAxis, + 0.0f, (float) Math.PI*2.0f); + + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + + rotator.setSchedulingBounds(bounds); + + // Add the behavior and the transform group to the object + objTrans.addChild(rotator); + objTrans.addChild(spinTg); + + return objTrans; + } + + private Canvas3D createUniverse() { + // Get the preferred graphics configuration for the default screen + GraphicsConfiguration config = + SimpleUniverse.getPreferredConfiguration(); + + // Create a Canvas3D using the preferred configuration + Canvas3D c = new Canvas3D(config); + + // Create simple universe with view branch + univ = new SimpleUniverse(c); + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + univ.getViewingPlatform().setNominalViewingTransform(); + + // Ensure at least 5 msec per frame (i.e., < 200Hz) + univ.getViewer().getView().setMinimumFrameCycleTime(5); + + return c; + } + + /** + * Creates new form AppearanceTest + */ + public AppearanceTest() { + + if (bgImage == null) { + // the path to the image for an applet + bgImage = Resources.getResource("resources/images/bg.jpg"); + if (bgImage == null) { + System.err.println("resources/images/bg.jpg not found"); + System.exit(1); + } + } + + if (texImage == null) { + // the path to the image for an applet + texImage = Resources.getResource("resources/images/stone.jpg"); + if (texImage == null) { + System.err.println("resources/images/stone.jpg not found"); + System.exit(1); + } + } + + // Initialize the GUI components + initComponents(); + + // Create Canvas3D and SimpleUniverse; add canvas to drawing panel + Canvas3D c = createUniverse(); + drawingPanel.add(c, java.awt.BorderLayout.CENTER); + + // Create the content branch and add it to the universe + scene = createSceneGraph(); + univ.addBranchGraph(scene); + } + + // ---------------------------------------------------------------- + + /** This method is called from within the constructor to + * initialize the form. + * WARNING: Do NOT modify this code. The content of this method is + * always regenerated by the Form Editor. + */ + // <editor-fold defaultstate="collapsed" desc=" Generated Code ">//GEN-BEGIN:initComponents + private void initComponents() { + drawingPanel = new javax.swing.JPanel(); + + setDefaultCloseOperation(javax.swing.WindowConstants.EXIT_ON_CLOSE); + setTitle("AppearanceTest"); + drawingPanel.setLayout(new java.awt.BorderLayout()); + + drawingPanel.setPreferredSize(new java.awt.Dimension(700, 700)); + getContentPane().add(drawingPanel, java.awt.BorderLayout.CENTER); + + pack(); + }// </editor-fold>//GEN-END:initComponents + + /** + * @param args the command line arguments + */ + public static void main(String args[]) {System.setProperty("sun.awt.noerasebackground", "true"); + java.awt.EventQueue.invokeLater(new Runnable() { + public void run() { + new AppearanceTest().setVisible(true); + } + }); + } + + // Variables declaration - do not modify//GEN-BEGIN:variables + private javax.swing.JPanel drawingPanel; + // End of variables declaration//GEN-END:variables + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/appearance/Tetrahedron.java b/src/main/java/org/jdesktop/j3d/examples/appearance/Tetrahedron.java new file mode 100644 index 0000000..625e7e4 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/appearance/Tetrahedron.java @@ -0,0 +1,113 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.appearance; + +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.Shape3D; +import org.jogamp.java3d.TriangleArray; +import org.jogamp.vecmath.Point3f; +import org.jogamp.vecmath.TexCoord2f; +import org.jogamp.vecmath.Vector3f; + +public class Tetrahedron extends Shape3D { + private static final float sqrt3 = (float) Math.sqrt(3.0); + private static final float sqrt3_3 = sqrt3 / 3.0f; + private static final float sqrt24_3 = (float) Math.sqrt(24.0) / 3.0f; + + private static final float ycenter = 0.5f * sqrt24_3; + private static final float zcenter = -sqrt3_3; + + private static final Point3f p1 = new Point3f(-1.0f, -ycenter, -zcenter); + private static final Point3f p2 = new Point3f(1.0f, -ycenter, -zcenter); + private static final Point3f p3 = + new Point3f(0.0f, -ycenter, -sqrt3 - zcenter); + private static final Point3f p4 = + new Point3f(0.0f, sqrt24_3 - ycenter, 0.0f); + + private static final Point3f[] verts = { + p1, p2, p4, // front face + p1, p4, p3, // left, back face + p2, p3, p4, // right, back face + p1, p3, p2, // bottom face + }; + + private TexCoord2f texCoord[] = { + new TexCoord2f(0.0f, 0.0f), + new TexCoord2f(1.0f, 0.0f), + new TexCoord2f(0.5f, sqrt3 / 2.0f), + }; + + public Tetrahedron() { + int i; + + TriangleArray tetra = new TriangleArray(12, TriangleArray.COORDINATES | + TriangleArray.NORMALS | TriangleArray.TEXTURE_COORDINATE_2); + + tetra.setCoordinates(0, verts); + for (i = 0; i < 12; i++) { + tetra.setTextureCoordinate(0, i, texCoord[i%3]); + } + + int face; + Vector3f normal = new Vector3f(); + Vector3f v1 = new Vector3f(); + Vector3f v2 = new Vector3f(); + Point3f [] pts = new Point3f[3]; + for (i = 0; i < 3; i++) pts[i] = new Point3f(); + + for (face = 0; face < 4; face++) { + tetra.getCoordinates(face*3, pts); + v1.sub(pts[1], pts[0]); + v2.sub(pts[2], pts[0]); + normal.cross(v1, v2); + normal.normalize(); + for (i = 0; i < 3; i++) { + tetra.setNormal((face * 3 + i), normal); + } + } + this.setGeometry(tetra); + this.setAppearance(new Appearance()); + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/applet3d/Applet3D.form b/src/main/java/org/jdesktop/j3d/examples/applet3d/Applet3D.form new file mode 100644 index 0000000..a70fb22 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/applet3d/Applet3D.form @@ -0,0 +1,69 @@ +<?xml version="1.0" encoding="UTF-8" ?> + +<Form version="1.0" type="org.netbeans.modules.form.forminfo.JPanelFormInfo"> + <AuxValues> + <AuxValue name="FormSettings_autoResourcing" type="java.lang.Integer" value="0"/> + <AuxValue name="FormSettings_generateMnemonicsCode" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_i18nAutoMode" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_layoutCodeTarget" type="java.lang.Integer" value="1"/> + <AuxValue name="FormSettings_listenerGenerationStyle" type="java.lang.Integer" value="0"/> + <AuxValue name="FormSettings_variablesLocal" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_variablesModifier" type="java.lang.Integer" value="2"/> + <AuxValue name="designerSize" type="java.awt.Dimension" value="-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,1,44,0,0,1,-112"/> + </AuxValues> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + <SubComponents> + <Container class="javax.swing.JPanel" name="guiPanel"> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout" value="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription"> + <BorderConstraints direction="North"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout"/> + <SubComponents> + <Component class="javax.swing.JButton" name="pauseButton"> + <Properties> + <Property name="text" type="java.lang.String" value="Pause"/> + </Properties> + <Events> + <EventHandler event="actionPerformed" listener="java.awt.event.ActionListener" parameters="java.awt.event.ActionEvent" handler="pauseButtonActionPerformed"/> + </Events> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout" value="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription"> + <GridBagConstraints gridX="-1" gridY="-1" gridWidth="1" gridHeight="1" fill="0" ipadX="0" ipadY="0" insetsTop="4" insetsLeft="4" insetsBottom="4" insetsRight="4" anchor="10" weightX="0.0" weightY="0.0"/> + </Constraint> + </Constraints> + </Component> + <Component class="javax.swing.JButton" name="resumeButton"> + <Properties> + <Property name="text" type="java.lang.String" value="Resume"/> + </Properties> + <Events> + <EventHandler event="actionPerformed" listener="java.awt.event.ActionListener" parameters="java.awt.event.ActionEvent" handler="resumeButtonActionPerformed"/> + </Events> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout" value="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription"> + <GridBagConstraints gridX="-1" gridY="-1" gridWidth="1" gridHeight="1" fill="0" ipadX="0" ipadY="0" insetsTop="4" insetsLeft="4" insetsBottom="4" insetsRight="4" anchor="10" weightX="0.0" weightY="0.0"/> + </Constraint> + </Constraints> + </Component> + </SubComponents> + </Container> + <Container class="javax.swing.JPanel" name="drawingPanel"> + <Properties> + <Property name="preferredSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor"> + <Dimension value="[500, 500]"/> + </Property> + </Properties> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout" value="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription"> + <BorderConstraints direction="Center"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + </Container> + </SubComponents> +</Form> diff --git a/src/main/java/org/jdesktop/j3d/examples/applet3d/Applet3D.html b/src/main/java/org/jdesktop/j3d/examples/applet3d/Applet3D.html new file mode 100644 index 0000000..037c7c1 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/applet3d/Applet3D.html @@ -0,0 +1,26 @@ +<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.0 Transitional//EN"> +<html> +<head> +<title>Simple 3D Applet</title> +</head> +<body> +<applet code="org.jdesktop.applet.util.JNLPAppletLauncher" + width=500 height=400 + archive="../../../../../../../dist/j3d-examples.jar, + http://download.java.net/media/applet-launcher/applet-launcher.jar, + http://download.java.net/media/java3d/webstart/release/j3d/latest/j3dcore.jar, + http://download.java.net/media/java3d/webstart/release/j3d/latest/j3dutils.jar, + http://download.java.net/media/java3d/webstart/release/vecmath/latest/vecmath.jar, + http://download.java.net/media/jogl/builds/archive/jsr-231-webstart-current/jogl.jar, + http://download.java.net/media/gluegen/webstart/gluegen-rt.jar"> + <param name="codebase_lookup" value="false"> + <param name="subapplet.classname" value="org.jdesktop.j3d.examples.applet3d.Applet3D$MyApplet"> + <param name="subapplet.displayname" value="Java 3D Simple Applet"> + <param name="jnlpNumExtensions" value="1"> + <param name="jnlpExtension1" value="http://download.java.net/media/java3d/webstart/release/java3d-latest.jnlp"> + <param name="progressbar" value="true"> + <param name="noddraw.check" value="true"> +</applet> +<p>Simple Java 3D Applet</p> +</body> +</html> diff --git a/src/main/java/org/jdesktop/j3d/examples/applet3d/Applet3D.java b/src/main/java/org/jdesktop/j3d/examples/applet3d/Applet3D.java new file mode 100644 index 0000000..1822cba --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/applet3d/Applet3D.java @@ -0,0 +1,275 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.applet3d; + +import java.awt.BorderLayout; +import java.awt.Container; +import java.awt.GraphicsConfiguration; +import java.awt.GraphicsDevice; +import java.awt.GraphicsEnvironment; + +import javax.swing.JApplet; +import javax.swing.JFrame; +import javax.swing.JPopupMenu; +import javax.swing.WindowConstants; + +import org.jogamp.java3d.Alpha; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.GraphicsConfigTemplate3D; +import org.jogamp.java3d.RotationInterpolator; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.utils.geometry.ColorCube; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.vecmath.Point3d; + +/** + * Simple Java 3D program that can be run as an application or as an applet. + */ +public class Applet3D extends javax.swing.JPanel { + + private SimpleUniverse univ = null; + private BranchGroup scene = null; + + private Alpha rotationAlpha1; + private Alpha rotationAlpha2; + + public BranchGroup createSceneGraph() { + // Create the root of the branch graph + BranchGroup objRoot = new BranchGroup(); + + // Create two TransformGroup nodes in series + TransformGroup objTrans1 = new TransformGroup(); + objTrans1.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + objRoot.addChild(objTrans1); + + // Create two TransformGroup nodes in series + TransformGroup objTrans2 = new TransformGroup(); + objTrans2.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + objTrans1.addChild(objTrans2); + + // Create a simple Shape3D node; add it to the scene graph. + objTrans2.addChild(new ColorCube(0.4)); + + // Create 2 new Behavior objects that will perform the + // desired operations on the specified transforms and add + // them into the scene graph. + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + + Transform3D yAxis1 = new Transform3D(); + rotationAlpha1 = new Alpha(-1, 4000); + + RotationInterpolator rotator1 = + new RotationInterpolator(rotationAlpha1, objTrans1, yAxis1, + 0.0f, (float) Math.PI*2.0f); + rotator1.setSchedulingBounds(bounds); + objRoot.addChild(rotator1); + + Transform3D yAxis2 = new Transform3D(); + yAxis2.rotX(Math.PI/4.0); + rotationAlpha2 = new Alpha(-1, 13000); + + RotationInterpolator rotator2 = + new RotationInterpolator(rotationAlpha2, objTrans2, yAxis2, + 0.0f, (float) Math.PI*2.0f); + rotator2.setSchedulingBounds(bounds); + objRoot.addChild(rotator2); + + return objRoot; + } + + private Canvas3D createUniverse(Container container) { + GraphicsDevice graphicsDevice; + if (container.getGraphicsConfiguration() != null) { + graphicsDevice = container.getGraphicsConfiguration().getDevice(); + } else { + graphicsDevice = + GraphicsEnvironment.getLocalGraphicsEnvironment().getDefaultScreenDevice(); + } + GraphicsConfigTemplate3D template = new GraphicsConfigTemplate3D(); + GraphicsConfiguration config = graphicsDevice.getBestConfiguration(template); + + Canvas3D c = new Canvas3D(config); + + univ = new SimpleUniverse(c); + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + univ.getViewingPlatform().setNominalViewingTransform(); + + // Ensure at least 5 msec per frame (i.e., < 200Hz) + univ.getViewer().getView().setMinimumFrameCycleTime(5); + + return c; + } + + private void destroy() { + univ.cleanup(); + } + + /** + * Creates new form Applet3D + */ + public Applet3D(Container container) { + // Initialize the GUI components + JPopupMenu.setDefaultLightWeightPopupEnabled(false); + initComponents(); + + // Create Canvas3D and SimpleUniverse; add canvas to drawing panel + Canvas3D c = createUniverse(container); + drawingPanel.add(c, BorderLayout.CENTER); + + // Create the content branch and add it to the universe + scene = createSceneGraph(); + univ.addBranchGraph(scene); + } + + // ---------------------------------------------------------------- + + // Applet framework + + public static class MyApplet extends JApplet { + Applet3D mainPanel; + + public void init() {System.setProperty("sun.awt.noerasebackground", "true"); + setLayout(new BorderLayout()); + mainPanel = new Applet3D(this); + add(mainPanel, BorderLayout.CENTER); + } + + public void destroy() { + mainPanel.destroy(); + } + } + + // Application framework + + private static class MyFrame extends JFrame { + MyFrame() { + setLayout(new BorderLayout()); + setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE); + setTitle("Simple 3D Applet"); + getContentPane().add(new Applet3D(this), BorderLayout.CENTER); + pack(); + } + } + + /** + * @param args the command line arguments + */ + public static void main(String args[]) {System.setProperty("sun.awt.noerasebackground", "true"); + java.awt.EventQueue.invokeLater(new Runnable() { + public void run() { + new MyFrame().setVisible(true); + } + }); + } + + /** This method is called from within the constructor to + * initialize the form. + * WARNING: Do NOT modify this code. The content of this method is + * always regenerated by the Form Editor. + */ + // <editor-fold defaultstate="collapsed" desc=" Generated Code ">//GEN-BEGIN:initComponents + private void initComponents() { + java.awt.GridBagConstraints gridBagConstraints; + + guiPanel = new javax.swing.JPanel(); + pauseButton = new javax.swing.JButton(); + resumeButton = new javax.swing.JButton(); + drawingPanel = new javax.swing.JPanel(); + + setLayout(new java.awt.BorderLayout()); + + guiPanel.setLayout(new java.awt.GridBagLayout()); + + pauseButton.setText("Pause"); + pauseButton.addActionListener(new java.awt.event.ActionListener() { + public void actionPerformed(java.awt.event.ActionEvent evt) { + pauseButtonActionPerformed(evt); + } + }); + gridBagConstraints = new java.awt.GridBagConstraints(); + gridBagConstraints.insets = new java.awt.Insets(4, 4, 4, 4); + guiPanel.add(pauseButton, gridBagConstraints); + + resumeButton.setText("Resume"); + resumeButton.addActionListener(new java.awt.event.ActionListener() { + public void actionPerformed(java.awt.event.ActionEvent evt) { + resumeButtonActionPerformed(evt); + } + }); + gridBagConstraints = new java.awt.GridBagConstraints(); + gridBagConstraints.insets = new java.awt.Insets(4, 4, 4, 4); + guiPanel.add(resumeButton, gridBagConstraints); + + add(guiPanel, java.awt.BorderLayout.NORTH); + + drawingPanel.setPreferredSize(new java.awt.Dimension(500, 500)); + drawingPanel.setLayout(new java.awt.BorderLayout()); + add(drawingPanel, java.awt.BorderLayout.CENTER); + }// </editor-fold>//GEN-END:initComponents + + private void resumeButtonActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_resumeButtonActionPerformed + rotationAlpha1.resume(); + rotationAlpha2.resume(); + }//GEN-LAST:event_resumeButtonActionPerformed + + private void pauseButtonActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_pauseButtonActionPerformed + rotationAlpha1.pause(); + rotationAlpha2.pause(); + }//GEN-LAST:event_pauseButtonActionPerformed + + // Variables declaration - do not modify//GEN-BEGIN:variables + private javax.swing.JPanel drawingPanel; + private javax.swing.JPanel guiPanel; + private javax.swing.JButton pauseButton; + private javax.swing.JButton resumeButton; + // End of variables declaration//GEN-END:variables + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/background/BackgroundGeometry.form b/src/main/java/org/jdesktop/j3d/examples/background/BackgroundGeometry.form new file mode 100644 index 0000000..9e76404 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/background/BackgroundGeometry.form @@ -0,0 +1,37 @@ +<?xml version="1.0" encoding="UTF-8" ?> + +<Form version="1.0" type="org.netbeans.modules.form.forminfo.JFrameFormInfo"> + <Properties> + <Property name="defaultCloseOperation" type="int" value="3"/> + <Property name="title" type="java.lang.String" value="BackgroundGeometry"/> + </Properties> + <SyntheticProperties> + <SyntheticProperty name="formSizePolicy" type="int" value="1"/> + </SyntheticProperties> + <AuxValues> + <AuxValue name="FormSettings_generateMnemonicsCode" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_listenerGenerationStyle" type="java.lang.Integer" value="0"/> + <AuxValue name="FormSettings_variablesLocal" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_variablesModifier" type="java.lang.Integer" value="2"/> + <AuxValue name="designerSize" type="java.awt.Dimension" value="-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,1,44,0,0,1,-112"/> + </AuxValues> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + <SubComponents> + <Container class="javax.swing.JPanel" name="drawingPanel"> + <Properties> + <Property name="opaque" type="boolean" value="false"/> + <Property name="preferredSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor"> + <Dimension value="[700, 700]"/> + </Property> + </Properties> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout" value="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription"> + <BorderConstraints direction="Center"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + </Container> + </SubComponents> +</Form> diff --git a/src/main/java/org/jdesktop/j3d/examples/background/BackgroundGeometry.java b/src/main/java/org/jdesktop/j3d/examples/background/BackgroundGeometry.java new file mode 100644 index 0000000..18d2f5f --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/background/BackgroundGeometry.java @@ -0,0 +1,280 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.background; + +import java.awt.GraphicsConfiguration; + +import org.jdesktop.j3d.examples.Resources; +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.Background; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.DirectionalLight; +import org.jogamp.java3d.Material; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.utils.behaviors.mouse.MouseRotate; +import org.jogamp.java3d.utils.behaviors.mouse.MouseTranslate; +import org.jogamp.java3d.utils.behaviors.mouse.MouseZoom; +import org.jogamp.java3d.utils.geometry.Box; +import org.jogamp.java3d.utils.geometry.Sphere; +import org.jogamp.java3d.utils.image.TextureLoader; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Vector3f; + +public class BackgroundGeometry extends javax.swing.JFrame { + + private SimpleUniverse univ = null; + private BranchGroup scene = null; + private java.net.URL bgImage = null; + private BoundingSphere bounds = new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + + public BranchGroup createSceneGraph() { + + // Create the root of the branch graph + BranchGroup objRoot = new BranchGroup(); + + // Create a Transformgroup to scale all objects so they + // appear in the scene. + TransformGroup objScale = new TransformGroup(); + Transform3D t3d = new Transform3D(); + t3d.setScale(0.4); + objScale.setTransform(t3d); + objRoot.addChild(objScale); + + // Create the transform group node and initialize it to the + // identity. Enable the TRANSFORM_WRITE capability so that + // our behavior code can modify it at runtime. + TransformGroup objTrans = new TransformGroup(); + objScale.addChild(objTrans); + + Background bg = new Background(); + bg.setApplicationBounds(bounds); + BranchGroup backGeoBranch = new BranchGroup(); + Sphere sphereObj = new Sphere(1.0f, Sphere.GENERATE_NORMALS | + Sphere.GENERATE_NORMALS_INWARD | + Sphere.GENERATE_TEXTURE_COORDS | + Sphere.GENERATE_TEXTURE_COORDS_Y_UP, 45); + Appearance backgroundApp = sphereObj.getAppearance(); + backGeoBranch.addChild(sphereObj); + bg.setGeometry(backGeoBranch); + objTrans.addChild(bg); + + TextureLoader tex = new TextureLoader(bgImage, + new String("RGB"), + TextureLoader.BY_REFERENCE | TextureLoader.Y_UP, + this); + if (tex != null) + backgroundApp.setTexture(tex.getTexture()); + + Vector3f tranlation = new Vector3f(2.0f, 0.0f, 0.0f); + Transform3D modelTransform = new Transform3D(); + Transform3D tmpTransform = new Transform3D(); + double angleInc = Math.PI/8.0; + double angle = 0.0; + int numBoxes = 16; + + float scaleX[] = {0.1f, 0.2f, 0.2f, 0.3f, + 0.2f, 0.1f, 0.2f, 0.3f, + 0.1f, 0.3f, 0.2f, 0.3f, + 0.1f, 0.3f, 0.2f, 0.3f}; + + float scaleY[] = {0.3f, 0.4f, 0.3f, 0.4f, + 0.3f, 0.4f, 0.3f, 0.4f, + 0.3f, 0.3f, 0.3f, 0.3f, + 0.3f, 0.3f, 0.3f, 0.4f}; + + float scaleZ[] = {0.3f, 0.2f, 0.1f, 0.1f, + 0.3f, 0.2f, 0.1f, 0.3f, + 0.3f, 0.2f, 0.1f, 0.3f, + 0.3f, 0.2f, 0.1f, 0.2f}; + + Appearance a1 = new Appearance(); + Color3f eColor = new Color3f(0.0f, 0.0f, 0.0f); + Color3f sColor = new Color3f(0.5f, 0.5f, 1.0f); + Color3f oColor = new Color3f(0.5f, 0.5f, 0.3f); + + Material m = new Material(oColor, eColor, oColor, sColor, 100.0f); + m.setLightingEnable(true); + a1.setMaterial(m); + + for (int i=0; i<numBoxes; i++, angle += angleInc) { + modelTransform.rotY(angle); + tmpTransform.set(tranlation); + modelTransform.mul(tmpTransform); + + TransformGroup tgroup = new TransformGroup(modelTransform); + objTrans.addChild(tgroup); + + tgroup.addChild( new Box(scaleX[i],scaleY[i],scaleZ[i], + Box.GENERATE_NORMALS,a1)); + } + + + // Shine it with two lights. + Color3f lColor1 = new Color3f(0.7f, 0.7f, 0.7f); + Color3f lColor2 = new Color3f(0.2f, 0.2f, 0.1f); + Vector3f lDir1 = new Vector3f(-1.0f, -1.0f, -1.0f); + Vector3f lDir2 = new Vector3f(0.0f, 0.0f, -1.0f); + DirectionalLight lgt1 = new DirectionalLight(lColor1, lDir1); + DirectionalLight lgt2 = new DirectionalLight(lColor2, lDir2); + lgt1.setInfluencingBounds(bounds); + lgt2.setInfluencingBounds(bounds); + objScale.addChild(lgt1); + objScale.addChild(lgt2); + + return objRoot; + } + + private Canvas3D createUniverse() { + // Get the preferred graphics configuration for the default screen + GraphicsConfiguration config = + SimpleUniverse.getPreferredConfiguration(); + + // Create a Canvas3D using the preferred configuration + Canvas3D c = new Canvas3D(config); + + // Create simple universe with view branch + univ = new SimpleUniverse(c); + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + univ.getViewingPlatform().setNominalViewingTransform(); + + // Ensure at least 5 msec per frame (i.e., < 200Hz) + univ.getViewer().getView().setMinimumFrameCycleTime(5); + + TransformGroup viewTrans = + univ.getViewingPlatform().getViewPlatformTransform(); + + // Create the rotate behavior node + MouseRotate behavior1 = new MouseRotate(viewTrans); + scene.addChild(behavior1); + behavior1.setSchedulingBounds(bounds); + + // Create the zoom behavior node + MouseZoom behavior2 = new MouseZoom(viewTrans); + scene.addChild(behavior2); + behavior2.setSchedulingBounds(bounds); + + // Create the translate behavior node + MouseTranslate behavior3 = new MouseTranslate(viewTrans); + scene.addChild(behavior3); + behavior3.setSchedulingBounds(bounds); + + return c; + } + + /** + * Creates new form BackgroundGeometry + */ + public BackgroundGeometry() { + + if (bgImage == null) { + // the path to the image for an applet + bgImage = Resources.getResource("resources/images/bg.jpg"); + if (bgImage == null) { + System.err.println("resources/images/bg.jpg not found"); + System.exit(1); + } + } + + // Initialize the GUI components + initComponents(); + + // Create the content branch and add it to the universe + scene = createSceneGraph(); + + // Create Canvas3D and SimpleUniverse; add canvas to drawing panel + Canvas3D c = createUniverse(); + drawingPanel.add(c, java.awt.BorderLayout.CENTER); + + // Let Java 3D perform optimizations on this scene graph. + scene.compile(); + + univ.addBranchGraph(scene); + } + + // ---------------------------------------------------------------- + + /** This method is called from within the constructor to + * initialize the form. + * WARNING: Do NOT modify this code. The content of this method is + * always regenerated by the Form Editor. + */ + // <editor-fold defaultstate="collapsed" desc=" Generated Code ">//GEN-BEGIN:initComponents + private void initComponents() { + drawingPanel = new javax.swing.JPanel(); + + setDefaultCloseOperation(javax.swing.WindowConstants.EXIT_ON_CLOSE); + setTitle("BackgroundGeometry"); + drawingPanel.setLayout(new java.awt.BorderLayout()); + + drawingPanel.setOpaque(false); + drawingPanel.setPreferredSize(new java.awt.Dimension(700, 700)); + getContentPane().add(drawingPanel, java.awt.BorderLayout.CENTER); + + pack(); + }// </editor-fold>//GEN-END:initComponents + + /** + * @param args the command line arguments + */ + public static void main(String args[]) {System.setProperty("sun.awt.noerasebackground", "true"); + java.awt.EventQueue.invokeLater(new Runnable() { + public void run() { + new BackgroundGeometry().setVisible(true); + } + }); + } + + // Variables declaration - do not modify//GEN-BEGIN:variables + private javax.swing.JPanel drawingPanel; + // End of variables declaration//GEN-END:variables + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/background/BackgroundGeometryGL2ES2.java b/src/main/java/org/jdesktop/j3d/examples/background/BackgroundGeometryGL2ES2.java new file mode 100644 index 0000000..709dd78 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/background/BackgroundGeometryGL2ES2.java @@ -0,0 +1,263 @@ +/* + * Copyright (c) 2016 JogAmp Community. All rights reserved. + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * This code is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 only, as + * published by the Free Software Foundation. Sun designates this + * particular file as subject to the "Classpath" exception as provided + * by Sun in the LICENSE file that accompanied this code. + * + * This code is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + * version 2 for more details (a copy is included in the LICENSE file that + * accompanied this code). + * + * You should have received a copy of the GNU General Public License version + * 2 along with this work; if not, write to the Free Software Foundation, + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. + * + */ + +package org.jdesktop.j3d.examples.background; + +import java.awt.GraphicsConfiguration; + +import org.jdesktop.j3d.examples.Resources; +import org.jdesktop.j3d.examples.gl2es2pipeline.SimpleShaderAppearance; +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.Background; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.DirectionalLight; +import org.jogamp.java3d.Material; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.utils.behaviors.mouse.MouseRotate; +import org.jogamp.java3d.utils.behaviors.mouse.MouseTranslate; +import org.jogamp.java3d.utils.behaviors.mouse.MouseZoom; +import org.jogamp.java3d.utils.geometry.Box; +import org.jogamp.java3d.utils.geometry.Sphere; +import org.jogamp.java3d.utils.image.TextureLoader; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Vector3f; + +public class BackgroundGeometryGL2ES2 extends javax.swing.JFrame { + + private SimpleUniverse univ = null; + private BranchGroup scene = null; + private java.net.URL bgImage = null; + private BoundingSphere bounds = new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + + public BranchGroup createSceneGraph() { + + // Create the root of the branch graph + BranchGroup objRoot = new BranchGroup(); + + // Create a Transformgroup to scale all objects so they + // appear in the scene. + TransformGroup objScale = new TransformGroup(); + Transform3D t3d = new Transform3D(); + t3d.setScale(0.4); + objScale.setTransform(t3d); + objRoot.addChild(objScale); + + // Create the transform group node and initialize it to the + // identity. Enable the TRANSFORM_WRITE capability so that + // our behavior code can modify it at runtime. + TransformGroup objTrans = new TransformGroup(); + objScale.addChild(objTrans); + + Background bg = new Background(); + bg.setApplicationBounds(bounds); + BranchGroup backGeoBranch = new BranchGroup(); + Sphere sphereObj = new Sphere(1.0f, Sphere.GENERATE_NORMALS | + Sphere.GENERATE_NORMALS_INWARD | + Sphere.GENERATE_TEXTURE_COORDS | + Sphere.GENERATE_TEXTURE_COORDS_Y_UP, 45); + Appearance backgroundApp = new SimpleShaderAppearance(true, false);//sphereObj.getAppearance(); + sphereObj.setAppearance(backgroundApp); + backGeoBranch.addChild(sphereObj); + bg.setGeometry(backGeoBranch); + objTrans.addChild(bg); + + TextureLoader tex = new TextureLoader(bgImage, + new String("RGB"), + TextureLoader.BY_REFERENCE | TextureLoader.Y_UP, + this); + if (tex != null) + backgroundApp.setTexture(tex.getTexture()); + + Vector3f tranlation = new Vector3f(2.0f, 0.0f, 0.0f); + Transform3D modelTransform = new Transform3D(); + Transform3D tmpTransform = new Transform3D(); + double angleInc = Math.PI/8.0; + double angle = 0.0; + int numBoxes = 16; + + float scaleX[] = {0.1f, 0.2f, 0.2f, 0.3f, + 0.2f, 0.1f, 0.2f, 0.3f, + 0.1f, 0.3f, 0.2f, 0.3f, + 0.1f, 0.3f, 0.2f, 0.3f}; + + float scaleY[] = {0.3f, 0.4f, 0.3f, 0.4f, + 0.3f, 0.4f, 0.3f, 0.4f, + 0.3f, 0.3f, 0.3f, 0.3f, + 0.3f, 0.3f, 0.3f, 0.4f}; + + float scaleZ[] = {0.3f, 0.2f, 0.1f, 0.1f, + 0.3f, 0.2f, 0.1f, 0.3f, + 0.3f, 0.2f, 0.1f, 0.3f, + 0.3f, 0.2f, 0.1f, 0.2f}; + + Appearance a1 = new SimpleShaderAppearance(true, false); + + Color3f eColor = new Color3f(0.0f, 0.0f, 0.0f); + Color3f sColor = new Color3f(0.5f, 0.5f, 1.0f); + Color3f oColor = new Color3f(0.5f, 0.5f, 0.3f); + + Material m = new Material(oColor, eColor, oColor, sColor, 100.0f); + m.setLightingEnable(true); + a1.setMaterial(m); + + for (int i=0; i<numBoxes; i++, angle += angleInc) { + modelTransform.rotY(angle); + tmpTransform.set(tranlation); + modelTransform.mul(tmpTransform); + + TransformGroup tgroup = new TransformGroup(modelTransform); + objTrans.addChild(tgroup); + + tgroup.addChild( new Box(scaleX[i],scaleY[i],scaleZ[i], + Box.GENERATE_NORMALS,a1)); + } + + + // Shine it with two lights. + Color3f lColor1 = new Color3f(0.7f, 0.7f, 0.7f); + Color3f lColor2 = new Color3f(0.2f, 0.2f, 0.1f); + Vector3f lDir1 = new Vector3f(-1.0f, -1.0f, -1.0f); + Vector3f lDir2 = new Vector3f(0.0f, 0.0f, -1.0f); + DirectionalLight lgt1 = new DirectionalLight(lColor1, lDir1); + DirectionalLight lgt2 = new DirectionalLight(lColor2, lDir2); + lgt1.setInfluencingBounds(bounds); + lgt2.setInfluencingBounds(bounds); + objScale.addChild(lgt1); + objScale.addChild(lgt2); + + return objRoot; + } + + private Canvas3D createUniverse() { + // Get the preferred graphics configuration for the default screen + GraphicsConfiguration config = + SimpleUniverse.getPreferredConfiguration(); + + // Create a Canvas3D using the preferred configuration + Canvas3D c = new Canvas3D(config); + + // Create simple universe with view branch + univ = new SimpleUniverse(c); + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + univ.getViewingPlatform().setNominalViewingTransform(); + + // Ensure at least 5 msec per frame (i.e., < 200Hz) + univ.getViewer().getView().setMinimumFrameCycleTime(5); + + TransformGroup viewTrans = + univ.getViewingPlatform().getViewPlatformTransform(); + + // Create the rotate behavior node + MouseRotate behavior1 = new MouseRotate(viewTrans); + scene.addChild(behavior1); + behavior1.setSchedulingBounds(bounds); + + // Create the zoom behavior node + MouseZoom behavior2 = new MouseZoom(viewTrans); + scene.addChild(behavior2); + behavior2.setSchedulingBounds(bounds); + + // Create the translate behavior node + MouseTranslate behavior3 = new MouseTranslate(viewTrans); + scene.addChild(behavior3); + behavior3.setSchedulingBounds(bounds); + + return c; + } + + /** + * Creates new form BackgroundGeometry + */ + public BackgroundGeometryGL2ES2() { + + if (bgImage == null) { + // the path to the image for an applet + bgImage = Resources.getResource("resources/images/bg.jpg"); + if (bgImage == null) { + System.err.println("resources/images/bg.jpg not found"); + System.exit(1); + } + } + + // Initialize the GUI components + initComponents(); + + // Create the content branch and add it to the universe + scene = createSceneGraph(); + + // Create Canvas3D and SimpleUniverse; add canvas to drawing panel + Canvas3D c = createUniverse(); + drawingPanel.add(c, java.awt.BorderLayout.CENTER); + + // Let Java 3D perform optimizations on this scene graph. + scene.compile(); + + univ.addBranchGraph(scene); + } + + // ---------------------------------------------------------------- + + /** This method is called from within the constructor to + * initialize the form. + * WARNING: Do NOT modify this code. The content of this method is + * always regenerated by the Form Editor. + */ + // <editor-fold defaultstate="collapsed" desc=" Generated Code ">//GEN-BEGIN:initComponents + private void initComponents() { + drawingPanel = new javax.swing.JPanel(); + + setDefaultCloseOperation(javax.swing.WindowConstants.EXIT_ON_CLOSE); + setTitle("BackgroundGeometry"); + drawingPanel.setLayout(new java.awt.BorderLayout()); + + drawingPanel.setOpaque(false); + drawingPanel.setPreferredSize(new java.awt.Dimension(700, 700)); + getContentPane().add(drawingPanel, java.awt.BorderLayout.CENTER); + + pack(); + }// </editor-fold>//GEN-END:initComponents + + /** + * @param args the command line arguments + */ + public static void main(String args[]) {System.setProperty("sun.awt.noerasebackground", "true"); + System.setProperty("j3d.rend", "jogl2es2");System.setProperty("j3d.displaylist", "false"); + java.awt.EventQueue.invokeLater(new Runnable() { + @Override + public void run() { + new BackgroundGeometryGL2ES2().setVisible(true); + } + }); + } + + // Variables declaration - do not modify//GEN-BEGIN:variables + private javax.swing.JPanel drawingPanel; + // End of variables declaration//GEN-END:variables + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/collision/Box.java b/src/main/java/org/jdesktop/j3d/examples/collision/Box.java new file mode 100644 index 0000000..a472fb3 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/collision/Box.java @@ -0,0 +1,102 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.collision; + +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.QuadArray; +import org.jogamp.java3d.Shape3D; +import org.jogamp.vecmath.Point3d; + +public class Box extends Shape3D { + + public Box(double xsize, double ysize, double zsize) { + super(); + double xmin = -xsize/2.0; + double xmax = xsize/2.0; + double ymin = -ysize/2.0; + double ymax = ysize/2.0; + double zmin = -zsize/2.0; + double zmax = zsize/2.0; + + QuadArray box = new QuadArray(24, QuadArray.COORDINATES); + + Point3d verts[] = new Point3d[24]; + + // front face + verts[0] = new Point3d(xmax, ymin, zmax); + verts[1] = new Point3d(xmax, ymax, zmax); + verts[2] = new Point3d(xmin, ymax, zmax); + verts[3] = new Point3d(xmin, ymin, zmax); + // back face + verts[4] = new Point3d(xmin, ymin, zmin); + verts[5] = new Point3d(xmin, ymax, zmin); + verts[6] = new Point3d(xmax, ymax, zmin); + verts[7] = new Point3d(xmax, ymin, zmin); + // right face + verts[8] = new Point3d(xmax, ymin, zmin); + verts[9] = new Point3d(xmax, ymax, zmin); + verts[10] = new Point3d(xmax, ymax, zmax); + verts[11] = new Point3d(xmax, ymin, zmax); + // left face + verts[12] = new Point3d(xmin, ymin, zmax); + verts[13] = new Point3d(xmin, ymax, zmax); + verts[14] = new Point3d(xmin, ymax, zmin); + verts[15] = new Point3d(xmin, ymin, zmin); + // top face + verts[16] = new Point3d(xmax, ymax, zmax); + verts[17] = new Point3d(xmax, ymax, zmin); + verts[18] = new Point3d(xmin, ymax, zmin); + verts[19] = new Point3d(xmin, ymax, zmax); + // bottom face + verts[20] = new Point3d(xmin, ymin, zmax); + verts[21] = new Point3d(xmin, ymin, zmin); + verts[22] = new Point3d(xmax, ymin, zmin); + verts[23] = new Point3d(xmax, ymin, zmax); + + box.setCoordinates(0, verts); + setGeometry(box); + setAppearance(new Appearance()); + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/collision/CollisionDetector.java b/src/main/java/org/jdesktop/j3d/examples/collision/CollisionDetector.java new file mode 100644 index 0000000..5d25810 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/collision/CollisionDetector.java @@ -0,0 +1,98 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.collision; + +import java.util.Enumeration; + +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.Behavior; +import org.jogamp.java3d.ColoringAttributes; +import org.jogamp.java3d.Shape3D; +import org.jogamp.java3d.WakeupOnCollisionEntry; +import org.jogamp.java3d.WakeupOnCollisionExit; +import org.jogamp.vecmath.Color3f; + +public class CollisionDetector extends Behavior { + private static final Color3f highlightColor = + new Color3f(0.0f, 1.0f, 0.0f); + private static final ColoringAttributes highlight = + new ColoringAttributes(highlightColor, + ColoringAttributes.SHADE_GOURAUD); + + private boolean inCollision = false; + private Shape3D shape; + private ColoringAttributes shapeColoring; + private Appearance shapeAppearance; + + private WakeupOnCollisionEntry wEnter; + private WakeupOnCollisionExit wExit; + + + public CollisionDetector(Shape3D s) { + shape = s; + shapeAppearance = shape.getAppearance(); + shapeColoring = shapeAppearance.getColoringAttributes(); + inCollision = false; + } + + public void initialize() { + wEnter = new WakeupOnCollisionEntry(shape); + wExit = new WakeupOnCollisionExit(shape); + wakeupOn(wEnter); + } + + public void processStimulus(Enumeration criteria) { + inCollision = !inCollision; + + if (inCollision) { + shapeAppearance.setColoringAttributes(highlight); + wakeupOn(wExit); + } + else { + shapeAppearance.setColoringAttributes(shapeColoring); + wakeupOn(wEnter); + } + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/collision/TickTockCollision.form b/src/main/java/org/jdesktop/j3d/examples/collision/TickTockCollision.form new file mode 100644 index 0000000..5a555b4 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/collision/TickTockCollision.form @@ -0,0 +1,36 @@ +<?xml version="1.0" encoding="UTF-8" ?> + +<Form version="1.0" type="org.netbeans.modules.form.forminfo.JFrameFormInfo"> + <Properties> + <Property name="defaultCloseOperation" type="int" value="3"/> + <Property name="title" type="java.lang.String" value="TickTockCollision"/> + </Properties> + <SyntheticProperties> + <SyntheticProperty name="formSizePolicy" type="int" value="1"/> + </SyntheticProperties> + <AuxValues> + <AuxValue name="FormSettings_generateMnemonicsCode" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_listenerGenerationStyle" type="java.lang.Integer" value="0"/> + <AuxValue name="FormSettings_variablesLocal" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_variablesModifier" type="java.lang.Integer" value="2"/> + <AuxValue name="designerSize" type="java.awt.Dimension" value="-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,1,44,0,0,1,-112"/> + </AuxValues> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + <SubComponents> + <Container class="javax.swing.JPanel" name="drawingPanel"> + <Properties> + <Property name="preferredSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor"> + <Dimension value="[700, 700]"/> + </Property> + </Properties> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout" value="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription"> + <BorderConstraints direction="Center"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + </Container> + </SubComponents> +</Form> diff --git a/src/main/java/org/jdesktop/j3d/examples/collision/TickTockCollision.java b/src/main/java/org/jdesktop/j3d/examples/collision/TickTockCollision.java new file mode 100644 index 0000000..8d1cba2 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/collision/TickTockCollision.java @@ -0,0 +1,272 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.collision; + +import java.awt.GraphicsConfiguration; + +import org.jogamp.java3d.Alpha; +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.Background; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.ColoringAttributes; +import org.jogamp.java3d.Group; +import org.jogamp.java3d.RotationInterpolator; +import org.jogamp.java3d.Shape3D; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.utils.geometry.ColorCube; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Vector3d; + +/** + * Simple Java 3D example program to display how collision work. + */ +public class TickTockCollision extends javax.swing.JFrame { + + private SimpleUniverse univ = null; + private BranchGroup scene = null; + + public BranchGroup createSceneGraph() { + // Create the root of the branch graph + BranchGroup objRoot = new BranchGroup(); + + // Create a Transformgroup to scale all objects so they + // appear in the scene. + TransformGroup objScale = new TransformGroup(); + Transform3D t3d = new Transform3D(); + t3d.setScale(0.4); + objScale.setTransform(t3d); + objRoot.addChild(objScale); + + // Create a bounds for the background and behaviors + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + + // Set up the background + Color3f bgColor = new Color3f(0.05f, 0.05f, 0.2f); + Background bg = new Background(bgColor); + bg.setApplicationBounds(bounds); + objScale.addChild(bg); + + // Create a pair of transform group nodes and initialize them to + // identity. Enable the TRANSFORM_WRITE capability so that + // our behaviors can modify them at runtime. Add them to the + // root of the subgraph. + TransformGroup objTrans1 = new TransformGroup(); + objTrans1.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + objScale.addChild(objTrans1); + + TransformGroup objTrans2 = new TransformGroup(); + objTrans2.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + objTrans1.addChild(objTrans2); + + // Create the positioning and scaling transform group node. + Transform3D t = new Transform3D(); + t.set(0.3, new Vector3d(0.0, -1.5, 0.0)); + TransformGroup objTrans3 = new TransformGroup(t); + objTrans2.addChild(objTrans3); + + // Create a simple shape leaf node, add it to the scene graph. + objTrans3.addChild(new ColorCube()); + + // Create a new Behavior object that will perform the desired + // rotation on the specified transform object and add it into + // the scene graph. + Transform3D yAxis1 = new Transform3D(); + yAxis1.rotX(Math.PI/2.0); + Alpha tickTockAlpha = new Alpha(-1, Alpha.INCREASING_ENABLE | + Alpha.DECREASING_ENABLE, + 0, 0, + 5000, 2500, 200, + 5000, 2500, 200); + + RotationInterpolator tickTock = + new RotationInterpolator(tickTockAlpha, objTrans1, yAxis1, + -(float) Math.PI/2.0f, + (float) Math.PI/2.0f); + tickTock.setSchedulingBounds(bounds); + objTrans2.addChild(tickTock); + + // Create a new Behavior object that will perform the desired + // rotation on the specified transform object and add it into + // the scene graph. + Transform3D yAxis2 = new Transform3D(); + Alpha rotationAlpha = new Alpha(-1, Alpha.INCREASING_ENABLE, + 0, 0, + 4000, 0, 0, + 0, 0, 0); + + RotationInterpolator rotator = + new RotationInterpolator(rotationAlpha, objTrans2, yAxis2, + 0.0f, (float) Math.PI*2.0f); + rotator.setSchedulingBounds(bounds); + objTrans2.addChild(rotator); + + // Now create a pair of rectangular boxes, each with a collision + // detection behavior attached. The behavior will highlight the + // object when it is in a state of collision. + + Group box1 = createBox(0.3, new Vector3d(-1.3, 0.0, 0.0)); + Group box2 = createBox(0.3, new Vector3d( 1.3, 0.0, 0.0)); + + objScale.addChild(box1); + objScale.addChild(box2); + + // Have Java 3D perform optimizations on this scene graph. + objRoot.compile(); + + return objRoot; + } + + private Group createBox(double scale, Vector3d pos) { + // Create a transform group node to scale and position the object. + Transform3D t = new Transform3D(); + t.set(scale, pos); + TransformGroup objTrans = new TransformGroup(t); + + // Create a simple shape leaf node and add it to the scene graph + Shape3D shape = new Box(0.5, 5.0, 1.0); + objTrans.addChild(shape); + + // Create a new ColoringAttributes object for the shape's + // appearance and make it writable at runtime. + Appearance app = shape.getAppearance(); + ColoringAttributes ca = new ColoringAttributes(); + ca.setColor(0.6f, 0.3f, 0.0f); + app.setCapability(app.ALLOW_COLORING_ATTRIBUTES_WRITE); + app.setColoringAttributes(ca); + + // Create a new Behavior object that will perform the collision + // detection on the specified object, and add it into + // the scene graph. + CollisionDetector cd = new CollisionDetector(shape); + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + cd.setSchedulingBounds(bounds); + + // Add the behavior to the scene graph + objTrans.addChild(cd); + + return objTrans; + } + + private Canvas3D createUniverse() { + // Get the preferred graphics configuration for the default screen + GraphicsConfiguration config = + SimpleUniverse.getPreferredConfiguration(); + + // Create a Canvas3D using the preferred configuration + Canvas3D c = new Canvas3D(config); + + // Create simple universe with view branch + univ = new SimpleUniverse(c); + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + univ.getViewingPlatform().setNominalViewingTransform(); + + // Ensure at least 5 msec per frame (i.e., < 200Hz) + univ.getViewer().getView().setMinimumFrameCycleTime(5); + + return c; + } + + /** + * Creates new form TickTockCollision + */ + public TickTockCollision() { + // Initialize the GUI components + initComponents(); + + // Create Canvas3D and SimpleUniverse; add canvas to drawing panel + Canvas3D c = createUniverse(); + drawingPanel.add(c, java.awt.BorderLayout.CENTER); + + // Create the content branch and add it to the universe + scene = createSceneGraph(); + univ.addBranchGraph(scene); + } + + // ---------------------------------------------------------------- + + /** This method is called from within the constructor to + * initialize the form. + * WARNING: Do NOT modify this code. The content of this method is + * always regenerated by the Form Editor. + */ + // <editor-fold defaultstate="collapsed" desc=" Generated Code ">//GEN-BEGIN:initComponents + private void initComponents() { + drawingPanel = new javax.swing.JPanel(); + + setDefaultCloseOperation(javax.swing.WindowConstants.EXIT_ON_CLOSE); + setTitle("TickTockCollision"); + drawingPanel.setLayout(new java.awt.BorderLayout()); + + drawingPanel.setPreferredSize(new java.awt.Dimension(700, 700)); + getContentPane().add(drawingPanel, java.awt.BorderLayout.CENTER); + + pack(); + }// </editor-fold>//GEN-END:initComponents + + /** + * @param args the command line arguments + */ + public static void main(String args[]) {System.setProperty("sun.awt.noerasebackground", "true"); + java.awt.EventQueue.invokeLater(new Runnable() { + public void run() { + new TickTockCollision().setVisible(true); + } + }); + } + + // Variables declaration - do not modify//GEN-BEGIN:variables + private javax.swing.JPanel drawingPanel; + // End of variables declaration//GEN-END:variables + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/collision/TickTockCollisionGL2ES2.java b/src/main/java/org/jdesktop/j3d/examples/collision/TickTockCollisionGL2ES2.java new file mode 100644 index 0000000..44db453 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/collision/TickTockCollisionGL2ES2.java @@ -0,0 +1,254 @@ +/* + * Copyright (c) 2016 JogAmp Community. All rights reserved. + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * This code is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 only, as + * published by the Free Software Foundation. Sun designates this + * particular file as subject to the "Classpath" exception as provided + * by Sun in the LICENSE file that accompanied this code. + * + * This code is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + * version 2 for more details (a copy is included in the LICENSE file that + * accompanied this code). + * + * You should have received a copy of the GNU General Public License version + * 2 along with this work; if not, write to the Free Software Foundation, + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. + * + */ +package org.jdesktop.j3d.examples.collision; + +import java.awt.GraphicsConfiguration; + +import org.jdesktop.j3d.examples.gl2es2pipeline.Cube; +import org.jdesktop.j3d.examples.gl2es2pipeline.SimpleShaderAppearance; +import org.jogamp.java3d.Alpha; +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.Background; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.ColoringAttributes; +import org.jogamp.java3d.Group; +import org.jogamp.java3d.RenderingAttributes; +import org.jogamp.java3d.RotationInterpolator; +import org.jogamp.java3d.Shape3D; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; + +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Vector3d; + +/** + * Simple Java 3D example program to display how collision work. + */ +public class TickTockCollisionGL2ES2 extends javax.swing.JFrame +{ + + private SimpleUniverse univ = null; + private BranchGroup scene = null; + + public BranchGroup createSceneGraph() + { + // Create the root of the branch graph + BranchGroup objRoot = new BranchGroup(); + + // Create a Transformgroup to scale all objects so they + // appear in the scene. + TransformGroup objScale = new TransformGroup(); + Transform3D t3d = new Transform3D(); + t3d.setScale(0.4); + objScale.setTransform(t3d); + objRoot.addChild(objScale); + + // Create a bounds for the background and behaviors + BoundingSphere bounds = new BoundingSphere(new Point3d(0.0, 0.0, 0.0), 100.0); + + // Set up the background + Color3f bgColor = new Color3f(0.05f, 0.05f, 0.2f); + Background bg = new Background(bgColor); + bg.setApplicationBounds(bounds); + objScale.addChild(bg); + + // Create a pair of transform group nodes and initialize them to + // identity. Enable the TRANSFORM_WRITE capability so that + // our behaviors can modify them at runtime. Add them to the + // root of the subgraph. + TransformGroup objTrans1 = new TransformGroup(); + objTrans1.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + objScale.addChild(objTrans1); + + TransformGroup objTrans2 = new TransformGroup(); + objTrans2.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + objTrans1.addChild(objTrans2); + + // Create the positioning and scaling transform group node. + Transform3D t = new Transform3D(); + t.set(0.3, new Vector3d(0.0, -1.5, 0.0)); + TransformGroup objTrans3 = new TransformGroup(t); + objTrans2.addChild(objTrans3); + + // Create a simple shape leaf node, add it to the scene graph. + objTrans3.addChild(new Cube()); + + // Create a new Behavior object that will perform the desired + // rotation on the specified transform object and add it into + // the scene graph. + Transform3D yAxis1 = new Transform3D(); + yAxis1.rotX(Math.PI / 2.0); + Alpha tickTockAlpha = new Alpha(-1, Alpha.INCREASING_ENABLE | Alpha.DECREASING_ENABLE, 0, 0, 5000, 2500, 200, 5000, 2500, 200); + + RotationInterpolator tickTock = new RotationInterpolator(tickTockAlpha, objTrans1, yAxis1, -(float) Math.PI / 2.0f, + (float) Math.PI / 2.0f); + tickTock.setSchedulingBounds(bounds); + objTrans2.addChild(tickTock); + + // Create a new Behavior object that will perform the desired + // rotation on the specified transform object and add it into + // the scene graph. + Transform3D yAxis2 = new Transform3D(); + Alpha rotationAlpha = new Alpha(-1, Alpha.INCREASING_ENABLE, 0, 0, 4000, 0, 0, 0, 0, 0); + + RotationInterpolator rotator = new RotationInterpolator(rotationAlpha, objTrans2, yAxis2, 0.0f, (float) Math.PI * 2.0f); + rotator.setSchedulingBounds(bounds); + objTrans2.addChild(rotator); + + // Now create a pair of rectangular boxes, each with a collision + // detection behavior attached. The behavior will highlight the + // object when it is in a state of collision. + + Group box1 = createBox(0.3, new Vector3d(-1.3, 0.0, 0.0)); + Group box2 = createBox(0.3, new Vector3d(1.3, 0.0, 0.0)); + + objScale.addChild(box1); + objScale.addChild(box2); + + // Have Java 3D perform optimizations on this scene graph. + objRoot.compile(); + + return objRoot; + } + + private static Group createBox(double scale, Vector3d pos) + { + // Create a transform group node to scale and position the object. + Transform3D t = new Transform3D(); + t.set(scale, pos); + TransformGroup objTrans = new TransformGroup(t); + + // Create a simple shape leaf node and add it to the scene graph + Shape3D shape = new Cube(0.5 / 2, 5.0 / 2, 1.0 / 2); + objTrans.addChild(shape); + + // Create a new ColoringAttributes object for the shape's + // appearance and make it writable at runtime. + Appearance app = new SimpleShaderAppearance(); + shape.setAppearance(app); + RenderingAttributes ra = new RenderingAttributes(); + ra.setIgnoreVertexColors(true); + app.setRenderingAttributes(ra); + ColoringAttributes ca = new ColoringAttributes(); + ca.setColor(0.6f, 0.3f, 0.0f); + app.setCapability(Appearance.ALLOW_COLORING_ATTRIBUTES_WRITE); + app.setColoringAttributes(ca); + + // Create a new Behavior object that will perform the collision + // detection on the specified object, and add it into + // the scene graph. + CollisionDetector cd = new CollisionDetector(shape); + BoundingSphere bounds = new BoundingSphere(new Point3d(0.0, 0.0, 0.0), 100.0); + cd.setSchedulingBounds(bounds); + + // Add the behavior to the scene graph + objTrans.addChild(cd); + + return objTrans; + } + + private Canvas3D createUniverse() + { + // Get the preferred graphics configuration for the default screen + GraphicsConfiguration config = SimpleUniverse.getPreferredConfiguration(); + + // Create a Canvas3D using the preferred configuration + Canvas3D c = new Canvas3D(config); + + // Create simple universe with view branch + univ = new SimpleUniverse(c); + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + univ.getViewingPlatform().setNominalViewingTransform(); + + // Ensure at least 5 msec per frame (i.e., < 200Hz) + univ.getViewer().getView().setMinimumFrameCycleTime(5); + + return c; + } + + /** + * Creates new form TickTockCollision + */ + public TickTockCollisionGL2ES2() + { + // Initialize the GUI components + initComponents(); + + // Create Canvas3D and SimpleUniverse; add canvas to drawing panel + Canvas3D c = createUniverse(); + drawingPanel.add(c, java.awt.BorderLayout.CENTER); + + // Create the content branch and add it to the universe + scene = createSceneGraph(); + univ.addBranchGraph(scene); + } + + // ---------------------------------------------------------------- + + /** This method is called from within the constructor to + * initialize the form. + * WARNING: Do NOT modify this code. The content of this method is + * always regenerated by the Form Editor. + */ + // <editor-fold defaultstate="collapsed" desc=" Generated Code ">//GEN-BEGIN:initComponents + private void initComponents() + { + drawingPanel = new javax.swing.JPanel(); + + setDefaultCloseOperation(javax.swing.WindowConstants.EXIT_ON_CLOSE); + setTitle("TickTockCollision"); + drawingPanel.setLayout(new java.awt.BorderLayout()); + + drawingPanel.setPreferredSize(new java.awt.Dimension(700, 700)); + getContentPane().add(drawingPanel, java.awt.BorderLayout.CENTER); + + pack(); + }// </editor-fold>//GEN-END:initComponents + + /** + * @param args the command line arguments + */ + public static void main(String args[]) + { + System.setProperty("sun.awt.noerasebackground", "true"); + System.setProperty("j3d.rend", "jogl2es2"); + System.setProperty("j3d.displaylist", "false"); + java.awt.EventQueue.invokeLater(new Runnable() { + @Override + public void run() + { + new TickTockCollisionGL2ES2().setVisible(true); + } + }); + } + + // Variables declaration - do not modify//GEN-BEGIN:variables + private javax.swing.JPanel drawingPanel; + // End of variables declaration//GEN-END:variables + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/configured_universe/ConfigObjLoad.java b/src/main/java/org/jdesktop/j3d/examples/configured_universe/ConfigObjLoad.java new file mode 100644 index 0000000..9afa414 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/configured_universe/ConfigObjLoad.java @@ -0,0 +1,327 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.configured_universe; + +import java.awt.event.KeyAdapter; +import java.awt.event.KeyEvent; +import java.io.FileNotFoundException; +import java.net.MalformedURLException; +import java.net.URL; +import java.util.Map; + +import org.jdesktop.j3d.examples.Resources; +import org.jogamp.java3d.Alpha; +import org.jogamp.java3d.AmbientLight; +import org.jogamp.java3d.Background; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.DirectionalLight; +import org.jogamp.java3d.RotationInterpolator; +import org.jogamp.java3d.Sensor; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.loaders.IncorrectFormatException; +import org.jogamp.java3d.loaders.ParsingErrorException; +import org.jogamp.java3d.loaders.Scene; +import org.jogamp.java3d.loaders.objectfile.ObjectFile; +import org.jogamp.java3d.utils.behaviors.sensor.Mouse6DPointerBehavior; +import org.jogamp.java3d.utils.behaviors.vp.OrbitBehavior; +import org.jogamp.java3d.utils.universe.ConfiguredUniverse; +import org.jogamp.java3d.utils.universe.ViewingPlatform; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Vector3f; + +public class ConfigObjLoad { + + private boolean spin = false; + private boolean noTriangulate = false; + private boolean noStripify = false; + private double creaseAngle = 60.0; + private URL filename = null; + + private ConfiguredUniverse u; + + public BranchGroup createSceneGraph() { + // Create the root of the branch graph + BranchGroup objRoot = new BranchGroup(); + + // Create a Transformgroup to scale all objects so they + // appear in the scene. + TransformGroup objScale = new TransformGroup(); + Transform3D t3d = new Transform3D(); + t3d.setScale(0.7); + objScale.setTransform(t3d); + objRoot.addChild(objScale); + + // Create the transform group node and initialize it to the + // identity. Enable the TRANSFORM_WRITE capability so that + // our behavior code can modify it at runtime. Add it to the + // root of the subgraph. + TransformGroup objTrans = new TransformGroup(); + objTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + objTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_READ); + objScale.addChild(objTrans); + + int flags = ObjectFile.RESIZE; + if (!noTriangulate) flags |= ObjectFile.TRIANGULATE; + if (!noStripify) flags |= ObjectFile.STRIPIFY; + ObjectFile f = new ObjectFile(flags, + (float)(creaseAngle * Math.PI / 180.0)); + Scene s = null; + try { + s = f.load(filename); + } + catch (FileNotFoundException e) { + System.err.println(e); + System.exit(1); + } + catch (ParsingErrorException e) { + System.err.println(e); + System.exit(1); + } + catch (IncorrectFormatException e) { + System.err.println(e); + System.exit(1); + } + + objTrans.addChild(s.getSceneGroup()); + + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + + if (spin) { + Transform3D yAxis = new Transform3D(); + Alpha rotationAlpha = new Alpha(-1, Alpha.INCREASING_ENABLE, + 0, 0, + 4000, 0, 0, + 0, 0, 0); + + RotationInterpolator rotator = + new RotationInterpolator(rotationAlpha, objTrans, yAxis, + 0.0f, (float) Math.PI*2.0f); + rotator.setSchedulingBounds(bounds); + objTrans.addChild(rotator); + } + + // Set up the background + Color3f bgColor = new Color3f(0.05f, 0.05f, 0.5f); + Background bgNode = new Background(bgColor); + bgNode.setApplicationBounds(bounds); + objRoot.addChild(bgNode); + + // Set up the ambient light + Color3f ambientColor = new Color3f(0.1f, 0.1f, 0.1f); + AmbientLight ambientLightNode = new AmbientLight(ambientColor); + ambientLightNode.setInfluencingBounds(bounds); + objRoot.addChild(ambientLightNode); + + // Set up the directional lights + Color3f light1Color = new Color3f(1.0f, 1.0f, 0.9f); + Vector3f light1Direction = new Vector3f(1.0f, 1.0f, 1.0f); + Color3f light2Color = new Color3f(1.0f, 1.0f, 1.0f); + Vector3f light2Direction = new Vector3f(-1.0f, -1.0f, -1.0f); + + DirectionalLight light1 + = new DirectionalLight(light1Color, light1Direction); + light1.setInfluencingBounds(bounds); + objRoot.addChild(light1); + + DirectionalLight light2 + = new DirectionalLight(light2Color, light2Direction); + light2.setInfluencingBounds(bounds); + objRoot.addChild(light2); + + return objRoot; + } + + private void usage() + { + System.out.println( + "Usage: java ConfigObjLoad [-s] [-n] [-t] [-c degrees] <.obj file>"); + System.out.println(" -s Spin (no user interaction)"); + System.out.println(" -n No triangulation"); + System.out.println(" -t No stripification"); + System.out.println( + " -c Set crease angle for normal generation (default is 60 without"); + System.out.println( + " smoothing group info, otherwise 180 within smoothing groups)"); + System.exit(0); + } // End of usage + + + public void init() {System.setProperty("sun.awt.noerasebackground", "true"); + if (filename == null) { + filename = Resources.getResource("resources/geometry/galleon.obj"); + if (filename == null) { + System.err.println("resources/geometry/galleon.obj not found"); + System.exit(1); + } + } + + // Get the config file URL from the j3d.configURL property or use the + // default config file "j3d1x1-window" in the current directory. + URL configURL = ConfiguredUniverse.getConfigURL(null); + if(configURL == null) { + configURL = Resources.getResource("configured_universe/j3d1x1-window.cfg"); + } + + // Create a simple scene and attach it to the virtual universe + BranchGroup scene = createSceneGraph(); + + u = new ConfiguredUniverse(configURL); + + // Get the ViewingPlatform. + ViewingPlatform viewingPlatform = u.getViewingPlatform(); + + // This will move the ViewPlatform back a bit so the objects in the + // scene can be viewed. This will only have an effect if the config + // file sets the window eyepoint policy to something other than + // RELATIVE_TO_COEXISTENCE, which is the default eyepoint policy + // applied by ConfiguredUniverse. + // + // The default view attach policy for ConfiguredUniverse applications + // is NOMINAL_SCREEN. This sets the view platform origin in the + // physical world to the center of coexistence, which allows eye + // positions expressed relative to coexistence to see the appropriate + // field of view automatically. + viewingPlatform.setNominalViewingTransform(); + + // Add a ViewPlatformBehavior if not specified in the config file. + if (!spin && viewingPlatform.getViewPlatformBehavior() == null) { + OrbitBehavior orbit = new OrbitBehavior(u.getCanvas(), + OrbitBehavior.REVERSE_ALL); + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0, 0.0, 0.0), 100.0); + + orbit.setSchedulingBounds(bounds); + viewingPlatform.setViewPlatformBehavior(orbit); + } + + // See if there's a 6 degree of freedom mouse in the environment. + // We look for one named "mouse6d". + Map sensorMap = null; + sensorMap = u.getNamedSensors(); + if (sensorMap != null) { + Sensor mouse6d = (Sensor)sensorMap.get("mouse6d"); + if (mouse6d != null) { + Mouse6DPointerBehavior behavior = + new Mouse6DPointerBehavior(mouse6d, 1.0, true); + + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + behavior.setSchedulingBounds(bounds); + + scene.addChild(behavior); + scene.addChild(behavior.getEcho()); + } + } + + // Listen for a typed "q", "Q", or "Escape" key on each canvas to + // allow a convenient exit from full screen configurations. + Canvas3D[] canvases; + canvases = u.getViewer().getCanvas3Ds(); + + class QuitListener extends KeyAdapter { + public void keyTyped(KeyEvent e) { + char c = e.getKeyChar(); + if (c == 'q' || c == 'Q' || c == 27) + System.exit(0); + } + } + + QuitListener quitListener = new QuitListener(); + for (int i = 0; i < canvases.length; i++) + canvases[i].addKeyListener(quitListener); + + // Make the scenegraph live. + u.addBranchGraph(scene); + } + + public ConfigObjLoad(String[] args) { + if (args.length != 0) { + for (int i = 0; i < args.length; i++) { + if (args[i].startsWith("-")) { + if (args[i].equals("-s")) { + spin = true; + } else if (args[i].equals("-n")) { + noTriangulate = true; + } else if (args[i].equals("-t")) { + noStripify = true; + } else if (args[i].equals("-c")) { + if (i < args.length - 1) { + creaseAngle = (new Double(args[++i])).doubleValue(); + } else usage(); + } else { + usage(); + } + } else { + try { + if ((args[i].indexOf("file:") == 0) || + (args[i].indexOf("http") == 0)) { + filename = new URL(args[i]); + } + else if (args[i].charAt(0) != '/') { + filename = new URL("file:./" + args[i]); + } + else { + filename = new URL("file:" + args[i]); + } + } + catch (MalformedURLException e) { + System.err.println(e); + System.exit(1); + } + } + } + } + init(); + } + + public static void main(String[] args) {System.setProperty("sun.awt.noerasebackground", "true"); + new ConfigObjLoad(args); + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/configured_universe/README.txt b/src/main/java/org/jdesktop/j3d/examples/configured_universe/README.txt new file mode 100644 index 0000000..77e5a37 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/configured_universe/README.txt @@ -0,0 +1,142 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +This directory contains a simple example application that demonstrates the +ConfiguredUniverse utility class available in the com.sun.j3d.utils.universe +package. J3DFly, available separately, is a fully featured application that +also uses ConfiguredUniverse. + +ConfiguredUniverse is an extension of SimpleUniverse that can set up an +interactive viewing environment based upon the contents of a site-specific +configuration file. This is useful when an application needs to run without +change across a broad range of viewing configurations and locally available +input and audio devices. InputDevice implementations can be instantiated by +ConfiguredUniverse and their Sensors can be retrieved by applications along +with the names bound to them in the configuration file. + +Supported viewing configurations include windows on conventional desktops, +stereo-enabled views, fullscreen immersive displays on single or multiple +screens, and virtual reality installations such as cave and head-mounted +displays incorporating 6-degree-of-freedom sensor devices. + +The ConfigObjLoad application is a modified version of the ObjLoad example +program which uses the ConfiguredUniverse utility instead of SimpleUniverse. +It also differs in the following other respects: + + It is an application and cannot be run in a browser. ConfiguredUniverse + creates a JFrame, JPanel, and Canvas3D itself for each screen and is + oriented towards multiple fullscreen viewing environments, although + conventional windowed displays are also supported. The components + created are easily accessable so applications can still incorporate them + into their own user interfaces. + + The configuration file to load is specified by the j3d.configURL + property. If one is not specified, it will load the file j3d1x1-window.cfg + in this directory. + + Alternative custom view platform behaviors other than OrbitBehavior can + be used by specifying the behavior in the configuration file. + + It can retrieve a 6DOF Sensor specified in the configuration file and + use it to demonstrate the Mouse6DPointerBehavior class. + + Typing a "q" or the Escape key will terminate the example program. This + is useful for fullscreen configurations. + +To load a specific configuration file, set the j3d.configURL property on the +command line: + + java -Dj3d.configURL=<URL string> ConfigObjLoad <args> <obj file> + +For example, to load j3d1x2-rot30.cfg in the current directory, run + + java -Dj3d.configURL=file:j3d1x2-rot30.cfg ConfigObjLoad <args> <obj file> + +This directory includes the following sample configuration files. Normally +a configuration file is site-specific but many of these can used as-is. +Others may need customization for screen sizes, available input devices, and +PhysicalBody parameters. + + j3d1x1.cfg: single fullscreen desktop configuration. + + j3d1x1-behavior.cfg: single fullscreen desktop configuration with a + configurable view platform behavior. + + j3d1x1-stereo.cfg: single fullscreen desktop configuration with stereo + viewing. + + j3d1x1-vr.cfg: single fullscreen desktop configuration with stereo viewing, + head tracker, and 6DOF mouse. + + j3d1x1-window.cfg: single screen windowed desktop configuration. + + j3d1x2-flat.cfg: dual-screen flat desktop configuration. + + j3d1x2-rot30.cfg: dual-screen desktop configuration with each screen rotated + toward the other by 30 degrees about Y. + + j3d1x3-cave.cfg: 3-projector configuration with screens to the left, front, + and right of the user. + + j3d1x3-cave-vr.cfg: 3-projector configuration with screens to the left, + front, and right of the user. Includes head tracking and stereo + viewing. + + j3d1x3-rot45.cfg: 3-screen desktop configuration with left and right screens + angled by 45 degrees from the center screen. + + j3d2x2-flat.cfg: 4-screen projector configuration arranged in a 2x2 power + wall. + +Note: JDK 1.4 or newer is required when configuring multiple screens if the +X11 Xinerama extension is being used to create a single virtual screen. +This is due to a limitation of the getScreenDevices() method in the JDK 1.3 +version of GraphicsConfiguration which returns only a single GraphicsDevice +from a virtual screen. ConfiguredUniverse will report this condition as an +error in specifying more screens than are available. + +Also: Graphics performance may be degraded in some environments when using a +virtual screen device. See the description of the j3d.disableXinerama +property for possible performance improvements when using Xinerama. + diff --git a/src/main/java/org/jdesktop/j3d/examples/configured_universe/j3d1x1-behavior.cfg b/src/main/java/org/jdesktop/j3d/examples/configured_universe/j3d1x1-behavior.cfg new file mode 100644 index 0000000..db56b2c --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/configured_universe/j3d1x1-behavior.cfg @@ -0,0 +1,149 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +/* + ************************************************************************ + * + * Java 3D configuration file for single fullscreen desktop configuration. + * A view platform behavior is created and configured here as well. + * + ************************************************************************ + */ + +// Create a new screen object and associate it with a logical name and a +// number. This number is used as an index to retrieve the AWT GraphicsDevice +// from the array that GraphicsEnvironment.getScreenDevices() returns. +// +// NOTE: The GraphicsDevice order in the array is specific to the local +// site and display system. +// +(NewScreen center 0) + +// Create a fullscreen window +// +(ScreenAttribute center WindowSize NoBorderFullScreen) + +// Set the available image area for the full screen. +// +(ScreenAttribute center PhysicalScreenWidth 0.360) +(ScreenAttribute center PhysicalScreenHeight 0.288) + +// Set the TrackerBaseToImagePlate transform for this screen. The coexistence +// to tracker base transform is identity by default, so the tracker base origin +// and orientation will also set the origin and orientation of coexistence +// coordinates in the physical world. This is the primary purpose of setting +// this transform when neither head tracking nor multiple screens are being +// used. +// +// The tracker base and center of coexistence are set here to the middle of the +// screen's image plate. Their basis vectors are aligned with the image plate +// basis vectors. The physical eyepoint position will be set relative to +// coexistence coordinates below. +// +(ScreenAttribute center TrackerBaseToImagePlate + (Translate 0.180 0.144 0.000)) + +// Create a view using the defined screen. +// +(NewView view0) +(ViewAttribute view0 Screen center) + +// Set the eyepoint relative to coexistence coordinates. Here it is set 45cm +// toward the user along +Z. Skewed projections can be set by by offsetting +// the eyepoint along X and Y. +// +(ViewAttribute view0 CenterEyeInCoexistence (0.0 0.0 0.45)) + +// Create a view platform behavior. Here we use OrbitBehavior, although any +// concrete subclass of the abstract ViewPlatformBehavior with a parameterless +// constructor could be used. The logical name to assign to this behavior is +// specified by the 2nd argument to the NewViewPlatformBehavior command, while +// the 3rd argument is the name of the ViewPlatformBehavior subclass. It is +// instantiated through introspection. +// +// Attributes defined by the abstract ViewPlatformBehavior superclass itself +// can be set directly with the ViewPlatformBehaviorAttribute command. The +// details of the subclass implementation are not known to ConfiguredUniverse, +// so any configuration information needed by such a subclass is set by the +// ViewPlatformBehaviorProperty command. The property name specified by that +// command is taken to be a method name of the subclass and invoked through +// introspection. +// +// View platform behaviors often need sensors or canvases as event sources to +// drive the behavior action. An implementation of ViewPlatformBehavior always +// gets the current ViewingPlatform through the setViewingPlatform() method. +// The canvases used by the ViewingPlatform can be retrieved by calling its +// getViewers() method and then calling each Viewer's getCanvas3Ds() +// method. Sensors can be retrived by calling the ViewingPlatform method +// getUniverse(), checking to see if the returned SimpleUniverse is a +// ConfiguredUniverse, and then calling its getNamedSensors() method. +// +(NewViewPlatformBehavior vpb com.sun.j3d.utils.behaviors.vp.OrbitBehavior) + +// Set the scheduling bounds to be a BoundingSphere with its center at +// (0.0 0.0 0.0) and a radius of 100 meters. +// +(ViewPlatformBehaviorAttribute vpb SchedulingBounds + (BoundingSphere (0.0 0.0 0.0) 100.0)) + +// Set properties specific to OrbitBehavior. All arguments following the +// method name are wrapped and passed to the specified method as an array of +// Objects. Strings "true" and "false" get turned into Boolean, and number +// strings get turned into Double. Constructs such as (0.0 1.0 2.0) and +// ((0.0 1.0 2.0 0.5) (3.0 4.0 5.0 1.0) (6.0 7.0 8.0 0.0)) get converted to +// Point3d and Matrix4d respectively. Note that last row of a Matrix4d doesn't +// need to be specified; it is implicitly (0.0 0.0 0.0 1.0). +// +// The REVERSE_ALL flags are usually passed to the OrbitBehavior constructor. +// Since it is being instantiated with its parameterless constructor the +// reverse flags are set here explicitly. +// +(ViewPlatformBehaviorProperty vpb ReverseTranslate true) +(ViewPlatformBehaviorProperty vpb ReverseRotate true) +(ViewPlatformBehaviorProperty vpb ReverseZoom true) + +// Create a new view platform and set the view platform behavior. +// +(NewViewPlatform vp) +(ViewPlatformAttribute vp ViewPlatformBehavior vpb) diff --git a/src/main/java/org/jdesktop/j3d/examples/configured_universe/j3d1x1-stereo.cfg b/src/main/java/org/jdesktop/j3d/examples/configured_universe/j3d1x1-stereo.cfg new file mode 100644 index 0000000..959064c --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/configured_universe/j3d1x1-stereo.cfg @@ -0,0 +1,113 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +/* + ************************************************************************ + * + * Java 3D configuration file for single fullscreen stereo desktop + * configuration with no head tracking. + * + ************************************************************************ + */ + +// Create a new screen object and associate it with a logical name and a +// number. This number is used as an index to retrieve the AWT GraphicsDevice +// from the array that GraphicsEnvironment.getScreenDevices() returns. +// +// NOTE: The GraphicsDevice order in the array is specific to the local +// site and display system. +// +(NewScreen center 0) + +// Create a fullscreen window +// +(ScreenAttribute center WindowSize NoBorderFullScreen) + +// Set the available image area for the full screen. +// +(ScreenAttribute center PhysicalScreenWidth 0.360) +(ScreenAttribute center PhysicalScreenHeight 0.288) + +// Set the TrackerBaseToImagePlate transform for this screen. The coexistence +// to tracker base transform is identity by default, so the tracker base origin +// and orientation will also set the origin and orientation of coexistence +// coordinates in the physical world. This is the primary purpose of setting +// this transform when neither head tracking nor multiple screens are being +// used. +// +// The tracker base and center of coexistence are set here to the middle of the +// screen's image plate. Their basis vectors are aligned with the image plate +// basis vectors. The physical eyepoint position will be set relative to +// coexistence coordinates below. +// +(ScreenAttribute center TrackerBaseToImagePlate + (Translate 0.180 0.144 0.000)) + +// Define the physical body. +// +// The head origin is halfway between the eyes, with X extending to the right, +// Y up, and positive Z extending into the skull. +// +(NewPhysicalBody SiteUser) + +// Set the interpupilary distance. This sets the LeftEyePosition and +// RightEyePosition to offsets of half this distance along both directions of +// the X axis. +// +(PhysicalBodyAttribute SiteUser StereoEyeSeparation 0.066) + +// Create a view using the defined screen and physical body. +// +(NewView view0) +(ViewAttribute view0 Screen center) +(ViewAttribute view0 PhysicalBody SiteUser) + +// Set the eyepoint relative to coexistence coordinates. Here it is set 45cm +// toward the user along +Z. +// +(ViewAttribute view0 CenterEyeInCoexistence (0.0 0.0 0.45)) + +// Enable stereo viewing. +// +(ViewAttribute view0 StereoEnable true) diff --git a/src/main/java/org/jdesktop/j3d/examples/configured_universe/j3d1x1-vr.cfg b/src/main/java/org/jdesktop/j3d/examples/configured_universe/j3d1x1-vr.cfg new file mode 100644 index 0000000..7da054d --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/configured_universe/j3d1x1-vr.cfg @@ -0,0 +1,212 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +/* + ************************************************************************ + * + * Java 3D configuration file for a single screen stereo desktop display + * using a head tracker and 6DOF mouse. + * + ************************************************************************ + */ + +// Configure the head tracker. The NewDevice command binds a logical name +// (the 2nd argument) to an InputDevice implementation whose class name is +// specified in the 3rd argument. The InputDevice implementation for a head +// tracker must generate position and orientation data relative to a fixed +// frame of reference in the physical world, the "tracker base" of the Java +// 3D view model. +// +// The InputDevice is instantiated through introspection of the class name. +// Available InputDevice implementations are site-specific, so substitute +// the class name in a NewDevice command below with one that is available at +// the local site. +// +// Note that properties are used to configure an InputDevice instead of +// attributes. The details of an InputDevice implementation are not known to +// ConfiguredUniverse, so the property name is invoked as a method through +// introspection. The example properties below must be replaced with the ones +// needed, if any, by specific InputDevice implementations. +// +// All property arguments following the method name are wrapped and passed to +// the specified method as an array of Objects. Strings "true" and "false" +// get wrapped into Boolean, and number strings get wrapped into Double. +// Construct such as (0.0 1.0 2.0) and ((0.0 1.0 2.0 0.5) (3.0 4.0 5.0 1.0) +// (6.0 7.0 8.0 0.0)) get converted to Point3d and Matrix4d respectively. +// Note that last row of a Matrix4d doesn't need to be specified; it is +// implicitly (0.0 0.0 0.0 1.0). +// +(NewDevice glasses LogitechRedBarron) +(DeviceProperty glasses SerialPort "/dev/ttya") // Unix paths need quoting. +(DeviceProperty glasses ReceiverBaseline 0.1450) +(DeviceProperty glasses ReceiverLeftLeg 0.0875) +(DeviceProperty glasses ReceiverHeight 0.0470) +(DeviceProperty glasses ReceiverTopOffset 0.0000) + +// Configure an InputDevice to use for a 6 degree of freedom mouse if +// required. In some implementations the same InputDevice instance can be +// used both for head tracking and multiple peripheral sensing devices. +// This example assumes an implementation that requires multiple instances, +// one for each sensor, sharing the same physical hardware used for the +// tracker base. In either case all the sensors must generate position and +// orientation relative to the same fixed tracker base frame of reference. +// +(NewDevice wand LogitechRedBarron) +(DeviceProperty wand SerialPort "/dev/ttyb") +(DeviceProperty wand ReceiverBaseline 0.0700) +(DeviceProperty wand ReceiverLeftLeg 0.0625) +(DeviceProperty wand ReceiverHeight 0.0510) +(DeviceProperty wand ReceiverTopOffset 0.0000) + +// Create logical names for the available sensors in the specified input +// devices. The last argument is the sensor's index in the input device. +// +(NewSensor head glasses 0) +(NewSensor mouse6d wand 0) + +// Set the 6DOF mouse sensor hotspot in the local sensor coordinate system. +// The hotspot is simply the "active" point relative to the sensor origin +// which interacts with the virtual world, such as the point used for picking +// or grabbing an object. Its interpretation is up to the sensor behavior. +// +// It is set here to 10 centimeters from the base to allow reaching into the +// screen without bumping the device into the glass, and to prevent the device +// itself from obscuring the pointer echo. +// +(SensorAttribute mouse6d Hotspot (0.0 0.0 -0.10)) + + +// Create a new screen object and associate it with a logical name and a +// number. This number is used as an index to retrieve the AWT GraphicsDevice +// from the array that GraphicsEnvironment.getScreenDevices() returns. +// +// NOTE: The GraphicsDevice order in the array is specific to the local +// site and display system. +// +(NewScreen center 0) + +// Set the actual available image area. This measured as 0.350 meters in +// width and 0.245 meters in height for the monitor in the sample setup when +// running in stereo resolution. +// +(ScreenAttribute center PhysicalScreenWidth 0.350) +(ScreenAttribute center PhysicalScreenHeight 0.245) +(ScreenAttribute center WindowSize NoBorderFullScreen) + +// Set the TrackerBaseToImagePlate transform for this screen. This transforms +// points in tracker base coordinates to image plate coordinates. +// +// For this sample setup the tracker base is leaning at 50 degrees about its +// X-axis over the top edge of the monitor. The middle of the tracker base +// (its origin) is offset by (0.175, 0.345, 0.020) from the lower left +// corner of the screen (origin of the image plate). +// +(ScreenAttribute center TrackerBaseToImagePlate + (RotateTranslate (Rotate 50.000 0.000 0.000) + (Translate 0.175 0.345 0.020))) + + +// Create a physical environment. This contains the available input devices, +// audio devices, and sensors, and defines the coexistence coordinate system. +// +(NewPhysicalEnvironment SampleSite) + +// Register the input devices defined in this file. +// +(PhysicalEnvironmentAttribute SampleSite InputDevice glasses) +(PhysicalEnvironmentAttribute SampleSite InputDevice wand) + +// Register the sensor which will drive head tracking. +// +(PhysicalEnvironmentAttribute SampleSite HeadTracker head) + +// Define coexistence coordinates. +// +// Coexistence coordinates are defined relative to the tracker base to simplify +// calibration measurements, just as the tracker base is used as the common +// reference frame for the TrackerBaseToImagePlate calibration. +// +// Here the coexistence origin is set to the middle of the center screen, using +// the same basis vectors as its image plate. This will put the tracker base +// origin at (0.0 0.220 0.020) relative to the coexistence origin along its +// basis vectors. +// +(PhysicalEnvironmentAttribute SampleSite CoexistenceToTrackerBase + (TranslateRotate (Translate 0.0 -0.220 -0.020) + (Rotate -50.0 0.0 0.0))) + +// Define the physical body. +// +// The head origin is halfway between the eyes, with X extending to the right, +// Y up, and positive Z extending into the skull. +// +(NewPhysicalBody SiteUser) + +// Set the interpupilary distance. This sets the LeftEyePosition and +// RightEyePosition to offsets of half this distance along both directions of +// the X axis. +// +(PhysicalBodyAttribute SiteUser StereoEyeSeparation 0.066) + +// Define the position and orientation of the head relative to the tracker +// mounted on the head. +// +(PhysicalBodyAttribute SiteUser HeadToHeadTracker ((1.0 0.0 0.0 0.000) + (0.0 1.0 0.0 0.020) + (0.0 0.0 1.0 0.018))) + + +// Create a view using the defined screens, PhysicalEnvironment, and +// PhysicalBody. +// +(NewView view0) +(ViewAttribute view0 Screen center) +(ViewAttribute view0 PhysicalEnvironment SampleSite) +(ViewAttribute view0 PhysicalBody SiteUser) + +// Enable stereo viewing. Enable head tracking to get the position of the eyes +// with respect to coexistence. +// +(ViewAttribute view0 StereoEnable true) +(ViewAttribute view0 TrackingEnable True) diff --git a/src/main/java/org/jdesktop/j3d/examples/configured_universe/j3d1x1-window.cfg b/src/main/java/org/jdesktop/j3d/examples/configured_universe/j3d1x1-window.cfg new file mode 100644 index 0000000..2496ee4 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/configured_universe/j3d1x1-window.cfg @@ -0,0 +1,89 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +/* + ************************************************************************ + * + * Java 3D configuration file for a conventional single screen, windowed + * desktop configuration. + * + ************************************************************************ + */ + +// Create a new screen object and associate it with a logical name and a +// number. This number is used as an index to retrieve the AWT GraphicsDevice +// from the array that GraphicsEnvironment.getScreenDevices() returns. +// +// NOTE: The GraphicsDevice order in the array is specific to the local +// site and display system. +// +(NewScreen center 0) + +// Create a 700x700 pixel window on the screen. +// +(ScreenAttribute center WindowSize (700.0 700.0)) + +// Create a view using the defined screen. +// +(NewView view0) +(ViewAttribute view0 Screen center) + +// ConfiguredUniverse is oriented toward multi-screen viewing environments, so +// it sets the following attributes to those listed. For a conventional window +// on a single screen desktop configuration we need to set them back to their +// normal defaults. +// +// View.windowEyePointPolicy RELATIVE_TO_COEXISTENCE +// View.windowMovementPolicy VIRTUAL_WORLD +// View.windowResizePolicy VIRTUAL_WORLD +// View.coexistenceCenteringEnable false +// ViewPlatform.viewAttachPolicy NOMINAL_SCREEN +// +(ViewAttribute view0 WindowEyepointPolicy RELATIVE_TO_FIELD_OF_VIEW) +(ViewAttribute view0 WindowMovementPolicy PHYSICAL_WORLD) +(ViewAttribute view0 WindowResizePolicy PHYSICAL_WORLD) +(ViewAttribute view0 CoexistenceCenteringEnable true) + +(NewViewPlatform vp) +(ViewPlatformAttribute vp ViewAttachPolicy NOMINAL_HEAD) diff --git a/src/main/java/org/jdesktop/j3d/examples/configured_universe/j3d1x1.cfg b/src/main/java/org/jdesktop/j3d/examples/configured_universe/j3d1x1.cfg new file mode 100644 index 0000000..a4977a3 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/configured_universe/j3d1x1.cfg @@ -0,0 +1,98 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +/* + ************************************************************************ + * + * Java 3D configuration file for a single fullscreen desktop configuration. + * + ************************************************************************ + */ + +// Create a new screen object and associate it with a logical name and a +// number. This number is used as an index to retrieve the AWT GraphicsDevice +// from the array that GraphicsEnvironment.getScreenDevices() returns. +// +// NOTE: The GraphicsDevice order in the array is specific to the local +// site and display system. +// +(NewScreen center 0) + +// Create a fullscreen window +// +(ScreenAttribute center WindowSize NoBorderFullScreen) + +// Set the available image area for the full screen. This is important when an +// explicit ScreenScale view attribute is defined for precise scaling between +// objects in the virtual world and their projections into the physical world. +// The defaults are 0.365 meters for width and 0.292 meters for height. +// +(ScreenAttribute center PhysicalScreenWidth 0.360) +(ScreenAttribute center PhysicalScreenHeight 0.288) + +// Set the TrackerBaseToImagePlate transform for this screen. The coexistence +// to tracker base transform is identity by default, so the tracker base origin +// and orientation will also set the origin and orientation of coexistence +// coordinates in the physical world. This is the primary purpose of setting +// this transform when neither head tracking nor multiple screens are being +// used. +// +// The tracker base and center of coexistence are set here to the middle of the +// screen's image plate. Their basis vectors are aligned with the image plate +// basis vectors. The physical eyepoint position will be set relative to +// coexistence coordinates below. +// +(ScreenAttribute center TrackerBaseToImagePlate + (Translate 0.180 0.144 0.000)) + +// Create a view using the defined screen. +// +(NewView view0) +(ViewAttribute view0 Screen center) + +// Set the eyepoint relative to coexistence coordinates. Here it is set 45cm +// toward the user along +Z. Skewed projections can be created by offsetting +// the eyepoint along X and/or Y. +// +(ViewAttribute view0 CenterEyeInCoexistence (0.0 0.0 0.45)) diff --git a/src/main/java/org/jdesktop/j3d/examples/configured_universe/j3d1x2-flat.cfg b/src/main/java/org/jdesktop/j3d/examples/configured_universe/j3d1x2-flat.cfg new file mode 100644 index 0000000..155f1f7 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/configured_universe/j3d1x2-flat.cfg @@ -0,0 +1,134 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +/* + ************************************************************************ + * + * Java 3D configuration file for dual-screen (flat) desktop configuration + * with no head tracking. + * + ************************************************************************ + */ + +// Create new screen objects and associate them with logical names and numbers. +// These numbers are used as indices to retrieve the AWT GraphicsDevice from +// the array that GraphicsEnvironment.getScreenDevices() returns. +// +// NOTE: The GraphicsDevice order in the array is specific to the local +// site and display system. +// +(NewScreen left 0) +(NewScreen right 1) + +// Set the screen dimensions. +// +(ScreenAttribute left PhysicalScreenWidth 0.360) +(ScreenAttribute left PhysicalScreenHeight 0.288) + +(ScreenAttribute right PhysicalScreenWidth 0.360) +(ScreenAttribute right PhysicalScreenHeight 0.288) + +// Specify full screen windows. +// +(ScreenAttribute left WindowSize NoBorderFullScreen) +(ScreenAttribute right WindowSize NoBorderFullScreen) + +// Set the TrackerBaseToImagePlate transforms for these screens. This +// transforms points in tracker base coordinates to each screen's image plate +// coordinates, where the origin of the image plate is defined to be the lower +// left corner of the screen with X increasing to the right, Y increasing to +// the top, and Z increasing away from the screen. +// +// Without head or sensor tracking the tracker base is still needed as a fixed +// frame of reference for describing the orientation and position of each +// screen to the others. The coexistence to tracker base transform is set to +// identity by default, so the tracker base origin and orientation will also +// set the origin and orientation of coexistence coordinates in the physical +// world. +// +// The tracker base and center of coexistence is set here to the middle of the +// edge shared by the two screens. +// +(ScreenAttribute left TrackerBaseToImagePlate + (Translate 0.360 0.144 0.0)) +(ScreenAttribute right TrackerBaseToImagePlate + (Translate 0.000 0.144 0.0)) + +// Sometimes it is desirable to include the bevels in between the monitors in +// the TrackerBaseToImagePlate transforms, so that the abutting bevels obscure +// the view of the virtual world instead of stretching it out between the +// monitors. For a bevel width of 4.5 cm on each monitor, the above commands +// would become the following: +// +// (ScreenAttribute left TrackerBaseToImagePlate +// (Translate 0.405 0.144 0.0)) +// (ScreenAttribute right TrackerBaseToImagePlate +// (Translate -0.045 0.144 0.0)) +// +// Conversely, a similar technique may be used to include overlap between the +// screens. This is useful for projection systems which use edge blending +// to provide seamless integration between screens. + + +// Create a view using the defined screens. +// +(NewView view0) +(ViewAttribute view0 Screen left) +(ViewAttribute view0 Screen right) + +// Set the eyepoint relative to coexistence coordinates. Here it is set 45cm +// toward the user along Z, extending out from the midpoint of the edge shared +// by the two screens. This will create the appropriate skewed projection +// frustums for each image plate. +// +// If a planar display surface is all that is required, the same effect could +// be achieved in a virtual screen enviroment such as Xinerama by simply +// creating a canvas that spans both screens. In some display environments the +// use of a canvas that spans multiple physical screens may cause significant +// performance degradation, however. +// +// See j3d1x2-rot30 for an example of a non-planar configuration that cannot be +// achieved through a single canvas spanning both screens. +// +(ViewAttribute view0 CenterEyeInCoexistence (0.0 0.0 0.45)) diff --git a/src/main/java/org/jdesktop/j3d/examples/configured_universe/j3d1x2-rot30.cfg b/src/main/java/org/jdesktop/j3d/examples/configured_universe/j3d1x2-rot30.cfg new file mode 100644 index 0000000..eccdb4b --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/configured_universe/j3d1x2-rot30.cfg @@ -0,0 +1,99 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +/* + ************************************************************************ + * + * Java 3D configuration file for a dual-screen desktop configuration + * with each screen rotated toward the other by 30 degrees about Y from + * planar. The inside angle between them is 120 degrees. + * + ************************************************************************ + */ + +// Create new screen objects and associate them with logical names and numbers. +// These numbers are used as indices to retrieve the AWT GraphicsDevice from +// the array that GraphicsEnvironment.getScreenDevices() returns. +// +// NOTE: The GraphicsDevice order in the array is specific to the local +// site and display system. +// +(NewScreen left 0) +(NewScreen right 1) + +// Set the available image areas for full screens. +// +(ScreenAttribute left PhysicalScreenWidth 0.360) +(ScreenAttribute left PhysicalScreenHeight 0.288) + +(ScreenAttribute right PhysicalScreenWidth 0.360) +(ScreenAttribute right PhysicalScreenHeight 0.288) + +// Specify full screen windows. +// +(ScreenAttribute left WindowSize NoBorderFullScreen) +(ScreenAttribute right WindowSize NoBorderFullScreen) + +// Set the TrackerBaseToImagePlate transforms for these screens. +// +// The tracker base is set here to the middle of the edge shared by the two +// screens. Each screen is rotated 30 degrees toward the other about the +// tracker base +Y axis, so that the tracker base +Z is centered between the +// two screens. +// +(ScreenAttribute left TrackerBaseToImagePlate + (RotateTranslate (Rotate 0.000 -30.000 0.0) + (Translate 0.360 0.144 0.0))) + +(ScreenAttribute right TrackerBaseToImagePlate + (RotateTranslate (Rotate 0.000 30.000 0.0) + (Translate 0.000 0.144 0.0))) + + +// Create a view using the defined screens. +// +(NewView view0) +(ViewAttribute view0 Screen left) +(ViewAttribute view0 Screen right) +(ViewAttribute view0 CenterEyeInCoexistence (0.0 0.0 0.45)) diff --git a/src/main/java/org/jdesktop/j3d/examples/configured_universe/j3d1x3-cave-vr.cfg b/src/main/java/org/jdesktop/j3d/examples/configured_universe/j3d1x3-cave-vr.cfg new file mode 100644 index 0000000..f87887d --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/configured_universe/j3d1x3-cave-vr.cfg @@ -0,0 +1,222 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +/* + ************************************************************************ + * + * Java 3D configuration file for a cave environment with head tracking and + * stereo viewing. This cave consists of 3 projectors with 3 screens to the + * left, front, and right of the user, all at 90 degrees to each other. + * + * The projectors in the VirtualPortal sample site are actually turned + * on their sides to get more height. Screen 0 is rotated 90 degrees + * counter-clockwise, while screens 1 and 2 are rotated 90 degrees + * clockwise. + * + ************************************************************************ + */ + +// Configure the head tracker. The NewDevice command binds a logical name +// (the 2nd argument) to an InputDevice implementation whose class name is +// specified in the 3rd argument. The InputDevice implementation for a head +// tracker must generate position and orientation data relative to a fixed +// frame of reference in the physical world, the "tracker base" of the Java +// 3D view model. +// +// The InputDevice is instantiated through introspection of the class name. +// Available InputDevice implementations are site-specific, so substitute +// the class name in a NewDevice command below with one that is available at +// the local site. +// +// Note that properties are used to configure an InputDevice instead of +// attributes. The details of an InputDevice implementation are not known to +// ConfiguredUniverse, so the property name is invoked as a method through +// introspection. The example properties below must be replaced with the ones +// needed, if any, by specific InputDevice implementations. All arguments +// following the method name are wrapped and passed to the specified method as +// an array of Objects. +// +// All property arguments following the method name are wrapped and passed to +// the specified method as an array of Objects. Strings "true" and "false" +// get wrapped into Boolean, and number strings get wrapped into Double. +// Construct such as (0.0 1.0 2.0) and ((0.0 1.0 2.0 0.5) (3.0 4.0 5.0 1.0) +// (6.0 7.0 8.0 0.0)) get converted to Point3d and Matrix4d respectively. +// Note that last row of a Matrix4d doesn't need to be specified; it is +// implicitly (0.0 0.0 0.0 1.0). +// +(NewDevice glasses LogitechRedBarron) +(DeviceProperty glasses SerialPort "/dev/ttya") // Unix paths need quoting. +(DeviceProperty glasses TransmitterBaseline 0.4600) +(DeviceProperty glasses TransmitterLeftLeg 0.4400) +(DeviceProperty glasses TransmitterCalibrationDistance 0.4120) + +// Create a logical name for the head tracker sensor. The last argument is +// the sensor's index in the input device. +// +(NewSensor head glasses 0) + +// Create new screen objects and associate them with logical names and numbers. +// These numbers are used as indices to retrieve the AWT GraphicsDevice from +// the array that GraphicsEnvironment.getScreenDevices() returns. +// +// NOTE: The GraphicsDevice order in the array is specific to the local +// site and display system. +// +(NewScreen left 0) +(NewScreen center 1) +(NewScreen right 2) + + +// Set the available image areas as well as their positition and orientation +// relative to the tracker base. From the orientation of a user standing +// within this VirtualPortal site and facing the center screen, the tracker +// base is along the vertical midline of the screen, 0.248 meters down from +// the top edge, and 1.340 meters in front of it. The tracker base is +// oriented so that its +X axis points to the left, its +Y axis points toward +// the screen, and its +Z axis points toward the floor. +// +(ScreenAttribute left PhysicalScreenWidth 2.480) +(ScreenAttribute left PhysicalScreenHeight 1.705) +(ScreenAttribute left WindowSize NoBorderFullScreen) +(ScreenAttribute left TrackerBaseToImagePlate + (( 0.0 0.0 -1.0 2.230) + ( 0.0 -1.0 0.0 1.340) + (-1.0 0.0 0.0 0.885))) + +(ScreenAttribute center PhysicalScreenWidth 2.485) +(ScreenAttribute center PhysicalScreenHeight 1.745) +(ScreenAttribute center WindowSize NoBorderFullScreen) +(ScreenAttribute center TrackerBaseToImagePlate + (( 0.0 0.0 1.0 0.248) + (-1.0 0.0 0.0 0.885) + ( 0.0 -1.0 0.0 1.340))) + +(ScreenAttribute right PhysicalScreenWidth 2.480) +(ScreenAttribute right PhysicalScreenHeight 1.775) +(ScreenAttribute right WindowSize NoBorderFullScreen) +(ScreenAttribute right TrackerBaseToImagePlate + (( 0.0 0.0 1.0 0.2488) + ( 0.0 -1.0 0.0 1.340) + ( 1.0 0.0 0.0 0.860))) + +// Create a physical environment. This contains the available input devices, +// audio devices, and sensors, and defines the coexistence coordinate system +// for mapping between the virtual and physical worlds. +// +(NewPhysicalEnvironment VirtualPortal) + +// Register the input device defined in this file and the sensor which will +// drive head tracking. +// +(PhysicalEnvironmentAttribute VirtualPortal InputDevice glasses) +(PhysicalEnvironmentAttribute VirtualPortal HeadTracker head) + +// Set the location of the center of coexistence relative to the tracker base. +// Here it set to the center of the center screen. The default view attach +// policy of NOMINAL_SCREEN used by ConfiguredUniverse will place the origin of +// the view platform in coexistence coordinates at the center of coexistence. +// +(PhysicalEnvironmentAttribute VirtualPortal + CoexistenceToTrackerBase + ((-1.0 0.0 0.0 0.000) + ( 0.0 0.0 -1.0 1.340) + ( 0.0 -1.0 0.0 0.994))) + +// The above center of coexistence is appropriate for the sample geometry +// files available in the programs/examples directory. Often a more +// immersive point of view is required for larger virtual worlds. This can be +// achieved by placing the center of coexistence closer to the nominal position +// of the user's head, so that the view platform origin in coexistence +// coordinates will map there as well. +// +// Here we set the location of the center of coexistence 0.5 meters along the +// tracker base +Z axis, 1.737 meters from the floor (about 5 ft 8.4 inches). +// +// (PhysicalEnvironmentAttribute VirtualPortal +// CoexistenceToTrackerBase +// ((-1.0 0.0 0.0 0.0) +// ( 0.0 0.0 -1.0 0.0) +// ( 0.0 -1.0 0.0 0.5))) + + +// Define the physical body. +// +// The head origin is halfway between the eyes, with X extending to the right, +// Y up, and positive Z extending into the skull. +// +(NewPhysicalBody LabRat) +(PhysicalBodyAttribute LabRat StereoEyeSeparation .07) + +// Define the position and orientation of the head relative to the tracker +// mounted on the head. +// +(PhysicalBodyAttribute LabRat HeadToHeadTracker + ((-1.0 0.0 0.0 0.00) + ( 0.0 0.0 -1.0 0.05) + ( 0.0 -1.0 0.0 0.11))) +// Now define the view. +// +(NewView view0) +(ViewAttribute view0 Screen left) +(ViewAttribute view0 Screen center) +(ViewAttribute view0 Screen right) +(ViewAttribute view0 PhysicalBody LabRat) +(ViewAttribute view0 PhysicalEnvironment VirtualPortal) + +// Set the screen scale. This is scale factor from virtual to physical +// coordinates. +// +(ViewAttribute view0 ScreenScalePolicy SCALE_SCREEN_SIZE) + +// Alternative for explict scaling. +// +//(ViewAttribute view0 ScreenScalePolicy SCALE_EXPLICIT) +//(ViewAttribute view0 ScreenScale 5.00) + +// Enable stereo viewing. Enable head tracking to get the position of the eyes +// with respect to coexistence. Boolean values may be specified as either +// true, True, false, or False. +// +(ViewAttribute view0 StereoEnable true) +(ViewAttribute view0 TrackingEnable True) diff --git a/src/main/java/org/jdesktop/j3d/examples/configured_universe/j3d1x3-cave.cfg b/src/main/java/org/jdesktop/j3d/examples/configured_universe/j3d1x3-cave.cfg new file mode 100644 index 0000000..88f86d8 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/configured_universe/j3d1x3-cave.cfg @@ -0,0 +1,171 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +/* + ************************************************************************ + * + * Java 3D configuration file for a cave environment. This cave + * consists of 3 projectors with 3 screens to the left, front, and right + * of the user, all at 90 degrees to each other. + * + * The projectors in the VirtualPortal sample site are actually turned + * on their sides to get more height. Screen 0 is rotated 90 degrees + * counter-clockwise, while screens 1 and 2 are rotated 90 degrees + * clockwise. + * + ************************************************************************ + */ + +// Create new screen objects and associate them with logical names and numbers. +// These numbers are used as indices to retrieve the AWT GraphicsDevice from +// the array that GraphicsEnvironment.getScreenDevices() returns. +// +// NOTE: The GraphicsDevice order in the array is specific to the local +// site and display system. +// +(NewScreen left 0) +(NewScreen center 1) +(NewScreen right 2) + + +// Set the available image areas as well as their positition and orientation +// relative to the tracker base. Although this config file doesn't enable +// head tracking, the tracker base is still needed as a point of reference to +// describe the position and orientation of the screens relative to the +// environment. +// +// From the orientation of a user standing within this VirtualPortal site and +// facing the center screen, the tracker base is along the vertical midline of +// the screen, 0.248 meters down from the top edge, and 1.340 meters in front +// of it. The tracker base is oriented so that its +X axis points to the left, +// its +Y axis points toward the screen, and its +Z axis points toward the +// floor. +// +(ScreenAttribute left PhysicalScreenWidth 2.480) +(ScreenAttribute left PhysicalScreenHeight 1.705) +(ScreenAttribute left WindowSize NoBorderFullScreen) +(ScreenAttribute left TrackerBaseToImagePlate + (( 0.0 0.0 -1.0 2.230) + ( 0.0 -1.0 0.0 1.340) + (-1.0 0.0 0.0 0.885))) + +(ScreenAttribute center PhysicalScreenWidth 2.485) +(ScreenAttribute center PhysicalScreenHeight 1.745) +(ScreenAttribute center WindowSize NoBorderFullScreen) +(ScreenAttribute center TrackerBaseToImagePlate + (( 0.0 0.0 1.0 0.248) + (-1.0 0.0 0.0 0.885) + ( 0.0 -1.0 0.0 1.340))) + +(ScreenAttribute right PhysicalScreenWidth 2.480) +(ScreenAttribute right PhysicalScreenHeight 1.775) +(ScreenAttribute right WindowSize NoBorderFullScreen) +(ScreenAttribute right TrackerBaseToImagePlate + (( 0.0 0.0 1.0 0.2488) + ( 0.0 -1.0 0.0 1.340) + ( 1.0 0.0 0.0 0.860))) + +// Set the location of the center of coexistence relative to the tracker base. +// Here it set to the center of the center screen. This config file will set +// the location of the user's eyes relative to this point. The default view +// attach policy of NOMINAL_SCREEN used by ConfiguredUniverse will place the +// origin of the view platform in coexistence coordinates at the center of +// coexistence. +// +(NewPhysicalEnvironment VirtualPortal) +(PhysicalEnvironmentAttribute VirtualPortal + CoexistenceToTrackerBase + ((-1.0 0.0 0.0 0.000) + ( 0.0 0.0 -1.0 1.340) + ( 0.0 -1.0 0.0 0.994))) + +// The above center of coexistence is appropriate for the sample geometry +// files available in the programs/examples directory. Often a more +// immersive point of view is required for larger virtual worlds. This can be +// achieved by placing the center of coexistence closer to the nominal position +// of the user's head, so that the view platform origin in coexistence +// coordinates will map there as well. +// +// Here we set the location of the center of coexistence 0.5 meters along the +// tracker base +Z axis, 1.737 meters from the floor (about 5 ft 8.4 inches). +// +// (PhysicalEnvironmentAttribute VirtualPortal +// CoexistenceToTrackerBase +// ((-1.0 0.0 0.0 0.0) +// ( 0.0 0.0 -1.0 0.0) +// ( 0.0 -1.0 0.0 0.5))) + + +// Now define the view. +// +(NewView view0) +(ViewAttribute view0 Screen left) +(ViewAttribute view0 Screen center) +(ViewAttribute view0 Screen right) +(ViewAttribute view0 PhysicalEnvironment VirtualPortal) + +// Set the user eye position in the display environment. It is set here to +// 1.340 meters back from the center screen (directly under the tracker), and +// 1.737 meters from the floor (about 5 ft 8.4 inches). +// +(ViewAttribute view0 CenterEyeInCoexistence (0.0 0.494 1.340)) + +// Here is an alternative center eye position to use with the immersive +// coexistence coordinate system defined in comments above. +// +// (ViewAttribute view0 CenterEyeInCoexistence (0.0 0.0 0.0)) + +// Set the screen scale. This is scale factor from virtual to physical +// coordinates. +// +(ViewAttribute view0 ScreenScalePolicy SCALE_SCREEN_SIZE) + +// Alternative for explict scaling. +// +// (ViewAttribute view0 ScreenScalePolicy SCALE_EXPLICIT) +// (ViewAttribute view0 ScreenScale 5.00) + +// No stereo viewing for this configuration. +// +(ViewAttribute view0 StereoEnable False) diff --git a/src/main/java/org/jdesktop/j3d/examples/configured_universe/j3d1x3-rot45.cfg b/src/main/java/org/jdesktop/j3d/examples/configured_universe/j3d1x3-rot45.cfg new file mode 100644 index 0000000..c84d548 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/configured_universe/j3d1x3-rot45.cfg @@ -0,0 +1,110 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +/* + ************************************************************************ + * + * Java 3D configuration file for 3 screens. Left and right screens are + * rotated 45 degrees from the center screen. + * + ************************************************************************ + */ + +// Create new screen objects and associate them with logical names and numbers. +// These numbers are used as indices to retrieve the AWT GraphicsDevice from +// the array that GraphicsEnvironment.getScreenDevices() returns. +// +// NOTE: The GraphicsDevice order in the array is specific to the local +// site and display system. +// +(NewScreen left 0) +(NewScreen center 1) +(NewScreen right 2) + +// Set the available image areas for full screens. +// +(ScreenAttribute left PhysicalScreenWidth 0.360) +(ScreenAttribute left PhysicalScreenHeight 0.288) + +(ScreenAttribute center PhysicalScreenWidth 0.360) +(ScreenAttribute center PhysicalScreenHeight 0.288) + +(ScreenAttribute right PhysicalScreenWidth 0.360) +(ScreenAttribute right PhysicalScreenHeight 0.288) + +// Specify full screen windows. +// +(ScreenAttribute left WindowSize NoBorderFullScreen) +(ScreenAttribute center WindowSize NoBorderFullScreen) +(ScreenAttribute right WindowSize NoBorderFullScreen) + +// Set the TrackerBaseToImagePlate transforms for these screens. +// +// The tracker base and center of coexistence are set here to the middle of the +// center screen. The basis vectors are aligned with the center screen image +// plate. The left and right screens are rotated 45 degrees toward each other +// about their shared edges with the center screen. +// +(ScreenAttribute center TrackerBaseToImagePlate + (Translate 0.180000 0.144000 0.000000)) + +// cos(45) * 0.360 * 0.5 = 0.127279; 0.360 + 0.127279 = 0.487279 +(ScreenAttribute left TrackerBaseToImagePlate + (RotateTranslate + (Rotate 0.000000 -45.000000 0.000000) + (Translate 0.487279 0.144000 0.127279))) + +// cos(45) * 0.360 * 0.5 = 0.127279 +(ScreenAttribute right TrackerBaseToImagePlate + (RotateTranslate + (Rotate 0.000000 45.000000 0.000000) + (Translate -0.127279 0.144000 0.127279))) + +// Create a view using the defined screens. +// +(NewView view0) +(ViewAttribute view0 Screen left) +(ViewAttribute view0 Screen center) +(ViewAttribute view0 Screen right) +(ViewAttribute view0 CenterEyeInCoexistence (0.0 0.0 0.5)) diff --git a/src/main/java/org/jdesktop/j3d/examples/configured_universe/j3d2x2-flat.cfg b/src/main/java/org/jdesktop/j3d/examples/configured_universe/j3d2x2-flat.cfg new file mode 100644 index 0000000..8bc4cb0 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/configured_universe/j3d2x2-flat.cfg @@ -0,0 +1,135 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +/* + ************************************************************************ + * + * Java 3D configuration file for 4 screen projection configuration + * arranged in a 2x2 power wall. + * + ************************************************************************ + */ + +// Create new screen objects and associate them with logical names and numbers. +// These numbers are used as indices to retrieve the AWT GraphicsDevice from +// the array that GraphicsEnvironment.getScreenDevices() returns. +// +// NOTE: The GraphicsDevice order in the array is specific to the local +// site and display system. +// +(NewScreen topleft 0) +(NewScreen topright 1) +(NewScreen bottomleft 3) +(NewScreen bottomright 2) + +// Set the available image areas for full screens. This is important when +// precise scaling between objects in the virtual world and their projections +// into the physical world is desired through use of explicit ScreenScale view +// attributes. The defaults are 0.365 meters for width and 0.292 meters for +// height. +// +(ScreenAttribute topleft PhysicalScreenWidth 0.912) +(ScreenAttribute topleft PhysicalScreenHeight 0.680) + +(ScreenAttribute topright PhysicalScreenWidth 0.912) +(ScreenAttribute topright PhysicalScreenHeight 0.680) + +(ScreenAttribute bottomleft PhysicalScreenWidth 0.912) +(ScreenAttribute bottomleft PhysicalScreenHeight 0.685) + +(ScreenAttribute bottomright PhysicalScreenWidth 0.912) +(ScreenAttribute bottomright PhysicalScreenHeight 0.685) + + +// Specify full screen windows. +// +(ScreenAttribute topleft WindowSize NoBorderFullScreen) +(ScreenAttribute topright WindowSize NoBorderFullScreen) +(ScreenAttribute bottomleft WindowSize NoBorderFullScreen) +(ScreenAttribute bottomright WindowSize NoBorderFullScreen) + +// Set the TrackerBaseToImagePlate transforms for these screens. This +// transforms points in tracker base coordinates to each screen's image plate +// coordinates, where the origin of the image plate is defined to be the lower +// left corner of the screen with X increasing to the right, Y increasing to +// the top, and Z increasing away from the screen. +// +// Without head or sensor tracking the tracker base is still needed as a point +// of reference for describing the orientation and position of each screen to +// the others. The coexistence to tracker base transform is set to identity by +// default, so the tracker base origin and orientation will also set the origin +// and orientation of coexistence coordinates in the physical world. +// +// The tracker base and center of coexistence are set here to the center of the +// 2x2 array with its basis vectors aligned to image plate coordinates. +// +(ScreenAttribute topleft TrackerBaseToImagePlate + (Translate 0.912 0.000 0.0)) +(ScreenAttribute topright TrackerBaseToImagePlate + (Translate 0.000 0.000 0.0)) +(ScreenAttribute bottomleft TrackerBaseToImagePlate + (Translate 0.912 0.685 0.0)) +(ScreenAttribute bottomright TrackerBaseToImagePlate + (Translate 0.000 0.685 0.0)) + +// Create a view using the defined screens. +// +(NewView view0) +(ViewAttribute view0 Screen topleft) +(ViewAttribute view0 Screen topright) +(ViewAttribute view0 Screen bottomleft) +(ViewAttribute view0 Screen bottomright) + +// Set the screen scale. This is scale factor from virtual to physical +// coordinates. The default policy of SCALE_SCREEN_SIZE doesn't work well here +// since in the 2x2 arrangement the individual screens are too small. The +// explicit scale factor below assumes a normalized range of object coordinates +// of [-1.0 .. +1.0]. +// +(ViewAttribute view0 ScreenScalePolicy SCALE_EXPLICIT) +(ViewAttribute view0 ScreenScale 0.912) + +// Set the user eye position in the display environment. +// +(ViewAttribute view0 CenterEyeInCoexistence (0.0 0.0 1.0)) diff --git a/src/main/java/org/jdesktop/j3d/examples/depth_func/DepthFuncTest.form b/src/main/java/org/jdesktop/j3d/examples/depth_func/DepthFuncTest.form new file mode 100644 index 0000000..b7d1376 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/depth_func/DepthFuncTest.form @@ -0,0 +1,217 @@ +<?xml version="1.0" encoding="UTF-8" ?> + +<Form version="1.2" type="org.netbeans.modules.form.forminfo.JFrameFormInfo"> + <Properties> + <Property name="defaultCloseOperation" type="int" value="3"/> + </Properties> + <SyntheticProperties> + <SyntheticProperty name="formSize" type="java.awt.Dimension" value="-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,0,-16,0,0,1,-109"/> + <SyntheticProperty name="formPosition" type="java.awt.Point" value="-84,-19,0,5,115,114,0,14,106,97,118,97,46,97,119,116,46,80,111,105,110,116,-74,-60,-118,114,52,126,-56,38,2,0,2,73,0,1,120,73,0,1,121,120,112,0,0,0,0,0,0,0,0"/> + <SyntheticProperty name="formSizePolicy" type="int" value="0"/> + <SyntheticProperty name="generatePosition" type="boolean" value="true"/> + <SyntheticProperty name="generateSize" type="boolean" value="true"/> + <SyntheticProperty name="generateCenter" type="boolean" value="false"/> + </SyntheticProperties> + <AuxValues> + <AuxValue name="FormSettings_generateMnemonicsCode" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_listenerGenerationStyle" type="java.lang.Integer" value="0"/> + <AuxValue name="FormSettings_variablesLocal" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_variablesModifier" type="java.lang.Integer" value="2"/> + <AuxValue name="designerSize" type="java.awt.Dimension" value="-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,0,-40,0,0,1,-117"/> + </AuxValues> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout"/> + <SubComponents> + <Container class="javax.swing.JPanel" name="jPanel1"> + <Properties> + <Property name="border" type="javax.swing.border.Border" editor="org.netbeans.modules.form.editors2.BorderEditor"> + <Border info="org.netbeans.modules.form.compat2.border.TitledBorderInfo"> + <TitledBorder title="WireFrame Object"/> + </Border> + </Property> + </Properties> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout" value="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription"> + <GridBagConstraints gridX="0" gridY="0" gridWidth="1" gridHeight="1" fill="1" ipadX="0" ipadY="0" insetsTop="0" insetsLeft="0" insetsBottom="0" insetsRight="0" anchor="10" weightX="0.0" weightY="0.0"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignFlowLayout"/> + <SubComponents> + <Component class="javax.swing.JLabel" name="jLabel1"> + <Properties> + <Property name="font" type="java.awt.Font" editor="org.netbeans.beaninfo.editors.FontEditor"> + <Font name="Dialog" size="12" style="0"/> + </Property> + <Property name="text" type="java.lang.String" value="Depth function"/> + <Property name="toolTipText" type="java.lang.String" value="Mode for normal object"/> + </Properties> + <AccessibilityProperties> + <Property name="AccessibleContext.accessibleParent" type="javax.accessibility.Accessible" editor="org.netbeans.modules.form.RADVisualComponent$AccessibleParentEditor"> + <ComponentRef name="shadedComboBox"/> + </Property> + </AccessibilityProperties> + </Component> + <Component class="javax.swing.JComboBox" name="normalComboBox"> + <Properties> + <Property name="font" type="java.awt.Font" editor="org.netbeans.beaninfo.editors.FontEditor"> + <Font name="Dialog" size="12" style="0"/> + </Property> + <Property name="model" type="javax.swing.ComboBoxModel" editor="org.netbeans.modules.form.editors2.ComboBoxModelEditor"> + <StringArray count="8"> + <StringItem index="0" value="ALWAYS"/> + <StringItem index="1" value="NEVER"/> + <StringItem index="2" value="EQUAL"/> + <StringItem index="3" value="NOT_EQUAL"/> + <StringItem index="4" value="LESS"/> + <StringItem index="5" value="LESS_OR_EQUAL"/> + <StringItem index="6" value="GREATER"/> + <StringItem index="7" value="GREATER_OR_EQUAL"/> + </StringArray> + </Property> + <Property name="selectedIndex" type="int" value="6"/> + <Property name="preferredSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor"> + <Dimension value="[150, 22]"/> + </Property> + </Properties> + <Events> + <EventHandler event="actionPerformed" listener="java.awt.event.ActionListener" parameters="java.awt.event.ActionEvent" handler="normalComboBoxActionPerformed"/> + </Events> + </Component> + <Component class="javax.swing.JCheckBox" name="wfCheckBox"> + <Properties> + <Property name="font" type="java.awt.Font" editor="org.netbeans.beaninfo.editors.FontEditor"> + <Font name="Dialog" size="12" style="0"/> + </Property> + <Property name="text" type="java.lang.String" value="Write Depth Buffer"/> + <Property name="toolTipText" type="java.lang.String" value="Depth will be written for the object, if selected"/> + </Properties> + <Events> + <EventHandler event="actionPerformed" listener="java.awt.event.ActionListener" parameters="java.awt.event.ActionEvent" handler="wfCheckBoxActionPerformed"/> + </Events> + </Component> + </SubComponents> + </Container> + <Container class="javax.swing.JPanel" name="jPanel2"> + <Properties> + <Property name="border" type="javax.swing.border.Border" editor="org.netbeans.modules.form.editors2.BorderEditor"> + <Border info="org.netbeans.modules.form.compat2.border.TitledBorderInfo"> + <TitledBorder title="Shaded Object"/> + </Border> + </Property> + </Properties> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout" value="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription"> + <GridBagConstraints gridX="0" gridY="1" gridWidth="1" gridHeight="1" fill="1" ipadX="0" ipadY="0" insetsTop="0" insetsLeft="0" insetsBottom="0" insetsRight="0" anchor="10" weightX="0.0" weightY="0.0"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignFlowLayout"/> + <SubComponents> + <Component class="javax.swing.JLabel" name="jLabel3"> + <Properties> + <Property name="font" type="java.awt.Font" editor="org.netbeans.beaninfo.editors.FontEditor"> + <Font name="Dialog" size="12" style="0"/> + </Property> + <Property name="text" type="java.lang.String" value="Depth Function"/> + <Property name="toolTipText" type="java.lang.String" value="Mode of shaded object"/> + </Properties> + </Component> + <Component class="javax.swing.JComboBox" name="shadedComboBox"> + <Properties> + <Property name="font" type="java.awt.Font" editor="org.netbeans.beaninfo.editors.FontEditor"> + <Font name="Dialog" size="12" style="0"/> + </Property> + <Property name="model" type="javax.swing.ComboBoxModel" editor="org.netbeans.modules.form.editors2.ComboBoxModelEditor"> + <StringArray count="8"> + <StringItem index="0" value="ALWAYS"/> + <StringItem index="1" value="NEVER"/> + <StringItem index="2" value="EQUAL"/> + <StringItem index="3" value="NOT_EQUAL"/> + <StringItem index="4" value="LESS"/> + <StringItem index="5" value="LESS_OR_EQUAL"/> + <StringItem index="6" value="GREATER"/> + <StringItem index="7" value="GREATER_OR_EQUAL"/> + </StringArray> + </Property> + <Property name="selectedIndex" type="int" value="4"/> + </Properties> + <Events> + <EventHandler event="actionPerformed" listener="java.awt.event.ActionListener" parameters="java.awt.event.ActionEvent" handler="shadedComboBoxActionPerformed"/> + </Events> + </Component> + <Component class="javax.swing.JCheckBox" name="shadedCheckBox"> + <Properties> + <Property name="font" type="java.awt.Font" editor="org.netbeans.beaninfo.editors.FontEditor"> + <Font name="Dialog" size="12" style="0"/> + </Property> + <Property name="selected" type="boolean" value="true"/> + <Property name="text" type="java.lang.String" value="Write Depth Buffer"/> + <Property name="toolTipText" type="java.lang.String" value="Depth will be written for the object, if selected"/> + </Properties> + <Events> + <EventHandler event="actionPerformed" listener="java.awt.event.ActionListener" parameters="java.awt.event.ActionEvent" handler="shadedCheckBoxActionPerformed"/> + </Events> + </Component> + </SubComponents> + </Container> + <Container class="javax.swing.JPanel" name="jPanel3"> + <Properties> + <Property name="border" type="javax.swing.border.Border" editor="org.netbeans.modules.form.editors2.BorderEditor"> + <Border info="org.netbeans.modules.form.compat2.border.TitledBorderInfo"> + <TitledBorder title="Rotating Cube"/> + </Border> + </Property> + </Properties> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout" value="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription"> + <GridBagConstraints gridX="0" gridY="2" gridWidth="1" gridHeight="1" fill="1" ipadX="0" ipadY="0" insetsTop="0" insetsLeft="0" insetsBottom="0" insetsRight="0" anchor="10" weightX="0.0" weightY="0.0"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignFlowLayout"/> + <SubComponents> + <Component class="javax.swing.JLabel" name="jLabel4"> + <Properties> + <Property name="font" type="java.awt.Font" editor="org.netbeans.beaninfo.editors.FontEditor"> + <Font name="Dialog" size="12" style="0"/> + </Property> + <Property name="text" type="java.lang.String" value="Raster Operator"/> + <Property name="toolTipText" type="java.lang.String" value="Raster mode of rotating object (try NOOP)"/> + </Properties> + </Component> + <Component class="javax.swing.JComboBox" name="rotatingComboBox"> + <Properties> + <Property name="font" type="java.awt.Font" editor="org.netbeans.beaninfo.editors.FontEditor"> + <Font name="Dialog" size="12" style="0"/> + </Property> + <Property name="model" type="javax.swing.ComboBoxModel" editor="org.netbeans.modules.form.editors2.ComboBoxModelEditor"> + <StringArray count="16"> + <StringItem index="0" value="CLEAR"/> + <StringItem index="1" value="AND"/> + <StringItem index="2" value="AND_REVERSE"/> + <StringItem index="3" value="COPY"/> + <StringItem index="4" value="AND_INVERTED"/> + <StringItem index="5" value="NOOP"/> + <StringItem index="6" value="XOR"/> + <StringItem index="7" value="OR"/> + <StringItem index="8" value="NOR"/> + <StringItem index="9" value="EQUIV"/> + <StringItem index="10" value="INVERT"/> + <StringItem index="11" value="OR_REVERSE"/> + <StringItem index="12" value="COPY_INVERTED"/> + <StringItem index="13" value="OR_INVERTED"/> + <StringItem index="14" value="NAND"/> + <StringItem index="15" value="SET"/> + </StringArray> + </Property> + <Property name="selectedIndex" type="int" value="3"/> + </Properties> + <Events> + <EventHandler event="actionPerformed" listener="java.awt.event.ActionListener" parameters="java.awt.event.ActionEvent" handler="rotatingComboBoxActionPerformed"/> + </Events> + </Component> + </SubComponents> + </Container> + </SubComponents> +</Form> diff --git a/src/main/java/org/jdesktop/j3d/examples/depth_func/DepthFuncTest.java b/src/main/java/org/jdesktop/j3d/examples/depth_func/DepthFuncTest.java new file mode 100644 index 0000000..0095ca9 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/depth_func/DepthFuncTest.java @@ -0,0 +1,359 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.depth_func; + +import org.jogamp.java3d.RenderingAttributes; + + +/** + *The goal of that example is to show the use of different ZBuffer comparison modes. + */ +public class DepthFuncTest extends javax.swing.JFrame +{ + + RenderFrame rf; + + /** + * Creates new form DepthFuncTest + */ + public DepthFuncTest(){ + initComponents(); + } + + /** This method is called from within the constructor to + * initialize the form. + * WARNING: Do NOT modify this code. The content of this method is + * always regenerated by the Form Editor. + */ + // <editor-fold defaultstate="collapsed" desc=" Generated Code ">//GEN-BEGIN:initComponents + private void initComponents() + { + java.awt.GridBagConstraints gridBagConstraints; + + jPanel1 = new javax.swing.JPanel(); + jLabel1 = new javax.swing.JLabel(); + normalComboBox = new javax.swing.JComboBox(); + wfCheckBox = new javax.swing.JCheckBox(); + jPanel2 = new javax.swing.JPanel(); + jLabel3 = new javax.swing.JLabel(); + shadedComboBox = new javax.swing.JComboBox(); + shadedCheckBox = new javax.swing.JCheckBox(); + jPanel3 = new javax.swing.JPanel(); + jLabel4 = new javax.swing.JLabel(); + rotatingComboBox = new javax.swing.JComboBox(); + + getContentPane().setLayout(new java.awt.GridBagLayout()); + + setDefaultCloseOperation(javax.swing.WindowConstants.EXIT_ON_CLOSE); + jPanel1.setBorder(new javax.swing.border.TitledBorder("WireFrame Object")); + jLabel1.setFont(new java.awt.Font("Dialog", 0, 12)); + jLabel1.setText("Depth function"); + jLabel1.setToolTipText("Mode for normal object"); + jPanel1.add(jLabel1); + jLabel1.getAccessibleContext().setAccessibleParent(shadedComboBox); + + normalComboBox.setFont(new java.awt.Font("Dialog", 0, 12)); + normalComboBox.setModel(new javax.swing.DefaultComboBoxModel(new String[] { "ALWAYS", "NEVER", "EQUAL", "NOT_EQUAL", "LESS", "LESS_OR_EQUAL", "GREATER", "GREATER_OR_EQUAL" })); + normalComboBox.setSelectedIndex(6); + normalComboBox.setPreferredSize(new java.awt.Dimension(150, 22)); + normalComboBox.addActionListener(new java.awt.event.ActionListener() + { + public void actionPerformed(java.awt.event.ActionEvent evt) + { + normalComboBoxActionPerformed(evt); + } + }); + + jPanel1.add(normalComboBox); + + wfCheckBox.setFont(new java.awt.Font("Dialog", 0, 12)); + wfCheckBox.setText("Write Depth Buffer"); + wfCheckBox.setToolTipText("Depth will be written for the object, if selected"); + wfCheckBox.addActionListener(new java.awt.event.ActionListener() + { + public void actionPerformed(java.awt.event.ActionEvent evt) + { + wfCheckBoxActionPerformed(evt); + } + }); + + jPanel1.add(wfCheckBox); + + gridBagConstraints = new java.awt.GridBagConstraints(); + gridBagConstraints.gridx = 0; + gridBagConstraints.gridy = 0; + gridBagConstraints.fill = java.awt.GridBagConstraints.BOTH; + getContentPane().add(jPanel1, gridBagConstraints); + + jPanel2.setBorder(new javax.swing.border.TitledBorder("Shaded Object")); + jLabel3.setFont(new java.awt.Font("Dialog", 0, 12)); + jLabel3.setText("Depth Function"); + jLabel3.setToolTipText("Mode of shaded object"); + jPanel2.add(jLabel3); + + shadedComboBox.setFont(new java.awt.Font("Dialog", 0, 12)); + shadedComboBox.setModel(new javax.swing.DefaultComboBoxModel(new String[] { "ALWAYS", "NEVER", "EQUAL", "NOT_EQUAL", "LESS", "LESS_OR_EQUAL", "GREATER", "GREATER_OR_EQUAL" })); + shadedComboBox.setSelectedIndex(4); + shadedComboBox.addActionListener(new java.awt.event.ActionListener() + { + public void actionPerformed(java.awt.event.ActionEvent evt) + { + shadedComboBoxActionPerformed(evt); + } + }); + + jPanel2.add(shadedComboBox); + + shadedCheckBox.setFont(new java.awt.Font("Dialog", 0, 12)); + shadedCheckBox.setSelected(true); + shadedCheckBox.setText("Write Depth Buffer"); + shadedCheckBox.setToolTipText("Depth will be written for the object, if selected"); + shadedCheckBox.addActionListener(new java.awt.event.ActionListener() + { + public void actionPerformed(java.awt.event.ActionEvent evt) + { + shadedCheckBoxActionPerformed(evt); + } + }); + + jPanel2.add(shadedCheckBox); + + gridBagConstraints = new java.awt.GridBagConstraints(); + gridBagConstraints.gridx = 0; + gridBagConstraints.gridy = 1; + gridBagConstraints.fill = java.awt.GridBagConstraints.BOTH; + getContentPane().add(jPanel2, gridBagConstraints); + + jPanel3.setBorder(new javax.swing.border.TitledBorder("Rotating Cube")); + jLabel4.setFont(new java.awt.Font("Dialog", 0, 12)); + jLabel4.setText("Raster Operator"); + jLabel4.setToolTipText("Raster mode of rotating object (try NOOP)"); + jPanel3.add(jLabel4); + + rotatingComboBox.setFont(new java.awt.Font("Dialog", 0, 12)); + rotatingComboBox.setModel(new javax.swing.DefaultComboBoxModel(new String[] { "CLEAR", "AND", "AND_REVERSE", "COPY", "AND_INVERTED", "NOOP", "XOR", "OR", "NOR", "EQUIV", "INVERT", "OR_REVERSE", "COPY_INVERTED", "OR_INVERTED", "NAND", "SET" })); + rotatingComboBox.setSelectedIndex(3); + rotatingComboBox.addActionListener(new java.awt.event.ActionListener() + { + public void actionPerformed(java.awt.event.ActionEvent evt) + { + rotatingComboBoxActionPerformed(evt); + } + }); + + jPanel3.add(rotatingComboBox); + + gridBagConstraints = new java.awt.GridBagConstraints(); + gridBagConstraints.gridx = 0; + gridBagConstraints.gridy = 2; + gridBagConstraints.fill = java.awt.GridBagConstraints.BOTH; + getContentPane().add(jPanel3, gridBagConstraints); + + setBounds(0, 0, 403, 240); + } + // </editor-fold>//GEN-END:initComponents + + private void rotatingComboBoxActionPerformed(java.awt.event.ActionEvent evt)//GEN-FIRST:event_rotatingComboBoxActionPerformed + {//GEN-HEADEREND:event_rotatingComboBoxActionPerformed + String selectedItem = rotatingComboBox.getSelectedItem().toString(); // how to avoid a cast and all that goes with it. (lazyness) + int mode = RenderingAttributes.ROP_COPY; + if ( "CLEAR".equals(selectedItem) ) + { + mode = RenderingAttributes.ROP_CLEAR; + } + else if ( "AND".equals(selectedItem) ) + { + mode = RenderingAttributes.ROP_AND; + } + else if ( "AND_REVERSE".equals(selectedItem) ) + { + mode = RenderingAttributes.ROP_AND_REVERSE; + } + else if ( "COPY".equals(selectedItem) ) + { + mode = RenderingAttributes.ROP_COPY; + } + else if ( "AND_INVERTED".equals(selectedItem) ) + { + mode = RenderingAttributes.ROP_AND_INVERTED; + } + else if ( "NOOP".equals(selectedItem) ) + { + mode = RenderingAttributes.ROP_NOOP; + } + else if ( "XOR".equals(selectedItem) ) + { + mode = RenderingAttributes.ROP_XOR; + } + else if ( "OR".equals(selectedItem) ) + { + mode = RenderingAttributes.ROP_OR; + } + else if ( "NOR".equals(selectedItem) ) + { + mode = RenderingAttributes.ROP_NOR; + } + else if ( "EQUIV".equals(selectedItem) ) + { + mode = RenderingAttributes.ROP_EQUIV; + } + else if ( "INVERT".equals(selectedItem) ) + { + mode = RenderingAttributes.ROP_INVERT; + } + else if ( "OR_REVERSE".equals(selectedItem) ) + { + mode = RenderingAttributes.ROP_OR_REVERSE; + } + else if ( "COPY_INVERTED".equals(selectedItem) ) + { + mode = RenderingAttributes.ROP_COPY_INVERTED; + } + else if ( "OR_INVERTED".equals(selectedItem) ) + { + mode = RenderingAttributes.ROP_OR_INVERTED; + } + else if ( "NAND".equals(selectedItem) ) + { + mode = RenderingAttributes.ROP_NAND; + } + else if ( "SET".equals(selectedItem) ) + { + mode = RenderingAttributes.ROP_SET; + } + else + { + System.out.println("oops. wrong mode in ROP combo: "+selectedItem); + } + rf.setRotatingObjectROPMode( mode ); + }//GEN-LAST:event_rotatingComboBoxActionPerformed + + private void shadedCheckBoxActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_shadedCheckBoxActionPerformed + rf.setStaticObjectDBWriteStatus( shadedCheckBox.isSelected() ); + }//GEN-LAST:event_shadedCheckBoxActionPerformed + + private void wfCheckBoxActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_wfCheckBoxActionPerformed + rf.setStaticWFObjectDBWriteStatus( wfCheckBox.isSelected() ); + }//GEN-LAST:event_wfCheckBoxActionPerformed + + private void shadedComboBoxActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_shadedComboBoxActionPerformed + int func = RenderingAttributes.LESS_OR_EQUAL; + String selectedItem = shadedComboBox.getSelectedItem().toString(); // how to avoid a cast and all that goes with it. (lazyness) + rf.setStaticObjectTestFunc( getID( selectedItem ) ); + }//GEN-LAST:event_shadedComboBoxActionPerformed + + private void normalComboBoxActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_normalComboBoxActionPerformed + int func = RenderingAttributes.LESS_OR_EQUAL; + String selectedItem = normalComboBox.getSelectedItem().toString(); // how to avoid a cast and all that goes with it. (lazyness) + rf.setStaticWFObjectTestFunc( getID( selectedItem ) ); + }//GEN-LAST:event_normalComboBoxActionPerformed + + int getID( String selectedItem ) + { + int func = RenderingAttributes.LESS_OR_EQUAL; + if ( "LESS_OR_EQUAL".equals(selectedItem) ) + { + func = RenderingAttributes.LESS_OR_EQUAL; + } + else if ( "NEVER".equals(selectedItem) ) + { + func = RenderingAttributes.NEVER; + } + else if ( "ALWAYS".equals(selectedItem) ) + { + func = RenderingAttributes.ALWAYS; + } + else if ( "GREATER".equals(selectedItem) ) + { + func = RenderingAttributes.GREATER; + } + else if ( "GREATER_OR_EQUAL".equals(selectedItem) ) + { + func = RenderingAttributes.GREATER_OR_EQUAL; + } + else if ( "LESS".equals(selectedItem) ) + { + func = RenderingAttributes.LESS; + } + else if ( "EQUAL".equals(selectedItem) ) + { + func = RenderingAttributes.EQUAL; + } + else if ( "NOT_EQUAL".equals(selectedItem) ) + { + func = RenderingAttributes.NOT_EQUAL; + } + return func; + } + + /** + * @param args the command line arguments + */ + public static void main(String args[]) {System.setProperty("sun.awt.noerasebackground", "true"); + java.awt.EventQueue.invokeLater(new Runnable() { + public void run() { + DepthFuncTest dpt = new DepthFuncTest(); + dpt.rf = new RenderFrame( dpt ); + dpt.setVisible(true); + dpt.rf.setVisible(true); + } + }); + } + + // Variables declaration - do not modify//GEN-BEGIN:variables + private javax.swing.JLabel jLabel1; + private javax.swing.JLabel jLabel3; + private javax.swing.JLabel jLabel4; + private javax.swing.JPanel jPanel1; + private javax.swing.JPanel jPanel2; + private javax.swing.JPanel jPanel3; + private javax.swing.JComboBox normalComboBox; + private javax.swing.JComboBox rotatingComboBox; + private javax.swing.JCheckBox shadedCheckBox; + private javax.swing.JComboBox shadedComboBox; + private javax.swing.JCheckBox wfCheckBox; + // End of variables declaration//GEN-END:variables + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/depth_func/DepthFuncTestGL2ES2.java b/src/main/java/org/jdesktop/j3d/examples/depth_func/DepthFuncTestGL2ES2.java new file mode 100644 index 0000000..ed34922 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/depth_func/DepthFuncTestGL2ES2.java @@ -0,0 +1,347 @@ +/* + * Copyright (c) 2016 JogAmp Community. All rights reserved. + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * This code is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 only, as + * published by the Free Software Foundation. Sun designates this + * particular file as subject to the "Classpath" exception as provided + * by Sun in the LICENSE file that accompanied this code. + * + * This code is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + * version 2 for more details (a copy is included in the LICENSE file that + * accompanied this code). + * + * You should have received a copy of the GNU General Public License version + * 2 along with this work; if not, write to the Free Software Foundation, + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. + * + */ + +package org.jdesktop.j3d.examples.depth_func; + +import org.jogamp.java3d.RenderingAttributes; + + +/** + *The goal of that example is to show the use of different ZBuffer comparison modes. + */ +public class DepthFuncTestGL2ES2 extends javax.swing.JFrame +{ + + RenderFrameGL2ES2 rf; + + /** + * Creates new form DepthFuncTest + */ + public DepthFuncTestGL2ES2(){ + initComponents(); + } + + /** This method is called from within the constructor to + * initialize the form. + * WARNING: Do NOT modify this code. The content of this method is + * always regenerated by the Form Editor. + */ + // <editor-fold defaultstate="collapsed" desc=" Generated Code ">//GEN-BEGIN:initComponents + private void initComponents() + { + java.awt.GridBagConstraints gridBagConstraints; + + jPanel1 = new javax.swing.JPanel(); + jLabel1 = new javax.swing.JLabel(); + normalComboBox = new javax.swing.JComboBox(); + wfCheckBox = new javax.swing.JCheckBox(); + jPanel2 = new javax.swing.JPanel(); + jLabel3 = new javax.swing.JLabel(); + shadedComboBox = new javax.swing.JComboBox(); + shadedCheckBox = new javax.swing.JCheckBox(); + jPanel3 = new javax.swing.JPanel(); + jLabel4 = new javax.swing.JLabel(); + rotatingComboBox = new javax.swing.JComboBox(); + + getContentPane().setLayout(new java.awt.GridBagLayout()); + + setDefaultCloseOperation(javax.swing.WindowConstants.EXIT_ON_CLOSE); + jPanel1.setBorder(new javax.swing.border.TitledBorder("WireFrame Object")); + jLabel1.setFont(new java.awt.Font("Dialog", 0, 12)); + jLabel1.setText("Depth function"); + jLabel1.setToolTipText("Mode for normal object"); + jPanel1.add(jLabel1); + jLabel1.getAccessibleContext().setAccessibleParent(shadedComboBox); + + normalComboBox.setFont(new java.awt.Font("Dialog", 0, 12)); + normalComboBox.setModel(new javax.swing.DefaultComboBoxModel(new String[] { "ALWAYS", "NEVER", "EQUAL", "NOT_EQUAL", "LESS", "LESS_OR_EQUAL", "GREATER", "GREATER_OR_EQUAL" })); + normalComboBox.setSelectedIndex(6); + normalComboBox.setPreferredSize(new java.awt.Dimension(150, 22)); + normalComboBox.addActionListener(new java.awt.event.ActionListener() + { + @Override + public void actionPerformed(java.awt.event.ActionEvent evt) + { + normalComboBoxActionPerformed(evt); + } + }); + + jPanel1.add(normalComboBox); + + wfCheckBox.setFont(new java.awt.Font("Dialog", 0, 12)); + wfCheckBox.setText("Write Depth Buffer"); + wfCheckBox.setToolTipText("Depth will be written for the object, if selected"); + wfCheckBox.addActionListener(new java.awt.event.ActionListener() + { + @Override + public void actionPerformed(java.awt.event.ActionEvent evt) + { + wfCheckBoxActionPerformed(evt); + } + }); + + jPanel1.add(wfCheckBox); + + gridBagConstraints = new java.awt.GridBagConstraints(); + gridBagConstraints.gridx = 0; + gridBagConstraints.gridy = 0; + gridBagConstraints.fill = java.awt.GridBagConstraints.BOTH; + getContentPane().add(jPanel1, gridBagConstraints); + + jPanel2.setBorder(new javax.swing.border.TitledBorder("Shaded Object")); + jLabel3.setFont(new java.awt.Font("Dialog", 0, 12)); + jLabel3.setText("Depth Function"); + jLabel3.setToolTipText("Mode of shaded object"); + jPanel2.add(jLabel3); + + shadedComboBox.setFont(new java.awt.Font("Dialog", 0, 12)); + shadedComboBox.setModel(new javax.swing.DefaultComboBoxModel(new String[] { "ALWAYS", "NEVER", "EQUAL", "NOT_EQUAL", "LESS", "LESS_OR_EQUAL", "GREATER", "GREATER_OR_EQUAL" })); + shadedComboBox.setSelectedIndex(4); + shadedComboBox.addActionListener(new java.awt.event.ActionListener() + { + @Override + public void actionPerformed(java.awt.event.ActionEvent evt) + { + shadedComboBoxActionPerformed(evt); + } + }); + + jPanel2.add(shadedComboBox); + + shadedCheckBox.setFont(new java.awt.Font("Dialog", 0, 12)); + shadedCheckBox.setSelected(true); + shadedCheckBox.setText("Write Depth Buffer"); + shadedCheckBox.setToolTipText("Depth will be written for the object, if selected"); + shadedCheckBox.addActionListener(new java.awt.event.ActionListener() + { + @Override + public void actionPerformed(java.awt.event.ActionEvent evt) + { + shadedCheckBoxActionPerformed(evt); + } + }); + + jPanel2.add(shadedCheckBox); + + gridBagConstraints = new java.awt.GridBagConstraints(); + gridBagConstraints.gridx = 0; + gridBagConstraints.gridy = 1; + gridBagConstraints.fill = java.awt.GridBagConstraints.BOTH; + getContentPane().add(jPanel2, gridBagConstraints); + + jPanel3.setBorder(new javax.swing.border.TitledBorder("Rotating Cube")); + jLabel4.setFont(new java.awt.Font("Dialog", 0, 12)); + jLabel4.setText("Raster Operator - Raster Ops are not availible in GL2ES2"); + jLabel4.setToolTipText("Raster mode of rotating object (try NOOP)"); + jPanel3.add(jLabel4); + + rotatingComboBox.setFont(new java.awt.Font("Dialog", 0, 12)); + rotatingComboBox.setModel(new javax.swing.DefaultComboBoxModel(new String[] { "CLEAR", "AND", "AND_REVERSE", "COPY", "AND_INVERTED", "NOOP", "XOR", "OR", "NOR", "EQUIV", "INVERT", "OR_REVERSE", "COPY_INVERTED", "OR_INVERTED", "NAND", "SET" })); + rotatingComboBox.setSelectedIndex(3); + rotatingComboBox.addActionListener(new java.awt.event.ActionListener() + { + @Override + public void actionPerformed(java.awt.event.ActionEvent evt) + { + rotatingComboBoxActionPerformed(evt); + } + }); + + //Raster Ops are not availible in GL2ES2 + //jPanel3.add(rotatingComboBox); + + gridBagConstraints = new java.awt.GridBagConstraints(); + gridBagConstraints.gridx = 0; + gridBagConstraints.gridy = 2; + gridBagConstraints.fill = java.awt.GridBagConstraints.BOTH; + getContentPane().add(jPanel3, gridBagConstraints); + + setBounds(0, 0, 403, 240); + } + // </editor-fold>//GEN-END:initComponents + + private void rotatingComboBoxActionPerformed(java.awt.event.ActionEvent evt)//GEN-FIRST:event_rotatingComboBoxActionPerformed + {//GEN-HEADEREND:event_rotatingComboBoxActionPerformed + String selectedItem = rotatingComboBox.getSelectedItem().toString(); // how to avoid a cast and all that goes with it. (lazyness) + int mode = RenderingAttributes.ROP_COPY; + if ( "CLEAR".equals(selectedItem) ) + { + mode = RenderingAttributes.ROP_CLEAR; + } + else if ( "AND".equals(selectedItem) ) + { + mode = RenderingAttributes.ROP_AND; + } + else if ( "AND_REVERSE".equals(selectedItem) ) + { + mode = RenderingAttributes.ROP_AND_REVERSE; + } + else if ( "COPY".equals(selectedItem) ) + { + mode = RenderingAttributes.ROP_COPY; + } + else if ( "AND_INVERTED".equals(selectedItem) ) + { + mode = RenderingAttributes.ROP_AND_INVERTED; + } + else if ( "NOOP".equals(selectedItem) ) + { + mode = RenderingAttributes.ROP_NOOP; + } + else if ( "XOR".equals(selectedItem) ) + { + mode = RenderingAttributes.ROP_XOR; + } + else if ( "OR".equals(selectedItem) ) + { + mode = RenderingAttributes.ROP_OR; + } + else if ( "NOR".equals(selectedItem) ) + { + mode = RenderingAttributes.ROP_NOR; + } + else if ( "EQUIV".equals(selectedItem) ) + { + mode = RenderingAttributes.ROP_EQUIV; + } + else if ( "INVERT".equals(selectedItem) ) + { + mode = RenderingAttributes.ROP_INVERT; + } + else if ( "OR_REVERSE".equals(selectedItem) ) + { + mode = RenderingAttributes.ROP_OR_REVERSE; + } + else if ( "COPY_INVERTED".equals(selectedItem) ) + { + mode = RenderingAttributes.ROP_COPY_INVERTED; + } + else if ( "OR_INVERTED".equals(selectedItem) ) + { + mode = RenderingAttributes.ROP_OR_INVERTED; + } + else if ( "NAND".equals(selectedItem) ) + { + mode = RenderingAttributes.ROP_NAND; + } + else if ( "SET".equals(selectedItem) ) + { + mode = RenderingAttributes.ROP_SET; + } + else + { + System.out.println("oops. wrong mode in ROP combo: "+selectedItem); + } + + rf.setRotatingObjectROPMode( mode ); + }//GEN-LAST:event_rotatingComboBoxActionPerformed + + private void shadedCheckBoxActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_shadedCheckBoxActionPerformed + rf.setStaticObjectDBWriteStatus( shadedCheckBox.isSelected() ); + }//GEN-LAST:event_shadedCheckBoxActionPerformed + + private void wfCheckBoxActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_wfCheckBoxActionPerformed + rf.setStaticWFObjectDBWriteStatus( wfCheckBox.isSelected() ); + }//GEN-LAST:event_wfCheckBoxActionPerformed + + private void shadedComboBoxActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_shadedComboBoxActionPerformed + //int func = RenderingAttributes.LESS_OR_EQUAL; + String selectedItem = shadedComboBox.getSelectedItem().toString(); // how to avoid a cast and all that goes with it. (lazyness) + rf.setStaticObjectTestFunc( getID( selectedItem ) ); + }//GEN-LAST:event_shadedComboBoxActionPerformed + + private void normalComboBoxActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_normalComboBoxActionPerformed + //int func = RenderingAttributes.LESS_OR_EQUAL; + String selectedItem = normalComboBox.getSelectedItem().toString(); // how to avoid a cast and all that goes with it. (lazyness) + rf.setStaticWFObjectTestFunc( getID( selectedItem ) ); + }//GEN-LAST:event_normalComboBoxActionPerformed + + int getID( String selectedItem ) + { + int func = RenderingAttributes.LESS_OR_EQUAL; + if ( "LESS_OR_EQUAL".equals(selectedItem) ) + { + func = RenderingAttributes.LESS_OR_EQUAL; + } + else if ( "NEVER".equals(selectedItem) ) + { + func = RenderingAttributes.NEVER; + } + else if ( "ALWAYS".equals(selectedItem) ) + { + func = RenderingAttributes.ALWAYS; + } + else if ( "GREATER".equals(selectedItem) ) + { + func = RenderingAttributes.GREATER; + } + else if ( "GREATER_OR_EQUAL".equals(selectedItem) ) + { + func = RenderingAttributes.GREATER_OR_EQUAL; + } + else if ( "LESS".equals(selectedItem) ) + { + func = RenderingAttributes.LESS; + } + else if ( "EQUAL".equals(selectedItem) ) + { + func = RenderingAttributes.EQUAL; + } + else if ( "NOT_EQUAL".equals(selectedItem) ) + { + func = RenderingAttributes.NOT_EQUAL; + } + return func; + } + + /** + * @param args the command line arguments + */ + public static void main(String args[]) {System.setProperty("sun.awt.noerasebackground", "true"); + System.setProperty("j3d.rend", "jogl2es2"); + System.setProperty("j3d.displaylist", "false"); + java.awt.EventQueue.invokeLater(new Runnable() { + @Override + public void run() { + DepthFuncTestGL2ES2 dpt = new DepthFuncTestGL2ES2(); + dpt.rf = new RenderFrameGL2ES2( dpt ); + dpt.setVisible(true); + dpt.rf.setVisible(true); + } + }); + } + + // Variables declaration - do not modify//GEN-BEGIN:variables + private javax.swing.JLabel jLabel1; + private javax.swing.JLabel jLabel3; + private javax.swing.JLabel jLabel4; + private javax.swing.JPanel jPanel1; + private javax.swing.JPanel jPanel2; + private javax.swing.JPanel jPanel3; + private javax.swing.JComboBox<?> normalComboBox; + private javax.swing.JComboBox<?> rotatingComboBox; + private javax.swing.JCheckBox shadedCheckBox; + private javax.swing.JComboBox<?> shadedComboBox; + private javax.swing.JCheckBox wfCheckBox; + // End of variables declaration//GEN-END:variables + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/depth_func/RenderFrame.form b/src/main/java/org/jdesktop/j3d/examples/depth_func/RenderFrame.form new file mode 100644 index 0000000..2edc4bb --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/depth_func/RenderFrame.form @@ -0,0 +1,25 @@ +<?xml version="1.0" encoding="UTF-8" ?> + +<Form version="1.0" type="org.netbeans.modules.form.forminfo.JFrameFormInfo"> + <Properties> + <Property name="defaultCloseOperation" type="int" value="3"/> + <Property name="title" type="java.lang.String" value="J3D frame"/> + </Properties> + <SyntheticProperties> + <SyntheticProperty name="formSize" type="java.awt.Dimension" value="-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,1,-32,0,0,2,-128"/> + <SyntheticProperty name="formPosition" type="java.awt.Point" value="-84,-19,0,5,115,114,0,14,106,97,118,97,46,97,119,116,46,80,111,105,110,116,-74,-60,-118,114,52,126,-56,38,2,0,2,73,0,1,120,73,0,1,121,120,112,0,0,1,-112,0,0,0,0"/> + <SyntheticProperty name="formSizePolicy" type="int" value="0"/> + <SyntheticProperty name="generatePosition" type="boolean" value="true"/> + <SyntheticProperty name="generateSize" type="boolean" value="true"/> + <SyntheticProperty name="generateCenter" type="boolean" value="false"/> + </SyntheticProperties> + <AuxValues> + <AuxValue name="FormSettings_generateMnemonicsCode" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_listenerGenerationStyle" type="java.lang.Integer" value="0"/> + <AuxValue name="FormSettings_variablesLocal" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_variablesModifier" type="java.lang.Integer" value="2"/> + <AuxValue name="designerSize" type="java.awt.Dimension" value="-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,1,-56,0,0,2,120"/> + </AuxValues> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> +</Form> diff --git a/src/main/java/org/jdesktop/j3d/examples/depth_func/RenderFrame.java b/src/main/java/org/jdesktop/j3d/examples/depth_func/RenderFrame.java new file mode 100644 index 0000000..04d8a58 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/depth_func/RenderFrame.java @@ -0,0 +1,309 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.depth_func; + +import java.awt.GraphicsConfiguration; + +import org.jogamp.java3d.Alpha; +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.Material; +import org.jogamp.java3d.OrderedGroup; +import org.jogamp.java3d.PointLight; +import org.jogamp.java3d.PolygonAttributes; +import org.jogamp.java3d.RenderingAttributes; +import org.jogamp.java3d.RotationInterpolator; +import org.jogamp.java3d.ScaleInterpolator; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.utils.behaviors.mouse.MouseRotate; +import org.jogamp.java3d.utils.geometry.Box; +import org.jogamp.java3d.utils.geometry.Sphere; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Point3f; +import org.jogamp.vecmath.Vector3f; + + +public class RenderFrame extends javax.swing.JFrame { + + DepthFuncTest dpt; + + SimpleUniverse su; + + RenderingAttributes staticWFBoxRA; + RenderingAttributes staticBoxRA; + + RenderingAttributes rotatingBoxRA; + + /** Creates new form RenderFrame */ + public RenderFrame( DepthFuncTest _dpt) { + dpt = _dpt; + initComponents(); + initUniverse(); + } + + /** This method is called from within the constructor to + * initialize the form. + * WARNING: Do NOT modify this code. The content of this method is + * always regenerated by the Form Editor. + */ + // <editor-fold defaultstate="collapsed" desc=" Generated Code ">//GEN-BEGIN:initComponents + private void initComponents() + { + + setDefaultCloseOperation(javax.swing.WindowConstants.EXIT_ON_CLOSE); + setTitle("J3D frame"); + setBounds(400, 0, 640, 480); + } + // </editor-fold>//GEN-END:initComponents + + void initUniverse() { + GraphicsConfiguration config = SimpleUniverse.getPreferredConfiguration(); + + Canvas3D c = new Canvas3D(config); + add("Center", c); + su = new SimpleUniverse(c); + su.addBranchGraph( createScene() ); + c.getView().setMinimumFrameCycleTime( 10 ); + } + + // Variables declaration - do not modify//GEN-BEGIN:variables + // End of variables declaration//GEN-END:variables + + BranchGroup createScene() { + BoundingSphere bounds = new BoundingSphere( new Point3d( 0.0, 0.0, 0.0 ), 100.0 ); + + BranchGroup globalBG = new BranchGroup(); + BranchGroup rotObjectBG = new BranchGroup(); + OrderedGroup staticObjectOG = new OrderedGroup(); + BranchGroup lampsBG = new BranchGroup(); + OrderedGroup oGroup = new OrderedGroup(); + TransformGroup staticBoxRotTG = new TransformGroup(); + staticBoxRotTG.addChild( staticObjectOG ); + TransformGroup objectsTGRot = new TransformGroup(); + TransformGroup objectsTGTrans = new TransformGroup(); + Transform3D objectsTGTransT3d = new Transform3D(); + objectsTGTransT3d.setTranslation( new Vector3f( 0.0f, 0.0f, -10.0f ) ); + objectsTGTrans.setTransform( objectsTGTransT3d ); + objectsTGRot.addChild( oGroup ); + objectsTGTrans.addChild( objectsTGRot ); + lampsBG.addChild( objectsTGTrans ); + + //adding a sphere as backgroung so there is something else than flat black, and cut cube removal as an other implication. (seeing through) + Appearance globalSphereAppearance = new Appearance(); + PolygonAttributes globalSpherePA = new PolygonAttributes(); + globalSpherePA.setCullFace( globalSpherePA.CULL_FRONT );// so that interior of the sphere is visible. + Material globalSphereMaterial = new Material(); + globalSphereMaterial.setEmissiveColor( .25f ,.3f ,.35f ); + globalSphereAppearance.setMaterial( globalSphereMaterial ); + globalSphereAppearance.setPolygonAttributes( globalSpherePA ); + Sphere globalSphere = new Sphere( 6.0f ); + globalSphere.setAppearance( globalSphereAppearance ); + globalSphere.setBounds( bounds ); + oGroup.addChild( globalSphere ); + + globalBG.addChild( lampsBG ); + + // adding lamps. + PointLight frontLamp = new PointLight( new Color3f( 1.0f, 1.0f, 1.0f ), new Point3f( 20, 20, 20 ), new Point3f( 0.0f, .0f, 0.f ) ); + lampsBG.addChild( frontLamp ); + frontLamp.setBounds( bounds ); + frontLamp.setInfluencingBounds( bounds ); + PointLight backLamp = new PointLight( new Color3f( 1.0f, .0f, .0f ), new Point3f( -20, -20, -20 ), new Point3f( 0.0f, .0f, 0.f ) ); + lampsBG.addChild( backLamp ); + backLamp.setBounds( bounds ); + backLamp.setInfluencingBounds( bounds ); + + //adding shapes. + { + //adding rotating and scaling cube + //doing the rotation + TransformGroup rotBoxTGRot = new TransformGroup(); + rotBoxTGRot.setCapability( rotBoxTGRot.ALLOW_TRANSFORM_WRITE ); + RotationInterpolator rotBoxRotInt = new RotationInterpolator( new Alpha( -1, 20000 ) , rotBoxTGRot ); + rotBoxRotInt.setSchedulingBounds( bounds ); + rotBoxRotInt.setBounds( bounds ); + + //doing the scaling + Transform3D scaleBoxt3d = new Transform3D(); + TransformGroup rotBoxTGScale = new TransformGroup(); + rotBoxTGScale.setCapability( rotBoxTGScale.ALLOW_TRANSFORM_WRITE ); + ScaleInterpolator rotBoxScaleInt = new ScaleInterpolator( new Alpha( -1, Alpha.INCREASING_ENABLE|Alpha.DECREASING_ENABLE, 0, 0, 3000, 1500, 0, 3000, 1500, 0 ) , rotBoxTGScale, new Transform3D(), 0.7f, 1.6f ); + rotBoxScaleInt.setSchedulingBounds( bounds ); + rotBoxScaleInt.setBounds( bounds ); + + Appearance rotBoxApp = new Appearance(); + Material rotBoxMat = new Material(); + rotBoxMat.setDiffuseColor( .4f, .4f, .4f ); + rotBoxApp.setMaterial( rotBoxMat ); + Box rotBox = new Box( 1.1f, 1.1f, 1.1f, rotBoxApp ); + rotBoxTGScale.addChild( rotBox ); + rotBoxTGRot.addChild( rotBoxTGScale ); + TransformGroup rotBoxTG = new TransformGroup(); + rotBoxTG.addChild( rotBoxTGRot ); + rotObjectBG.addChild( rotBoxTG ); + rotObjectBG.addChild( rotBoxScaleInt ); + rotObjectBG.addChild( rotBoxRotInt ); + rotBox.setBounds( bounds ); + + rotatingBoxRA = new RenderingAttributes(); + rotatingBoxRA.setRasterOpEnable( true ); + rotatingBoxRA.setCapability( staticBoxRA.ALLOW_RASTER_OP_WRITE ); +// rotatingBoxRA.setRasterOp( rotatingBoxRA.ROP_XOR ); + rotBoxApp.setRenderingAttributes( rotatingBoxRA ); + + + rotBox.setAppearance( rotBoxApp ); + } + + //adding static back face wireframe cube + { + Box staticWFBoxBack = new Box( ); + Appearance staticWFBoxApp = new Appearance(); + Material staticWFBoxMat = new Material(); + staticWFBoxMat.setDiffuseColor( 0.f, 0.f, 0.f ); + staticWFBoxMat.setEmissiveColor( 0.f, .4f, 0.f ); + staticWFBoxApp.setMaterial( staticWFBoxMat ); + PolygonAttributes staticWFBoxPABack = new PolygonAttributes( PolygonAttributes.POLYGON_LINE, PolygonAttributes.CULL_FRONT, 0.0f ); + staticWFBoxApp.setPolygonAttributes( staticWFBoxPABack ); + staticWFBoxRA = new RenderingAttributes(); + staticWFBoxRA.setCapability( staticWFBoxRA.ALLOW_DEPTH_TEST_FUNCTION_WRITE ); + staticWFBoxRA.setCapability( staticWFBoxRA.ALLOW_DEPTH_ENABLE_WRITE ); + staticWFBoxRA.setDepthTestFunction( staticWFBoxRA.GREATER ); + staticWFBoxRA.setDepthBufferWriteEnable( false ); + staticWFBoxApp.setRenderingAttributes( staticWFBoxRA ); + staticWFBoxBack.setAppearance( staticWFBoxApp ); + staticWFBoxBack.setBounds( bounds ); + staticObjectOG.addChild( staticWFBoxBack ); + } + + //adding static front face wireframe cube + { + Box staticWFBox = new Box( ); + Appearance staticWFBoxApp = new Appearance(); + Material staticWFBoxMat = new Material(); + staticWFBoxMat.setDiffuseColor( 0.f, 0.f, 0.f ); + staticWFBoxMat.setEmissiveColor( 0.f, 1.f, 0.f ); + staticWFBoxApp.setMaterial( staticWFBoxMat ); + PolygonAttributes staticWFBoxPA = new PolygonAttributes( PolygonAttributes.POLYGON_LINE, PolygonAttributes.CULL_BACK, 0.0f ); + staticWFBoxApp.setPolygonAttributes( staticWFBoxPA ); + staticWFBoxApp.setRenderingAttributes( staticWFBoxRA ); + staticWFBox.setAppearance( staticWFBoxApp ); + staticWFBox.setBounds( bounds ); + staticObjectOG.addChild( staticWFBox ); + } + + + {// rotating the static cubes + Transform3D boxt3d = new Transform3D(); + Transform3D tempt3d = new Transform3D(); + boxt3d.rotZ( Math.PI/4.0f ); + tempt3d.rotX( Math.PI/4.0f ); + boxt3d.mul( tempt3d ); + tempt3d.rotY( Math.PI/4.0f ); + boxt3d.mul( tempt3d ); + staticBoxRotTG.setTransform( boxt3d ); + } + + // adding static flat cube + { + Box staticBox = new Box( ); + staticBox.setBounds( bounds ); + Appearance boxApp = new Appearance(); + Material boxMat = new Material(); + boxMat.setDiffuseColor( .7f, .7f, .7f ); + boxApp.setMaterial( boxMat ); + staticBoxRA = new RenderingAttributes(); + staticBoxRA.setCapability( staticBoxRA.ALLOW_DEPTH_TEST_FUNCTION_WRITE ); + staticBoxRA.setCapability( staticBoxRA.ALLOW_DEPTH_ENABLE_WRITE ); + staticBoxRA.setDepthTestFunction( staticBoxRA.LESS ); + staticBoxRA.setDepthBufferWriteEnable( false ); + boxApp.setRenderingAttributes( staticBoxRA ); + staticBox.setAppearance( boxApp ); + staticObjectOG.addChild( staticBox ); + } + oGroup.addChild( rotObjectBG ); + oGroup.addChild( staticBoxRotTG ); + + //adding the mouse rotate behavior to the group of cubes. + MouseRotate behavior = new MouseRotate(); + behavior.setTransformGroup( objectsTGRot ); + objectsTGRot.addChild( behavior ); + objectsTGRot.setCapability( objectsTGRot.ALLOW_TRANSFORM_READ ); + objectsTGRot.setCapability( objectsTGRot.ALLOW_TRANSFORM_WRITE ); + behavior.setSchedulingBounds(bounds); + return globalBG; + } + + public void setStaticWFObjectTestFunc( int func ) + { + staticWFBoxRA.setDepthTestFunction( func ); + } + + public void setStaticObjectTestFunc( int func ) + { + staticBoxRA.setDepthTestFunction( func ); + } + + public void setStaticWFObjectDBWriteStatus( boolean status ) + { + staticWFBoxRA.setDepthBufferWriteEnable( status ); + } + + public void setStaticObjectDBWriteStatus( boolean status ) + { + staticBoxRA.setDepthBufferWriteEnable( status ); + } + + public void setRotatingObjectROPMode( int mode ) + { + rotatingBoxRA.setRasterOp( mode ); + } + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/depth_func/RenderFrameGL2ES2.java b/src/main/java/org/jdesktop/j3d/examples/depth_func/RenderFrameGL2ES2.java new file mode 100644 index 0000000..7eaed6e --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/depth_func/RenderFrameGL2ES2.java @@ -0,0 +1,294 @@ +/* + * Copyright (c) 2016 JogAmp Community. All rights reserved. + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * This code is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 only, as + * published by the Free Software Foundation. Sun designates this + * particular file as subject to the "Classpath" exception as provided + * by Sun in the LICENSE file that accompanied this code. + * + * This code is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + * version 2 for more details (a copy is included in the LICENSE file that + * accompanied this code). + * + * You should have received a copy of the GNU General Public License version + * 2 along with this work; if not, write to the Free Software Foundation, + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. + * + */ + +package org.jdesktop.j3d.examples.depth_func; + +import java.awt.GraphicsConfiguration; + +import org.jdesktop.j3d.examples.gl2es2pipeline.Cube; +import org.jdesktop.j3d.examples.gl2es2pipeline.SimpleShaderAppearance; +import org.jogamp.java3d.Alpha; +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.Material; +import org.jogamp.java3d.OrderedGroup; +import org.jogamp.java3d.PointLight; +import org.jogamp.java3d.PolygonAttributes; +import org.jogamp.java3d.RenderingAttributes; +import org.jogamp.java3d.RotationInterpolator; +import org.jogamp.java3d.ScaleInterpolator; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.utils.behaviors.mouse.MouseRotate; +import org.jogamp.java3d.utils.geometry.Sphere; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Point3f; +import org.jogamp.vecmath.Vector3f; + +public class RenderFrameGL2ES2 extends javax.swing.JFrame +{ + + DepthFuncTestGL2ES2 dpt; + + SimpleUniverse su; + + RenderingAttributes staticWFBoxRA; + RenderingAttributes staticBoxRA; + + RenderingAttributes rotatingBoxRA; + + /** Creates new form RenderFrame */ + public RenderFrameGL2ES2(DepthFuncTestGL2ES2 _dpt) + { + dpt = _dpt; + initComponents(); + initUniverse(); + } + + /** This method is called from within the constructor to + * initialize the form. + * WARNING: Do NOT modify this code. The content of this method is + * always regenerated by the Form Editor. + */ + // <editor-fold defaultstate="collapsed" desc=" Generated Code ">//GEN-BEGIN:initComponents + private void initComponents() + { + + setDefaultCloseOperation(javax.swing.WindowConstants.EXIT_ON_CLOSE); + setTitle("J3D frame"); + setBounds(400, 0, 640, 480); + } + // </editor-fold>//GEN-END:initComponents + + void initUniverse() + { + GraphicsConfiguration config = SimpleUniverse.getPreferredConfiguration(); + + Canvas3D c = new Canvas3D(config); + add("Center", c); + su = new SimpleUniverse(c); + su.addBranchGraph(createScene()); + c.getView().setMinimumFrameCycleTime(10); + } + + // Variables declaration - do not modify//GEN-BEGIN:variables + // End of variables declaration//GEN-END:variables + + BranchGroup createScene() + { + BoundingSphere bounds = new BoundingSphere(new Point3d(0.0, 0.0, 0.0), 100.0); + + BranchGroup globalBG = new BranchGroup(); + BranchGroup rotObjectBG = new BranchGroup(); + OrderedGroup staticObjectOG = new OrderedGroup(); + BranchGroup lampsBG = new BranchGroup(); + OrderedGroup oGroup = new OrderedGroup(); + TransformGroup staticBoxRotTG = new TransformGroup(); + staticBoxRotTG.addChild(staticObjectOG); + TransformGroup objectsTGRot = new TransformGroup(); + TransformGroup objectsTGTrans = new TransformGroup(); + Transform3D objectsTGTransT3d = new Transform3D(); + objectsTGTransT3d.setTranslation(new Vector3f(0.0f, 0.0f, -10.0f)); + objectsTGTrans.setTransform(objectsTGTransT3d); + objectsTGRot.addChild(oGroup); + objectsTGTrans.addChild(objectsTGRot); + lampsBG.addChild(objectsTGTrans); + + //adding a sphere as backgroung so there is something else than flat black, and cut cube removal as an other implication. (seeing through) + Appearance globalSphereAppearance = new SimpleShaderAppearance(true, false); + PolygonAttributes globalSpherePA = new PolygonAttributes(); + globalSpherePA.setCullFace(PolygonAttributes.CULL_FRONT);// so that interior of the sphere is visible. + Material globalSphereMaterial = new Material(); + globalSphereMaterial.setEmissiveColor(.25f, .3f, .35f); + globalSphereAppearance.setMaterial(globalSphereMaterial); + globalSphereAppearance.setPolygonAttributes(globalSpherePA); + Sphere globalSphere = new Sphere(6.0f); + globalSphere.setAppearance(globalSphereAppearance); + globalSphere.setBounds(bounds); + oGroup.addChild(globalSphere); + + globalBG.addChild(lampsBG); + + // adding lamps. + PointLight frontLamp = new PointLight(new Color3f(1.0f, 1.0f, 1.0f), new Point3f(20, 20, 20), new Point3f(0.0f, .0f, 0.f)); + lampsBG.addChild(frontLamp); + frontLamp.setBounds(bounds); + frontLamp.setInfluencingBounds(bounds); + PointLight backLamp = new PointLight(new Color3f(1.0f, .0f, .0f), new Point3f(-20, -20, -20), new Point3f(0.0f, .0f, 0.f)); + lampsBG.addChild(backLamp); + backLamp.setBounds(bounds); + backLamp.setInfluencingBounds(bounds); + + //adding shapes. + { + //adding rotating and scaling cube + //doing the rotation + TransformGroup rotBoxTGRot = new TransformGroup(); + rotBoxTGRot.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + RotationInterpolator rotBoxRotInt = new RotationInterpolator(new Alpha(-1, 20000), rotBoxTGRot); + rotBoxRotInt.setSchedulingBounds(bounds); + rotBoxRotInt.setBounds(bounds); + + //doing the scaling + //Transform3D scaleBoxt3d = new Transform3D(); + TransformGroup rotBoxTGScale = new TransformGroup(); + rotBoxTGScale.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + ScaleInterpolator rotBoxScaleInt = new ScaleInterpolator( + new Alpha(-1, Alpha.INCREASING_ENABLE | Alpha.DECREASING_ENABLE, 0, 0, 3000, 1500, 0, 3000, 1500, 0), rotBoxTGScale, + new Transform3D(), 0.7f, 1.6f); + rotBoxScaleInt.setSchedulingBounds(bounds); + rotBoxScaleInt.setBounds(bounds); + + Appearance rotBoxApp = new SimpleShaderAppearance(false, false); + Material rotBoxMat = new Material(); + rotBoxMat.setDiffuseColor(.4f, .4f, .4f); + rotBoxApp.setMaterial(rotBoxMat); + Cube rotBox = new Cube(1.1f / 2, 1.1f / 2, 1.1f / 2); + rotBox.setAppearance(rotBoxApp); + rotBoxTGScale.addChild(rotBox); + rotBoxTGRot.addChild(rotBoxTGScale); + TransformGroup rotBoxTG = new TransformGroup(); + rotBoxTG.addChild(rotBoxTGRot); + rotObjectBG.addChild(rotBoxTG); + rotObjectBG.addChild(rotBoxScaleInt); + rotObjectBG.addChild(rotBoxRotInt); + rotBox.setBounds(bounds); + + rotatingBoxRA = new RenderingAttributes(); + //Raster Ops are not availible in GL2ES2 + // rotatingBoxRA.setRasterOpEnable( true ); + rotatingBoxRA.setCapability(RenderingAttributes.ALLOW_RASTER_OP_WRITE); + // rotatingBoxRA.setRasterOp( rotatingBoxRA.ROP_XOR ); + rotBoxApp.setRenderingAttributes(rotatingBoxRA); + + rotBox.setAppearance(rotBoxApp); + } + + //adding static back face wireframe cube + { + Cube staticWFBoxBack = new Cube(); + Appearance staticWFBoxApp = new SimpleShaderAppearance(false, false); + Material staticWFBoxMat = new Material(); + staticWFBoxMat.setDiffuseColor(0.f, 0.f, 0.f); + staticWFBoxMat.setEmissiveColor(0.f, .4f, 0.f); + staticWFBoxApp.setMaterial(staticWFBoxMat); + PolygonAttributes staticWFBoxPABack = new PolygonAttributes(PolygonAttributes.POLYGON_LINE, PolygonAttributes.CULL_FRONT, 0.0f); + staticWFBoxApp.setPolygonAttributes(staticWFBoxPABack); + staticWFBoxRA = new RenderingAttributes(); + staticWFBoxRA.setCapability(RenderingAttributes.ALLOW_DEPTH_TEST_FUNCTION_WRITE); + staticWFBoxRA.setCapability(RenderingAttributes.ALLOW_DEPTH_ENABLE_WRITE); + staticWFBoxRA.setDepthTestFunction(RenderingAttributes.GREATER); + staticWFBoxRA.setDepthBufferWriteEnable(false); + staticWFBoxApp.setRenderingAttributes(staticWFBoxRA); + staticWFBoxBack.setAppearance(staticWFBoxApp); + staticWFBoxBack.setBounds(bounds); + staticObjectOG.addChild(staticWFBoxBack); + } + + //adding static front face wireframe cube + { + Cube staticWFBox = new Cube(); + Appearance staticWFBoxApp = new SimpleShaderAppearance(false, false); + Material staticWFBoxMat = new Material(); + staticWFBoxMat.setDiffuseColor(0.f, 0.f, 0.f); + staticWFBoxMat.setEmissiveColor(0.f, 1.f, 0.f); + staticWFBoxApp.setMaterial(staticWFBoxMat); + PolygonAttributes staticWFBoxPA = new PolygonAttributes(PolygonAttributes.POLYGON_LINE, PolygonAttributes.CULL_BACK, 0.0f); + staticWFBoxApp.setPolygonAttributes(staticWFBoxPA); + staticWFBoxApp.setRenderingAttributes(staticWFBoxRA); + staticWFBox.setAppearance(staticWFBoxApp); + staticWFBox.setBounds(bounds); + staticObjectOG.addChild(staticWFBox); + } + + {// rotating the static cubes + Transform3D boxt3d = new Transform3D(); + Transform3D tempt3d = new Transform3D(); + boxt3d.rotZ(Math.PI / 4.0f); + tempt3d.rotX(Math.PI / 4.0f); + boxt3d.mul(tempt3d); + tempt3d.rotY(Math.PI / 4.0f); + boxt3d.mul(tempt3d); + staticBoxRotTG.setTransform(boxt3d); + } + + // adding static flat cube + { + Cube staticBox = new Cube(); + staticBox.setBounds(bounds); + Appearance boxApp = new SimpleShaderAppearance(false, false); + Material boxMat = new Material(); + boxMat.setDiffuseColor(.7f, .7f, .7f); + boxApp.setMaterial(boxMat); + staticBoxRA = new RenderingAttributes(); + staticBoxRA.setCapability(RenderingAttributes.ALLOW_DEPTH_TEST_FUNCTION_WRITE); + staticBoxRA.setCapability(RenderingAttributes.ALLOW_DEPTH_ENABLE_WRITE); + staticBoxRA.setDepthTestFunction(RenderingAttributes.LESS); + staticBoxRA.setDepthBufferWriteEnable(false); + boxApp.setRenderingAttributes(staticBoxRA); + staticBox.setAppearance(boxApp); + staticObjectOG.addChild(staticBox); + } + oGroup.addChild(rotObjectBG); + oGroup.addChild(staticBoxRotTG); + + //adding the mouse rotate behavior to the group of cubes. + MouseRotate behavior = new MouseRotate(); + behavior.setTransformGroup(objectsTGRot); + objectsTGRot.addChild(behavior); + objectsTGRot.setCapability(TransformGroup.ALLOW_TRANSFORM_READ); + objectsTGRot.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + behavior.setSchedulingBounds(bounds); + return globalBG; + } + + public void setStaticWFObjectTestFunc(int func) + { + staticWFBoxRA.setDepthTestFunction(func); + } + + public void setStaticObjectTestFunc(int func) + { + staticBoxRA.setDepthTestFunction(func); + } + + public void setStaticWFObjectDBWriteStatus(boolean status) + { + staticWFBoxRA.setDepthBufferWriteEnable(status); + } + + public void setStaticObjectDBWriteStatus(boolean status) + { + staticBoxRA.setDepthBufferWriteEnable(status); + } + + public void setRotatingObjectROPMode(int mode) + { + //Raster Ops are not availible in GL2ES2 + //rotatingBoxRA.setRasterOp( mode ); + } + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/distort_glyph/DistortBehavior.java b/src/main/java/org/jdesktop/j3d/examples/distort_glyph/DistortBehavior.java new file mode 100644 index 0000000..3ba873f --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/distort_glyph/DistortBehavior.java @@ -0,0 +1,193 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.distort_glyph; + +import java.util.Enumeration; + +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.Behavior; +import org.jogamp.java3d.GeometryArray; +import org.jogamp.java3d.Shape3D; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.WakeupCondition; +import org.jogamp.java3d.WakeupCriterion; +import org.jogamp.java3d.WakeupOnElapsedFrames; +import org.jogamp.java3d.WakeupOnElapsedTime; +import org.jogamp.vecmath.Vector3f; + +public class DistortBehavior extends Behavior { + // the wake up condition for the behavior + protected WakeupCondition m_InitialWakeupCondition = null; + protected WakeupCondition m_FrameWakeupCondition = null; + + // the GeometryArray for the Shape3D that we are modifying + protected Shape3D m_Shape3D = null; + protected GeometryArray m_GeometryArray = null; + + protected float[] m_CoordinateArray = null; + protected float[] m_OriginalCoordinateArray = null; + protected Appearance m_Appearance = null; + + protected int m_nElapsedTime = 0; + protected int m_nNumFrames = 0; + protected int m_nFrameNumber = 0; + + private int frame = 0; + protected Vector3f m_Vector = null; + + public DistortBehavior(Shape3D shape3D, int nElapsedTime, int nNumFrames) { + // allocate a temporary vector + m_Vector = new Vector3f(); + + m_FrameWakeupCondition = new WakeupOnElapsedFrames(0); + + restart(shape3D, nElapsedTime, nNumFrames); + } + + public WakeupCondition restart(Shape3D shape3D, int nElapsedTime, int nNumFrames) { + m_Shape3D = shape3D; + m_nElapsedTime = nElapsedTime; + m_nNumFrames = nNumFrames; + m_nFrameNumber = 0; + + // create the WakeupCriterion for the behavior + m_InitialWakeupCondition = new WakeupOnElapsedTime(m_nElapsedTime); + + // save the GeometryArray that we are modifying + m_GeometryArray = (GeometryArray) m_Shape3D.getGeometry(); + + if (m_Shape3D.isLive() == false && m_Shape3D.isCompiled() == false) { + // set the capability bits that the behavior requires + m_Shape3D.setCapability(Shape3D.ALLOW_APPEARANCE_READ); + m_Shape3D.setCapability(Shape3D.ALLOW_APPEARANCE_WRITE); + + m_Shape3D.getAppearance().setCapability(Appearance.ALLOW_POINT_ATTRIBUTES_WRITE); + m_Shape3D.getAppearance().setCapability(Appearance.ALLOW_POLYGON_ATTRIBUTES_WRITE); + m_Shape3D.getAppearance().setCapability(Appearance.ALLOW_TRANSPARENCY_ATTRIBUTES_WRITE); + m_Shape3D.getAppearance().setCapability(Appearance.ALLOW_TEXTURE_WRITE); + + m_GeometryArray.setCapability(GeometryArray.ALLOW_COORDINATE_READ); + m_GeometryArray.setCapability(GeometryArray.ALLOW_COORDINATE_WRITE); + m_GeometryArray.setCapability(GeometryArray.ALLOW_COUNT_READ); + } + + // make a copy of the object's original appearance + m_Appearance = new Appearance(); + m_Appearance = (Appearance) m_Shape3D.getAppearance().cloneNodeComponent(true); + + // allocate an array for the model coordinates + m_CoordinateArray = new float[3 * m_GeometryArray.getVertexCount()]; + + // make a copy of the models original coordinates + m_OriginalCoordinateArray = new float[3 * m_GeometryArray.getVertexCount()]; + m_GeometryArray.getCoordinates(0, m_OriginalCoordinateArray); + + // start (or restart) the behavior + setEnable(true); + + return m_InitialWakeupCondition; + } + + public void initialize() { + // apply the initial WakeupCriterion + wakeupOn(m_InitialWakeupCondition); + } + + public void processStimulus(Enumeration criteria) { + while (criteria.hasMoreElements()) { + WakeupCriterion wakeUp = (WakeupCriterion) criteria.nextElement(); + + if (wakeUp instanceof WakeupOnElapsedTime) { + } else { + // we are mid explosion, modify the GeometryArray + m_nFrameNumber++; + frame++; + m_GeometryArray.getCoordinates(0, m_CoordinateArray); + + Transform3D t3 = new Transform3D(); + for (int n = 0; n < m_CoordinateArray.length; n += 3) { + m_Vector.x = m_OriginalCoordinateArray[n]; + m_Vector.y = m_OriginalCoordinateArray[n + 1]; + m_Vector.z = m_OriginalCoordinateArray[n + 2]; + + float spx = (float) (Math.sin(frame *3f / 500)); + float spy = (float) (Math.cos(frame *5f / 500)); + Vector3f v = new Vector3f(spx, spy, 0); + + float px = (m_Vector.x - v.x); + float py = (m_Vector.y - v.y); + float pz = (m_Vector.z - v.z); + float d = (float) Math.sqrt(px * px + py * py + pz * pz); + + + m_Vector.add(new Vector3f(-.25f, -.25f, -.25f)); + //m_Vector.scale(d); + + t3.rotZ(d); + t3.rotX(d*2); + t3.rotY(d); + t3.transform(m_Vector); + + m_CoordinateArray[n] = m_Vector.x; + m_CoordinateArray[n + 1] = m_Vector.y; + m_CoordinateArray[n + 2] = m_Vector.z; + + } + + // assign the new coordinates + m_GeometryArray.setCoordinates(0, m_CoordinateArray); + } + } + + if (m_nFrameNumber < m_nNumFrames) { + // assign the next WakeUpCondition, so we are notified again + wakeupOn(m_FrameWakeupCondition); + } else { + // restart + m_nFrameNumber = 0; + wakeupOn(m_FrameWakeupCondition); + } + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/distort_glyph/DistortGlyphTest.form b/src/main/java/org/jdesktop/j3d/examples/distort_glyph/DistortGlyphTest.form new file mode 100644 index 0000000..22838dc --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/distort_glyph/DistortGlyphTest.form @@ -0,0 +1,36 @@ +<?xml version="1.0" encoding="UTF-8" ?> + +<Form version="1.0" type="org.netbeans.modules.form.forminfo.JFrameFormInfo"> + <Properties> + <Property name="defaultCloseOperation" type="int" value="3"/> + <Property name="title" type="java.lang.String" value="DistortGlyphTest"/> + </Properties> + <SyntheticProperties> + <SyntheticProperty name="formSizePolicy" type="int" value="1"/> + </SyntheticProperties> + <AuxValues> + <AuxValue name="FormSettings_generateMnemonicsCode" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_listenerGenerationStyle" type="java.lang.Integer" value="0"/> + <AuxValue name="FormSettings_variablesLocal" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_variablesModifier" type="java.lang.Integer" value="2"/> + <AuxValue name="designerSize" type="java.awt.Dimension" value="-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,1,44,0,0,1,-112"/> + </AuxValues> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + <SubComponents> + <Container class="javax.swing.JPanel" name="drawingPanel"> + <Properties> + <Property name="preferredSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor"> + <Dimension value="[700, 700]"/> + </Property> + </Properties> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout" value="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription"> + <BorderConstraints direction="Center"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + </Container> + </SubComponents> +</Form> diff --git a/src/main/java/org/jdesktop/j3d/examples/distort_glyph/DistortGlyphTest.java b/src/main/java/org/jdesktop/j3d/examples/distort_glyph/DistortGlyphTest.java new file mode 100644 index 0000000..cf88439 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/distort_glyph/DistortGlyphTest.java @@ -0,0 +1,254 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.distort_glyph; + +import java.awt.Font; +import java.awt.GraphicsConfiguration; +import java.awt.GraphicsEnvironment; + +import org.jdesktop.j3d.examples.Resources; +import org.jogamp.java3d.AmbientLight; +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.DirectionalLight; +import org.jogamp.java3d.Font3D; +import org.jogamp.java3d.FontExtrusion; +import org.jogamp.java3d.GeometryArray; +import org.jogamp.java3d.GraphicsConfigTemplate3D; +import org.jogamp.java3d.Light; +import org.jogamp.java3d.Material; +import org.jogamp.java3d.PointLight; +import org.jogamp.java3d.Shape3D; +import org.jogamp.java3d.TexCoordGeneration; +import org.jogamp.java3d.Texture; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.utils.behaviors.mouse.MouseRotate; +import org.jogamp.java3d.utils.behaviors.mouse.MouseTranslate; +import org.jogamp.java3d.utils.behaviors.mouse.MouseZoom; +import org.jogamp.java3d.utils.image.TextureLoader; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Point3f; +import org.jogamp.vecmath.Vector3f; + +public class DistortGlyphTest extends javax.swing.JFrame { + + private SimpleUniverse univ = null; + private BranchGroup scene = null; + + // get a nice graphics config + private static GraphicsConfiguration getGraphicsConfig() { + GraphicsConfigTemplate3D template = new GraphicsConfigTemplate3D(); + template.setSceneAntialiasing(GraphicsConfigTemplate3D.PREFERRED); + GraphicsConfiguration gcfg = GraphicsEnvironment.getLocalGraphicsEnvironment().getDefaultScreenDevice().getBestConfiguration(template); + return gcfg; + } + + private void setupLights(BranchGroup root) { + // set up the BoundingSphere for all the lights + BoundingSphere bounds = new BoundingSphere(new Point3d(), 100.0); + + // Set up the ambient light + AmbientLight lightAmbient = new AmbientLight(new Color3f(0.37f, 0.37f, 0.37f)); + lightAmbient.setInfluencingBounds(bounds); + root.addChild(lightAmbient); + + // Set up the directional light + Vector3f lightDirection1 = new Vector3f(0.0f, 0.0f, -1.0f); + DirectionalLight lightDirectional1 = new DirectionalLight(new Color3f(1.00f, 0.10f, 0.00f), lightDirection1); + lightDirectional1.setInfluencingBounds(bounds); + lightDirectional1.setCapability(Light.ALLOW_STATE_WRITE); + root.addChild(lightDirectional1); + + Point3f lightPos1 = new Point3f(-4.0f, 8.0f, 16.0f); + Point3f lightAttenuation1 = new Point3f(1.0f, 0.0f, 0.0f); + PointLight pointLight1 = new PointLight(new Color3f(0.37f, 1.00f, 0.37f), lightPos1, lightAttenuation1); + pointLight1.setInfluencingBounds(bounds); + root.addChild(pointLight1); + + Point3f lightPos2 = new Point3f(-16.0f, 8.0f, 4.0f); + Point3f lightAttenuation2 = new Point3f(1.0f, 0.0f, 0.0f); + PointLight pointLight2 = new PointLight(new Color3f(0.37f, 0.37f, 1.00f), lightPos2, lightAttenuation2); + pointLight2.setInfluencingBounds(bounds); + root.addChild(pointLight2); + } + + public BranchGroup createSceneGraph() { + // Create the root of the branch graph + BranchGroup objRoot = new BranchGroup(); + + setupLights(objRoot); + + TransformGroup objTransform = new TransformGroup(); + objTransform.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + objTransform.setCapability(TransformGroup.ALLOW_TRANSFORM_READ); + + objRoot.addChild(objTransform); + + // setup a nice textured appearance + Appearance app = new Appearance(); + Color3f objColor = new Color3f(1.0f, 0.7f, 0.8f); + Color3f black = new Color3f(0.0f, 0.0f, 0.0f); + app.setMaterial(new Material(objColor, black, objColor, black, 80.0f)); + Texture txtr = new TextureLoader(Resources.getResource("resources/images/gold.jpg"),this).getTexture(); + app.setTexture(txtr); + TexCoordGeneration tcg = new TexCoordGeneration(TexCoordGeneration.SPHERE_MAP,TexCoordGeneration.TEXTURE_COORDINATE_2); + app.setTexCoordGeneration(tcg); + + // use a customized FontExtrusion object to control the depth of the text + java.awt.geom.GeneralPath gp = new java.awt.geom.GeneralPath(); + gp.moveTo(0, 0); + gp.lineTo(.01f, .01f); + gp.lineTo(.2f, .01f); + gp.lineTo(.21f, 0f); + FontExtrusion fontEx = new FontExtrusion(gp); + + // our glyph + Font fnt = new Font("dialog", Font.BOLD, 1); + Font3D f3d = new Font3D(fnt, .001, fontEx); + GeometryArray geom = f3d.getGlyphGeometry('A'); + Shape3D shape = new Shape3D(geom, app); + objTransform.addChild(shape); + + // the DistortBehavior + DistortBehavior eb = new DistortBehavior(shape, 1000, 1000); + eb.setSchedulingBounds(new BoundingSphere()); + objTransform.addChild(eb); + + MouseRotate myMouseRotate = new MouseRotate(); + myMouseRotate.setTransformGroup(objTransform); + myMouseRotate.setSchedulingBounds(new BoundingSphere()); + objRoot.addChild(myMouseRotate); + + MouseTranslate myMouseTranslate = new MouseTranslate(); + myMouseTranslate.setTransformGroup(objTransform); + myMouseTranslate.setSchedulingBounds(new BoundingSphere()); + objRoot.addChild(myMouseTranslate); + + MouseZoom myMouseZoom = new MouseZoom(); + myMouseZoom.setTransformGroup(objTransform); + myMouseZoom.setSchedulingBounds(new BoundingSphere()); + objRoot.addChild(myMouseZoom); + + // Let Java 3D perform optimizations on this scene graph. + objRoot.compile(); + + return objRoot; + } + + private Canvas3D createUniverse() { + + // Create a Canvas3D using a nice configuration + Canvas3D c = new Canvas3D(getGraphicsConfig()); + + // Create simple universe with view branch + univ = new SimpleUniverse(c); + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + univ.getViewingPlatform().setNominalViewingTransform(); + + // Ensure at least 5 msec per frame (i.e., < 200Hz) + univ.getViewer().getView().setMinimumFrameCycleTime(5); + + return c; + } + + /** + * Creates new form DistortGlyphTest2 + */ + public DistortGlyphTest() { + // Initialize the GUI components + initComponents(); + + // Create Canvas3D and SimpleUniverse; add canvas to drawing panel + Canvas3D c = createUniverse(); + drawingPanel.add(c, java.awt.BorderLayout.CENTER); + + // Create the content branch and add it to the universe + scene = createSceneGraph(); + univ.addBranchGraph(scene); + } + + // ---------------------------------------------------------------- + + /** This method is called from within the constructor to + * initialize the form. + * WARNING: Do NOT modify this code. The content of this method is + * always regenerated by the Form Editor. + */ + // <editor-fold defaultstate="collapsed" desc=" Generated Code ">//GEN-BEGIN:initComponents + private void initComponents() { + drawingPanel = new javax.swing.JPanel(); + + setDefaultCloseOperation(javax.swing.WindowConstants.EXIT_ON_CLOSE); + setTitle("DistortGlyphTest"); + drawingPanel.setLayout(new java.awt.BorderLayout()); + + drawingPanel.setPreferredSize(new java.awt.Dimension(700, 700)); + getContentPane().add(drawingPanel, java.awt.BorderLayout.CENTER); + + pack(); + }// </editor-fold>//GEN-END:initComponents + + /** + * @param args the command line arguments + */ + public static void main(String args[]) {System.setProperty("sun.awt.noerasebackground", "true"); + java.awt.EventQueue.invokeLater(new Runnable() { + public void run() { + new DistortGlyphTest().setVisible(true); + } + }); + } + + // Variables declaration - do not modify//GEN-BEGIN:variables + private javax.swing.JPanel drawingPanel; + // End of variables declaration//GEN-END:variables + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/distort_glyph/DistortGlyphTestGL2ES2.java b/src/main/java/org/jdesktop/j3d/examples/distort_glyph/DistortGlyphTestGL2ES2.java new file mode 100644 index 0000000..c92725a --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/distort_glyph/DistortGlyphTestGL2ES2.java @@ -0,0 +1,324 @@ +/* + * Copyright (c) 2016 JogAmp Community. All rights reserved. + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * This code is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 only, as + * published by the Free Software Foundation. Sun designates this + * particular file as subject to the "Classpath" exception as provided + * by Sun in the LICENSE file that accompanied this code. + * + * This code is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + * version 2 for more details (a copy is included in the LICENSE file that + * accompanied this code). + * + * You should have received a copy of the GNU General Public License version + * 2 along with this work; if not, write to the Free Software Foundation, + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. + * + */ + +package org.jdesktop.j3d.examples.distort_glyph; + +import java.awt.Font; +import java.awt.GraphicsConfiguration; +import java.awt.GraphicsEnvironment; + +import org.jdesktop.j3d.examples.Resources; + +import org.jogamp.java3d.AmbientLight; +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.DirectionalLight; +import org.jogamp.java3d.Font3D; +import org.jogamp.java3d.FontExtrusion; +import org.jogamp.java3d.GLSLShaderProgram; +import org.jogamp.java3d.GeometryArray; +import org.jogamp.java3d.GraphicsConfigTemplate3D; +import org.jogamp.java3d.Light; +import org.jogamp.java3d.Material; +import org.jogamp.java3d.PointLight; +import org.jogamp.java3d.Shader; +import org.jogamp.java3d.ShaderAppearance; +import org.jogamp.java3d.ShaderAttributeSet; +import org.jogamp.java3d.ShaderAttributeValue; +import org.jogamp.java3d.Shape3D; +import org.jogamp.java3d.SourceCodeShader; +import org.jogamp.java3d.TexCoordGeneration; +import org.jogamp.java3d.Texture; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.utils.behaviors.mouse.MouseRotate; +import org.jogamp.java3d.utils.behaviors.mouse.MouseTranslate; +import org.jogamp.java3d.utils.behaviors.mouse.MouseZoom; +import org.jogamp.java3d.utils.image.TextureLoader; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Point3f; +import org.jogamp.vecmath.Vector3f; + +public class DistortGlyphTestGL2ES2 extends javax.swing.JFrame +{ + + private SimpleUniverse univ = null; + private BranchGroup scene = null; + + // get a nice graphics config + private static GraphicsConfiguration getGraphicsConfig() + { + GraphicsConfigTemplate3D template = new GraphicsConfigTemplate3D(); + template.setSceneAntialiasing(GraphicsConfigTemplate3D.PREFERRED); + GraphicsConfiguration gcfg = GraphicsEnvironment.getLocalGraphicsEnvironment().getDefaultScreenDevice() + .getBestConfiguration(template); + return gcfg; + } + + private void setupLights(BranchGroup root) + { + // set up the BoundingSphere for all the lights + BoundingSphere bounds = new BoundingSphere(new Point3d(), 100.0); + + // Set up the ambient light + AmbientLight lightAmbient = new AmbientLight(new Color3f(0.37f, 0.37f, 0.37f)); + lightAmbient.setInfluencingBounds(bounds); + root.addChild(lightAmbient); + + // Set up the directional light + Vector3f lightDirection1 = new Vector3f(0.0f, 0.0f, -1.0f); + DirectionalLight lightDirectional1 = new DirectionalLight(new Color3f(1.00f, 0.10f, 0.00f), lightDirection1); + lightDirectional1.setInfluencingBounds(bounds); + lightDirectional1.setCapability(Light.ALLOW_STATE_WRITE); + root.addChild(lightDirectional1); + + Point3f lightPos1 = new Point3f(-4.0f, 8.0f, 16.0f); + Point3f lightAttenuation1 = new Point3f(1.0f, 0.0f, 0.0f); + PointLight pointLight1 = new PointLight(new Color3f(0.37f, 1.00f, 0.37f), lightPos1, lightAttenuation1); + pointLight1.setInfluencingBounds(bounds); + root.addChild(pointLight1); + + Point3f lightPos2 = new Point3f(-16.0f, 8.0f, 4.0f); + Point3f lightAttenuation2 = new Point3f(1.0f, 0.0f, 0.0f); + PointLight pointLight2 = new PointLight(new Color3f(0.37f, 0.37f, 1.00f), lightPos2, lightAttenuation2); + pointLight2.setInfluencingBounds(bounds); + root.addChild(pointLight2); + } + + public BranchGroup createSceneGraph() + { + // Create the root of the branch graph + BranchGroup objRoot = new BranchGroup(); + + setupLights(objRoot); + + TransformGroup objTransform = new TransformGroup(); + objTransform.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + objTransform.setCapability(TransformGroup.ALLOW_TRANSFORM_READ); + + objRoot.addChild(objTransform); + + // setup a nice textured appearance + Appearance app = makeShaderAppearance(); + Color3f objColor = new Color3f(1.0f, 0.7f, 0.8f); + Color3f black = new Color3f(0.0f, 0.0f, 0.0f); + app.setMaterial(new Material(objColor, black, objColor, black, 80.0f)); + Texture txtr = new TextureLoader(Resources.getResource("resources/images/gold.jpg"), this).getTexture(); + app.setTexture(txtr); + // done in shader see makeShaderAppearance() below + //TexCoordGeneration tcg = new TexCoordGeneration(TexCoordGeneration.SPHERE_MAP, TexCoordGeneration.TEXTURE_COORDINATE_2); + //app.setTexCoordGeneration(tcg); + + // use a customized FontExtrusion object to control the depth of the text + java.awt.geom.GeneralPath gp = new java.awt.geom.GeneralPath(); + gp.moveTo(0, 0); + gp.lineTo(.01f, .01f); + gp.lineTo(.2f, .01f); + gp.lineTo(.21f, 0f); + FontExtrusion fontEx = new FontExtrusion(gp); + + // our glyph + Font fnt = new Font("dialog", Font.BOLD, 1); + Font3D f3d = new Font3D(fnt, .001, fontEx); + GeometryArray geom = f3d.getGlyphGeometry('A'); + Shape3D shape = new Shape3D(geom, app); + objTransform.addChild(shape); + + // the DistortBehavior + DistortBehavior eb = new DistortBehavior(shape, 1000, 1000); + eb.setSchedulingBounds(new BoundingSphere()); + objTransform.addChild(eb); + + MouseRotate myMouseRotate = new MouseRotate(); + myMouseRotate.setTransformGroup(objTransform); + myMouseRotate.setSchedulingBounds(new BoundingSphere()); + objRoot.addChild(myMouseRotate); + + MouseTranslate myMouseTranslate = new MouseTranslate(); + myMouseTranslate.setTransformGroup(objTransform); + myMouseTranslate.setSchedulingBounds(new BoundingSphere()); + objRoot.addChild(myMouseTranslate); + + MouseZoom myMouseZoom = new MouseZoom(); + myMouseZoom.setTransformGroup(objTransform); + myMouseZoom.setSchedulingBounds(new BoundingSphere()); + objRoot.addChild(myMouseZoom); + + // Let Java 3D perform optimizations on this scene graph. + objRoot.compile(); + + return objRoot; + } + + private Canvas3D createUniverse() + { + + // Create a Canvas3D using a nice configuration + Canvas3D c = new Canvas3D(getGraphicsConfig()); + + // Create simple universe with view branch + univ = new SimpleUniverse(c); + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + univ.getViewingPlatform().setNominalViewingTransform(); + + // Ensure at least 5 msec per frame (i.e., < 200Hz) + univ.getViewer().getView().setMinimumFrameCycleTime(5); + + return c; + } + + /** + * Creates new form DistortGlyphTest2 + */ + public DistortGlyphTestGL2ES2() + { + // Initialize the GUI components + initComponents(); + + // Create Canvas3D and SimpleUniverse; add canvas to drawing panel + Canvas3D c = createUniverse(); + drawingPanel.add(c, java.awt.BorderLayout.CENTER); + + // Create the content branch and add it to the universe + scene = createSceneGraph(); + univ.addBranchGraph(scene); + } + + // ---------------------------------------------------------------- + + /** This method is called from within the constructor to + * initialize the form. + * WARNING: Do NOT modify this code. The content of this method is + * always regenerated by the Form Editor. + */ + // <editor-fold defaultstate="collapsed" desc=" Generated Code ">//GEN-BEGIN:initComponents + private void initComponents() + { + drawingPanel = new javax.swing.JPanel(); + + setDefaultCloseOperation(javax.swing.WindowConstants.EXIT_ON_CLOSE); + setTitle("DistortGlyphTest"); + drawingPanel.setLayout(new java.awt.BorderLayout()); + + drawingPanel.setPreferredSize(new java.awt.Dimension(700, 700)); + getContentPane().add(drawingPanel, java.awt.BorderLayout.CENTER); + + pack(); + }// </editor-fold>//GEN-END:initComponents + + /** + * @param args the command line arguments + */ + public static void main(String args[]) + { + System.setProperty("sun.awt.noerasebackground", "true"); + System.setProperty("j3d.rend", "jogl2es2"); + System.setProperty("j3d.displaylist", "false"); + java.awt.EventQueue.invokeLater(new Runnable() { + public void run() + { + new DistortGlyphTestGL2ES2().setVisible(true); + } + }); + } + + // Variables declaration - do not modify//GEN-BEGIN:variables + private javax.swing.JPanel drawingPanel; + // End of variables declaration//GEN-END:variables + + public static ShaderAppearance makeShaderAppearance() + { + ShaderAppearance app = new ShaderAppearance(); + GLSLShaderProgram litTextureShaderProgram = new GLSLShaderProgram() { + @Override + public String toString() + { + return "SimpleShaderAppearance litTextureShaderProgram"; + } + }; + litTextureShaderProgram.setShaders(makeShaders(vertShader, fragShader)); + litTextureShaderProgram.setShaderAttrNames(new String[] { "EnvMap" }); + + app.setShaderProgram(litTextureShaderProgram); + + ShaderAttributeSet shaderAttributeSet = new ShaderAttributeSet(); + shaderAttributeSet.put(new ShaderAttributeValue("EnvMap", new Integer(0))); + app.setShaderAttributeSet(shaderAttributeSet); + return app; + } + + private static Shader[] makeShaders(String vertexProgram, String fragmentProgram) + { + Shader[] shaders = new Shader[2]; + shaders[0] = new SourceCodeShader(Shader.SHADING_LANGUAGE_GLSL, Shader.SHADER_TYPE_VERTEX, vertexProgram) { + @Override + public String toString() + { + return "vertexProgram"; + } + }; + shaders[1] = new SourceCodeShader(Shader.SHADING_LANGUAGE_GLSL, Shader.SHADER_TYPE_FRAGMENT, fragmentProgram) { + @Override + public String toString() + { + return "fragmentProgram"; + } + }; + return shaders; + } + + public static String fragShader = "uniform sampler2D EnvMap;\n" + // + "varying vec2 texCoord0;\n" + // + "void main (void)\n" + // + "{\n" + // + " vec2 tc0 = texCoord0.xy;\n" + // + " vec3 color = vec3(texture2D(EnvMap, tc0));\n" + // + " gl_FragColor = vec4(color, 1.0);\n" + // + "}\n"; + + public static String vertShader = "attribute vec4 glVertex;\n" + // + "attribute vec3 glNormal; \n" + // + "uniform mat4 glModelViewProjectionMatrix;\n" + // + "uniform mat4 glModelViewMatrix;\n" + // + "uniform mat3 glNormalMatrix;\n" + // + "varying vec3 Normal;\n" + // + "varying vec2 texCoord0;\n" + // + "vec2 sphere_map(vec3 position, vec3 normal)\n" + // + "{\n" + // + " vec3 reflection = reflect(position, normal);\n" + // + " float m = 2.0 * sqrt(reflection.x * reflection.x + reflection.y * reflection.y + (reflection.z + 1.0) * (reflection.z + 1.0)); \n" + + // + " return vec2((reflection.x / m + 0.5), (reflection.y / m + 0.5));\n" + // + "}\n" + // + "void main()\n" + // + "{\n" + // + " Normal = normalize(vec3(glNormalMatrix * glNormal));\n" + // + " gl_Position = glModelViewProjectionMatrix * glVertex; \n" + // + " texCoord0 = sphere_map(normalize(vec3(glModelViewMatrix*glVertex)), Normal);\n" + // + "}\n"; // + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/dot3/Dot3Demo.java b/src/main/java/org/jdesktop/j3d/examples/dot3/Dot3Demo.java new file mode 100644 index 0000000..8e5ec84 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/dot3/Dot3Demo.java @@ -0,0 +1,548 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.dot3; + +import java.awt.BorderLayout; +import java.awt.Color; +import java.awt.Dimension; +import java.awt.Graphics2D; +import java.awt.GraphicsConfiguration; +import java.awt.image.BufferedImage; +import java.util.Enumeration; + +import javax.swing.JFrame; +import javax.swing.JPanel; + +import org.jdesktop.j3d.examples.Resources; +import org.jogamp.java3d.AmbientLight; +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.Background; +import org.jogamp.java3d.Behavior; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.DirectionalLight; +import org.jogamp.java3d.GeometryArray; +import org.jogamp.java3d.ImageComponent2D; +import org.jogamp.java3d.Material; +import org.jogamp.java3d.PolygonAttributes; +import org.jogamp.java3d.Shape3D; +import org.jogamp.java3d.TexCoordGeneration; +import org.jogamp.java3d.Texture; +import org.jogamp.java3d.Texture2D; +import org.jogamp.java3d.TextureAttributes; +import org.jogamp.java3d.TextureUnitState; +import org.jogamp.java3d.WakeupOnElapsedFrames; +import org.jogamp.java3d.utils.behaviors.vp.OrbitBehavior; +import org.jogamp.java3d.utils.geometry.GeometryInfo; +import org.jogamp.java3d.utils.image.TextureLoader; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.java3d.utils.universe.ViewingPlatform; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Vector3f; + +/** + * This example program is contributed by Alessandro Borges + */ + +/** + * <pre> + * DOT3 per-pixel lighting demo. + * It uses a Normal map and a Light map, both coded as independent textures. + * Each pixel color is a vector coded, where color range [0,255] is mapped + * as vector in range [-1.0,+1.0]. + * + * A math operation called DOT3 applied to Light vector and Normal vector results + * a scalar value, interpreted as light intensity. This operation is made for each + * pixel on texture. + * Light Intensity = DOT3(light, normal); + * + * This technique allows complex lighting effects, as bumps, on low polygon count + * geometries. + * </pre> + * + */ + +public class Dot3Demo extends JFrame { + // a external control panel for this demo + private TextureControlPanel ctrlPanel = null; + // default bounds used in this application + private BoundingSphere bounds = new BoundingSphere(new Point3d(0.0, 0.0, 0.0), + 100.0); + // TextureUnitStates used in this application + TextureUnitState tuLightMap; + TextureUnitState tuDOT3NormalMap; + TextureUnitState tuColor; + + /** Where the TUs are applied **/ + TextureUnitState[] tusArr; + /** appearance will be changed at runtime **/ + Appearance appearance; + /** polygonAttributes will be changed at runtime **/ + PolygonAttributes polygonAttributes; + + // textures used + Texture textureColor; + Texture textureDOT3NormalMap; + Texture2D textureLightMap; + // needs for runtime updates on lightMap + ImageComponent2D imageLightMap; + + // default texture names used + String textureColorName= "resources/images/wood.jpg"; + String textureDOT3NormalMapName = "resources/images/Java3Ddot3.jpg"; + + /** + * Constructor. + */ + public Dot3Demo() { + super("Java3D DOT3 demo"); + try { + init(); + } catch (Exception e) { + e.printStackTrace(); + } + } + + private void init() throws Exception { + this.setSize(new Dimension(400, 400)); + this.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); + + JPanel mainPanel = new JPanel(); + this.getContentPane().add(mainPanel, null); + mainPanel.setLayout(new BorderLayout()); + // get default configuration for 3D + GraphicsConfiguration conf = SimpleUniverse.getPreferredConfiguration(); + Canvas3D canvas = new Canvas3D(conf); + // create simpleUniverse + SimpleUniverse su = new SimpleUniverse(canvas); + // create sceneGraph and add it to universe + BranchGroup sceneGraph = createSceneGraph(); + su.addBranchGraph(sceneGraph); + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + su.getViewingPlatform().setNominalViewingTransform(); + + // Ensure at least 5 msec per frame (i.e., < 200Hz) + su.getViewer().getView().setMinimumFrameCycleTime(5); + + // add the behaviors to the ViewingPlatform + ViewingPlatform viewingPlatform = su.getViewingPlatform(); + viewingPlatform.setNominalViewingTransform(); + + // add orbit behavior to ViewingPlatform + OrbitBehavior orbit = new OrbitBehavior(canvas, OrbitBehavior.REVERSE_ALL | + OrbitBehavior.STOP_ZOOM); + orbit.setSchedulingBounds(bounds); + viewingPlatform.setViewPlatformBehavior(orbit); + + mainPanel.add(canvas, BorderLayout.CENTER); + this.setVisible(true); + //create a control panel to user interaction + ctrlPanel = new TextureControlPanel(this); + ctrlPanel.setVisible(true); + ctrlPanel.setLocation(410,10); + } + + /** + * loads all needed textures, and creates light map texture + */ + private void loadTextures() { + try { + //java.net.URL urlColor = new java.net.URL("file:" + textureColorName); + //java.net.URL urlDot3 = new java.net.URL("file:" + textureDOT3NormalMapName); + java.net.URL urlColor = Resources.getResource(textureColorName); + java.net.URL urlDot3 = Resources.getResource(textureDOT3NormalMapName); + + // loading textures + textureColor = new TextureLoader(urlColor,this).getTexture(); + textureDOT3NormalMap = new TextureLoader(urlDot3,this) .getTexture(); + + // create Image for textureLightMap + BufferedImage image = new BufferedImage(256,256,BufferedImage.TYPE_INT_RGB); + Graphics2D graphics = image.createGraphics(); + graphics.setPaint(new Color(130,130,250)); + graphics.fillRect(0,0,image.getWidth(),image.getHeight()); + graphics.dispose(); + + imageLightMap = new ImageComponent2D(ImageComponent2D.FORMAT_RGB,image,false,false); + imageLightMap.setCapability(ImageComponent2D.ALLOW_IMAGE_WRITE); + imageLightMap.setCapability(ImageComponent2D.ALLOW_IMAGE_READ); + + //create textureLightMap with above imageLightMap + textureLightMap = new Texture2D(Texture2D.BASE_LEVEL,Texture2D.RGB,256,256); + textureLightMap.setImage(0,imageLightMap); + textureLightMap.setMagFilter(Texture2D.NICEST); + textureLightMap.setMinFilter(Texture2D.NICEST); + + // application with update textureLightMap at runtime, so lets enable some caps + textureLightMap.setCapability(Texture2D.ALLOW_ENABLE_WRITE); + textureLightMap.setCapability(Texture2D.ALLOW_ENABLE_READ); + textureLightMap.setCapability(Texture2D.ALLOW_IMAGE_WRITE); + textureLightMap.setCapability(Texture2D.ALLOW_IMAGE_READ); + + } catch(Exception e) { + System.err.println("Failed to load textures"); + e.printStackTrace(); + } + } + + /** + * setup TextureUnitStates used in this demo. * + * @return + */ + private TextureUnitState[] setupTextureUnitState() { + //texture Attributes for DOT3 normal map + TextureAttributes textAttDot3 = new TextureAttributes(); + + + // lightMap uses TextureAttributes with default REPLACE mode + TextureAttributes textAttLightMap = new TextureAttributes(); + + TextureAttributes texAttColor = new TextureAttributes(); + texAttColor.setTextureMode(TextureAttributes.COMBINE); + + //CombineRgbMode could be also COMBINE_ADD or COMBINE_ADD_SIGNED, with + //different results + texAttColor.setCombineRgbMode(TextureAttributes.COMBINE_MODULATE); + // increase light depth effect + texAttColor.setCombineRgbScale(2); + + textAttDot3.setTextureMode(TextureAttributes.COMBINE); + textAttDot3.setCombineRgbMode(TextureAttributes.COMBINE_DOT3); + textAttDot3.setCombineAlphaMode(TextureAttributes.COMBINE_DOT3); + textAttDot3.setTextureBlendColor(1.f,1.0f,1.0f,0.0f); + // increase light intesity + textAttDot3.setCombineRgbScale(2); + // setup functions + textAttDot3.setCombineRgbFunction(0,TextureAttributes.COMBINE_SRC_COLOR); + textAttDot3.setCombineRgbFunction(1,TextureAttributes.COMBINE_SRC_COLOR); + textAttDot3.setCombineRgbFunction(2,TextureAttributes.COMBINE_SRC_COLOR); + //combine with previous TUS, lightMap + textAttDot3.setCombineRgbSource(0,TextureAttributes.COMBINE_PREVIOUS_TEXTURE_UNIT_STATE); + textAttDot3.setCombineRgbSource(1,TextureAttributes.COMBINE_TEXTURE_COLOR ); + textAttDot3.setCombineRgbSource(2,TextureAttributes.COMBINE_OBJECT_COLOR); + + TexCoordGeneration tcg1=null; + // SphereMap tcg can add nice dynamic effects for curved surfaces, because it + // distributes texture like a light bean over geometry. + // It os not used in this demo, but you can try yourself at home + // with *complex* lightmaps, i.e., spherical light distributions, + // multi light sorces, degradee, waves,etc + /* + tcg1 = new TexCoordGeneration(TexCoordGeneration.SPHERE_MAP, + TexCoordGeneration.TEXTURE_COORDINATE_3); + */ + + // create TUS + tuLightMap = new TextureUnitState(textureLightMap,textAttLightMap,tcg1); + tuDOT3NormalMap = new TextureUnitState(textureDOT3NormalMap,textAttDot3,null); + tuColor = new TextureUnitState(textureColor,texAttColor,null); + + // this TUS array is used by geometry at runtime + TextureUnitState[] tus = new TextureUnitState[3]; + tus[0] = tuLightMap; + tus[1] = tuDOT3NormalMap; + tus[2] = tuColor; + // enable texture units for read/write at runtime + for (int i = 0; i < tus.length; i++) { + tus[i].setCapability(TextureUnitState.ALLOW_STATE_WRITE); + tus[i].setCapability(TextureUnitState.ALLOW_STATE_READ); + } + + return tus; + } + + /** + * creates a single Quad geometry with 4 TextureCoordinateMaps, for multitexture use.<br> + * Dimension is scale*(2m , 1m) + * @param scale a scale for this quad + * @return quad geometry for multitexture use + */ + private GeometryArray createGeometry(float scale) { + // vertex coordinates + float[] verts = { 2.0f, -1.0f, 0.0f, + 2.0f, 1.0f, 0.0f, + -2.0f, 1.0f, 0.0f, + -2.0f, -1.0f, 0.0f }; + // 2D texture Coords - each texture unit will use one set of this + float[] texCoords = { 1.0f, 0.0f, + 1.0f, 1.0f, + 0.0f, 1.0f, + 0.0f, 0.0f}; + // all texture units will use texCoords from unit 0 + int[] texCoordSetMap = {0,0,0,0}; + // normals + Vector3f normal = new Vector3f( 0.0f, 0.0f, 1.0f); + Vector3f[] normals = { normal, normal, normal, normal} ; + // resize quad dimension + for(int i = 0;i<verts.length;i++) { + verts[i] *= scale; + } + // create geometry using GeometryInfo + GeometryInfo gi = new GeometryInfo(GeometryInfo.QUAD_ARRAY); + + gi.setCoordinates(verts); + gi.setNormals(normals); + // preparing for multitexture + // To get up to 4 TUS, it needs 4 sets of 2D texture + gi.setTextureCoordinateParams(4, 2); + gi.setTexCoordSetMap(texCoordSetMap); + + // this demo needs just 3 TUS, but geometry + // is prepared for up to 4 TUS stages + gi.setTextureCoordinates(0,texCoords); + gi.setTextureCoordinates(1,texCoords); + gi.setTextureCoordinates(2,texCoords); + gi.setTextureCoordinates(3,texCoords); + + return gi.getGeometryArray(); + } + + /** + * Creates scenegraphs + * @return a BranchGroup with all needed objects in scene + */ + private BranchGroup createSceneGraph() { + BranchGroup bgRoot = new BranchGroup(); + CheckNewLightMapBehavior checkNewLightMapBehavior = new CheckNewLightMapBehavior(); + + bgRoot.addChild(checkNewLightMapBehavior); + + // a blue background + Background background = new Background(0.4f,0.4f,0.8f); + background.setApplicationBounds(bounds); + bgRoot.addChild(background); + + AmbientLight alit = new AmbientLight(true,new Color3f(0.4f,0.4f,0.4f)); + bgRoot.addChild(alit); + + // Set up some directional lights + // DOT3 doesnot need light, because it is a perpixel lighting technique + //but we add this lights to show + // geometry when using non-DOT3 lighting, as color texture only and + // light map texture mode + Color3f light1Color = new Color3f(1.0f, 1.0f, 0.9f); + Vector3f light1Direction = new Vector3f(1.0f, 1.0f, 1.0f); + Color3f light2Color = new Color3f(1.0f, 1.0f, 0.9f); + Vector3f light2Direction = new Vector3f(-1.0f, -1.0f, -1.0f); + + DirectionalLight light1 + = new DirectionalLight(light1Color, light1Direction); + light1.setInfluencingBounds(bounds); + bgRoot.addChild(light1); + + DirectionalLight light2 + = new DirectionalLight(light2Color, light2Direction); + light2.setInfluencingBounds(bounds); + bgRoot.addChild(light2); + + //loading color and DOT3 normal map textures from disk, + //and creating light map at runtime + loadTextures(); + //our single Quad geometry, enabled for multitexture + GeometryArray geo = createGeometry(0.4f); + // a appearance for our geometry + appearance = new Appearance(); + // polygon and texture unit will be updated at runtime + // so we must enabled read/write operations for then + appearance.setCapability(Appearance.ALLOW_POLYGON_ATTRIBUTES_READ); + appearance.setCapability(Appearance.ALLOW_POLYGON_ATTRIBUTES_WRITE); + appearance.setCapability(Appearance.ALLOW_TEXTURE_UNIT_STATE_READ); + appearance.setCapability(Appearance.ALLOW_TEXTURE_UNIT_STATE_WRITE); + + //use a default material. It is necessary when running + //on non per-pixel lighting mod, i.e., using non DOT3 textures + appearance.setMaterial(new Material()); + + polygonAttributes = new PolygonAttributes(); + polygonAttributes.setCapability(PolygonAttributes.ALLOW_MODE_WRITE); + polygonAttributes.setCullFace(PolygonAttributes.CULL_NONE); + + appearance.setPolygonAttributes(polygonAttributes); + + // uses a TUS dot3 enabled + tusArr = setupTextureUnitState(); + appearance.setTextureUnitState(tusArr); + + // joining geometry and appearance in a shape3D + Shape3D shape3D = new Shape3D(geo,appearance); + shape3D.setCapability(Shape3D.ALLOW_APPEARANCE_READ); + shape3D.setCapability(Shape3D.ALLOW_APPEARANCE_WRITE); + + bgRoot.addChild(shape3D); + + bgRoot.compile(); + + return bgRoot; + } + + /** + * Toggles wireframe mode + * @param mode true for wireframe, false for fill polygon + */ + public void setWireframeMode(boolean mode) { + if(mode) + polygonAttributes.setPolygonMode(PolygonAttributes.POLYGON_LINE); + else + polygonAttributes.setPolygonMode(PolygonAttributes.POLYGON_FILL); + } + + + /** + * This method togles on/off textures and updates TextureUnitState in correct Order. + * Some video drivers does not accept TextureUnitState arrays with null values among + * non-null values + * @param showLightMap togles LightMap texture + * @param showDot3 togles DOT3 Normal texture + * @param showColor togles Color texture + */ + public void showTextures(boolean showLightMap, boolean showDot3, boolean showColor) { + int bitSet = 0; + bitSet |= showLightMap ? 4 : 0; + bitSet |= showDot3 ? 2 : 0; + bitSet |= showColor ? 1 : 0; + + tusArr[0] = null; + tusArr[1] = null; + tusArr[2] = null; + + switch (bitSet) { + case 7: { //all bit == all tus + tusArr[0] = tuLightMap; + tusArr[1] = tuDOT3NormalMap; + tusArr[2] = tuColor; + } + break; + case 6: { //no Color + tusArr[0] = tuLightMap; + tusArr[1] = tuDOT3NormalMap; + } + break; + case 5: { //no Dot3 + tusArr[0] = tuLightMap; + tusArr[1] = tuColor; + } + break; + case 4: { //lightMap only + tusArr[0] = tuLightMap; + } + break; + case 3: { //no LightMap + tusArr[0] = tuDOT3NormalMap; + tusArr[1] = tuColor; + } + break; + case 2: { //Dot3 Only + tusArr[0] = tuDOT3NormalMap; + } + break; + case 1: { // Color Only + tusArr[0] = tuColor; + } + break; + default: { // case 0, no textures shows at all + } + break; + } + appearance.setTextureUnitState(tusArr); + } + + /** + * updates LightMap texture. + * This method is called from checkNewLightMapBehavior + * @param image new image to be applied + */ + public void updateLighMap(BufferedImage image) { + imageLightMap.setSubImage(image,image.getWidth(),image.getHeight(),0,0,0,0); + } + + private BufferedImage tempImage; + private boolean lockTempImage = false; + + + /** + * main method + * @param args + */ + public static void main(String[] args) {System.setProperty("sun.awt.noerasebackground", "true"); + javax.swing.SwingUtilities.invokeLater(new Runnable() { + public void run() { + new Dot3Demo(); + } + }); + + } + + /** + * A internal class to check if there is a new Light Map to be applied + */ + class CheckNewLightMapBehavior extends Behavior { + WakeupOnElapsedFrames wakeup = new WakeupOnElapsedFrames(0); + + public CheckNewLightMapBehavior() {// auto enable and set schedulling bounds + setEnable(true); + setSchedulingBounds(bounds); + } + + public void initialize() { + wakeupOn(wakeup); + } + + public void processStimulus(Enumeration e) { + // check if there are a new light map ready to use + if (ctrlPanel.hasTextureImageReady()) { + updateLighMap(ctrlPanel.getTextureImage()); + } + //wake up on next frame + wakeupOn(wakeup); + } + } + +} + + diff --git a/src/main/java/org/jdesktop/j3d/examples/dot3/MyCanvas.java b/src/main/java/org/jdesktop/j3d/examples/dot3/MyCanvas.java new file mode 100644 index 0000000..f5f4cfc --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/dot3/MyCanvas.java @@ -0,0 +1,247 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.dot3; + +import java.awt.Color; +import java.awt.Dimension; +import java.awt.Graphics; +import java.awt.Graphics2D; +import java.awt.Image; +import java.awt.Point; +import java.awt.event.MouseEvent; +import java.awt.image.BufferedImage; + +import javax.swing.JPanel; +import javax.swing.event.MouseInputListener; + +/** + * A mouse interactive canvas for lightMap image + */ +public class MyCanvas extends JPanel implements MouseInputListener { + BufferedImage lightMask = null; + BufferedImage textureImage = null; + Graphics2D gr = null; + Point location = new Point(); + // default color light map + Color bgColor = new Color(147, 147, 147); + + int x = 0; + int y = 0; + int z = 142; + // texture image size + private static final int textureSize = 256; + boolean mouseOut = true; + //flag about image is ready or not for use + boolean imageReady = false; + // allows mask be dragged with mouse + boolean dragMask = false; + boolean updateLightDir = false; + boolean updateMaskPosition = false; + + /** + * Creates a MyCanvas object with a image lightMask. + * Also creates a default ImageLight map + * @param mask light lightMask used + */ + public MyCanvas(BufferedImage mask) { + super(); + this.lightMask = mask; + // create a light map + setTextureImage(new BufferedImage(textureSize, textureSize, + BufferedImage.TYPE_INT_RGB)); + // Graphics used to update lightmap + gr = getTextureImage().createGraphics(); + + Dimension dimSize = new Dimension(textureSize, textureSize); + // lock size + this.setSize(dimSize); + this.setMaximumSize(dimSize); + this.setMinimumSize(dimSize); + + this.setDoubleBuffered(true); + this.setOpaque(true); + this.addMouseMotionListener(this); + this.addMouseListener(this); + } + + /** + * Handles mouse click event. + * Get mouse coords call repaint for proper imageLight update + * @param ev mouse event + */ + public void mouseClicked(MouseEvent ev) { + x = ev.getX(); + y = this.getHeight() - ev.getY(); + updateLightDir = true; + repaint(); + } + + public void mousePressed(MouseEvent e) { + } + + public void mouseReleased(MouseEvent e) { + } + + /** + * Handles mouse drag event. + * get current mouse position and calls repaint for proper imageLight update + * @param ev + */ + public void mouseDragged(MouseEvent ev) { + if (!mouseOut) { + x = ev.getX(); + y = this.getHeight() - ev.getY(); + + //changes lightDir + if ((ev.getModifiers()& MouseEvent.BUTTON1_MASK) == + MouseEvent.BUTTON1_MASK) { + updateLightDir = true; + updateMaskPosition = false; + } + //updates light mask position + if ((ev.getModifiers() & ev.BUTTON2_MASK) == ev.BUTTON2_MASK || + (ev.getModifiers() & ev.BUTTON3_MASK) == ev.BUTTON3_MASK) { + updateLightDir = false; + updateMaskPosition = true; + } + repaint(); + } + } + + public void mouseMoved(MouseEvent ev) { + // disable updates on lightMap + updateLightDir = false; + updateMaskPosition = false; + } + + public void mouseEntered(MouseEvent e) { + mouseOut = false; + } + + public void mouseExited(MouseEvent e) { + mouseOut = true; + } + + /** + * updates imageLight using current setings + * @param g + */ + public void paintComponent(Graphics g) { + imageReady = false; + Graphics2D g2d = (Graphics2D)g; + + // ligthDir has changed, we must update bgColor li + if(updateLightDir) { + int blue = bgColor.getBlue(); + //clamp values to 255 + y = y>255?255:y; + x = x>255?255:x; + bgColor = new Color(y,x,blue); + } + // paint lightMap + gr.setColor(bgColor); + gr.fillRect(0, 0, textureSize, textureSize); + + // draw mask on mouse position + if (dragMask || updateMaskPosition) { + int maskWH = lightMask.getWidth()/2; + int mx = x - maskWH ; + int my = textureSize - y - maskWH ; // y value is inverted + // clamp mouse position, to avoid drawing outside imageLigh bounds + mx = mx > textureSize ? textureSize : mx; + my = my > textureSize ? textureSize : my; + // draw light mask + gr.drawImage(lightMask, mx, my, this); + } + + g2d.drawImage(getTextureImage(), 0, 0, this); + imageReady = true; + } + + /** + * + * @return true if exists a new texture image available + */ + public boolean hasTextureImageReady() { + return imageReady; + } + + /** + * Returns a texture image.<br> + * You can avoid calling the same image several times + * by checking hasTextureImageReady() first. + * @return latest texture image available + */ + public BufferedImage getTextureImage() { + // sign as texture used for next call; + imageReady = false; + //return image + return textureImage; + } + + + public Image getMask() { + return lightMask; + } + + public void setLightMask(BufferedImage mask) { + this.lightMask = mask; + } + + public Color getBgColor() { + return bgColor; + } + + public void setBgColor(Color bgColor) { + this.bgColor = bgColor; + } + + public void setTextureImage(BufferedImage textureImage) { + this.textureImage = textureImage; + } + + +} + diff --git a/src/main/java/org/jdesktop/j3d/examples/dot3/TextureControlPanel.java b/src/main/java/org/jdesktop/j3d/examples/dot3/TextureControlPanel.java new file mode 100644 index 0000000..0aef5f0 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/dot3/TextureControlPanel.java @@ -0,0 +1,232 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.dot3; + +import java.awt.BorderLayout; +import java.awt.Color; +import java.awt.Dimension; +import java.awt.Rectangle; +import java.awt.event.ActionEvent; +import java.awt.event.ActionListener; +import java.awt.image.BufferedImage; +import java.net.URL; + +import javax.imageio.ImageIO; +import javax.swing.JCheckBox; +import javax.swing.JComponent; +import javax.swing.JDialog; +import javax.swing.JLabel; +import javax.swing.JPanel; +import javax.swing.JSlider; +import javax.swing.event.ChangeEvent; +import javax.swing.event.ChangeListener; + +import org.jdesktop.j3d.examples.Resources; + +/** + * A control panel for Dot3Demo. + * It enables user change LightMap, enables/disables textures units states + * and toggles geometry wireframes on/off + */ +public class TextureControlPanel extends JDialog implements ChangeListener, + ActionListener { + /** renderer for lightMap, with support for mouse interaction **/ + private MyCanvas canvas = null; + /** file name for light mask */ + private String maskFileName = "resources/images/mask.png"; + /** a slider to change Z light direction, i.e, blue channel */ + private JSlider sliderZ = new JSlider(JSlider.HORIZONTAL, 1, 255, 142); + /** target demo instance to be controled **/ + private Dot3Demo dot3DemoFrame; + + // some checkboxes for user interaction + private JCheckBox cbWireframe = new JCheckBox("Show as Wireframe", false); + private JCheckBox cbDot3 = new JCheckBox("Show Dot3 texture", true); + private JCheckBox cbShowLightMap = new JCheckBox("Show LightMap texture", true); + private JCheckBox cbShowColor = new JCheckBox("Show Color texture", true); + private JCheckBox cbDragLightMask = new JCheckBox("Drag light mask"); + + private JLabel lbSliderZ = new JLabel(); + private JLabel lbMessage = new JLabel(); + + public TextureControlPanel(Dot3Demo owner) { + super(owner); + dot3DemoFrame = owner; + try { + URL url = Resources.getResource(maskFileName); + BufferedImage mask = ImageIO.read(url); + canvas = new MyCanvas(mask); + init(); + } catch (Exception e) { + e.printStackTrace(); + } + } + + public TextureControlPanel() { + this(null); + } + + /** + * Creates Graphical User Interface + * @throws Exception + */ + private void init() throws Exception { + Dimension dim = new Dimension(540, 350); + this.setSize(dim); + this.setPreferredSize(dim); + this.setTitle("DOT3Demo Texture Control Panel"); + this.setLayout(new BorderLayout()); + + JPanel panel = new JPanel(); + this.getContentPane().add(panel, BorderLayout.CENTER); + canvas.setSize(new Dimension(256, 256)); + canvas.setBounds(new Rectangle(40, 40, 256, 256)); + + sliderZ.setBounds(new Rectangle(310, 190, 205, 45)); + sliderZ.setPaintTicks(true); + sliderZ.setMajorTickSpacing(63); + + cbWireframe.setBounds(new Rectangle(310, 50, 200, 20)); + cbWireframe.setToolTipText("Toggles Wireframe"); + cbDot3.setBounds(new Rectangle(310, 70, 150, 20)); + cbShowLightMap.setBounds(new Rectangle(310, 90, 200, 20)); + cbShowLightMap.setToolTipText("Toggles DOT3 texture"); + cbShowColor.setBounds(new Rectangle(310, 110, 200, 20)); + cbShowColor.setToolTipText("Toggles Color texture"); + + panel.setLayout(null); + + cbDragLightMask.setBounds(new Rectangle(310, 135, 200, 20)); + lbMessage.setText("<html>Left-click and drag to change Light Direction." + + " Right-click and drag to move spotlight.</html>"); + lbMessage.setBounds(new Rectangle(305, 245, 210, 60)); + + lbSliderZ.setText("Blue Light (Dot3 Z axis)"); + lbSliderZ.setBounds(new Rectangle(310, 170, 210, 15)); + lbSliderZ.setToolTipText("changes light intensity from Z axis"); + + panel.add(cbDragLightMask, null); + panel.add(lbMessage, null); + panel.add(lbSliderZ, null); + panel.add(sliderZ, null); + panel.add(canvas, null); + panel.add(cbShowColor, null); + panel.add(cbShowLightMap, null); + panel.add(cbWireframe, null); + panel.add(cbDot3, null); + + sliderZ.addChangeListener(this); + + cbDot3.addActionListener(this); + cbShowColor.addActionListener(this); + cbShowLightMap.addActionListener(this); + cbWireframe.addActionListener(this); + cbDragLightMask.addActionListener(this); + } + + public void stateChanged(ChangeEvent ev) { + JComponent source = (JComponent)ev.getSource(); + if (sliderZ.equals(source)) { + int xVal = canvas.getBgColor().getRed(); + int yVal = canvas.getBgColor().getGreen(); + int zVal = sliderZ.getValue(); + Color ligtDir = new Color(xVal, yVal, zVal); + updateLightMap(ligtDir) ; + } + } + + private void updateLightMap(Color ligtDir) { + canvas.setBgColor(ligtDir); + canvas.repaint(); + dot3DemoFrame.updateLighMap(canvas.getTextureImage()); + } + + + public void actionPerformed(ActionEvent ev) { + JComponent source = (JComponent)ev.getSource(); + if (cbWireframe.equals(source)) { + dot3DemoFrame.setWireframeMode(cbWireframe.isSelected()); + } else + if (cbDot3.equals(source) + || cbShowColor.equals(source) + || cbShowLightMap.equals(source)) { + dot3DemoFrame.showTextures(cbShowLightMap.isSelected(), + cbDot3.isSelected(), + cbShowColor.isSelected()); + } else if (cbDragLightMask.equals(source)) { + canvas.dragMask = cbDragLightMask.isSelected(); + } + + } + + /** + * Wrapper method call for MyCanvas. hasTextureImageReady() + * @return true if exists a new texture image available + */ + public boolean hasTextureImageReady() { + return canvas.hasTextureImageReady(); + } + + /** + * Wrapper method call for MyCanvas.getTextureImage() + * Returns a texture image.<br> + * Avoid calling the same image several times + * by cheking hasTextureImageReady() first. + * @return latest texture image available + */ + public BufferedImage getTextureImage() { + return canvas.getTextureImage(); + } + + /** + * Wrapper method to MyCanvas.setLightMask(mask) + * @param mask a new light mask + */ + public void setLightMask(BufferedImage mask) { + canvas.setLightMask(mask); + } +} + + diff --git a/src/main/java/org/jdesktop/j3d/examples/four_by_four/BigCube.java b/src/main/java/org/jdesktop/j3d/examples/four_by_four/BigCube.java new file mode 100644 index 0000000..3609c97 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/four_by_four/BigCube.java @@ -0,0 +1,139 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.four_by_four; + +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.QuadArray; +import org.jogamp.java3d.Shape3D; + +/** + * Class BigCube + * + * Description: Creates the "big" cube used to mark the computer's + * position. + * + * Version: 1.0 + */ +public class BigCube extends Object { + + private Shape3D shape3D; + + private static final float[] verts = { + // Front Face + 5.0f, -5.0f, 5.0f, 5.0f, 5.0f, 5.0f, + -5.0f, 5.0f, 5.0f, -5.0f, -5.0f, 5.0f, + // Back Face + -5.0f, -5.0f, -5.0f, -5.0f, 5.0f, -5.0f, + 5.0f, 5.0f, -5.0f, 5.0f, -5.0f, -5.0f, + // Right Face + 5.0f, -5.0f, -5.0f, 5.0f, 5.0f, -5.0f, + 5.0f, 5.0f, 5.0f, 5.0f, -5.0f, 5.0f, + // Left Face + -5.0f, -5.0f, 5.0f, -5.0f, 5.0f, 5.0f, + -5.0f, 5.0f, -5.0f, -5.0f, -5.0f, -5.0f, + // Top Face + 5.0f, 5.0f, 5.0f, 5.0f, 5.0f, -5.0f, + -5.0f, 5.0f, -5.0f, -5.0f, 5.0f, 5.0f, + // Bottom Face + -5.0f, -5.0f, 5.0f, -5.0f, -5.0f, -5.0f, + 5.0f, -5.0f, -5.0f, 5.0f, -5.0f, 5.0f, + }; + + private static final float[] normals = { + // Front Face + 0.0f, 0.0f, 1.0f, 0.0f, 0.0f, 1.0f, + 0.0f, 0.0f, 1.0f, 0.0f, 0.0f, 1.0f, + // Back Face + 0.0f, 0.0f, -1.0f, 0.0f, 0.0f, -1.0f, + 0.0f, 0.0f, -1.0f, 0.0f, 0.0f, -1.0f, + // Right Face + 1.0f, 0.0f, 0.0f, 1.0f, 0.0f, 0.0f, + 1.0f, 0.0f, 0.0f, 1.0f, 0.0f, 0.0f, + // Left Face + -1.0f, 0.0f, 0.0f, -1.0f, 0.0f, 0.0f, + -1.0f, 0.0f, 0.0f, -1.0f, 0.0f, 0.0f, + // Top Face + 0.0f, 1.0f, 0.0f, 0.0f, 1.0f, 0.0f, + 0.0f, 1.0f, 0.0f, 0.0f, 1.0f, 0.0f, + // Bottom Face + 0.0f, -1.0f, 0.0f, 0.0f, -1.0f, 0.0f, + 0.0f, -1.0f, 0.0f, 0.0f, -1.0f, 0.0f, + }; + + public BigCube(Appearance appearance) { + + QuadArray quadArray = new QuadArray(24, QuadArray.COORDINATES | + QuadArray.NORMALS ); + quadArray.setCoordinates(0, verts); + quadArray.setNormals(0, normals); + + shape3D = new Shape3D(quadArray, appearance); + shape3D.setCapability(Shape3D.ALLOW_GEOMETRY_READ); + shape3D.setCapability(Shape3D.ALLOW_GEOMETRY_WRITE); + shape3D.setCapability(Shape3D.ALLOW_APPEARANCE_READ); + shape3D.setCapability(Shape3D.ALLOW_APPEARANCE_WRITE); + } + + public BigCube(Appearance appearance, float size) { + + QuadArray quadArray = new QuadArray(24, QuadArray.COORDINATES | + QuadArray.NORMALS ); + + for (int i=0; i<72; i++) verts[i] *= size; + + quadArray.setCoordinates(0, verts); + quadArray.setNormals(0, normals); + + shape3D = new Shape3D(quadArray, appearance); + shape3D.setCapability(Shape3D.ALLOW_GEOMETRY_READ); + shape3D.setCapability(Shape3D.ALLOW_GEOMETRY_WRITE); + shape3D.setCapability(Shape3D.ALLOW_APPEARANCE_READ); + shape3D.setCapability(Shape3D.ALLOW_APPEARANCE_WRITE); + } + + public Shape3D getChild() { + return shape3D; + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/four_by_four/Board.java b/src/main/java/org/jdesktop/j3d/examples/four_by_four/Board.java new file mode 100644 index 0000000..3ed2f89 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/four_by_four/Board.java @@ -0,0 +1,2313 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.four_by_four; + +import java.awt.Color; +import java.awt.Graphics; + +/** + * Class: Board + * + * Description: Handles all logic with respect to play. Also renders + * the 2D window. + * + * Version: 1.1 + * + */ +class Board { + + final static int UNOCCUPIED = 0; + final static int HUMAN = 1; + final static int MACHINE = 2; + final static int END = 3; + + private int[] moves; + private int[] occupied; + private int[][] combinations; + private int[][] outside_four; + private int[][] inside_four; + private int[][] faces; + private int[][] pos_to_comb; + private int[][] best_picks; + private int num_points; + private int num_balls; + private int num_polygons; + private int num_pt_indexes; + private int num_normal_indexes; + private int pt_start; + private int color_index; + private int width; + private int height; + private int center_x; + private int center_y; + private int player; + private int skill_level; + private int outside_four_index; + private int inside_four_index; + private int face_index; + private int nmoves; + private int current_face; + private int min = 1000; + private int max = 0; + private long[] sort_array; + private long time; + private long beg_time; + private long end_time; + private Color[] color_ramp; + private Color background; + private Color label_color; + private Color red; + private Color blue; + private Color white; + private Color gray; + private Color yellow; + private double max_dist; + private FourByFour panel; + private boolean debug; + private boolean outside_four_flag; + private boolean inside_four_flag; + private boolean face_flag; + private boolean label_flag; + private boolean block_chair_flag; + private boolean undoFlag; + private boolean[] highlight; + private int block_chair_next_move; + private int block_chair_face; + private Positions positions; + private Canvas2D canvas; + + Board (FourByFour panel, Positions positions, int width, int height) { + + // Set the debug state. + debug = false; + + // Store arguments + this.width = width; + this.height = height; + this.panel = panel; + this.positions = positions; + + // Initialize flags + label_flag = false; + outside_four_flag = false; + inside_four_flag = false; + block_chair_flag = false; + undoFlag = false; + + // Total number of board positions. + num_points = 64; + + // Allocate the logic arrays. + moves = new int[64]; + occupied = new int[64]; + combinations = new int[76][7]; + outside_four = new int[18][6]; + inside_four = new int[18][6]; + faces = new int[18][18]; + pos_to_comb = new int[64][8]; + best_picks = new int[64][8]; + highlight = new boolean[18]; + + // Initialize the logic arrays. + init_combinations(); + init_faces(); + init_outside_four(); + init_inside_four(); + + // Set the player with the first move. + player = HUMAN; + + // Set the default skill level. + skill_level = 4; + + // Initialize the number of moves. + nmoves = 0; + + // Define colors + background = new Color(13, 13, 51); + red = new Color(230, 26, 51); + blue = new Color(51, 51, 230); + white = new Color(255, 255, 255); + gray = new Color(240, 240, 240); + yellow = new Color(240, 240, 0); + + // Record the start time + beg_time = System.currentTimeMillis(); + } + + public void setCanvas(Canvas2D canvas) { + this.canvas = canvas; + } + + public void init_combinations () { + + // The combination array contains all possible winning combinations. + // + // Each combination has the following format: + // + // combinations[x][0] = status: 0 = no player has selected positons in this row + // -1 = both players have men in this row + // 1 to 4 = number of positions occupied by player + // + // combinations[x][1] = player who owns this row (valid only if status = 1-4) + // combinations[x][2] = postion that define the row + // combinations[x][3] = postion that define the row + // combinations[x][4] = postion that define the row + // combinations[x][5] = postion that define the row + + // Horizontal, Z + + combinations[ 0][0] = 0; combinations[ 1][0] = 0; combinations[ 2][0] = 0; combinations[ 3][0] = 0; + combinations[ 0][1] = 0; combinations[ 1][1] = 0; combinations[ 2][1] = 0; combinations[ 3][1] = 0; + combinations[ 0][2] = 0; combinations[ 1][2] = 4; combinations[ 2][2] = 8; combinations[ 3][2] = 12; + combinations[ 0][3] = 1; combinations[ 1][3] = 5; combinations[ 2][3] = 9; combinations[ 3][3] = 13; + combinations[ 0][4] = 2; combinations[ 1][4] = 6; combinations[ 2][4] = 10; combinations[ 3][4] = 14; + combinations[ 0][5] = 3; combinations[ 1][5] = 7; combinations[ 2][5] = 11; combinations[ 3][5] = 15; + + combinations[ 4][0] = 0; combinations[ 5][0] = 0; combinations[ 6][0] = 0; combinations[ 7][0] = 0; + combinations[ 4][1] = 0; combinations[ 5][1] = 0; combinations[ 6][1] = 0; combinations[ 7][1] = 0; + combinations[ 4][2] = 16; combinations[ 5][2] = 20; combinations[ 6][2] = 24; combinations[ 7][2] = 28; + combinations[ 4][3] = 17; combinations[ 5][3] = 21; combinations[ 6][3] = 25; combinations[ 7][3] = 29; + combinations[ 4][4] = 18; combinations[ 5][4] = 22; combinations[ 6][4] = 26; combinations[ 7][4] = 30; + combinations[ 4][5] = 19; combinations[ 5][5] = 23; combinations[ 6][5] = 27; combinations[ 7][5] = 31; + + combinations[ 8][0] = 0; combinations[ 9][0] = 0; combinations[10][0] = 0; combinations[11][0] = 0; + combinations[ 8][1] = 0; combinations[ 9][1] = 0; combinations[10][1] = 0; combinations[11][1] = 0; + combinations[ 8][2] = 32; combinations[ 9][2] = 36; combinations[10][2] = 40; combinations[11][2] = 44; + combinations[ 8][3] = 33; combinations[ 9][3] = 37; combinations[10][3] = 41; combinations[11][3] = 45; + combinations[ 8][4] = 34; combinations[ 9][4] = 38; combinations[10][4] = 42; combinations[11][4] = 46; + combinations[ 8][5] = 35; combinations[ 9][5] = 39; combinations[10][5] = 43; combinations[11][5] = 47; + + combinations[12][0] = 0; combinations[13][0] = 0; combinations[14][0] = 0; combinations[15][0] = 0; + combinations[12][1] = 0; combinations[13][1] = 0; combinations[14][1] = 0; combinations[15][1] = 0; + combinations[12][2] = 48; combinations[13][2] = 52; combinations[14][2] = 56; combinations[15][2] = 60; + combinations[12][3] = 49; combinations[13][3] = 53; combinations[14][3] = 57; combinations[15][3] = 61; + combinations[12][4] = 50; combinations[13][4] = 54; combinations[14][4] = 58; combinations[15][4] = 62; + combinations[12][5] = 51; combinations[13][5] = 55; combinations[14][5] = 59; combinations[15][5] = 63; + + // Vertical, Z + + combinations[16][0] = 0; combinations[17][0] = 0; combinations[18][0] = 0; combinations[19][0] = 0; + combinations[16][1] = 0; combinations[17][1] = 0; combinations[18][1] = 0; combinations[19][1] = 0; + combinations[16][2] = 0; combinations[17][2] = 1; combinations[18][2] = 2; combinations[19][2] = 3; + combinations[16][3] = 4; combinations[17][3] = 5; combinations[18][3] = 6; combinations[19][3] = 7; + combinations[16][4] = 8; combinations[17][4] = 9; combinations[18][4] = 10; combinations[19][4] = 11; + combinations[16][5] = 12; combinations[17][5] = 13; combinations[18][5] = 14; combinations[19][5] = 15; + + combinations[20][0] = 0; combinations[21][0] = 0; combinations[22][0] = 0; combinations[23][0] = 0; + combinations[20][1] = 0; combinations[21][1] = 0; combinations[22][1] = 0; combinations[23][1] = 0; + combinations[20][2] = 16; combinations[21][2] = 17; combinations[22][2] = 18; combinations[23][2] = 19; + combinations[20][3] = 20; combinations[21][3] = 21; combinations[22][3] = 22; combinations[23][3] = 23; + combinations[20][4] = 24; combinations[21][4] = 25; combinations[22][4] = 26; combinations[23][4] = 27; + combinations[20][5] = 28; combinations[21][5] = 29; combinations[22][5] = 30; combinations[23][5] = 31; + + combinations[24][0] = 0; combinations[25][0] = 0; combinations[26][0] = 0; combinations[27][0] = 0; + combinations[24][1] = 0; combinations[25][1] = 0; combinations[26][1] = 0; combinations[27][1] = 0; + combinations[24][2] = 32; combinations[25][2] = 33; combinations[26][2] = 34; combinations[27][2] = 35; + combinations[24][3] = 36; combinations[25][3] = 37; combinations[26][3] = 38; combinations[27][3] = 39; + combinations[24][4] = 40; combinations[25][4] = 41; combinations[26][4] = 42; combinations[27][4] = 43; + combinations[24][5] = 44; combinations[25][5] = 45; combinations[26][5] = 46; combinations[27][5] = 47; + + combinations[28][0] = 0; combinations[29][0] = 0; combinations[30][0] = 0; combinations[31][0] = 0; + combinations[28][1] = 0; combinations[29][1] = 0; combinations[30][1] = 0; combinations[31][1] = 0; + combinations[28][2] = 48; combinations[29][2] = 49; combinations[30][2] = 50; combinations[31][2] = 51; + combinations[28][3] = 52; combinations[29][3] = 53; combinations[30][3] = 54; combinations[31][3] = 55; + combinations[28][4] = 56; combinations[29][4] = 57; combinations[30][4] = 58; combinations[31][4] = 59; + combinations[28][5] = 60; combinations[29][5] = 61; combinations[30][5] = 62; combinations[31][5] = 63; + + // Diagonal, Z + + combinations[32][0] = 0; combinations[33][0] = 0; combinations[34][0] = 0; combinations[35][0] = 0; + combinations[32][1] = 0; combinations[33][1] = 0; combinations[34][1] = 0; combinations[35][1] = 0; + combinations[32][2] = 0; combinations[33][2] = 16; combinations[34][2] = 32; combinations[35][2] = 48; + combinations[32][3] = 5; combinations[33][3] = 21; combinations[34][3] = 37; combinations[35][3] = 53; + combinations[32][4] = 10; combinations[33][4] = 26; combinations[34][4] = 42; combinations[35][4] = 58; + combinations[32][5] = 15; combinations[33][5] = 31; combinations[34][5] = 47; combinations[35][5] = 63; + + combinations[36][0] = 0; combinations[37][0] = 0; combinations[38][0] = 0; combinations[39][0] = 0; + combinations[36][1] = 0; combinations[37][1] = 0; combinations[38][1] = 0; combinations[39][1] = 0; + combinations[36][2] = 3; combinations[37][2] = 19; combinations[38][2] = 35; combinations[39][2] = 51; + combinations[36][3] = 6; combinations[37][3] = 22; combinations[38][3] = 38; combinations[39][3] = 54; + combinations[36][4] = 9; combinations[37][4] = 25; combinations[38][4] = 41; combinations[39][4] = 57; + combinations[36][5] = 12; combinations[37][5] = 28; combinations[38][5] = 44; combinations[39][5] = 60; + + // Horizontal, X + + combinations[40][0] = 0; combinations[41][0] = 0; combinations[42][0] = 0; combinations[43][0] = 0; + combinations[40][1] = 0; combinations[41][1] = 0; combinations[42][1] = 0; combinations[43][1] = 0; + combinations[40][2] = 51; combinations[41][2] = 55; combinations[42][2] = 59; combinations[43][2] = 63; + combinations[40][3] = 35; combinations[41][3] = 39; combinations[42][3] = 43; combinations[43][3] = 47; + combinations[40][4] = 19; combinations[41][4] = 23; combinations[42][4] = 27; combinations[43][4] = 31; + combinations[40][5] = 3; combinations[41][5] = 7; combinations[42][5] = 11; combinations[43][5] = 15; + + combinations[44][0] = 0; combinations[45][0] = 0; combinations[46][0] = 0; combinations[47][0] = 0; + combinations[44][1] = 0; combinations[45][1] = 0; combinations[46][1] = 0; combinations[47][1] = 0; + combinations[44][2] = 50; combinations[45][2] = 54; combinations[46][2] = 58; combinations[47][2] = 62; + combinations[44][3] = 34; combinations[45][3] = 38; combinations[46][3] = 42; combinations[47][3] = 46; + combinations[44][4] = 18; combinations[45][4] = 22; combinations[46][4] = 26; combinations[47][4] = 30; + combinations[44][5] = 2; combinations[45][5] = 6; combinations[46][5] = 10; combinations[47][5] = 14; + + combinations[48][0] = 0; combinations[49][0] = 0; combinations[50][0] = 0; combinations[51][0] = 0; + combinations[48][1] = 0; combinations[49][1] = 0; combinations[50][1] = 0; combinations[51][1] = 0; + combinations[48][2] = 49; combinations[49][2] = 53; combinations[50][2] = 57; combinations[51][2] = 61; + combinations[48][3] = 33; combinations[49][3] = 37; combinations[50][3] = 41; combinations[51][3] = 45; + combinations[48][4] = 17; combinations[49][4] = 21; combinations[50][4] = 25; combinations[51][4] = 29; + combinations[48][5] = 1; combinations[49][5] = 5; combinations[50][5] = 9; combinations[51][5] = 13; + + combinations[52][0] = 0; combinations[53][0] = 0; combinations[54][0] = 0; combinations[55][0] = 0; + combinations[52][1] = 0; combinations[53][1] = 0; combinations[54][1] = 0; combinations[55][1] = 0; + combinations[52][2] = 48; combinations[53][2] = 52; combinations[54][2] = 56; combinations[55][2] = 60; + combinations[52][3] = 32; combinations[53][3] = 36; combinations[54][3] = 40; combinations[55][3] = 44; + combinations[52][4] = 16; combinations[53][4] = 20; combinations[54][4] = 24; combinations[55][4] = 28; + combinations[52][5] = 0; combinations[53][5] = 4; combinations[54][5] = 8; combinations[55][5] = 12; + + // Diagonal, X + + combinations[56][0] = 0; combinations[57][0] = 0; combinations[58][0] = 0; combinations[59][0] = 0; + combinations[56][1] = 0; combinations[57][1] = 0; combinations[58][1] = 0; combinations[59][1] = 0; + combinations[56][2] = 51; combinations[57][2] = 50; combinations[58][2] = 49; combinations[59][2] = 48; + combinations[56][3] = 39; combinations[57][3] = 38; combinations[58][3] = 37; combinations[59][3] = 36; + combinations[56][4] = 27; combinations[57][4] = 26; combinations[58][4] = 25; combinations[59][4] = 24; + combinations[56][5] = 15; combinations[57][5] = 14; combinations[58][5] = 13; combinations[59][5] = 12; + + combinations[60][0] = 0; combinations[61][0] = 0; combinations[62][0] = 0; combinations[63][0] = 0; + combinations[60][1] = 0; combinations[61][1] = 0; combinations[62][1] = 0; combinations[63][1] = 0; + combinations[60][2] = 3; combinations[61][2] = 2; combinations[62][2] = 1; combinations[63][2] = 0; + combinations[60][3] = 23; combinations[61][3] = 22; combinations[62][3] = 21; combinations[63][3] = 20; + combinations[60][4] = 43; combinations[61][4] = 42; combinations[62][4] = 41; combinations[63][4] = 40; + combinations[60][5] = 63; combinations[61][5] = 62; combinations[62][5] = 61; combinations[63][5] = 60; + + // Diagonal, Y + + combinations[64][0] = 0; combinations[65][0] = 0; combinations[66][0] = 0; combinations[67][0] = 0; + combinations[64][1] = 0; combinations[65][1] = 0; combinations[66][1] = 0; combinations[67][1] = 0; + combinations[64][2] = 63; combinations[65][2] = 59; combinations[66][2] = 55; combinations[67][2] = 51; + combinations[64][3] = 46; combinations[65][3] = 42; combinations[66][3] = 38; combinations[67][3] = 34; + combinations[64][4] = 29; combinations[65][4] = 25; combinations[66][4] = 21; combinations[67][4] = 17; + combinations[64][5] = 12; combinations[65][5] = 8; combinations[66][5] = 4; combinations[67][5] = 0; + + combinations[68][0] = 0; combinations[69][0] = 0; combinations[70][0] = 0; combinations[71][0] = 0; + combinations[68][1] = 0; combinations[69][1] = 0; combinations[70][1] = 0; combinations[71][1] = 0; + combinations[68][2] = 15; combinations[69][2] = 11; combinations[70][2] = 7; combinations[71][2] = 3; + combinations[68][3] = 30; combinations[69][3] = 26; combinations[70][3] = 22; combinations[71][3] = 18; + combinations[68][4] = 45; combinations[69][4] = 41; combinations[70][4] = 37; combinations[71][4] = 33; + combinations[68][5] = 60; combinations[69][5] = 56; combinations[70][5] = 52; combinations[71][5] = 48; + + // Corner to Corner + + combinations[72][0] = 0; combinations[73][0] = 0; combinations[74][0] = 0; combinations[75][0] = 0; + combinations[72][1] = 0; combinations[73][1] = 0; combinations[74][1] = 0; combinations[75][1] = 0; + combinations[72][2] = 0; combinations[73][2] = 3; combinations[74][2] = 12; combinations[75][2] = 15; + combinations[72][3] = 21; combinations[73][3] = 22; combinations[74][3] = 25; combinations[75][3] = 26; + combinations[72][4] = 42; combinations[73][4] = 41; combinations[74][4] = 38; combinations[75][4] = 37; + combinations[72][5] = 63; combinations[73][5] = 60; combinations[74][5] = 51; combinations[75][5] = 48; + + // Initialize the combination flags to zero. + for (int i=0; i<76; i++) + combinations[i][6] = 0; + + // Set up the pos_to_comb array to point to every winning combination that a given + // position may have. + setup_pos_to_comb(); + + // Set up the best_picks array. + update_best_picks(); + } + + + /** + * Initialize the "outside four" array. + */ + public void init_outside_four() { + for (int i=0; i<18; i++) { + outside_four[i][0] = 0; + outside_four[i][1] = 0; + outside_four[i][2] = faces[i][ 2]; + outside_four[i][3] = faces[i][ 5]; + outside_four[i][4] = faces[i][14]; + outside_four[i][5] = faces[i][17]; + } + } + + + /** + * Initialize the "inside four" array. + */ + public void init_inside_four() { + for (int i=0; i<18; i++) { + inside_four[i][0] = 0; + inside_four[i][1] = 0; + inside_four[i][2] = faces[i][ 7]; + inside_four[i][3] = faces[i][ 8]; + inside_four[i][4] = faces[i][11]; + inside_four[i][5] = faces[i][12]; + } + } + + /** + * Initialize the "faces" array. + */ + public void init_faces () { + + faces[ 0][ 0] = 0; + faces[ 0][ 1] = 0; + faces[ 0][ 2] = 12; faces[ 0][ 6] = 13; faces[ 0][10] = 14; faces[ 0][14] = 15; + faces[ 0][ 3] = 8; faces[ 0][ 7] = 9; faces[ 0][11] = 10; faces[ 0][15] = 11; + faces[ 0][ 4] = 4; faces[ 0][ 8] = 5; faces[ 0][12] = 6; faces[ 0][16] = 7; + faces[ 0][ 5] = 0; faces[ 0][ 9] = 1; faces[ 0][13] = 2; faces[ 0][17] = 3; + + faces[ 1][ 0] = 0; + faces[ 1][ 1] = 0; + faces[ 1][ 2] = 28; faces[ 1][ 6] = 29; faces[ 1][10] = 30; faces[ 1][14] = 31; + faces[ 1][ 3] = 24; faces[ 1][ 7] = 25; faces[ 1][11] = 26; faces[ 1][15] = 27; + faces[ 1][ 4] = 20; faces[ 1][ 8] = 21; faces[ 1][12] = 22; faces[ 1][16] = 23; + faces[ 1][ 5] = 16; faces[ 1][ 9] = 17; faces[ 1][13] = 18; faces[ 1][17] = 19; + + faces[ 2][ 0] = 0; + faces[ 2][ 1] = 0; + faces[ 2][ 2] = 44; faces[ 2][ 6] = 45; faces[ 2][10] = 46; faces[ 2][14] = 47; + faces[ 2][ 3] = 40; faces[ 2][ 7] = 41; faces[ 2][11] = 42; faces[ 2][15] = 43; + faces[ 2][ 4] = 36; faces[ 2][ 8] = 37; faces[ 2][12] = 38; faces[ 2][16] = 39; + faces[ 2][ 5] = 32; faces[ 2][ 9] = 33; faces[ 2][13] = 34; faces[ 2][17] = 35; + + faces[ 3][ 0] = 0; + faces[ 3][ 1] = 0; + faces[ 3][ 2] = 60; faces[ 3][ 6] = 61; faces[ 3][10] = 62; faces[ 3][14] = 63; + faces[ 3][ 3] = 56; faces[ 3][ 7] = 57; faces[ 3][11] = 58; faces[ 3][15] = 59; + faces[ 3][ 4] = 52; faces[ 3][ 8] = 53; faces[ 3][12] = 54; faces[ 3][16] = 55; + faces[ 3][ 5] = 48; faces[ 3][ 9] = 49; faces[ 3][13] = 50; faces[ 3][17] = 51; + + faces[ 4][ 0] = 0; + faces[ 4][ 1] = 0; + faces[ 4][ 2] = 12; faces[ 4][ 6] = 28; faces[ 4][10] = 44; faces[ 4][14] = 60; + faces[ 4][ 3] = 8; faces[ 4][ 7] = 24; faces[ 4][11] = 40; faces[ 4][15] = 56; + faces[ 4][ 4] = 4; faces[ 4][ 8] = 20; faces[ 4][12] = 36; faces[ 4][16] = 52; + faces[ 4][ 5] = 0; faces[ 4][ 9] = 16; faces[ 4][13] = 32; faces[ 4][17] = 48; + + faces[ 5][ 0] = 0; + faces[ 5][ 1] = 0; + faces[ 5][ 2] = 13; faces[ 5][ 6] = 29; faces[ 5][10] = 45; faces[ 5][14] = 61; + faces[ 5][ 3] = 9; faces[ 5][ 7] = 25; faces[ 5][11] = 41; faces[ 5][15] = 57; + faces[ 5][ 4] = 5; faces[ 5][ 8] = 21; faces[ 5][12] = 37; faces[ 5][16] = 53; + faces[ 5][ 5] = 1; faces[ 5][ 9] = 17; faces[ 5][13] = 33; faces[ 5][17] = 49; + + faces[ 6][ 0] = 0; + faces[ 6][ 1] = 0; + faces[ 6][ 2] = 14; faces[ 6][ 6] = 30; faces[ 6][10] = 46; faces[ 6][14] = 62; + faces[ 6][ 3] = 10; faces[ 6][ 7] = 26; faces[ 6][11] = 42; faces[ 6][15] = 58; + faces[ 6][ 4] = 6; faces[ 6][ 8] = 22; faces[ 6][12] = 38; faces[ 6][16] = 54; + faces[ 6][ 5] = 2; faces[ 6][ 9] = 18; faces[ 6][13] = 34; faces[ 6][17] = 50; + + faces[ 7][ 0] = 0; + faces[ 7][ 1] = 0; + faces[ 7][ 2] = 15; faces[ 7][ 6] = 31; faces[ 7][10] = 47; faces[ 7][14] = 63; + faces[ 7][ 3] = 11; faces[ 7][ 7] = 27; faces[ 7][11] = 43; faces[ 7][15] = 59; + faces[ 7][ 4] = 7; faces[ 7][ 8] = 23; faces[ 7][12] = 39; faces[ 7][16] = 55; + faces[ 7][ 5] = 3; faces[ 7][ 9] = 19; faces[ 7][13] = 35; faces[ 7][17] = 51; + + faces[ 8][ 0] = 0; + faces[ 8][ 1] = 0; + faces[ 8][ 2] = 12; faces[ 8][ 6] = 28; faces[ 8][10] = 44; faces[ 8][14] = 60; + faces[ 8][ 3] = 13; faces[ 8][ 7] = 29; faces[ 8][11] = 45; faces[ 8][15] = 61; + faces[ 8][ 4] = 14; faces[ 8][ 8] = 30; faces[ 8][12] = 46; faces[ 8][16] = 62; + faces[ 8][ 5] = 15; faces[ 8][ 9] = 31; faces[ 8][13] = 47; faces[ 8][17] = 63; + + faces[ 9][ 0] = 0; + faces[ 9][ 1] = 0; + faces[ 9][ 2] = 8; faces[ 9][ 6] = 24; faces[ 9][10] = 40; faces[ 9][14] = 56; + faces[ 9][ 3] = 9; faces[ 9][ 7] = 25; faces[ 9][11] = 41; faces[ 9][15] = 57; + faces[ 9][ 4] = 10; faces[ 9][ 8] = 26; faces[ 9][12] = 42; faces[ 9][16] = 58; + faces[ 9][ 5] = 11; faces[ 9][ 9] = 27; faces[ 9][13] = 43; faces[ 9][17] = 59; + + faces[10][ 0] = 0; + faces[10][ 1] = 0; + faces[10][ 2] = 4; faces[10][ 6] = 20; faces[10][10] = 36; faces[10][14] = 52; + faces[10][ 3] = 5; faces[10][ 7] = 21; faces[10][11] = 37; faces[10][15] = 53; + faces[10][ 4] = 6; faces[10][ 8] = 22; faces[10][12] = 38; faces[10][16] = 54; + faces[10][ 5] = 7; faces[10][ 9] = 23; faces[10][13] = 39; faces[10][17] = 55; + + faces[11][ 0] = 0; + faces[11][ 1] = 0; + faces[11][ 2] = 0; faces[11][ 6] = 16; faces[11][10] = 32; faces[11][14] = 48; + faces[11][ 3] = 1; faces[11][ 7] = 17; faces[11][11] = 33; faces[11][15] = 49; + faces[11][ 4] = 2; faces[11][ 8] = 18; faces[11][12] = 34; faces[11][16] = 50; + faces[11][ 5] = 3; faces[11][ 9] = 19; faces[11][13] = 35; faces[11][17] = 51; + + faces[12][ 0] = 0; + faces[12][ 1] = 0; + faces[12][ 2] = 12; faces[12][ 6] = 13; faces[12][10] = 14; faces[12][14] = 15; + faces[12][ 3] = 24; faces[12][ 7] = 25; faces[12][11] = 26; faces[12][15] = 27; + faces[12][ 4] = 36; faces[12][ 8] = 37; faces[12][12] = 38; faces[12][16] = 39; + faces[12][ 5] = 48; faces[12][ 9] = 49; faces[12][13] = 50; faces[12][17] = 51; + + faces[13][ 0] = 0; + faces[13][ 1] = 0; + faces[13][ 2] = 0; faces[13][ 6] = 1; faces[13][10] = 2; faces[13][14] = 3; + faces[13][ 3] = 20; faces[13][ 7] = 21; faces[13][11] = 22; faces[13][15] = 23; + faces[13][ 4] = 40; faces[13][ 8] = 41; faces[13][12] = 42; faces[13][16] = 43; + faces[13][ 5] = 60; faces[13][ 9] = 61; faces[13][13] = 62; faces[13][17] = 63; + + faces[14][ 0] = 0; + faces[14][ 1] = 0; + faces[14][ 2] = 12; faces[14][ 6] = 28; faces[14][10] = 44; faces[14][14] = 60; + faces[14][ 3] = 9; faces[14][ 7] = 25; faces[14][11] = 41; faces[14][15] = 57; + faces[14][ 4] = 6; faces[14][ 8] = 22; faces[14][12] = 38; faces[14][16] = 54; + faces[14][ 5] = 3; faces[14][ 9] = 19; faces[14][13] = 35; faces[14][17] = 51; + + faces[15][ 0] = 0; + faces[15][ 1] = 0; + faces[15][ 2] = 15; faces[15][ 6] = 31; faces[15][10] = 47; faces[15][14] = 63; + faces[15][ 3] = 10; faces[15][ 7] = 26; faces[15][11] = 42; faces[15][15] = 58; + faces[15][ 4] = 5; faces[15][ 8] = 21; faces[15][12] = 37; faces[15][16] = 53; + faces[15][ 5] = 0; faces[15][ 9] = 16; faces[15][13] = 32; faces[15][17] = 48; + + faces[16][ 0] = 0; + faces[16][ 1] = 0; + faces[16][ 2] = 12; faces[16][ 6] = 29; faces[16][10] = 46; faces[16][14] = 63; + faces[16][ 3] = 8; faces[16][ 7] = 25; faces[16][11] = 42; faces[16][15] = 59; + faces[16][ 4] = 4; faces[16][ 8] = 21; faces[16][12] = 38; faces[16][16] = 55; + faces[16][ 5] = 0; faces[16][ 9] = 17; faces[16][13] = 34; faces[16][17] = 51; + + faces[17][ 0] = 0; + faces[17][ 1] = 0; + faces[17][ 2] = 15; faces[17][ 6] = 30; faces[17][10] = 45; faces[17][14] = 60; + faces[17][ 3] = 11; faces[17][ 7] = 26; faces[17][11] = 41; faces[17][15] = 56; + faces[17][ 4] = 7; faces[17][ 8] = 22; faces[17][12] = 37; faces[17][16] = 52; + faces[17][ 5] = 3; faces[17][ 9] = 18; faces[17][13] = 33; faces[17][17] = 48; + } + + /** + * Render the current face set in the 2D window. + */ + public void render2D(Graphics gc) { + + gc.setColor(background); + gc.fillRect(0, 0, width, height); + + int id; + int x, y; + + float begX; + float begY; + + for (int l=0; l<3; l++) { + begY = 28.0f + l*(5.f*23.3f); + for (int k=0; k<6; k++) { + begX = 11.65f + k*(5.f*11.65f); + int count = 0; + int face = l*6+k; + for (int i=0; i<4; i++) { + for (int j=0; j<4; j++) { + x = (int)begX + i*12; + y = (int)begY + j*12; + id = faces[face][count+2]; + if (occupied[id] == HUMAN) { + x -= 2; + y -= 2; + gc.setColor(red); + gc.fillRect(x, y, 5, 5); + } + else if (occupied[id] == MACHINE) { + x -= 2; + y -= 2; + gc.setColor(blue); + gc.fillRect(x, y, 5, 5); + } + else { + x -= 1; + y -= 1; + gc.setColor(gray); + gc.fillRect(x, y, 2, 2); + } + if (highlight[face]) { + gc.setColor(yellow); + positions.setHighlight(faces[face][count+2]); + } + count++; + } + } + if (highlight[face]) + gc.setColor(yellow); + else + gc.setColor(white); + if ((face+1)<10) + gc.drawString("Face "+(face+1), (int)begX-2, (int)begY+60); + else + gc.drawString("Face "+(face+1), (int)begX-4, (int)begY+60); + } + } + } + + /** + * Determine what position has been selected in the 2D window. + */ + public void checkSelection2D(int x, int y, int player) { + + int id; + int posX, posY; + + float begX; + float begY; + + for (int l=0; l<3; l++) { + begY = 28.0f + l*(5.f*23.3f); + for (int k=0; k<6; k++) { + begX = 11.65f + k*(5.f*11.65f); + int count = 0; + int face = l*6+k; + for (int i=0; i<4; i++) { + for (int j=0; j<4; j++) { + posX = (int)begX + i*12; + posY = (int)begY + j*12; + if (x > posX-4 && x < posX+4 && + y > posY-4 && y < posY+4) { + + id = faces[face][count+2]; + + if (occupied[id] == UNOCCUPIED) { + positions.set(id, player); + selection(id, player); + canvas.repaint(); + } + return; + } + count++; + } + } + if ((x > begX-4 && x < begX+40) && + (y > begY+45 && y < begY+60) ) { + + count = 0; + for (int i=0; i<4; i++) { + for (int j=0; j<4; j++) { + if (highlight[face]) + positions.clearHighlight(faces[face][count+2]); + count++; + } + } + if (highlight[face]) + highlight[face] = false; + else + highlight[face] = true; + canvas.repaint(); + } + } + } + + } + + + /** + * Record the player's move. + */ + public void selection(int pos, int player) { + + int num_combinations; + int comb; + + this.player = player; + + if (player == HUMAN) { + + // If position is already occupied, return. + if (occupied[pos] != 0) return; + + // Mark the position as HUMAN. + occupied[pos] = HUMAN; + + // Update the logic arrays. + this.player = update_logic_arrays(pos); + + // Have the computer determine its move. + choose_move(); + } + } + + + /** + * Determine the computer's move. + */ + public void choose_move () { + + if (player == MACHINE) { + + // Babe in the woods. + if (skill_level == 0) { + if (!block_winning_move()) { + if (!pick_7()) { + if (!check_outside_four()) { + pick_best_position(); + } + } + } + } + + // Walk and chew gum. + else if (skill_level == 1) { + if (!block_winning_move()) { + if (!block_intersecting_rows()) { + if (!block_inside_four()) { + if (!block_outside_four()) { + pick_best_position(); + } + } + } + } + } + + // Jeopordy contestant. + else if (skill_level == 2) { + if (!block_winning_move()) { + if (!block_intersecting_rows()) { + if (!block_inside_four()) { + if (!block_outside_four()) { + if (!pick_7()) { + pick_best_position(); + } + } + } + } + } + } + + // Rocket scientist. + else if (skill_level == 3) { + if (!block_winning_move()) { + if (!block_intersecting_rows()) { + if (!block_chair_move()) { + if (!check_face_three()) { + if (!block_central_four()) { + if (!block_inside_four()) { + if (!block_outside_four()) { + if (!take_inside_four()) { + if (!take_outside_four()) { + if (!pick_7()) { + if (!check_outside_four()) { + pick_best_position(); + } + } + } + } + } + } + } + } + } + } + } + } + + // Be afraid, be very afraid. + else if (skill_level == 4) { + if (!block_winning_move()) { + if (!block_intersecting_rows()) { + if (!block_chair_move()) { + if (!block_walk_move()) { + if (!block_central_four()) { + if (!block_inside_four()) { + if (!block_outside_four()) { + if (!check_face_three()) { + if (!check_intersecting_rows2()) { + if (!take_inside_four()) { + if (!take_outside_four()) { + if (!pick_7()) { + if (!check_outside_four()) { + pick_best_position(); + } + } + } + } + } + } + } + } + } + } + } + } + } + } + } + } + + + /** + * Check for a winning move. + */ + public boolean block_winning_move() { + + // Loop through each combination and see if any player occupies + // three positions. If so, take the last remaining position. + int pos; + for (int i=0; i<76; i++) { + if (combinations[i][0] == 3) { + for (int j=2; j<6; j++) { + pos = combinations[i][j]; + if (occupied[pos] == 0) { + occupied[pos] = MACHINE; + positions.set(pos, MACHINE); + player = update_logic_arrays(pos); + if (debug) System.out.println("block_winning_move: true"); + return true; + } + } + } + } + if (debug) System.out.println("check_winning_move: false"); + return false; + } + + + /** + * Block outside four + */ + public boolean block_outside_four() { + + int pos; + int index = 0; + int max = 0; + + // Block the opponent, if necessary. + for (int i=0; i<18; i++) { + if (outside_four[i][0] > 0 && + outside_four[i][1] == HUMAN) { + if(outside_four[i][0] > max) { + index = i; + max = outside_four[i][0]; + } + } + } + + if (max > 0) { + for (int j=2; j<6; j++) { + pos = outside_four[index][j]; + if (occupied[pos] == 0) { + occupied[pos] = MACHINE; + positions.set(pos, MACHINE); + player = update_logic_arrays(pos); + if (debug) System.out.println("block_outside_four: true"); + return true; + } + } + } + + if (debug) System.out.println("block_outside_four: false"); + return false; + } + + + /** + * Block central four + */ + public boolean block_central_four() { + + int pos; + int index = 0; + int max = 0; + + // Block the opponent, if necessary. + for (int i=1; i<3; i++) { + if (inside_four[i][0] > 0 && + inside_four[i][1] == HUMAN) { + if(inside_four[i][0] > max) { + index = i; + max = inside_four[i][0]; + } + } + } + + if (max > 0) { + for (int j=2; j<6; j++) { + pos = inside_four[index][j]; + if (occupied[pos] == 0) { + occupied[pos] = MACHINE; + positions.set(pos, MACHINE); + player = update_logic_arrays(pos); + if (debug) System.out.println("block_central_four: true"); + return true; + } + } + } + + if (debug) System.out.println("block_central_four: false"); + return false; + } + + /** + * Check each face for a forced win. + */ + public boolean check_face_three() { + + int pos; + int index = 0; + int human = 0; + int machine = 0; + + // Block the opponent from a forced win. + for (int i=0; i<18; i++) { + if (outside_four[i][0] == -1) { + human = 0; + machine = 0; + for (int j=2; j<6; j++) { + if (occupied[outside_four[i][j]] == MACHINE) + machine++; + else if (occupied[outside_four[i][j]] == HUMAN) + human++; + } + if (debug) System.out.println("machine = " + machine); + if (debug) System.out.println("human = " + human); + if (human == 3 && machine == 1) { + if (debug) System.out.println("human == 3 && machine == 1"); + for (int j=2; j<18; j++) { + pos = faces[i][j]; + if (occupied[pos] == 0) { + for (int k=0; k<76; k++) { + if (combinations[i][0] == 2 & + combinations[i][1] == HUMAN) { + for (int l=0; l<4; l++) { + if (combinations[i][l] == pos) { + occupied[pos] = MACHINE; + positions.set(pos, MACHINE); + player = update_logic_arrays(pos); + if (debug) System.out.println("check_face_three: true"); + return true; + } + } + } + } + } + } + } + } + } + + if (debug) System.out.println("check_face_three: false"); + return false; + } + + + + /** + * Block inside four + */ + public boolean block_inside_four() { + + int pos; + int index = 0; + int max = 0; + + // Block the opponent, if necessary. + for (int i=0; i<18; i++) { + if (inside_four[i][0] > 0 && + inside_four[i][1] == HUMAN) { + if(inside_four[i][0] > max) { + index = i; + max = inside_four[i][0]; + } + } + } + + if (max > 0) { + for (int j=2; j<6; j++) { + pos = inside_four[index][j]; + if (occupied[pos] == 0) { + occupied[pos] = MACHINE; + positions.set(pos, MACHINE); + player = update_logic_arrays(pos); + if (debug) System.out.println("block_inside_four: true"); + return true; + } + } + } + + if (debug) System.out.println("block_inside_four: false"); + return false; + } + + + public boolean block_chair_move() { + + int pos; + + int ncorners = 0; // Number of corners owned by human + int corner = 0; // Corner owned by machine + + if (debug) System.out.println("inside block_chair_move"); + + // Loop through all of the faces. + for(int i=0; i<18; i++) { + + // Determine which corners the human owns. + if (occupied[faces[i][2]] == HUMAN) + ncorners++; + else if (occupied[faces[i][2]] == MACHINE) + corner = 2; + if (occupied[faces[i][5]] == HUMAN) + ncorners++; + else if (occupied[faces[i][5]] == MACHINE) + corner = 5; + if (occupied[faces[i][14]] == HUMAN) + ncorners++; + else if (occupied[faces[i][14]] == MACHINE) + corner = 14; + if (occupied[faces[i][17]] == HUMAN) + ncorners++; + else if (occupied[faces[i][17]] == MACHINE) + corner = 17; + + // If the human owns three corners, continue with the search. + if (ncorners == 3) { + if (corner == 2) { + if (occupied[faces[i][ 3]] == HUMAN && occupied[faces[i][ 7]] == 0 && + occupied[faces[i][ 8]] == 0 && occupied[faces[i][11]] == 0 && + occupied[faces[i][15]] == 0 && occupied[faces[i][16]] == 0) { + pos = faces[i][11]; + occupied[pos] = MACHINE; + positions.set(pos, MACHINE); + player = update_logic_arrays(pos); + if (debug) System.out.println("block_chair_move: found"); + return true; + } + if (occupied[faces[i][ 4]] == HUMAN && occupied[faces[i][ 8]] == 0 && + occupied[faces[i][11]] == 0 && occupied[faces[i][12]] == 0 && + occupied[faces[i][15]] == 0 && occupied[faces[i][16]] == 0) { + pos = faces[i][12]; + occupied[pos] = MACHINE; + positions.set(pos, MACHINE); + player = update_logic_arrays(pos); + if (debug) System.out.println("block_chair_move: found"); + return true; + } + if (occupied[faces[i][ 6]] == HUMAN && occupied[faces[i][ 7]] == 0 && + occupied[faces[i][ 8]] == 0 && occupied[faces[i][ 9]] == 0 && + occupied[faces[i][11]] == 0 && occupied[faces[i][13]] == 0) { + pos = faces[i][8]; + occupied[pos] = MACHINE; + positions.set(pos, MACHINE); + player = update_logic_arrays(pos); + if (debug) System.out.println("block_chair_move: found"); + return true; + } + if (occupied[faces[i][10]] == HUMAN && occupied[faces[i][ 8]] == 0 && + occupied[faces[i][ 9]] == 0 && occupied[faces[i][11]] == 0 && + occupied[faces[i][12]] == 0 && occupied[faces[i][13]] == 0) { + pos = faces[i][11]; + occupied[pos] = MACHINE; + positions.set(pos, MACHINE); + player = update_logic_arrays(pos); + if (debug) System.out.println("block_chair_move: found"); + return true; + } + if (occupied[faces[i][ 7]] == HUMAN && occupied[faces[i][ 3]] == 0 && + occupied[faces[i][ 8]] == 0 && occupied[faces[i][11]] == 0 && + occupied[faces[i][15]] == 0 && occupied[faces[i][16]] == 0) { + pos = faces[i][11]; + occupied[pos] = MACHINE; + positions.set(pos, MACHINE); + player = update_logic_arrays(pos); + if (debug) System.out.println("block_chair_move: found"); + return true; + } + if (occupied[faces[i][12]] == HUMAN && occupied[faces[i][ 4]] == 0 && + occupied[faces[i][ 8]] == 0 && occupied[faces[i][11]] == 0 && + occupied[faces[i][15]] == 0 && occupied[faces[i][16]] == 0) { + pos = faces[i][16]; + occupied[pos] = MACHINE; + positions.set(pos, MACHINE); + player = update_logic_arrays(pos); + if (debug) System.out.println("block_chair_move: found"); + return true; + } + } + else if (corner == 5) { + if (occupied[faces[i][ 9]] == HUMAN && occupied[faces[i][ 6]] == 0 && + occupied[faces[i][ 7]] == 0 && occupied[faces[i][ 8]] == 0 && + occupied[faces[i][10]] == 0 && occupied[faces[i][12]] == 0) { + pos = faces[i][7]; + occupied[pos] = MACHINE; + positions.set(pos, MACHINE); + player = update_logic_arrays(pos); + if (debug) System.out.println("block_chair_move: found"); + return true; + } + if (occupied[faces[i][13]] == HUMAN && occupied[faces[i][ 7]] == 0 && + occupied[faces[i][ 7]] == 0 && occupied[faces[i][10]] == 0 && + occupied[faces[i][11]] == 0 && occupied[faces[i][12]] == 0) { + pos = faces[i][12]; + occupied[pos] = MACHINE; + positions.set(pos, MACHINE); + player = update_logic_arrays(pos); + if (debug) System.out.println("block_chair_move: found"); + return true; + } + if (occupied[faces[i][ 4]] == HUMAN && occupied[faces[i][ 8]] == 0 && + occupied[faces[i][11]] == 0 && occupied[faces[i][12]] == 0 && + occupied[faces[i][15]] == 0 && occupied[faces[i][16]] == 0) { + pos = faces[i][12]; + occupied[pos] = MACHINE; + positions.set(pos, MACHINE); + player = update_logic_arrays(pos); + if (debug) System.out.println("block_chair_move: found"); + return true; + } + if (occupied[faces[i][ 3]] == HUMAN && occupied[faces[i][ 7]] == 0 && + occupied[faces[i][11]] == 0 && occupied[faces[i][12]] == 0 && + occupied[faces[i][15]] == 0 && occupied[faces[i][16]] == 0) { + pos = faces[i][7]; + occupied[pos] = MACHINE; + positions.set(pos, MACHINE); + player = update_logic_arrays(pos); + if (debug) System.out.println("block_chair_move: found"); + return true; + } + if (occupied[faces[i][ 8]] == HUMAN && occupied[faces[i][ 4]] == 0 && + occupied[faces[i][11]] == 0 && occupied[faces[i][12]] == 0 && + occupied[faces[i][15]] == 0 && occupied[faces[i][16]] == 0) { + pos = faces[i][12]; + occupied[pos] = MACHINE; + positions.set(pos, MACHINE); + player = update_logic_arrays(pos); + if (debug) System.out.println("block_chair_move: found"); + return true; + } + if (occupied[faces[i][11]] == HUMAN && occupied[faces[i][ 3]] == 0 && + occupied[faces[i][ 7]] == 0 && occupied[faces[i][12]] == 0 && + occupied[faces[i][15]] == 0 && occupied[faces[i][16]] == 0) { + pos = faces[i][ 7]; + occupied[pos] = MACHINE; + positions.set(pos, MACHINE); + player = update_logic_arrays(pos); + if (debug) System.out.println("block_chair_move: found"); + return true; + } + } + else if (corner == 14) { + if (occupied[faces[i][ 6]] == HUMAN && occupied[faces[i][ 7]] == 0 && + occupied[faces[i][ 8]] == 0 && occupied[faces[i][ 9]] == 0 && + occupied[faces[i][11]] == 0 && occupied[faces[i][13]] == 0) { + pos = faces[i][7]; + occupied[pos] = MACHINE; + positions.set(pos, MACHINE); + player = update_logic_arrays(pos); + if (debug) System.out.println("block_chair_move: found"); + return true; + } + if (occupied[faces[i][10]] == HUMAN && occupied[faces[i][ 8]] == 0 && + occupied[faces[i][ 9]] == 0 && occupied[faces[i][11]] == 0 && + occupied[faces[i][12]] == 0 && occupied[faces[i][13]] == 0) { + pos = faces[i][12]; + occupied[pos] = MACHINE; + positions.set(pos, MACHINE); + player = update_logic_arrays(pos); + if (debug) System.out.println("block_chair_move: found"); + return true; + } + if (occupied[faces[i][15]] == HUMAN && occupied[faces[i][ 3]] == 0 && + occupied[faces[i][ 4]] == 0 && occupied[faces[i][ 7]] == 0 && + occupied[faces[i][11]] == 0 && occupied[faces[i][12]] == 0) { + pos = faces[i][3]; + occupied[pos] = MACHINE; + positions.set(pos, MACHINE); + player = update_logic_arrays(pos); + if (debug) System.out.println("block_chair_move: found"); + return true; + } + if (occupied[faces[i][16]] == HUMAN && occupied[faces[i][ 3]] == 0 && + occupied[faces[i][ 4]] == 0 && occupied[faces[i][ 7]] == 0 && + occupied[faces[i][ 8]] == 0 && occupied[faces[i][12]] == 0) { + pos = faces[i][12]; + occupied[pos] = MACHINE; + positions.set(pos, MACHINE); + player = update_logic_arrays(pos); + if (debug) System.out.println("block_chair_move: found"); + return true; + } + if (occupied[faces[i][11]] == HUMAN && occupied[faces[i][ 3]] == 0 && + occupied[faces[i][ 4]] == 0 && occupied[faces[i][ 7]] == 0 && + occupied[faces[i][12]] == 0 && occupied[faces[i][15]] == 0) { + pos = faces[i][7]; + occupied[pos] = MACHINE; + positions.set(pos, MACHINE); + player = update_logic_arrays(pos); + if (debug) System.out.println("block_chair_move: found"); + return true; + } + if (occupied[faces[i][ 8]] == HUMAN && occupied[faces[i][ 6]] == 0 && + occupied[faces[i][ 7]] == 0 && occupied[faces[i][ 9]] == 0 && + occupied[faces[i][12]] == 0 && occupied[faces[i][13]] == 0) { + pos = faces[i][7]; + occupied[pos] = MACHINE; + positions.set(pos, MACHINE); + player = update_logic_arrays(pos); + if (debug) System.out.println("block_chair_move: found"); + return true; + } + } + else if (corner == 17) { + if (occupied[faces[i][ 9]] == HUMAN && occupied[faces[i][ 6]] == 0 && + occupied[faces[i][ 7]] == 0 && occupied[faces[i][ 8]] == 0 && + occupied[faces[i][10]] == 0 && occupied[faces[i][11]] == 0) { + pos = faces[i][8]; + occupied[pos] = MACHINE; + positions.set(pos, MACHINE); + player = update_logic_arrays(pos); + if (debug) System.out.println("block_chair_move: found"); + return true; + } + if (occupied[faces[i][13]] == HUMAN && occupied[faces[i][ 6]] == 0 && + occupied[faces[i][ 8]] == 0 && occupied[faces[i][10]] == 0 && + occupied[faces[i][11]] == 0 && occupied[faces[i][12]] == 0) { + pos = faces[i][11]; + occupied[pos] = MACHINE; + positions.set(pos, MACHINE); + player = update_logic_arrays(pos); + if (debug) System.out.println("block_chair_move: found"); + return true; + } + if (occupied[faces[i][15]] == HUMAN && occupied[faces[i][ 3]] == 0 && + occupied[faces[i][ 4]] == 0 && occupied[faces[i][ 7]] == 0 && + occupied[faces[i][ 8]] == 0 && occupied[faces[i][11]] == 0) { + pos = faces[i][11]; + occupied[pos] = MACHINE; + positions.set(pos, MACHINE); + player = update_logic_arrays(pos); + if (debug) System.out.println("block_chair_move: found"); + return true; + } + if (occupied[faces[i][16]] == HUMAN && occupied[faces[i][ 3]] == 0 && + occupied[faces[i][ 4]] == 0 && occupied[faces[i][ 8]] == 0 && + occupied[faces[i][11]] == 0 && occupied[faces[i][12]] == 0) { + pos = faces[i][8]; + occupied[pos] = MACHINE; + positions.set(pos, MACHINE); + player = update_logic_arrays(pos); + if (debug) System.out.println("block_chair_move: found"); + return true; + } + if (occupied[faces[i][12]] == HUMAN && occupied[faces[i][ 3]] == 0 && + occupied[faces[i][ 4]] == 0 && occupied[faces[i][ 8]] == 0 && + occupied[faces[i][11]] == 0 && occupied[faces[i][16]] == 0) { + pos = faces[i][8]; + occupied[pos] = MACHINE; + positions.set(pos, MACHINE); + player = update_logic_arrays(pos); + if (debug) System.out.println("block_chair_move: found"); + return true; + } + if (occupied[faces[i][ 7]] == HUMAN && occupied[faces[i][ 3]] == 0 && + occupied[faces[i][ 4]] == 0 && occupied[faces[i][ 8]] == 0 && + occupied[faces[i][11]] == 0 && occupied[faces[i][15]] == 0) { + pos = faces[i][11]; + occupied[pos] = MACHINE; + positions.set(pos, MACHINE); + player = update_logic_arrays(pos); + if (debug) System.out.println("block_chair_move: found"); + return true; + } + } + } + ncorners = 0; + corner = -1; + } + if (debug) System.out.println("block_chair_move: false"); + return false; + } + + public boolean block_walk_move() { + + int pos; + + if (debug) System.out.println("inside block_walk_move"); + + // Loop through all of the faces. + for(int i=0; i<18; i++) { + + // Look for a matching pattern. + if (occupied[faces[i][ 2]] == HUMAN && occupied[faces[i][14]] == HUMAN && + occupied[faces[i][ 3]] == HUMAN && occupied[faces[i][15]] == HUMAN && + occupied[faces[i][ 6]] == 0 && occupied[faces[i][10]] == 0 && + occupied[faces[i][ 7]] == 0 && occupied[faces[i][11]] == 0) { + + if (occupied[faces[i][ 8]] == HUMAN && occupied[faces[i][ 9]] == 0) { + pos = faces[i][6]; + occupied[pos] = MACHINE; + positions.set(pos, MACHINE); + player = update_logic_arrays(pos); + return true; + } + else if (occupied[faces[i][12]] == HUMAN && occupied[faces[i][13]] == 0) { + pos = faces[i][10]; + occupied[pos] = MACHINE; + positions.set(pos, MACHINE); + player = update_logic_arrays(pos); + return true; + } + } + + // Look for a matching pattern. + if (occupied[faces[i][14]] == HUMAN && occupied[faces[i][17]] == HUMAN && + occupied[faces[i][10]] == HUMAN && occupied[faces[i][13]] == HUMAN && + occupied[faces[i][15]] == 0 && occupied[faces[i][16]] == 0 && + occupied[faces[i][11]] == 0 && occupied[faces[i][12]] == 0) { + + if (occupied[faces[i][7]] == HUMAN && occupied[faces[i][3]] == 0) { + pos = faces[i][15]; + occupied[pos] = MACHINE; + positions.set(pos, MACHINE); + player = update_logic_arrays(pos); + return true; + } + else if (occupied[faces[i][8]] == HUMAN && occupied[faces[i][4]] == 0) { + pos = faces[i][16]; + occupied[pos] = MACHINE; + positions.set(pos, MACHINE); + player = update_logic_arrays(pos); + return true; + } + } + + // Look for a matching pattern. + if (occupied[faces[i][ 4]] == HUMAN && occupied[faces[i][16]] == HUMAN && + occupied[faces[i][ 5]] == HUMAN && occupied[faces[i][17]] == HUMAN && + occupied[faces[i][ 8]] == 0 && occupied[faces[i][12]] == 0 && + occupied[faces[i][ 9]] == 0 && occupied[faces[i][13]] == 0) { + + if (occupied[faces[i][11]] == HUMAN && occupied[faces[i][10]] == 0) { + pos = faces[i][18]; + occupied[pos] = MACHINE; + positions.set(pos, MACHINE); + player = update_logic_arrays(pos); + return true; + } + else if (occupied[faces[i][7]] == HUMAN && occupied[faces[i][6]] == 0) { + pos = faces[i][9]; + occupied[pos] = MACHINE; + positions.set(pos, MACHINE); + player = update_logic_arrays(pos); + return true; + } + } + + // Look for a matching pattern. + if (occupied[faces[i][ 6]] == HUMAN && occupied[faces[i][ 9]] == HUMAN && + occupied[faces[i][ 2]] == HUMAN && occupied[faces[i][ 5]] == HUMAN && + occupied[faces[i][ 7]] == 0 && occupied[faces[i][ 8]] == 0 && + occupied[faces[i][ 3]] == 0 && occupied[faces[i][ 4]] == 0) { + + if (occupied[faces[i][11]] == HUMAN && occupied[faces[i][15]] == 0) { + pos = faces[i][3]; + occupied[pos] = MACHINE; + positions.set(pos, MACHINE); + player = update_logic_arrays(pos); + return true; + } + else if (occupied[faces[i][12]] == HUMAN && occupied[faces[i][16]] == 0) { + pos = faces[i][4]; + occupied[pos] = MACHINE; + positions.set(pos, MACHINE); + player = update_logic_arrays(pos); + return true; + } + } + + // Look for a matching pattern. + if (occupied[faces[i][ 2]] == HUMAN && occupied[faces[i][14]] == HUMAN && + occupied[faces[i][ 4]] == HUMAN && occupied[faces[i][16]] == HUMAN && + occupied[faces[i][ 6]] == 0 && occupied[faces[i][10]] == 0 && + occupied[faces[i][ 8]] == 0 && occupied[faces[i][12]] == 0) { + + if ((occupied[faces[i][7]] == HUMAN && occupied[faces[i][9]] == 0) || + (occupied[faces[i][9]] == HUMAN && occupied[faces[i][7]] == 0) ) { + pos = faces[i][6]; + occupied[pos] = MACHINE; + positions.set(pos, MACHINE); + player = update_logic_arrays(pos); + return true; + } + else if ((occupied[faces[i][11]] == HUMAN && occupied[faces[i][13]] == 0) || + (occupied[faces[i][13]] == HUMAN && occupied[faces[i][11]] == 0) ) { + pos = faces[i][10]; + occupied[pos] = MACHINE; + positions.set(pos, MACHINE); + player = update_logic_arrays(pos); + return true; + } + } + + // Look for a matching pattern. + if (occupied[faces[i][14]] == HUMAN && occupied[faces[i][17]] == HUMAN && + occupied[faces[i][ 6]] == HUMAN && occupied[faces[i][ 9]] == HUMAN && + occupied[faces[i][15]] == 0 && occupied[faces[i][16]] == 0 && + occupied[faces[i][ 7]] == 0 && occupied[faces[i][ 8]] == 0) { + + if ((occupied[faces[i][11]] == HUMAN && occupied[faces[i][ 3]] == 0) || + (occupied[faces[i][ 3]] == HUMAN && occupied[faces[i][11]] == 0) ) { + pos = faces[i][15]; + occupied[pos] = MACHINE; + positions.set(pos, MACHINE); + player = update_logic_arrays(pos); + return true; + } + else if ((occupied[faces[i][12]] == HUMAN && occupied[faces[i][ 4]] == 0) || + (occupied[faces[i][ 4]] == HUMAN && occupied[faces[i][12]] == 0) ) { + pos = faces[i][16]; + occupied[pos] = MACHINE; + positions.set(pos, MACHINE); + player = update_logic_arrays(pos); + return true; + } + } + + // Look for a matching pattern. + if (occupied[faces[i][ 3]] == HUMAN && occupied[faces[i][15]] == HUMAN && + occupied[faces[i][ 5]] == HUMAN && occupied[faces[i][17]] == HUMAN && + occupied[faces[i][ 7]] == 0 && occupied[faces[i][11]] == 0 && + occupied[faces[i][ 9]] == 0 && occupied[faces[i][13]] == 0) { + + if ((occupied[faces[i][ 6]] == HUMAN && occupied[faces[i][ 8]] == 0) || + (occupied[faces[i][ 8]] == HUMAN && occupied[faces[i][ 6]] == 0) ) { + pos = faces[i][9]; + occupied[pos] = MACHINE; + positions.set(pos, MACHINE); + player = update_logic_arrays(pos); + return true; + } + else if ((occupied[faces[i][10]] == HUMAN && occupied[faces[i][12]] == 0) || + (occupied[faces[i][12]] == HUMAN && occupied[faces[i][10]] == 0) ) { + pos = faces[i][13]; + occupied[pos] = MACHINE; + positions.set(pos, MACHINE); + player = update_logic_arrays(pos); + return true; + } + } + + // Look for a matching pattern. + if (occupied[faces[i][10]] == HUMAN && occupied[faces[i][13]] == HUMAN && + occupied[faces[i][ 2]] == HUMAN && occupied[faces[i][ 5]] == HUMAN && + occupied[faces[i][11]] == 0 && occupied[faces[i][12]] == 0 && + occupied[faces[i][ 3]] == 0 && occupied[faces[i][ 4]] == 0) { + + if ((occupied[faces[i][ 7]] == HUMAN && occupied[faces[i][15]] == 0) || + (occupied[faces[i][15]] == HUMAN && occupied[faces[i][ 7]] == 0) ) { + pos = faces[i][3]; + occupied[pos] = MACHINE; + positions.set(pos, MACHINE); + player = update_logic_arrays(pos); + return true; + } + else if ((occupied[faces[i][ 8]] == HUMAN && occupied[faces[i][16]] == 0) || + (occupied[faces[i][16]] == HUMAN && occupied[faces[i][ 8]] == 0) ) { + pos = faces[i][4]; + occupied[pos] = MACHINE; + positions.set(pos, MACHINE); + player = update_logic_arrays(pos); + return true; + } + } + + } + + if (debug) System.out.println("block_walk_move: false"); + return false; + } + + public boolean check_chair_move() { + + int pos; + + // If the "block chair flag" is set, all we need to do is + // block the winning path... + if (block_chair_flag) { + pos = faces[block_chair_face][block_chair_next_move]; + occupied[pos] = MACHINE; + positions.set(pos, MACHINE); + player = update_logic_arrays(pos); + if (debug) System.out.println("block_chair_move: march"); + return true; + } + + int ncorners = 0; // Number of corners owned by human + int corner = 0; // Corner owned by machine + + // Loop through all of the faces. + for(int i=0; i<18; i++) { + + // Determine which corners the human owns. + if (faces[i][ 2] == HUMAN) + ncorners++; + else + corner = 2; + if (faces[i][ 5] == HUMAN) + ncorners++; + else + corner = 5; + if (faces[i][14] == HUMAN) + ncorners++; + else + corner = 14; + if (faces[i][17] == HUMAN) + ncorners++; + else + corner = 17; + + // If the human owns three corners, continue with the search. + if (ncorners == 3) { + if (corner == 2) { + if (faces[i][ 3] == HUMAN && faces[i][ 7] == 0 && + faces[i][ 8] == 0 && faces[i][11] == 0 && + faces[i][15] == 0 && faces[i][16] == 0) { + block_chair_flag = true; + block_chair_next_move = 11; + block_chair_face = i; + pos = faces[i][15]; + occupied[pos] = MACHINE; + positions.set(pos, MACHINE); + player = update_logic_arrays(pos); + if (debug) System.out.println("block_chair_move: found"); + return true; + } + if (faces[i][ 4] == HUMAN && faces[i][ 8] == 0 && + faces[i][11] == 0 && faces[i][12] == 0 && + faces[i][15] == 0 && faces[i][16] == 0) { + block_chair_flag = true; + block_chair_next_move = 16; + block_chair_face = i; + pos = faces[i][8]; + occupied[pos] = MACHINE; + positions.set(pos, MACHINE); + player = update_logic_arrays(pos); + if (debug) System.out.println("block_chair_move: found"); + return true; + } + } + else if (corner == 5) { + block_chair_flag = true; + block_chair_next_move = 11; + block_chair_face = i; + pos = faces[i][15]; + occupied[pos] = MACHINE; + positions.set(pos, MACHINE); + player = update_logic_arrays(pos); + if (debug) System.out.println("check_face_three: true"); + return true; + } + else if (corner == 14) { + block_chair_flag = true; + block_chair_next_move = 11; + block_chair_face = i; + pos = faces[i][15]; + occupied[pos] = MACHINE; + positions.set(pos, MACHINE); + player = update_logic_arrays(pos); + if (debug) System.out.println("check_face_three: true"); + return true; + } + else if (corner == 17) { + block_chair_flag = true; + block_chair_next_move = 11; + block_chair_face = i; + pos = faces[i][15]; + occupied[pos] = MACHINE; + positions.set(pos, MACHINE); + player = update_logic_arrays(pos); + if (debug) System.out.println("check_face_three: true"); + return true; + } + } + } + return false; + } + + /** + * Take inside four + */ + public boolean take_inside_four() { + + int pos = 0; + boolean found = false; + + if (occupied[21] == 0) { + found = true; + pos = 21; + } + else if (occupied[22] == 0) { + found = true; + pos = 22; + } + else if (occupied[25] == 0) { + found = true; + pos = 25; + } + else if (occupied[26] == 0) { + found = true; + pos = 26; + } + else if (occupied[37] == 0) { + found = true; + pos = 37; + } + else if (occupied[38] == 0) { + found = true; + pos = 38; + } + else if (occupied[41] == 0) { + found = true; + pos = 41; + } + else if (occupied[42] == 0) { + found = true; + pos = 42; + } + + if (found) { + occupied[pos] = MACHINE; + positions.set(pos, MACHINE); + player = update_logic_arrays(pos); + if (debug) System.out.println("take_inside_four: true"); + return true; + } + + if (debug) System.out.println("take_inside_four: false"); + return false; + } + + + /** + * Check occupancy of outside four. + */ + public boolean check_outside_four() { + + int pos = 0; + + // Finish off the four corner combination. + if (outside_four_flag) { + if (occupied[faces[face_index][7]] == 0) { + pos = faces[face_index][7]; + } + else if (occupied[faces[face_index][6]] == 0) { + pos = faces[face_index][6]; + } + + if (occupied[pos] == 0) { + occupied[pos] = MACHINE; + positions.set(pos, MACHINE); + player = update_logic_arrays(pos); + return true; + } + } + + // Look for a four corner combination. + for (int i=0; i<18; i++) { + if (outside_four[i][0] == 4 && + outside_four[i][1] == MACHINE) { + if (faces[i][0] > 0 && + faces[i][1] == MACHINE) { + if (occupied[faces[i][8]] == 0) { + pos = faces[i][8]; + outside_four_flag = true; + face_index = i; + } + if (occupied[pos] == 0) { + occupied[pos] = MACHINE; + positions.set(pos, MACHINE); + player = update_logic_arrays(pos); + if (debug) System.out.println("check_outside_four: true"); + return true; + } + } + } + } + + // Take the corners, if available. + for (int i=0; i<18; i++) { + if (outside_four[i][0] > 0 && + outside_four[i][1] == MACHINE) { + if (faces[i][0] > 0 && + faces[i][1] == MACHINE) { + for (int j=2; j<6; j++) { + pos = outside_four[i][j]; + if (occupied[pos] == 0) { + occupied[pos] = MACHINE; + positions.set(pos, MACHINE); + player = update_logic_arrays(pos); + if (debug) System.out.println("check_outside_four: true"); + return true; + } + } + } + } + } + + // Look for an "outside four" combination in a face in which the + // opponent holds no positions. + for (int i=0; i<18; i++) { + if (outside_four[i][0] == 0 || (outside_four[i][0] > 0 && + outside_four[i][1] == MACHINE)) { + + if (outside_four[i][1] == MACHINE) + outside_four_flag = true; + for (int j=2; j<6; j++) { + pos = outside_four[i][j]; + if (occupied[pos] == 0) { + occupied[pos] = MACHINE; + positions.set(pos, MACHINE); + player = update_logic_arrays(pos); + if (debug) System.out.println("check_outside_four: true"); + return true; + } + } + } + } + + if (debug) System.out.println("check_outside_four: false"); + return false; + } + + + /** + * Take outside four + */ + public boolean take_outside_four() { + + int pos = 0; + boolean found = false; + + if (occupied[0] == 0) { + found = true; + pos = 0; + } + else if (occupied[3] == 0) { + found = true; + pos = 3; + } + else if (occupied[12] == 0) { + found = true; + pos = 12; + } + else if (occupied[15] == 0) { + found = true; + pos = 15; + } + else if (occupied[48] == 0) { + found = true; + pos = 48; + } + else if (occupied[51] == 0) { + found = true; + pos = 51; + } + else if (occupied[60] == 0) { + found = true; + pos = 60; + } + else if (occupied[63] == 0) { + found = true; + pos = 63; + } + + if (found) { + occupied[pos] = MACHINE; + positions.set(pos, MACHINE); + player = update_logic_arrays(pos); + if (debug) System.out.println("take_outside_four: true"); + return true; + } + + if (debug) System.out.println("take_outside_four: false"); + return false; + } + + + /** + * Check for a forced win by intersecting rows. Block + * if necessary. + */ + public boolean block_intersecting_rows() { + + int pos; + + // Loop through each row and check for rows that have two + // positions occupied by the human and two positions which are empty. + // Make sure that none of the empty positions in this row intersect + // with another row that also contains two positions held by the human. + // If so, block the row by taking the position at the intersection + // of these two row. + + // Loop through each row. + for (int i=0; i<76; i++) { + + // Look for a row that has two positions held by the human. + if (combinations[i][0] == 2 && combinations[i][1] == HUMAN) { + + if (debug) + System.out.println(" row " + i + "has 2 positions occupied by the human"); + + // Mark this row with a flag. + combinations[i][6] = 1; + + // Check each position in the row. + for (int j=2; j<6; j++) { + + // Look for the empty positions in the row. + pos = combinations[i][j]; + if (occupied[pos] == 0) { + + // Loop through the rows again. + for (int k=0; k<76; k++) { + + if (debug) System.out.println(" row " + k); + + // Look for another row that has two positions held + // by the human (and which is unmarked.) modified + if (combinations[k][0] == 2 && + combinations[k][1] == HUMAN && + combinations[k][6] == 0) { + + if (debug) + System.out.println("found an intersecting row: row " + k); + + // Check the positions in this row and see if + // any match the position we're looking for. If + // we find a match, grab the position and return. + for (int l=2; l<6; l++) { + if (pos == combinations[k][l]) { + combinations[i][6] = 0; + occupied[pos] = MACHINE; + positions.set(pos, MACHINE); + player = update_logic_arrays(pos); + if (debug) System.out.println("block_intersecting_rows: true"); + return true; + } + } + } + } + } + } + + // Unmark the combination before moving on. + combinations[i][6] = 0; + } + + } + if (debug) System.out.println("block_intersecting_rows: false"); + return false; + } + + /** + * Check for a forced win by intersecting rows. Block + * if necessary. + */ + public boolean check_intersecting_rows2() { + + int pos; + + // Loop through each row and check for rows that have two + // positions occupied by the human and two positions which are empty. + // Make sure that none of the empty positions in this row intersect + // with another row that also contains two positions held by the human. + // If so, block the row by taking the position at the intersection + // of these two row. + + // Loop through each row. + for (int i=0; i<76; i++) { + + // Look for a row that has two positions held by the human. + if (combinations[i][0] == 2 && combinations[i][1] == HUMAN) { + + if (debug) { + System.out.println(" row " + i + "has 2 positions occupied by the human"); + } + + // Mark this row with a flag. + combinations[i][6] = 1; + + // Check each position in the row. + for (int j=2; j<6; j++) { + + // Look for the empty positions in the row. + pos = combinations[i][j]; + if (occupied[pos] == 0) { + + // Loop through the rows again. + for (int k=0; k<76; k++) { + + if (debug) System.out.println(" row " + k); + + // Look for another row that has two positions held + // by the human (and which is unmarked.) modified + if (combinations[k][0] == 1 && + combinations[k][1] == HUMAN && + combinations[k][6] == 0) { + + if (debug) + System.out.println("found an intersecting row: row " + k); + + // Check the positions in this row and see if + // any match the position we're looking for. If + // we find a match, grab the position and return. + for (int l=2; l<6; l++) { + if (pos == combinations[k][l]) { + combinations[i][6] = 0; + occupied[pos] = MACHINE; + positions.set(pos, MACHINE); + player = update_logic_arrays(pos); + if (debug) System.out.println("check_intersecting_rows: true"); + return true; + } + } + } + } + } + } + + // Unmark the combination before moving on. + combinations[i][6] = 0; + } + + } + if (debug) System.out.println("check_intersecting_rows: false"); + return false; + } + + + /** + * Check for a forced win by intersecting rows. Block + * if necessary. + */ + public boolean check_for_two() { + + int pos; + + // Loop through the rows. + for (int i=0; i<76; i++) { + + // Look for a row that has two positions held + // by the human (and which is unmarked.) + if (combinations[i][0] == 2 && + combinations[i][1] == HUMAN && + combinations[i][6] == 0) { + + // Take the first available spot. + for (int j=2; j<6; j++) { + pos = combinations[i][j]; + if (occupied[pos] == 0) { + occupied[pos] = MACHINE; + positions.set(pos, MACHINE); + player = update_logic_arrays(pos); + if (debug) System.out.println("check_for_two: true"); + return true; + } + } + + } + } + if (debug) System.out.println("check_for_two: false"); + return false; + } + + public void undo_move() { + + // Return if no moves are recorded + if (nmoves == 0) return; + + // Set the undo flag + undoFlag = true; + + // Undo the last two moves + positions.clear(moves[--nmoves]); + positions.clear(moves[--nmoves]); + + // Undo the winner flag in the positions object + positions.noWinner(); + + // Repaint the 2D canvas. + canvas.repaint(); + + // Reset the inside/outside flags + inside_four_flag = false; + outside_four_flag = false; + block_chair_flag = false; + + // Reset the board + for (int i=0; i<64; i++) { + occupied[i] = 0; + } + + // Reset the inside/outside arrays + for (int i=0; i<18; i++) { + inside_four[i][0] = 0; + inside_four[i][1] = 0; + outside_four[i][0] = 0; + outside_four[i][1] = 0; + } + + // Reset the faces array + for (int i=0; i<18; i++) { + faces[i][0] = 0; + faces[i][1] = 0; + } + + // Reset the combinations array + for (int i=0; i<76; i++) { + combinations[i][0] = 0; + combinations[i][1] = 0; + } + + if (nmoves == 0) { + undoFlag = false; + player = HUMAN; + return; + } + + // Update the logic arrays + int pos; + player = HUMAN; + for (int i=0; i<nmoves; i++) { + pos = moves[i]; + occupied[pos] = player; + player = update_logic_arrays(pos); + } + + // Reset the "best picks" array + update_best_picks(); + + // Reset the player and undo flag + player = HUMAN; + undoFlag = false; + } + + /** + * Update the logic arrays that keep track of positions and status. + * If we have a winner, stop the game. + */ + public int update_logic_arrays(int pos) { + + // Record the move. + if (!undoFlag) { + moves[nmoves++] = pos; + } + + // Get the number of combinations that this position has. + int num_combinations = pos_to_comb[pos][0]; + + // Go through each combination associated with this position + // and update the status. If we have a winner, stop the game. + int comb; + for (int j=0; j<num_combinations; j++) { + comb = pos_to_comb[pos][j+1]; + if (combinations[comb][1] != player && + combinations[comb][1] != 0) { + combinations[comb][0] = -1; + } + else { + combinations[comb][0]++; + if (combinations[comb][0] == 4) { + end_time = System.currentTimeMillis(); + time = (end_time - beg_time)/1000; + panel.winner(player, skill_level, nmoves, time); + panel.repaint(); + canvas.repaint(); + positions.winner(); + return END; + } + else { + combinations[comb][1] = player; + } + } + } + + // Update the best_picks array. + update_best_picks(); + + // Update the inside_four array. + for (int i=0; i<18; i++) { + for (int j=2; j<6; j++) { + if (pos == inside_four[i][j]) { + if (inside_four[i][0] == 0) { + inside_four[i][0] = 1; + inside_four[i][1] = player; + } + else if (inside_four[i][1] == player) { + inside_four[i][0]++; + inside_four[i][1] = player; + } + else { + inside_four[i][0] = -1; + } + } + } + } + + // Update the outside_four array. + for (int i=0; i<18; i++) { + for (int j=2; j<6; j++) { + if (pos == outside_four[i][j]) { + if (outside_four[i][0] == 0) { + outside_four[i][0] = 1; + outside_four[i][1] = player; + } + else if (outside_four[i][1] == player) { + outside_four[i][0]++; + outside_four[i][1] = player; + } + else { + outside_four[i][0] = -1; + } + } + } + } + + // Update the faces array. + for (int i=0; i<18; i++) { + for (int j=2; j<18; j++) { + if (pos == faces[i][j]) { + if (faces[i][0] == 0) { + faces[i][0] = 1; + faces[i][1] = player; + } + else if (faces[i][1] == player) { + faces[i][0]++; + } + else { + faces[i][0] = -1; + } + } + } + + } + + // Switch players. + if (player == HUMAN) + return MACHINE; + else + return HUMAN; + } + + + /** + * Start a new game. + */ + public void newGame() { + + // Initialize the inside/outside flags. + inside_four_flag = false; + outside_four_flag = false; + block_chair_flag = false; + + // Initialize the inside/outside arrays. + for (int i=0; i<18; i++) { + inside_four[i][0] = 0; + inside_four[i][1] = 0; + outside_four[i][0] = 0; + outside_four[i][1] = 0; + } + + // Initialize the faces array. + for (int i=0; i<18; i++) { + faces[i][0] = 0; + faces[i][1] = 0; + } + + // Initialize the board. + for (int i=0; i<64; i++) { + occupied[i] = 0; + } + for (int i=0; i<76; i++) { + combinations[i][0] = 0; + combinations[i][1] = 0; + } + + // Reset the best_picks array. + update_best_picks(); + + // Set the player with the first move. + player = HUMAN; + + // Initialize the number of moves. + nmoves = 0; + + // Reset the playing positions. + positions.newGame(); + } + + + /** + * Set the skill level. + */ + public void set_skill_level(int level) { + skill_level = level; + } + + + /** + * Set up the pos_to_comb array. + */ + public void setup_pos_to_comb() { + + // Set up the pos_to_comb array to point to every winning + // combination a given position may have. + int count; + for (int i=0; i<64; i++) { + count = 1; + pos_to_comb[i][0] = 0; + for (int j=0; j<76; j++) { + for (int k=2; k<6; k++) { + if (combinations[j][k] == i) { + pos_to_comb[i][0]++; + pos_to_comb[i][count++] = j; + } + } + } + } + + if (debug) { + for (int i=0; i<64; i++) { + System.out.println(""); + for (int j=0; j<8; j++) { + System.out.println("pos_to_comb[" + i + "][" + j + "] = " + pos_to_comb[i][j]); + } + } + } + + } + + + /** + * Update the best_picks array. + */ + public void update_best_picks() { + + // Re-calculate the best_picks array to point to every (current) winning + // combination a given position may have. + int count; + for (int i=0; i<64; i++) { + + count = 1; + best_picks[i][0] = 0; + if (occupied[i] == 0) { + for (int j=0; j<76; j++) { + + if (combinations[j][0] == 0 || + combinations[j][1] == MACHINE) { + + for (int k=2; k<6; k++) { + if (combinations[j][k] == i) { + best_picks[i][0]++; + best_picks[i][count++] = j; + } + } + } + } + } + } + + if (debug) { + for (int i=0; i<64; i++) { + System.out.println(""); + for (int j=0; j<8; j++) { + System.out.println("best_picks[" + i + "][" + j + "] = " + best_picks[i][j]); + } + } + } + } + + + /** + * Pick the computer's best possible move based on the number + * of combinations per position. Choose the position with the + * most combinations. + */ + public void pick_best_position() { + + int pos = 0; + int max_num = 0; + for (int i=0; i<64; i++) { + if (best_picks[i][0] > max_num && + occupied[i] == 0) { + pos = i; + max_num = best_picks[i][0]; + } + } + + // Mark the position as MACHINE. + occupied[pos] = MACHINE; + + positions.set(pos, MACHINE); + + // Udate the logic arrays and reset the player. + player = update_logic_arrays(pos); + } + + + public boolean pick_7() { + + for (int i=0; i<64; i++) { + if (best_picks[i][0] == 7) { + occupied[i] = MACHINE; + positions.set(i, MACHINE); + player = update_logic_arrays(i); + return true; + } + } + return false; + + } + + public void change_face() { + current_face = ++current_face%18; + } + + public void label() { + label_flag ^= true; + } + + public boolean unoccupied(int pos) { + if (occupied[pos] == UNOCCUPIED) + return true; + else + return false; + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/four_by_four/Canvas2D.java b/src/main/java/org/jdesktop/j3d/examples/four_by_four/Canvas2D.java new file mode 100644 index 0000000..ea63b4b --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/four_by_four/Canvas2D.java @@ -0,0 +1,96 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.four_by_four; + +import java.awt.Canvas; +import java.awt.Graphics; +import java.awt.Image; +import java.awt.event.MouseEvent; +import java.awt.event.MouseListener; + +/** + * Class: Canvas2D + * + * Description: Used to respond to mouse events in the 2D window. + * + * Version: 1.0 + * + */ +class Canvas2D extends Canvas implements MouseListener { + + Image backbuffer; // Backbuffer image + Graphics gc; // Graphics context of backbuffer + Board board; // Game board + + Canvas2D(Board board) { + this.board = board; + } + + public void setBuffer(Image backbuffer) { + this.backbuffer = backbuffer; + gc = backbuffer.getGraphics(); + } + + public void update(Graphics g) { + paint(g); + } + + public void paint(Graphics g) { + if (board != null) { + board.render2D(gc); + g.drawImage(backbuffer, 0, 0, this); + } + } + + public void mousePressed(MouseEvent e) { + board.checkSelection2D(e.getX(), e.getY(), 1); + repaint(); + } + + public void mouseClicked(MouseEvent e) {} + public void mouseReleased(MouseEvent e) {} + public void mouseEntered(MouseEvent e) {} + public void mouseExited(MouseEvent e) {} +} diff --git a/src/main/java/org/jdesktop/j3d/examples/four_by_four/Cube.java b/src/main/java/org/jdesktop/j3d/examples/four_by_four/Cube.java new file mode 100644 index 0000000..2460881 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/four_by_four/Cube.java @@ -0,0 +1,132 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.four_by_four; + +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.QuadArray; +import org.jogamp.java3d.Shape3D; + +public class Cube extends Object { + + private Shape3D shape3D; + + private static final float[] verts = { + // Front Face + 1.0f, -1.0f, 1.0f, 1.0f, 1.0f, 1.0f, + -1.0f, 1.0f, 1.0f, -1.0f, -1.0f, 1.0f, + // Back Face + -1.0f, -1.0f, -1.0f, -1.0f, 1.0f, -1.0f, + 1.0f, 1.0f, -1.0f, 1.0f, -1.0f, -1.0f, + // Right Face + 1.0f, -1.0f, -1.0f, 1.0f, 1.0f, -1.0f, + 1.0f, 1.0f, 1.0f, 1.0f, -1.0f, 1.0f, + // Left Face + -1.0f, -1.0f, 1.0f, -1.0f, 1.0f, 1.0f, + -1.0f, 1.0f, -1.0f, -1.0f, -1.0f, -1.0f, + // Top Face + 1.0f, 1.0f, 1.0f, 1.0f, 1.0f, -1.0f, + -1.0f, 1.0f, -1.0f, -1.0f, 1.0f, 1.0f, + // Bottom Face + -1.0f, -1.0f, 1.0f, -1.0f, -1.0f, -1.0f, + 1.0f, -1.0f, -1.0f, 1.0f, -1.0f, 1.0f, + }; + + private static final float[] normals = { + // Front Face + 0.0f, 0.0f, 1.0f, 0.0f, 0.0f, 1.0f, + 0.0f, 0.0f, 1.0f, 0.0f, 0.0f, 1.0f, + // Back Face + 0.0f, 0.0f, -1.0f, 0.0f, 0.0f, -1.0f, + 0.0f, 0.0f, -1.0f, 0.0f, 0.0f, -1.0f, + // Right Face + 1.0f, 0.0f, 0.0f, 1.0f, 0.0f, 0.0f, + 1.0f, 0.0f, 0.0f, 1.0f, 0.0f, 0.0f, + // Left Face + -1.0f, 0.0f, 0.0f, -1.0f, 0.0f, 0.0f, + -1.0f, 0.0f, 0.0f, -1.0f, 0.0f, 0.0f, + // Top Face + 0.0f, 1.0f, 0.0f, 0.0f, 1.0f, 0.0f, + 0.0f, 1.0f, 0.0f, 0.0f, 1.0f, 0.0f, + // Bottom Face + 0.0f, -1.0f, 0.0f, 0.0f, -1.0f, 0.0f, + 0.0f, -1.0f, 0.0f, 0.0f, -1.0f, 0.0f, + }; + + public Cube(Appearance appearance) { + + QuadArray quadArray = new QuadArray(24, QuadArray.COORDINATES | + QuadArray.NORMALS | + QuadArray.TEXTURE_COORDINATE_2); + quadArray.setCoordinates(0, verts); + quadArray.setNormals(0, normals); + + shape3D = new Shape3D(quadArray, appearance); + shape3D.setCapability(Shape3D.ALLOW_GEOMETRY_READ); + shape3D.setCapability(Shape3D.ALLOW_GEOMETRY_WRITE); + shape3D.setCapability(Shape3D.ALLOW_APPEARANCE_READ); + shape3D.setCapability(Shape3D.ALLOW_APPEARANCE_WRITE); + } + + public Cube(Appearance appearance, float size) { + + QuadArray quadArray = new QuadArray(24, QuadArray.COORDINATES | + QuadArray.NORMALS); + for (int i=0; i<72; i++) + verts[i] *= size; + + quadArray.setCoordinates(0, verts); + quadArray.setNormals(0, normals); + + shape3D = new Shape3D(quadArray, appearance); + shape3D.setCapability(Shape3D.ALLOW_GEOMETRY_READ); + shape3D.setCapability(Shape3D.ALLOW_GEOMETRY_WRITE); + shape3D.setCapability(Shape3D.ALLOW_APPEARANCE_READ); + shape3D.setCapability(Shape3D.ALLOW_APPEARANCE_WRITE); + } + + public Shape3D getChild() { + return shape3D; + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/four_by_four/Cylinder.java b/src/main/java/org/jdesktop/j3d/examples/four_by_four/Cylinder.java new file mode 100644 index 0000000..db13a32 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/four_by_four/Cylinder.java @@ -0,0 +1,117 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.four_by_four; + +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.QuadArray; +import org.jogamp.java3d.Shape3D; + +public class Cylinder { + + float verts[]; + float normals[]; + QuadArray quad = null; + float div = 3.0f; + Shape3D shape; + + public Cylinder(float x, float z, float radius, float length, int quality, Appearance a) { + + if (quality < 3) quality = 3; + + div = (float) quality; + + verts = new float[quality*12]; + normals = new float[quality*12]; + + double inc = 2.0*Math.PI/(double)div; + for (int i=0; i< quality; i++){ + float z1 = radius * (float)Math.sin((double)i*inc) + z; + float x1 = radius * (float)Math.cos((double)i*inc) + x; + float z2 = radius * (float)Math.sin((double)(i+1)*inc) + z; + float x2 = radius * (float)Math.cos((double)(i+1)*inc) + x; + + verts[12*i] = x1; + verts[12*i+1] = -length/2.f; + verts[12*i+2] = z1; + verts[12*i+3] = x1; + verts[12*i+4] = length/2.f; + verts[12*i+5] = z1; + verts[12*i+6] = x2; + verts[12*i+7] = length/2.f; + verts[12*i+8] = z2; + verts[12*i+9] = x2; + verts[12*i+10] = -length/2.f; + verts[12*i+11] = z2; + + float nz1 = (float)Math.sin((double)i*inc); + float nx1 = (float)Math.cos((double)i*inc); + float nz2 = (float)Math.sin((double)(i+1)*inc); + float nx2 = (float)Math.cos((double)(i+1)*inc); + + normals[12*i] = nx1; + normals[12*i+1] = 0.0f; + normals[12*i+2] = nz1; + normals[12*i+3] = nx1; + normals[12*i+4] = 0.0f; + normals[12*i+5] = nz1; + normals[12*i+6] = nx2; + normals[12*i+7] = 0.0f; + normals[12*i+8] = nz2; + normals[12*i+9] = nx2; + normals[12*i+10] = 0.0f; + normals[12*i+11] = nz2; + } + + quad = new QuadArray(quality*4, QuadArray.COORDINATES | + QuadArray.NORMALS ); + quad.setCoordinates(0, verts); + quad.setNormals(0, normals); + shape = new Shape3D(quad, a); + } + + Shape3D getShape(){ + return shape; + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/four_by_four/FourByFour.html b/src/main/java/org/jdesktop/j3d/examples/four_by_four/FourByFour.html new file mode 100644 index 0000000..db06814 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/four_by_four/FourByFour.html @@ -0,0 +1,15 @@ +<HTML> +<HEAD> +<TITLE>Drag the mouse in the window</TITLE> +</HEAD> +<BODY BGCOLOR="#0C0C33"> +<applet align=middle codebase="../../../../.." code="org.jdesktop.j3d.examples.four_by_four.FourByFour" width=716 height=410> +<blockquote> +<hr> +If you were using a Java-capable browser, +you would see "FourByFour" instead of this paragraph. +<hr> +</blockquote> +</applet> +</BODY> +</HTML> diff --git a/src/main/java/org/jdesktop/j3d/examples/four_by_four/FourByFour.java b/src/main/java/org/jdesktop/j3d/examples/four_by_four/FourByFour.java new file mode 100644 index 0000000..3f1a3e1 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/four_by_four/FourByFour.java @@ -0,0 +1,893 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.four_by_four; + +import java.applet.Applet; +import java.awt.Button; +import java.awt.Checkbox; +import java.awt.CheckboxGroup; +import java.awt.Color; +import java.awt.Image; +import java.awt.Label; +import java.awt.Panel; +import java.awt.TextArea; +import java.awt.TextField; +import java.awt.event.ActionEvent; +import java.awt.event.ActionListener; +import java.awt.event.WindowAdapter; +import java.awt.event.WindowEvent; +import java.io.BufferedInputStream; +import java.io.BufferedReader; +import java.io.FileOutputStream; +import java.io.IOException; +import java.io.InputStream; +import java.io.InputStreamReader; +import java.io.OutputStreamWriter; +import java.io.Reader; +import java.io.StreamTokenizer; +import java.net.URL; + +import org.jdesktop.j3d.examples.Resources; +import org.jogamp.java3d.AmbientLight; +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.Background; +import org.jogamp.java3d.BoundingLeaf; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.DirectionalLight; +import org.jogamp.java3d.Material; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.View; +import org.jogamp.java3d.utils.applet.MainFrame; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Vector3f; + +/** + * Class FourByFour + * + * Description: High level class for the game FourByFour + * + * Version: 1.2 + * + */ +public class FourByFour extends Applet implements ActionListener { + + // To write scores to scores file + private static final boolean writeScoresFile = false; + + String host; // Host from which this applet came from + int port; // Port number for writing high scores + Image backbuffer2D; // Backbuffer image used for 2D double buffering + int width, height; // Size of the graphics window in pixels + int score; // Final game score + int level_weight; // Weighting factor for skill level + int move_weight; // Weighting factor for number of moves to win + int time_weight; // Weighting factor for amount of time it took to win + int skill_level; // Skill level, 0 - 4 + Canvas2D canvas2D; // 2D rendering canvas + Canvas3D canvas3D; // 3D rendering canvas + Board board; // Game board object + Panel b_container; // Container to hold the buttons + Panel c_container; // Container to hold the canvas + Panel l_container; // Container to hold the labels + Panel skill_panel; // Panel to hold skill levels + Panel instruct_panel; // Panel to hold instructions + Panel winner_panel; // Panel to hold winner announcement + Panel high_panel; // Panel to hold high scores + Button instruct_button; // Instructions button + Button new_button; // New Game button + Button skill_button; // Skill Level button + Button high_button; // High Scores button + Button undo_button; // Undo Move button + Label skill_label; // Label on skill panel + Label winner_label; // Label on winner panel + Label winner_score_label; // Score label on winner panel + Label winner_name_label; // Name label on winner panel + Label winner_top_label; // Top 20 label on winner panel + Label high_label; // High score label + Label high_places[]; // Labels to hold places + Label high_names[]; // Labels to hold names + Label high_scores[]; // Labels to hold scores + TextArea instruct_text; // TextArea object that holds instructions + TextArea high_text; // TextArea object that holds top 20 scores + TextField winner_name; // TextField object that holds winner's name + Button instruct_return_button; // Return button for instruction panel + Button skill_return_button; // Return button for skill level panel + Button winner_return_button; // Return button for winner panel + Button high_return_button; // Return button for high scores panel + CheckboxGroup group; // CheckboxGroup object for skill level panel + InputStream inStream; // Input stream for reading instructions and high scores + static boolean appletFlag = true; // Applet flag + boolean winner_flag = false; // Winner flag + byte text[]; // Temporary storage area for reading instructions file + byte outText[]; // Temporary storage area for writing high scores file + String textString; // Storage area for instructions + String scoresString; // String used for writing high scores file + int places[]; // Storage area for high score places + int scores[]; // Storage area for high score scores + String names[]; // Storage area for high score names + Positions positions; // Positions object, used to render player positions + + private SimpleUniverse universe = null; + + /** + * Initialization + */ + public void init() {System.setProperty("sun.awt.noerasebackground", "true"); + + // Set the port number. + port = 4111; + + // Set the graphics window size. + width = 350; + height = 350; + + // Set the weighting factors used for scoring. + level_weight = 1311; + move_weight = 111; + time_weight = 1000; + + // Create the "base" color for the AWT components. + setBackground(new Color(200, 200, 200)); + + // Read the instructions file. + if (appletFlag) { + + // Get the host from which this applet came. + host = getCodeBase().getHost(); + + try { + URL instrURL = Resources.getResource("four_by_four/instructions.txt"); + inStream = new BufferedInputStream((instrURL).openStream(), 8192); + text = new byte[5000]; + int character = inStream.read(); + int count = 0; + while (character != -1) { + text[count++] = (byte) character; + character = inStream.read(); + } + textString = new String(text); + inStream.close(); + } + catch(Exception e) { + System.out.println("Error: " + e.toString()); + } + } + else { + + try { + URL instrURL = Resources.getResource("four_by_four/instructions.txt"); + inStream = new BufferedInputStream((instrURL).openStream(), 8192); + text = new byte[5000]; + int character = inStream.read(); + int count = 0; + while (character != -1) { + text[count++] = (byte) character; + character = inStream.read(); + } + textString = new String(text); + inStream.close(); + } + catch(Exception e) { + System.out.println("Error: " + e.toString()); + } + } + + // Read the high-scores file. + places = new int[20]; + scores = new int[20]; + names = new String[20]; + if (appletFlag) { + try { + URL scoreURL = Resources.getResource("four_by_four/scores.txt"); + inStream = new BufferedInputStream((scoreURL).openStream(), 8192); + Reader read = new BufferedReader(new InputStreamReader(inStream)); + StreamTokenizer st = new StreamTokenizer(read); + st.whitespaceChars(32,44); + st.eolIsSignificant(false); + + int count = 0; + int token = st.nextToken(); + boolean scoreFlag = true; + String string; + while (count<20) { + places[count] = (int) st.nval; + string = new String(""); + token = st.nextToken(); + while (token == StreamTokenizer.TT_WORD) { + string += st.sval; + string += " "; + token = st.nextToken(); + } + names[count] = string; + scores[count] = (int) st.nval; + token = st.nextToken(); + count++; + } + inStream.close(); + } + catch(Exception e) { + System.out.println("Error: " + e.toString()); + } + } + else { + try { + URL scoreURL = Resources.getResource("four_by_four/scores.txt"); + inStream = new BufferedInputStream((scoreURL).openStream(), 8192); + Reader read = new BufferedReader(new InputStreamReader(inStream)); + StreamTokenizer st = new StreamTokenizer(read); + st.whitespaceChars(32,44); + st.eolIsSignificant(false); + + int count = 0; + int token = st.nextToken(); + boolean scoreFlag = true; + String string; + while (count<20) { + places[count] = (int) st.nval; + string = new String(""); + token = st.nextToken(); + while (token == StreamTokenizer.TT_WORD) { + string += st.sval; + string += " "; + token = st.nextToken(); + } + names[count] = string; + scores[count] = (int) st.nval; + token = st.nextToken(); + count++; + } + inStream.close(); + } + catch(Exception e) { + System.out.println("Error: " + e.toString()); + } + } + + // The positions object sets up the switch nodes which + // control the rendering of the player's positions. + positions = new Positions(); + + // Create the game board object which is responsible + // for keeping track of the moves on the game board + // and determining what move the computer should make. + board = new Board(this, positions, width, height); + positions.setBoard(board); + + // Create a 2D graphics canvas. + canvas2D = new Canvas2D(board); + canvas2D.setSize(width, height); + canvas2D.setLocation(width+10, 5); + canvas2D.addMouseListener(canvas2D); + board.setCanvas(canvas2D); + + // Create the 2D backbuffer + backbuffer2D = createImage(width, height); + canvas2D.setBuffer(backbuffer2D); + + // Create a 3D graphics canvas. + canvas3D = new Canvas3D(SimpleUniverse.getPreferredConfiguration()); + canvas3D.setSize(width, height); + canvas3D.setLocation(5, 5); + + // Create the scene branchgroup. + BranchGroup scene3D = createScene3D(); + + // Create a universe with the Java3D universe utility. + universe = new SimpleUniverse(canvas3D); + universe.addBranchGraph(scene3D); + + // Use parallel projection. + View view = universe.getViewer().getView(); + view.setProjectionPolicy(View.PARALLEL_PROJECTION); + + // Set the universe Transform3D object. + TransformGroup tg = + universe.getViewingPlatform().getViewPlatformTransform(); + Transform3D transform = new Transform3D(); + transform.set(65.f, new Vector3f(0.0f, 0.0f, 400.0f)); + tg.setTransform(transform); + + // Create the canvas container. + c_container = new Panel(); + c_container.setSize(720, 360); + c_container.setLocation(0, 0); + c_container.setVisible(true); + c_container.setLayout(null); + add(c_container); + + // Add the 2D and 3D canvases to the container. + c_container.add(canvas2D); + c_container.add(canvas3D); + + // Turn off the layout manager, widgets will be sized + // and positioned explicitly. + setLayout(null); + + // Create the button container. + b_container = new Panel(); + b_container.setSize(720, 70); + b_container.setLocation(0, 360); + b_container.setVisible(true); + b_container.setLayout(null); + + // Create the buttons. + instruct_button = new Button("Instructions"); + instruct_button.setSize(135, 25); + instruct_button.setLocation(10, 10); + instruct_button.setVisible(true); + instruct_button.addActionListener(this); + + new_button = new Button("New Game"); + new_button.setSize(135, 25); + new_button.setLocation(150, 10); + new_button.setVisible(true); + new_button.addActionListener(this); + + undo_button = new Button("Undo Move"); + undo_button.setSize(135, 25); + undo_button.setLocation(290, 10); + undo_button.setVisible(true); + undo_button.addActionListener(this); + + skill_button = new Button("Skill Level"); + skill_button.setSize(135, 25); + skill_button.setLocation(430, 10); + skill_button.setVisible(true); + skill_button.addActionListener(this); + + high_button = new Button("High Scores"); + high_button.setSize(135, 25); + high_button.setLocation(570, 10); + high_button.setVisible(true); + high_button.addActionListener(this); + + b_container.add(new_button); + b_container.add(undo_button); + b_container.add(skill_button); + b_container.add(high_button); + b_container.add(instruct_button); + + // Add the button container to the applet. + add(b_container); + + // Create the "Skill Level" dialog box. + skill_panel = new Panel(); + skill_panel.setSize(400, 300); + skill_panel.setLocation(200, 20); + skill_panel.setLayout(null); + + skill_label = new Label("Pick your skill level:"); + skill_label.setSize(200, 25); + skill_label.setLocation(25, 20); + skill_label.setVisible(true); + skill_panel.add(skill_label); + + group = new CheckboxGroup(); + Checkbox skill_1 = new Checkbox("Babe in the Woods ", group, false); + Checkbox skill_2 = new Checkbox("Walk and Chew Gum ", group, false); + Checkbox skill_3 = new Checkbox("Jeopardy Contestant ", group, false); + Checkbox skill_4 = new Checkbox("Rocket Scientist ", group, false); + Checkbox skill_5 = new Checkbox("Be afraid, be very afraid", group, true); + skill_1.setSize(170, 25); + skill_1.setLocation(80, 60); + skill_1.setVisible(true); + skill_2.setSize(170, 25); + skill_2.setLocation(80, 100); + skill_2.setVisible(true); + skill_3.setSize(170, 25); + skill_3.setLocation(80, 140); + skill_3.setVisible(true); + skill_4.setSize(170, 25); + skill_4.setLocation(80, 180); + skill_4.setVisible(true); + skill_5.setSize(170, 25); + skill_5.setLocation(80, 220); + skill_5.setVisible(true); + skill_return_button = new Button("Return"); + skill_return_button.setSize(120, 25); + skill_return_button.setLocation(300, 370); + skill_return_button.setVisible(false); + skill_return_button.addActionListener(this); + skill_panel.add(skill_1); + skill_panel.add(skill_2); + skill_panel.add(skill_3); + skill_panel.add(skill_4); + skill_panel.add(skill_5); + skill_panel.setVisible(false); + add(skill_return_button); + add(skill_panel); + + // Create the "Instructions" panel. + instruct_return_button = new Button("Return"); + instruct_return_button.setLocation(300, 370); + instruct_return_button.setSize(120, 25); + instruct_return_button.setVisible(false); + instruct_return_button.addActionListener(this); + instruct_text = + new TextArea(textString, 100, 200, TextArea.SCROLLBARS_VERTICAL_ONLY); + instruct_text.setSize(715, 350); + instruct_text.setLocation(0, 0); + instruct_text.setVisible(false); + add(instruct_text); + + add(instruct_return_button); + + high_panel = new Panel(); + high_panel.setSize(715, 350); + high_panel.setLocation(0, 0); + high_panel.setVisible(false); + high_panel.setLayout(null); + + high_label = new Label("High Scores"); + high_label.setLocation(330, 5); + high_label.setSize(200, 30); + high_label.setVisible(true); + high_panel.add(high_label); + + high_places = new Label[20]; + high_names = new Label[20]; + high_scores = new Label[20]; + for (int i=0; i<20; i++) { + high_places[i] = new Label(Integer.toString(i+1)); + high_places[i].setSize(20, 30); + high_places[i].setVisible(true); + high_names[i] = new Label(names[i]); + high_names[i].setSize(150, 30); + high_names[i].setVisible(true); + high_scores[i] = new Label(Integer.toString(scores[i])); + high_scores[i].setSize(150, 30); + high_scores[i].setVisible(true); + if (i<10) { + high_places[i].setLocation(70, i*30+40); + high_names[i].setLocation(100, i*30+40); + high_scores[i].setLocation(260, i*30+40); + } + else { + high_places[i].setLocation(425, (i-10)*30+40); + high_names[i].setLocation(455, (i-10)*30+40); + high_scores[i].setLocation(615, (i-10)*30+40); + } + high_panel.add(high_places[i]); + high_panel.add(high_names[i]); + high_panel.add(high_scores[i]); + } + high_return_button = new Button("Return"); + high_return_button.setSize(120, 25); + high_return_button.setLocation(300, 370); + high_return_button.setVisible(false); + high_return_button.addActionListener(this); + add(high_return_button); + add(high_panel); + + // Create the "Winner" dialog box + winner_panel = new Panel(); + winner_panel.setLayout(null); + winner_panel.setSize(600, 500); + winner_panel.setLocation(0, 0); + winner_return_button = new Button("Return"); + winner_return_button.setSize(120, 25); + winner_return_button.setLocation(300, 360); + winner_return_button.addActionListener(this); + winner_panel.add(winner_return_button); + winner_label = new Label(""); + winner_label.setSize(200, 30); + winner_label.setLocation(270, 110); + winner_score_label = new Label(""); + winner_score_label.setSize(200, 30); + winner_top_label = new Label("You have a score in the top 20."); + winner_top_label.setSize(200, 25); + winner_top_label.setLocation(260, 185); + winner_top_label.setVisible(false); winner_name_label = new Label("Enter your name here:"); + winner_name_label.setSize(150, 25); + winner_name_label.setLocation(260, 210); + winner_name_label.setVisible(false); + winner_name = new TextField(""); + winner_name.setSize(200, 30); + winner_name.setLocation(260, 240); + winner_name.setVisible(false); + winner_panel.add(winner_label); + winner_panel.add(winner_score_label); + winner_panel.add(winner_top_label); + winner_panel.add(winner_name_label); + winner_panel.add(winner_name); + winner_panel.setVisible(false); + add(winner_panel); + } + + public void destroy() { + universe.cleanup(); + } + + /** + * Create the scenegraph for the 3D view. + */ + public BranchGroup createScene3D() { + + // Define colors + Color3f white = new Color3f(1.0f, 1.0f, 1.0f); + Color3f black = new Color3f(0.0f, 0.0f, 0.0f); + Color3f red = new Color3f(0.80f, 0.20f, 0.2f); + Color3f ambient = new Color3f(0.25f, 0.25f, 0.25f); + Color3f diffuse = new Color3f(0.7f, 0.7f, 0.7f); + Color3f specular = new Color3f(0.9f, 0.9f, 0.9f); + Color3f ambientRed = new Color3f(0.2f, 0.05f, 0.0f); + Color3f bgColor = new Color3f(0.05f, 0.05f, 0.2f); + + // Create the branch group + BranchGroup branchGroup = new BranchGroup(); + + // Create the bounding leaf node + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0,0.0,0.0), 1000.0); + BoundingLeaf boundingLeaf = new BoundingLeaf(bounds); + branchGroup.addChild(boundingLeaf); + + // Create the background + Background bg = new Background(bgColor); + bg.setApplicationBounds(bounds); + branchGroup.addChild(bg); + + // Create the ambient light + AmbientLight ambLight = new AmbientLight(white); + ambLight.setInfluencingBounds(bounds); + branchGroup.addChild(ambLight); + + // Create the directional light + Vector3f dir = new Vector3f(-1.0f, -1.0f, -1.0f); + DirectionalLight dirLight = new DirectionalLight(white, dir); + dirLight.setInfluencingBounds(bounds); + branchGroup.addChild(dirLight); + + // Create the pole appearance + Material poleMaterial = + new Material(ambient, black, diffuse, specular, 110.f); + poleMaterial.setLightingEnable(true); + Appearance poleAppearance = new Appearance(); + poleAppearance.setMaterial(poleMaterial); + + // Create the transform group node + TransformGroup transformGroup = new TransformGroup(); + transformGroup.setCapability(TransformGroup.ALLOW_TRANSFORM_READ); + transformGroup.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + branchGroup.addChild(transformGroup); + + // Create the poles + Poles poles = new Poles(poleAppearance); + transformGroup.addChild(poles.getChild()); + + // Add the position markers to the transform group + transformGroup.addChild(positions.getChild()); + + // Let the positions object know about the transform group + positions.setTransformGroup(transformGroup); + + // Create the mouse pick and drag behavior node + PickDragBehavior behavior = new PickDragBehavior(canvas2D, canvas3D, positions, + branchGroup, transformGroup); + behavior.setSchedulingBounds(bounds); + transformGroup.addChild(behavior); + + return branchGroup; + } + + public void actionPerformed (ActionEvent event) { + + Object target = event.getSource(); + + // Process the button events. + if (target == skill_return_button) { + skill_panel.setVisible(false); + skill_return_button.setVisible(false); + c_container.setVisible(true); + b_container.setVisible(true); + newGame(); + } + else if (target == winner_return_button) { + if (winner_flag) { + String name = winner_name.getText(); + String tmp_name = new String(""); + int tmp_score = 0; + boolean insert_flag = false; + winner_flag = false; + for (int i=0; i<20; i++) { + if (insert_flag) { + name = names[i]; + score = scores[i]; + names[i] = tmp_name; + scores[i] = tmp_score; + tmp_name = name; + tmp_score = score; + } + if (!insert_flag && score > scores[i]) { + tmp_name = names[i]; + tmp_score = scores[i]; + scores[i] = score; + names[i] = name; + insert_flag = true; + } + high_names[i].setText(names[i]); + high_scores[i].setText(Integer.toString(scores[i])); + } + scoresString = new String(""); + int place; + for (int i=0; i<20; i++) { + place = (int) places[i]; + scoresString += Integer.toString(place); + scoresString += "\t"; + scoresString += names[i]; + scoresString += " "; + scoresString += Integer.toString(scores[i]); + scoresString += "\n"; + } + + if(writeScoresFile) { + if (appletFlag) { + try { + OutputStreamWriter outFile = + new OutputStreamWriter(new FileOutputStream("scores.txt")); + outFile.write(scoresString); + outFile.flush(); + outFile.close(); + outFile = null; + } catch (IOException ioe) { + System.out.println("Error: " + ioe.toString()); + } catch (Exception e) { + System.out.println("Error: " + e.toString()); + } + + } else { + + try { + + OutputStreamWriter outFile = + new OutputStreamWriter(new FileOutputStream("scores.txt")); + outFile.write(scoresString); + outFile.flush(); + outFile.close(); + outFile = null; + } catch (IOException ioe) { + System.out.println("Error: " + ioe.toString()); + } + } + } + } + winner_panel.setVisible(false); + winner_return_button.setVisible(false); + winner_label.setVisible(false); + winner_score_label.setVisible(false); + winner_name_label.setVisible(false); + winner_top_label.setVisible(false); + winner_name.setVisible(false); + c_container.setVisible(true); + b_container.setVisible(true); + } + else if (target == high_return_button) { + high_return_button.setVisible(false); + high_panel.setVisible(false); + c_container.setVisible(true); + b_container.setVisible(true); + } + else if (target == instruct_return_button) { + instruct_text.setVisible(false); + instruct_return_button.setVisible(false); + instruct_text.repaint(); + c_container.setVisible(true); + b_container.setVisible(true); + } + else if (target == undo_button) { + board.undo_move(); + canvas2D.repaint(); + } + else if (target == instruct_button) { + c_container.setVisible(false); + b_container.setVisible(false); + instruct_text.setVisible(true); + instruct_return_button.setVisible(true); + } + else if (target == new_button) { + newGame(); + } + else if (target == skill_button) { + c_container.setVisible(false); + b_container.setVisible(false); + skill_panel.setVisible(true); + skill_return_button.setVisible(true); + } + else if (target == high_button) { + // Read the high scores file. + if (appletFlag) { + try { + URL scoreURL = Resources.getResource("four_by_four/scores.txt"); + inStream = new BufferedInputStream(scoreURL.openStream(), 8192); + Reader read = new BufferedReader(new InputStreamReader(inStream)); + StreamTokenizer st = new StreamTokenizer(read); + st.whitespaceChars(32,44); + st.eolIsSignificant(false); + + int count = 0; + int token = st.nextToken(); + boolean scoreFlag = true; + String string; + while (count<20) { + places[count] = (int) st.nval; + string = new String(""); + token = st.nextToken(); + while (token == StreamTokenizer.TT_WORD) { + string += st.sval; + string += " "; + token = st.nextToken(); + } + names[count] = string; + scores[count] = (int) st.nval; + token = st.nextToken(); + count++; + } + inStream.close(); + } + catch(Exception ioe) { + System.out.println("Error: " + ioe.toString()); + } + } + else { + try { + URL scoreURL = Resources.getResource("four_by_four/scores.txt"); + inStream = new BufferedInputStream(scoreURL.openStream(), 8192); + Reader read = new BufferedReader(new InputStreamReader(inStream)); + StreamTokenizer st = new StreamTokenizer(read); + st.whitespaceChars(32,44); + st.eolIsSignificant(false); + + int count = 0; + int token = st.nextToken(); + boolean scoreFlag = true; + String string; + while (count<20) { + places[count] = (int) st.nval; + string = new String(""); + token = st.nextToken(); + while (token == StreamTokenizer.TT_WORD) { + string += st.sval; + string += " "; + token = st.nextToken(); + } + names[count] = string; + scores[count] = (int) st.nval; + token = st.nextToken(); + count++; + } + inStream.close(); + } + catch(Exception ioe) { + System.out.println("Error: " + ioe.toString()); + } + } + c_container.setVisible(false); + b_container.setVisible(false); + high_panel.setVisible(true); + high_return_button.setVisible(true); + } + + Checkbox box = group.getSelectedCheckbox(); + String label = box.getLabel(); + if (label.equals("Babe in the Woods ")) { + board.set_skill_level(0); + } + else if (label.equals("Walk and Chew Gum ")) { + board.set_skill_level(1); + } + else if (label.equals("Jeopardy Contestant ")) { + board.set_skill_level(2); + } + else if (label.equals("Rocket Scientist ")) { + board.set_skill_level(3); + } + else if (label.equals("Be afraid, be very afraid")) { + board.set_skill_level(4); + } + } + + public void newGame() { + board.newGame(); + canvas2D.repaint(); + } + + public void start() { + if (appletFlag) showStatus("FourByFour"); + } + + public void winner(int player, int level, int nmoves, long time) { + + if (player == 1) { + score = level * level_weight + + (66 - nmoves) * move_weight - + (int) Math.min(time * time_weight, 5000); + winner_label.setText("Game over, you win!"); + winner_label.setLocation(290, 90); + winner_score_label.setText("Score = " + score); + winner_score_label.setVisible(true); + winner_score_label.setLocation(315, 120); + if (score > scores[19]) { + winner_name_label.setVisible(true); + winner_top_label.setVisible(true); + winner_name.setVisible(true); + winner_flag = true; + } + } + else { + winner_label.setText("Game over, the computer wins!"); + winner_label.setLocation(250, 150); + } + c_container.setVisible(false); + b_container.setVisible(false); + winner_panel.setVisible(true); + winner_label.setVisible(true); + winner_return_button.setVisible(true); + repaint(); + } + + /** + * Inner class used to "kill" the window when running as + * an application. + */ + static class killAdapter extends WindowAdapter { + public void windowClosing(WindowEvent event) { + System.exit(0); + } + } + + /** + * Main method, only used when running as an application. + */ + public static void main(String[] args) {System.setProperty("sun.awt.noerasebackground", "true"); + FourByFour.appletFlag = false; + new MainFrame(new FourByFour(), 730, 450); + } + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/four_by_four/ID.java b/src/main/java/org/jdesktop/j3d/examples/four_by_four/ID.java new file mode 100644 index 0000000..062f69a --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/four_by_four/ID.java @@ -0,0 +1,61 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.four_by_four; + +class ID { + int id; + + public ID(int id) { + this.id = id; + } + + public int get() { + return id; + } + + public void set(int id) { + this.id = id; + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/four_by_four/PickDragBehavior.java b/src/main/java/org/jdesktop/j3d/examples/four_by_four/PickDragBehavior.java new file mode 100644 index 0000000..697e934 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/four_by_four/PickDragBehavior.java @@ -0,0 +1,234 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.four_by_four; + +import java.awt.AWTEvent; +import java.awt.event.MouseEvent; +import java.util.Enumeration; + +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.Behavior; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.CapabilityNotSetException; +import org.jogamp.java3d.Material; +import org.jogamp.java3d.Node; +import org.jogamp.java3d.PickRay; +import org.jogamp.java3d.SceneGraphPath; +import org.jogamp.java3d.Shape3D; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.WakeupCriterion; +import org.jogamp.java3d.WakeupOnAWTEvent; +import org.jogamp.java3d.WakeupOr; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Vector3d; + +/** + * Class: PickDragBehavior + * + * Description: Used to respond to mouse pick and drag events + * in the 3D window. + * + * Version: 1.0 + * + */ +public class PickDragBehavior extends Behavior { + + WakeupCriterion[] mouseEvents; + WakeupOr mouseCriterion; + int x, y; + int x_last, y_last; + double x_angle, y_angle; + double x_factor, y_factor; + Transform3D modelTrans; + Transform3D transformX; + Transform3D transformY; + TransformGroup transformGroup; + BranchGroup branchGroup; + Canvas2D canvas2D; + Canvas3D canvas3D; + Positions positions; + PickRay pickRay = new PickRay(); + SceneGraphPath sceneGraphPath[]; + Appearance highlight; + boolean parallel; + + PickDragBehavior(Canvas2D canvas2D, Canvas3D canvas3D, Positions positions, + BranchGroup branchGroup, TransformGroup transformGroup) { + + this.canvas2D = canvas2D; + this.canvas3D = canvas3D; + this.positions = positions; + this.branchGroup = branchGroup; + this.transformGroup = transformGroup; + + modelTrans = new Transform3D(); + transformX = new Transform3D(); + transformY = new Transform3D(); + + Color3f white = new Color3f(1.0f, 1.0f, 1.0f); + Color3f black = new Color3f(0.0f, 0.0f, 0.0f); + Color3f green = new Color3f(0.0f, 1.0f, 0.0f); + + highlight = new Appearance(); + highlight.setMaterial(new Material(green, black, green, white, 80.f)); + + parallel = true; + } + + public void initialize() { + x = 0; + y = 0; + x_last = 0; + y_last = 0; + x_angle = 0; + y_angle = 0; + x_factor = .02; + y_factor = .02; + + mouseEvents = new WakeupCriterion[2]; + mouseEvents[0] = new WakeupOnAWTEvent(MouseEvent.MOUSE_DRAGGED); + mouseEvents[1] = new WakeupOnAWTEvent(MouseEvent.MOUSE_PRESSED); + mouseCriterion = new WakeupOr(mouseEvents); + wakeupOn (mouseCriterion); + } + + public void processStimulus (Enumeration criteria) { + WakeupCriterion wakeup; + AWTEvent[] event; + int id; + int dx, dy; + + while (criteria.hasMoreElements()) { + wakeup = (WakeupCriterion) criteria.nextElement(); + if (wakeup instanceof WakeupOnAWTEvent) { + event = ((WakeupOnAWTEvent)wakeup).getAWTEvent(); + for (int i=0; i<event.length; i++) { + id = event[i].getID(); + if (id == MouseEvent.MOUSE_DRAGGED) { + + x = ((MouseEvent)event[i]).getX(); + y = ((MouseEvent)event[i]).getY(); + + dx = x - x_last; + dy = y - y_last; + + x_angle = dy * y_factor; + y_angle = dx * x_factor; + + transformX.rotX(x_angle); + transformY.rotY(y_angle); + + modelTrans.mul(transformX, modelTrans); + modelTrans.mul(transformY, modelTrans); + + transformGroup.setTransform(modelTrans); + + x_last = x; + y_last = y; + } + else if (id == MouseEvent.MOUSE_PRESSED) { + + x = x_last = ((MouseEvent)event[i]).getX(); + y = y_last = ((MouseEvent)event[i]).getY(); + + Point3d eyePos = new Point3d(); + canvas3D.getCenterEyeInImagePlate(eyePos); + + Point3d mousePos = new Point3d(); + canvas3D.getPixelLocationInImagePlate(x, y, mousePos); + + Transform3D transform3D = new Transform3D(); + canvas3D.getImagePlateToVworld(transform3D); + + transform3D.transform(eyePos); + transform3D.transform(mousePos); + + Vector3d mouseVec; + if (parallel) { + mouseVec = new Vector3d(0.f, 0.f, -1.f); + } + else { + mouseVec = new Vector3d(); + mouseVec.sub(mousePos, eyePos); + mouseVec.normalize(); + } + + pickRay.set(mousePos, mouseVec); + sceneGraphPath = branchGroup.pickAllSorted(pickRay); + + if (sceneGraphPath != null) { + for (int j=0; j<sceneGraphPath.length; j++) { + if (sceneGraphPath[j] != null) { + Node node = sceneGraphPath[j].getObject(); + if (node instanceof Shape3D) { + try { + ID posID = (ID) node.getUserData(); + if (posID != null) { + int pos = posID.get(); + positions.set(pos, Positions.HUMAN); + canvas2D.repaint(); + break; + } + } + catch (CapabilityNotSetException e) { + // Catch all CapabilityNotSet exceptions and + // throw them away, prevents renderer from + // locking up when encountering "non-selectable" + // objects. + } + } + } + } + } + } + } + } + } + wakeupOn (mouseCriterion); + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/four_by_four/Poles.java b/src/main/java/org/jdesktop/j3d/examples/four_by_four/Poles.java new file mode 100644 index 0000000..47ba07e --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/four_by_four/Poles.java @@ -0,0 +1,80 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.four_by_four; + +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.Group; + +/** + * Class: Poles + * + * Description: Creates the "poles" in the 3D window. + * + * Version: 1.0 + * + */ +public class Poles extends Object { + + private Group group; + + public Poles(Appearance appearance) { + float x = -30.0f; + float z = -30.0f; + group = new Group(); + for(int i=0; i<4; i++) { + for(int j=0; j<4; j++) { + Cylinder c = new Cylinder(x, z, 1.0f, 60.0f, 10, appearance); + group.addChild(c.getShape()); + x += 20.0f; + } + x = -30.0f; + z += 20.0f; + } + } + + public Group getChild() { + return group; + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/four_by_four/Positions.java b/src/main/java/org/jdesktop/j3d/examples/four_by_four/Positions.java new file mode 100644 index 0000000..4f5d927 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/four_by_four/Positions.java @@ -0,0 +1,319 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.four_by_four; + +import java.util.BitSet; + +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.Group; +import org.jogamp.java3d.Material; +import org.jogamp.java3d.Shape3D; +import org.jogamp.java3d.Switch; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.utils.geometry.Sphere; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Vector3f; + +/** + * Class: Positions + * + * Description: Creates the position markers. + * + * Version: 1.0 + * + */ +public class Positions extends Object { + + final static int UNOCCUPIED = 0; + final static int HUMAN = 1; + final static int MACHINE = 2; + final static int END = 3; + + private Vector3f point[]; + private Switch posSwitch; + private Switch humanSwitch; + private Switch machineSwitch; + private BitSet posMask; + private BitSet humanMask; + private BitSet machineMask; + private Group group; + private Material redMat; + private Material blueMat; + private Material yellowMat; + private Material whiteMat; + private Appearance redApp; + private Appearance blueApp; + private Appearance yellowApp; + private Appearance whiteApp; + private Board board; + private Sphere posSphere[]; + private BigCube cube[]; + private TransformGroup tgroup; + private boolean winnerFlag = false; + + public Positions() { + + // Define colors for lighting + Color3f white = new Color3f(1.0f, 1.0f, 1.0f); + Color3f black = new Color3f(0.0f, 0.0f, 0.0f); + Color3f red = new Color3f(0.9f, 0.1f, 0.2f); + Color3f blue = new Color3f(0.3f, 0.3f, 0.8f); + Color3f yellow = new Color3f(1.0f, 1.0f, 0.0f); + Color3f ambRed = new Color3f(0.3f, 0.03f, 0.03f); + Color3f ambBlue = new Color3f(0.03f, 0.03f, 0.3f); + Color3f ambYellow = new Color3f(0.3f, 0.3f, 0.03f); + Color3f ambWhite = new Color3f(0.3f, 0.3f, 0.3f); + Color3f specular = new Color3f(1.0f, 1.0f, 1.0f); + + // Create the red appearance node + redMat= new Material(ambRed, black, red, specular, 100.f); + redMat.setLightingEnable(true); + redApp = new Appearance(); + redApp.setMaterial(redMat); + + // Create the blue appearance node + blueMat= new Material(ambBlue, black, blue, specular, 100.f); + blueMat.setLightingEnable(true); + blueApp = new Appearance(); + blueApp.setMaterial(blueMat); + + // Create the yellow appearance node + yellowMat= new Material(ambYellow, black, yellow, specular, 100.f); + yellowMat.setLightingEnable(true); + yellowApp = new Appearance(); + yellowApp.setMaterial(yellowMat); + + // Create the white appearance node + whiteMat= new Material(ambWhite, black, white, specular, 100.f); + whiteMat.setLightingEnable(true); + whiteApp = new Appearance(); + whiteApp.setMaterial(whiteMat); + + // Load the point array with the offset (coordinates) for each of + // the 64 positions. + point = new Vector3f[64]; + int count = 0; + for (int i=-30; i<40; i+=20) { + for (int j=-30; j<40; j+=20) { + for (int k=-30; k<40; k+=20) { + point[count] = new Vector3f((float) k, (float) j, (float) i); + count++; + } + } + } + + // Create the switch nodes + posSwitch = new Switch(Switch.CHILD_MASK); + humanSwitch = new Switch(Switch.CHILD_MASK); + machineSwitch = new Switch(Switch.CHILD_MASK); + + // Set the capability bits + posSwitch.setCapability(Switch.ALLOW_SWITCH_READ); + posSwitch.setCapability(Switch.ALLOW_SWITCH_WRITE); + + humanSwitch.setCapability(Switch.ALLOW_SWITCH_READ); + humanSwitch.setCapability(Switch.ALLOW_SWITCH_WRITE); + + machineSwitch.setCapability(Switch.ALLOW_SWITCH_READ); + machineSwitch.setCapability(Switch.ALLOW_SWITCH_WRITE); + + // Create the bit masks + posMask = new BitSet(); + humanMask = new BitSet(); + machineMask = new BitSet(); + + // Create the small white spheres that mark unoccupied + // positions. + posSphere = new Sphere[64]; + for (int i=0; i<64; i++) { + Transform3D transform3D = new Transform3D(); + transform3D.set(point[i]); + TransformGroup transformGroup = new TransformGroup(transform3D); + posSphere[i] = new Sphere(2.0f, Sphere.GENERATE_NORMALS | + Sphere.ENABLE_APPEARANCE_MODIFY, + 12, whiteApp); + Shape3D shape = posSphere[i].getShape(); + ID id = new ID(i); + shape.setUserData(id); + transformGroup.addChild(posSphere[i]); + posSwitch.addChild(transformGroup); + posMask.set(i); + } + + // Create the red spheres that mark the user's positions. + for (int i=0; i<64; i++) { + Transform3D transform3D = new Transform3D(); + transform3D.set(point[i]); + TransformGroup transformGroup = new TransformGroup(transform3D); + transformGroup.addChild(new Sphere(7.0f, redApp)); + humanSwitch.addChild(transformGroup); + humanMask.clear(i); + } + + // Create the blue cubes that mark the computer's positions. + for (int i=0; i<64; i++) { + Transform3D transform3D = new Transform3D(); + transform3D.set(point[i]); + TransformGroup transformGroup = new TransformGroup(transform3D); + BigCube cube = new BigCube(blueApp); + transformGroup.addChild(cube.getChild()); + machineSwitch.addChild(transformGroup); + machineMask.clear(i); + } + + // Set the positions mask + posSwitch.setChildMask(posMask); + humanSwitch.setChildMask(humanMask); + machineSwitch.setChildMask(machineMask); + + // Throw everything into a single group + group = new Group(); + group.addChild(posSwitch); + group.addChild(humanSwitch); + group.addChild(machineSwitch); + } + + public void setTransformGroup(TransformGroup transformGroup) { + tgroup = transformGroup; + } + + public Group getChild() { + return group; + } + + public void setBoard(Board board) { + this.board = board; + } + + public void winner() { + winnerFlag = true; + } + + public void noWinner() { + winnerFlag = false; + } + + public void setHighlight(int pos) { + posSphere[pos].setAppearance(yellowApp); + } + + public void clearHighlight(int pos) { + posSphere[pos].setAppearance(whiteApp); + } + + public void newGame() { + + // Clear the board + for (int i=0; i<64; i++) { + posMask.set(i); + humanMask.clear(i); + machineMask.clear(i); + } + posSwitch.setChildMask(posMask); + humanSwitch.setChildMask(humanMask); + machineSwitch.setChildMask(machineMask); + + // The following three lines fix a bug in J3D + Transform3D t = new Transform3D(); + tgroup.getTransform(t); + tgroup.setTransform(t); + + // Reset the winner flag + winnerFlag = false; + } + + public void set(int pos, int player) { + + // Stop accepting selections when the game + // is over. + if (winnerFlag) return; + + // Make sure the position is not occupied. + if (player == HUMAN) + if (!board.unoccupied(pos)) return; + + // Turn off the position marker for the given position + posMask.clear(pos); + posSwitch.setChildMask(posMask); + + // Turn on the player marker + if (player == Positions.HUMAN) { + humanMask.set(pos); + humanSwitch.setChildMask(humanMask); + board.selection(pos, Positions.HUMAN); + } + else { + machineMask.set(pos); + machineSwitch.setChildMask(machineMask); + } + + // The following three lines fix a bug in J3D + Transform3D t = new Transform3D(); + tgroup.getTransform(t); + tgroup.setTransform(t); + } + + public void clear(int pos) { + + // Turn on the position marker + posMask.set(pos); + posSwitch.setChildMask(posMask); + + // Turn off the player marker + humanMask.clear(pos); + humanSwitch.setChildMask(humanMask); + machineMask.clear(pos); + machineSwitch.setChildMask(machineMask); + + // The following three lines are a workaround for a bug + // in dev09 in which the transform3D of certain items are + // not updated properly. Scheduled to be fixed in dev10 + Transform3D t = new Transform3D(); + tgroup.getTransform(t); + tgroup.setTransform(t); + } + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/four_by_four/README.txt b/src/main/java/org/jdesktop/j3d/examples/four_by_four/README.txt new file mode 100644 index 0000000..40798d0 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/four_by_four/README.txt @@ -0,0 +1,8 @@ +FourByFour + +To run: + + appletviewer FourByFour.html + +Press the "Instructions" button to get instructions on +how to play FourByFour. diff --git a/src/main/java/org/jdesktop/j3d/examples/four_by_four/instructions.txt b/src/main/java/org/jdesktop/j3d/examples/four_by_four/instructions.txt new file mode 100644 index 0000000..3dcc736 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/four_by_four/instructions.txt @@ -0,0 +1,98 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + + Four By Four + +Description: + + A three dimensional game of tic-tac-toe on a 4x4x4 cube. + +Object: + + Be the first to score four in a row. + +Instructions: + + 1. It's you versus the computer. + + 2. There are five skill levels. Press the "Skill Level" button to select your level + of play. The program defaults to the hardest level. Changing the skill level in + the middle of a game will force the start of a new game. + + 3. The screen on the left is a 3D window. A mouse drag in this window will rotate the + view to any desired position. + + 4. The screen on the right is a 2D window which displays all 18 faces that exist in the + 4x4x4 array. + + 5. Click on any of the small gray spheres (in either the 2D or 3D window) to select a position. + + 6. Positions owned by you will be marked in red. Positions owned by the computer will be + marked in blue. + + 7. Click the "Undo Move" button to take back a move. + + 8. Clicking on any of words "Face X" in the 2D window will cause that particular face to highlight + in the 3D window. Clicking the word again will un-highlight the face. + + 9. The final score is based on skill level, number of moves, and time. Select the button + "High Scores" to see a list of the top 20 scores. There is no penalty for using the + undo button. + + 10. Good luck. + +General Strategy: + + 1. There are a 64 positions from which to choose. In total, there are 72 possible winning + combinations. + + 2. The outer four corners and the inner "core" of eight have the most winning combinations, + 7 each, and should perhaps be chosen first. + + 3. Use the 2D window to keep an eye on all the faces. + + 4. The computer plays well at the highest skill level (the default). There are, however, + faults in it's logic that can be exploited. Thus the human player can win even at the + highest skill level. In the beginning, however, you may want to start at the lower skill + levels and work your way up. diff --git a/src/main/java/org/jdesktop/j3d/examples/four_by_four/scores.txt b/src/main/java/org/jdesktop/j3d/examples/four_by_four/scores.txt new file mode 100644 index 0000000..0ebc31a --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/four_by_four/scores.txt @@ -0,0 +1,20 @@ +1 Bart Simpson 5283 +2 Dwight Eisenhower 5105 +3 Ken 5061 +4 Barbie 2883 +5 DoubleMint Twins 2195 +6 Robin Hood 1772 +7 Jack Benny 1604 +8 Anonymous 1550 +9 Duke 1501 +10 Jack Paar 1499 +11 Barney 1488 +12 Mick Jagger 1472 +13 Howard Hughes 1329 +14 Bugs Bunny 1328 +15 Suzi Chapstick 1302 +16 Forest Gump 1244 +17 Alfred Hitchcock 1231 +18 Roman Polaski 1168 +19 Missy Giovi 1106 +20 Bill Joy 1002 diff --git a/src/main/java/org/jdesktop/j3d/examples/fps_counter/FPSCounter.java b/src/main/java/org/jdesktop/j3d/examples/fps_counter/FPSCounter.java new file mode 100644 index 0000000..fa57927 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/fps_counter/FPSCounter.java @@ -0,0 +1,282 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.fps_counter; + +import java.text.NumberFormat; + +import org.jogamp.java3d.Behavior; +import org.jogamp.java3d.WakeupOnElapsedFrames; + +/** This behavior calculates the frame rate and average frame rate of a + * Java3D application. + * The behavior sets itself up to wakeup every time a new frame is rendered. + * + * <p> The HotSpot(tm) compiler performs some initial optimizations before + * running at optimal speed. Frame rates measured during this warmup period + * will be inaccurate and not indicative of the true performance of the the + * application. Therefore, before beginning the frame rate computation, + * the frame counter waits for a fixed time period to allow the HotSpot(tm) + * compiler to stablilize. + * + * <p> To avoid computing the frame rate too frequently (which would also + * hamper rendering performance), the frame counter only computes the frame + * rate at fixed time intervals. The default sampling duration is 10 seconds. + * After waiting for the warmup period, the frame counter needs to calibrate + * itself. It computes the number of frames rendered during the sampling + * period. After doing this calibration, the frame counter reports the frame + * rate after these many frames are rendered. It also reports the average + * frame rate after a fixed number of sampling intervals (the default is 5). + * + * <p>The frame counter can be set up to run for a fixed number of sampling + * intervals or to run indefinitely. The defaultis to run indefinitely. + */ + +public class FPSCounter extends Behavior { + // Wakeup condition - framecount = 0 -> wakeup on every frame + WakeupOnElapsedFrames FPSwakeup = new WakeupOnElapsedFrames(0); + + // Do calibration for these many millisec + private static final long testduration = 1000; + + // Report frame rate after every sampleduration milliseconds + private static final long sampleduration = 10000; + + // Flag to indicate that it is time to (re)calibrate + private boolean doCalibration = true; + + // Flag to indicate the counter has started + private boolean startup = true; + + // Wait for HotSpot compiler to perform optimizations + private boolean warmup = true; + + // Time to wait for HotSpot compiler to stabilize (in milliseconds) + private long warmupTime = 20000; + + // Counter for number of frames rendered + private int numframes = 0; + + // Report frame rate after maxframe number of frames have been rendered + private int maxframes = 1; + + // Variables to keep track of elapsed time + private long startuptime = 0; + private long currtime = 0; + private long lasttime = 0; + private long deltatime; + + // Run indefinitely or for a fixed duration + private boolean finiteLoop = false; + + // No. of sampling intervals to run for if not running indefinitely + private long maxLoops; + + // No. of sampling intervals run for so far + private long numLoops = 0; + + // Total number of frames rendered so far + private int sumFrames = 0; + + // Total time since last reporting of average frame rate + private long sumTimes = 0; + + // Counts no. of sampling intervals + private int loop = 0; + + // Average frame rate is reported after loopCount number of + // sampling intervals + private int loopCount = 5; + private double sumFps = 0.0; + + private String symbol[] = {"\\", "|", "|", "/", "-", "|", "-"}; + int index = 0; + private NumberFormat nf = null; + + public FPSCounter() { + setEnable(true); + nf = NumberFormat.getNumberInstance(); + } + + /** + * Called to init the behavior + */ + public void initialize() { + // Set the trigger for the behavior to wakeup on every frame rendered + wakeupOn(FPSwakeup); + } + + /** + * Called every time the behavior is activated + */ + public void processStimulus(java.util.Enumeration critera) { + // Apply calibration algorithm to determine number of frames to + // wait before computing frames per second. + // sampleduration = 10000 -> to run test, pass for 10 seconds. + + if (doCalibration) { // start calibration + if (startup) { + // Record time at which the behavior was first invoked + startuptime = System.currentTimeMillis(); + startup = false; + } + else if(warmup) { // Wait for the system to stabilize. + System.out.print("\rFPSCounter warming up..." + + symbol[(index++)%symbol.length]); + currtime = System.currentTimeMillis(); + deltatime = currtime - startuptime; + if(deltatime > warmupTime) { + // Done waiting for warmup + warmup = false; + lasttime = System.currentTimeMillis(); + System.out.println("\rFPSCounter warming up...Done"); + } + } + else { + numframes += 1; + // Wait till at least maxframe no. of frames have been rendered + if (numframes >= maxframes) { + currtime = System.currentTimeMillis(); + deltatime = currtime - lasttime; + // Do the calibration for testduration no. of millisecs + if (deltatime > testduration) { + // Compute total no. of frames rendered so far in the + // current sampling duration + maxframes = (int)Math.ceil((double)numframes * + ((double)sampleduration / + (double)deltatime)); + + // Done with calibration + doCalibration = false; + // reset the value for the measurement + numframes = 0; + lasttime = System.currentTimeMillis(); + } + else { + // Need to run the calibration routine for some more + // time. Increase the no. of frames to be rendered + maxframes *= 2; + } + } + } + } + else { // do the measurement + numframes += 1; + if (numframes >= maxframes) { + currtime = System.currentTimeMillis(); + deltatime = currtime - lasttime; + // time is in millisec, so multiply by 1000 to get frames/sec + double fps = (double)numframes / ((double)deltatime / 1000.0); + + System.out.println("Frame Rate : \n\tNo. of frames : " + + numframes + "\n\tTime : " + + ((double)deltatime / 1000.0) + + " sec." + "\n\tFrames/sec : " + nf.format(fps)); + + // Calculate average frame rate + sumFrames += numframes; + sumTimes += deltatime; + sumFps += fps; + loop++; + if (loop >= loopCount) { + double avgFps = (double)sumFrames*1000.0/(double)sumTimes; + double ravgFps = sumFps/(double)loopCount; + System.out.println("Aggregate frame rate " + + nf.format(avgFps) + " frames/sec"); + System.out.println("Average frame rate " + + nf.format(ravgFps) + " frames/sec"); + numLoops++; + if (finiteLoop && numLoops >= maxLoops) { + System.out.println("************** The End **************\n"); + setEnable(false); + } + loop = 0; + sumFps = 0; + } + numframes = 0; + lasttime = System.currentTimeMillis();; + } + } + // Set the trigger for the behavior + wakeupOn(FPSwakeup); + } + + /** + * The frame counter waits for some time before computing the + * frame rate. This allows the HotSpot compiler to perform + * initial optimizations. The amount of time to wait for is set + * by this method. The default is 20000 (20 sec) + * + * @param amount of time to wait for before computing frame rate + * (specified in milliseconds) + */ + public void setWarmupTime(long wt) { + warmupTime = wt; + } + + /** + * Sets the number of sampling intervals to wait for before computing + * the average frame rate. + * The default is 5. + * + * @param number of sampling intervals over which to compute frame rate. + * A value of 0 implies the average frame rate is computed over one + * sampling interval + */ + public void setLoopCount(int lc) { + loopCount = lc; + } + + /** + * This method sets the number of sampling intervals for which + * the frame counter should run. + * + * @param number of sampling intervals to run for + */ + public void setMaxLoops(int ml) { + maxLoops = ml; + finiteLoop = true; + } + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/fps_counter/FPSCounterDemo.form b/src/main/java/org/jdesktop/j3d/examples/fps_counter/FPSCounterDemo.form new file mode 100644 index 0000000..0a6a276 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/fps_counter/FPSCounterDemo.form @@ -0,0 +1,36 @@ +<?xml version="1.0" encoding="UTF-8" ?> + +<Form version="1.0" type="org.netbeans.modules.form.forminfo.JFrameFormInfo"> + <Properties> + <Property name="defaultCloseOperation" type="int" value="3"/> + <Property name="title" type="java.lang.String" value="FPSCounterDemo"/> + </Properties> + <SyntheticProperties> + <SyntheticProperty name="formSizePolicy" type="int" value="1"/> + </SyntheticProperties> + <AuxValues> + <AuxValue name="FormSettings_generateMnemonicsCode" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_listenerGenerationStyle" type="java.lang.Integer" value="0"/> + <AuxValue name="FormSettings_variablesLocal" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_variablesModifier" type="java.lang.Integer" value="2"/> + <AuxValue name="designerSize" type="java.awt.Dimension" value="-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,1,44,0,0,1,-112"/> + </AuxValues> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + <SubComponents> + <Container class="javax.swing.JPanel" name="drawingPanel"> + <Properties> + <Property name="preferredSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor"> + <Dimension value="[250, 250]"/> + </Property> + </Properties> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout" value="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription"> + <BorderConstraints direction="Center"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + </Container> + </SubComponents> +</Form> diff --git a/src/main/java/org/jdesktop/j3d/examples/fps_counter/FPSCounterDemo.java b/src/main/java/org/jdesktop/j3d/examples/fps_counter/FPSCounterDemo.java new file mode 100644 index 0000000..d72aa9f --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/fps_counter/FPSCounterDemo.java @@ -0,0 +1,255 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.fps_counter; + +import java.awt.GraphicsConfiguration; + +import javax.swing.JOptionPane; + +import org.jogamp.java3d.Alpha; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.RotationInterpolator; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.utils.geometry.ColorCube; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.vecmath.Point3d; + +/** + * This program demonstrates the use of the frames per second counter. + * The program displays a rotating cube and sets up the FPSCounter to compute + * the frame rate. The FPSCounter is set up with default values: + * - run indefinitely + * - 2 sec. warmup time + * - display average frame rate every fifth sampling interval. + * The default values can be changed through the command line + * arguments. Use FPSCounterDemo1 -h for help on the various arguments. + */ +public class FPSCounterDemo extends javax.swing.JFrame { + + private SimpleUniverse univ = null; + private BranchGroup scene = null; + private FPSCounter fpsCounter = new FPSCounter(); + + BranchGroup createSceneGraph() { + // Create the root of the branch graph + BranchGroup objRoot = new BranchGroup(); + + // Create the TransformGroup node and initialize it to the + // identity. Enable the TRANSFORM_WRITE capability so that + // our behavior code can modify it at run time. Add it to + // the root of the subgraph. + TransformGroup objTrans = new TransformGroup(); + objTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + objRoot.addChild(objTrans); + + // Create a simple Shape3D node; add it to the scene graph. + objTrans.addChild(new ColorCube(0.4)); + + // Create a new Behavior object that will perform the + // desired operation on the specified transform and add + // it into the scene graph. + Transform3D yAxis = new Transform3D(); + Alpha rotationAlpha = new Alpha(-1, 4000); + + RotationInterpolator rotator = + new RotationInterpolator(rotationAlpha, objTrans, yAxis, + 0.0f, (float) Math.PI*2.0f); + BoundingSphere bounds = new BoundingSphere(new Point3d(0.0,0.0,0.0), + 100.0); + rotator.setSchedulingBounds(bounds); + objRoot.addChild(rotator); + + // Create the Framecounter behavior + fpsCounter.setSchedulingBounds(bounds); + objRoot.addChild(fpsCounter); + + return objRoot; + } + + private Canvas3D createUniverse() { + // Get the preferred graphics configuration for the default screen + GraphicsConfiguration config = + SimpleUniverse.getPreferredConfiguration(); + + // Create a Canvas3D using the preferred configuration + Canvas3D c = new Canvas3D(config); + + // Create simple universe with view branch + univ = new SimpleUniverse(c); + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + univ.getViewingPlatform().setNominalViewingTransform(); + + return c; + } + + /** + * Creates new form FPSCounterDemo + */ + public FPSCounterDemo() { + // Initialize the GUI components + initComponents(); + + // Create Canvas3D and SimpleUniverse; add canvas to drawing panel + Canvas3D c = createUniverse(); + drawingPanel.add(c, java.awt.BorderLayout.CENTER); + + // Create the content branch and add it to the universe + scene = createSceneGraph(); + univ.addBranchGraph(scene); + + JOptionPane.showMessageDialog(this, + ("This program measures the number of frames rendered per second.\n" + + "Note that the frame rate is limited by the refresh rate of the monitor.\n" + + "To get the true frame rate you need to disable vertical retrace.\n\n" + + "On Windows(tm) you do this through the Control Panel.\n\n" + + "On Solaris set the environment variable OGL_NO_VBLANK"), + "Frame Counter", + JOptionPane.INFORMATION_MESSAGE); + + } + + /** Parses the commandline for the various switches to set the FPSCounter + * variables. + * All arguments are of the form <i>-name value</i>. + * All -name arguments can be shortened to one character. All the value + * arguments take a number. The arguments accepted are : + * <ul> + * <li>warmupTime : Specifies amount of time the FPSCounter should wait + * for the HotSpot<sup><font size="-2">TM</font></sup> VM to perform + * initial optimizations. Specified in milliseconds<br> + * <li>loopCount : Specifies the number of sampling intervals over which + * the FPSCounter should calculate the aggregate and average frame rate. + * Specified as a count. <br> + * <li>maxLoops : Specifies that the FPSCounter should run for only + * these many sampling intervals. Specified as number. If this argument + * is not specified, the FPSCounter runs indefinitely. <br> + * <li>help : Prints the accepted arguments. <br> + * </ul> + */ + private void parseArgs(String args[]) { + for(int i = 0; i < args.length; i++) { + if(args[i].startsWith("-")) { + if(args[i].startsWith("w", 1)) { + i++; + System.out.println("Warmup time : " + args[i]); + int w = new Integer(args[i]).intValue(); + fpsCounter.setWarmupTime(w); + } + else if(args[i].startsWith("l", 1)) { + i++; + System.out.println("Loop count : " + args[i]); + int l = new Integer(args[i]).intValue(); + fpsCounter.setLoopCount(l); + } + else if(args[i].startsWith("m", 1)) { + i++; + System.out.println("Max Loop Count : " + args[i]); + int m = new Integer(args[i]).intValue(); + fpsCounter.setMaxLoops(m); + } + else if(args[i].startsWith("h", 1)) { + System.out.println("Usage : FPSCounterDemo [-name value]\n" + + "All arguments are of the form: -name value. All -name arguments can be\n" + + "shortened to one character. All the value arguments take a number. The\n" + + "arguments accepted are:\n\n" + + " -warmupTime : Specifies amount of time the FPSCounter should wait\n" + + " for the HotSpot(tm) VM to perform initial\n" + + " optimizations. Specified in milliseconds\n\n" + + " -loopCount : Specifies the number of sampling intervals over which\n" + + " the FPSCounter should calculate the aggregate and average\n" + + " frame rate. Specified as a count\n\n" + + " -maxLoops : Specifies that the FPSCounter should run for only these\n" + + " many sampling intervals. Specified as number. If this argument\n" + + " is not specified, the FPSCounter runs indefinitely.\n\n" + + " -help : Prints this message."); + } + } + } + } + + // ---------------------------------------------------------------- + + /** This method is called from within the constructor to + * initialize the form. + * WARNING: Do NOT modify this code. The content of this method is + * always regenerated by the Form Editor. + */ + // <editor-fold defaultstate="collapsed" desc=" Generated Code ">//GEN-BEGIN:initComponents + private void initComponents() { + drawingPanel = new javax.swing.JPanel(); + + setDefaultCloseOperation(javax.swing.WindowConstants.EXIT_ON_CLOSE); + setTitle("FPSCounterDemo"); + drawingPanel.setLayout(new java.awt.BorderLayout()); + + drawingPanel.setPreferredSize(new java.awt.Dimension(250, 250)); + getContentPane().add(drawingPanel, java.awt.BorderLayout.CENTER); + + pack(); + }// </editor-fold>//GEN-END:initComponents + + /** + * @param args the command line arguments + */ + public static void main(final String args[]) { + java.awt.EventQueue.invokeLater(new Runnable() { + public void run() { + FPSCounterDemo fp = new FPSCounterDemo(); + fp.parseArgs(args); + fp.setVisible(true); + } + }); + } + + // Variables declaration - do not modify//GEN-BEGIN:variables + private javax.swing.JPanel drawingPanel; + // End of variables declaration//GEN-END:variables + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/gears/Gear.java b/src/main/java/org/jdesktop/j3d/examples/gears/Gear.java new file mode 100644 index 0000000..63ececf --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/gears/Gear.java @@ -0,0 +1,403 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.gears; + +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.GeometryArray; +import org.jogamp.java3d.Shape3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.TriangleStripArray; +import org.jogamp.vecmath.Point3f; +import org.jogamp.vecmath.Vector3f; + +public class Gear extends TransformGroup { + + // Specifiers determining whether to generate outward facing normals or + // inward facing normals. + static final int OutwardNormals = 1; + static final int InwardNormals = -1; + + // The number of teeth in the gear + int toothCount; + + // Gear start differential angle. All gears are constructed with the + // center of a tooth at Z-axis angle = 0. + double gearStartAngle; + // The Z-rotation angle to place the tooth center at theta = 0 + float toothTopCenterAngle; + // The Z-rotation angle to place the valley center at theta = 0 + float valleyCenterAngle; + // The angle about Z subtended by one tooth and its associated valley + float circularPitchAngle; + + // Increment angles + float toothValleyAngleIncrement; + + // Front and rear facing normals for the gear's body + final Vector3f frontNormal = new Vector3f(0.0f, 0.0f, -1.0f); + final Vector3f rearNormal = new Vector3f(0.0f, 0.0f, 1.0f); + + + Gear(int toothCount) { + this.toothCount = toothCount; + } + + void addBodyDisks(float shaftRadius, float bodyOuterRadius, + float thickness, Appearance look) { + int gearBodySegmentVertexCount; // #(segments) per tooth-unit + int gearBodyTotalVertexCount; // #(vertices) in a gear face + int gearBodyStripCount[] = new int[1]; // per strip (1) vertex count + + // A ray from the gear center, used in normal calculations + float xDirection, yDirection; + + // The x and y coordinates at each point of a facet and at each + // point on the gear: at the shaft, the root of the teeth, and + // the outer point of the teeth + float xRoot0, yRoot0, xShaft0, yShaft0; + float xRoot3, yRoot3, xShaft3, yShaft3; + float xRoot4, yRoot4, xShaft4, yShaft4; + + // Temporary variables for storing coordinates and vectors + Point3f coordinate = new Point3f(0.0f, 0.0f, 0.0f); + + // Gear start differential angle. All gears are constructed with the + // center of a tooth at Z-axis angle = 0. + double gearStartAngle = -1.0 * toothTopCenterAngle; + + // Temporaries that store start angle for each portion of tooth facet + double toothStartAngle, toothTopStartAngle, + toothDeclineStartAngle, toothValleyStartAngle, + nextToothStartAngle; + + Shape3D newShape; + int index; + + // The z coordinates for the body disks + final float frontZ = -0.5f * thickness; + final float rearZ = 0.5f * thickness; + + /* Construct the gear's front body (front facing torus disk) + * __2__ + * - | - 4 + * - /| /- + * / / | /| \ + * 0\ / | / / > + * \ / | / | > + * \ / | / / | + * \ / ____|/ | > + * \-- --__/ | + * 1 3 5 + * + */ + gearBodySegmentVertexCount = 4; + gearBodyTotalVertexCount = 2 + gearBodySegmentVertexCount * toothCount; + gearBodyStripCount[0] = gearBodyTotalVertexCount; + + TriangleStripArray frontGearBody + = new TriangleStripArray(gearBodyTotalVertexCount, + GeometryArray.COORDINATES + | GeometryArray.NORMALS, + gearBodyStripCount); + + xDirection = (float)Math.cos(gearStartAngle); + yDirection = (float)Math.sin(gearStartAngle); + xShaft0 = shaftRadius * xDirection; + yShaft0 = shaftRadius * yDirection; + xRoot0 = bodyOuterRadius * xDirection; + yRoot0 = bodyOuterRadius * yDirection; + + coordinate.set(xRoot0, yRoot0, frontZ); + frontGearBody.setCoordinate(0, coordinate); + frontGearBody.setNormal(0, frontNormal); + + coordinate.set(xShaft0, yShaft0, frontZ); + frontGearBody.setCoordinate(1, coordinate); + frontGearBody.setNormal(1, frontNormal); + + for(int count = 0; count < toothCount; count++) { + index = 2 + count * 4; + toothStartAngle + = gearStartAngle + circularPitchAngle * (double)count; + toothValleyStartAngle + = toothStartAngle + toothValleyAngleIncrement; + nextToothStartAngle = toothStartAngle + circularPitchAngle; + + xDirection = (float)Math.cos(toothValleyStartAngle); + yDirection = (float)Math.sin(toothValleyStartAngle); + xShaft3 = shaftRadius * xDirection; + yShaft3 = shaftRadius * yDirection; + xRoot3 = bodyOuterRadius * xDirection; + yRoot3 = bodyOuterRadius * yDirection; + + xDirection = (float)Math.cos(nextToothStartAngle); + yDirection = (float)Math.sin(nextToothStartAngle); + xShaft4 = shaftRadius * xDirection; + yShaft4 = shaftRadius * yDirection; + xRoot4 = bodyOuterRadius * xDirection; + yRoot4 = bodyOuterRadius * yDirection; + + coordinate.set(xRoot3, yRoot3, frontZ); + frontGearBody.setCoordinate(index, coordinate); + frontGearBody.setNormal(index, frontNormal); + + coordinate.set(xShaft3, yShaft3, frontZ); + frontGearBody.setCoordinate(index + 1, coordinate); + frontGearBody.setNormal(index + 1, frontNormal); + + coordinate.set(xRoot4, yRoot4, frontZ); + frontGearBody.setCoordinate(index + 2, coordinate); + frontGearBody.setNormal(index + 2, frontNormal); + + coordinate.set(xShaft4, yShaft4, frontZ); + frontGearBody.setCoordinate(index + 3, coordinate); + frontGearBody.setNormal(index + 3, frontNormal); + } + newShape = new Shape3D(frontGearBody, look); + this.addChild(newShape); + + // Construct the gear's rear body (rear facing torus disc) + TriangleStripArray rearGearBody + = new TriangleStripArray(gearBodyTotalVertexCount, + GeometryArray.COORDINATES + | GeometryArray.NORMALS, + gearBodyStripCount); + xDirection = (float)Math.cos(gearStartAngle); + yDirection = (float)Math.sin(gearStartAngle); + xShaft0 = shaftRadius * xDirection; + yShaft0 = shaftRadius * yDirection; + xRoot0 = bodyOuterRadius * xDirection; + yRoot0 = bodyOuterRadius * yDirection; + + coordinate.set(xShaft0, yShaft0, rearZ); + rearGearBody.setCoordinate(0, coordinate); + rearGearBody.setNormal(0, rearNormal); + + coordinate.set(xRoot0, yRoot0, rearZ); + rearGearBody.setCoordinate(1, coordinate); + rearGearBody.setNormal(1, rearNormal); + + for(int count = 0; count < toothCount; count++) { + index = 2 + count * 4; + toothStartAngle + = gearStartAngle + circularPitchAngle * (double)count; + toothValleyStartAngle + = toothStartAngle + toothValleyAngleIncrement; + nextToothStartAngle = toothStartAngle + circularPitchAngle; + + xDirection = (float)Math.cos(toothValleyStartAngle); + yDirection = (float)Math.sin(toothValleyStartAngle); + xShaft3 = shaftRadius * xDirection; + yShaft3 = shaftRadius * yDirection; + xRoot3 = bodyOuterRadius * xDirection; + yRoot3 = bodyOuterRadius * yDirection; + + xDirection = (float)Math.cos(nextToothStartAngle); + yDirection = (float)Math.sin(nextToothStartAngle); + xShaft4 = shaftRadius * xDirection; + yShaft4 = shaftRadius * yDirection; + xRoot4 = bodyOuterRadius * xDirection; + yRoot4 = bodyOuterRadius * yDirection; + + coordinate.set(xShaft3, yShaft3, rearZ); + rearGearBody.setCoordinate(index, coordinate); + rearGearBody.setNormal(index, rearNormal); + + coordinate.set(xRoot3, yRoot3, rearZ); + rearGearBody.setCoordinate(index + 1, coordinate); + rearGearBody.setNormal(index + 1, rearNormal); + + coordinate.set(xShaft4, yShaft4, rearZ); + rearGearBody.setCoordinate(index + 2, coordinate); + rearGearBody.setNormal(index + 2, rearNormal); + + coordinate.set(xRoot4, yRoot4, rearZ); + rearGearBody.setCoordinate(index + 3, coordinate); + rearGearBody.setNormal(index + 3, rearNormal); + + } + newShape = new Shape3D(rearGearBody, look); + this.addChild(newShape); + } + + void addCylinderSkins(float shaftRadius, float length, + int normalDirection, Appearance look) { + int insideShaftVertexCount; // #(vertices) for shaft + int insideShaftStripCount[] = new int[1]; // #(vertices) in strip/strip + double toothStartAngle, nextToothStartAngle, toothValleyStartAngle; + + // A ray from the gear center, used in normal calculations + float xDirection, yDirection; + + // The z coordinates for the body disks + final float frontZ = -0.5f * length; + final float rearZ = 0.5f * length; + + // Temporary variables for storing coordinates, points, and vectors + float xShaft3, yShaft3, xShaft4, yShaft4; + Point3f coordinate = new Point3f(0.0f, 0.0f, 0.0f); + Vector3f surfaceNormal = new Vector3f(); + + Shape3D newShape; + int index; + int firstIndex; + int secondIndex; + + + /* + * Construct gear's inside shaft cylinder + * First the tooth's up, flat outer, and down distances + * Second the tooth's flat inner distance + * + * Outward facing vertex order: + * 0_______2____4 + * | /| /| + * | / | / | + * | / | / | + * |/______|/___| + * 1 3 5 + * + * Inward facing vertex order: + * 1_______3____5 + * |\ |\ | + * | \ | \ | + * | \ | \ | + * |______\|___\| + * 0 2 4 + */ + insideShaftVertexCount = 4 * toothCount + 2; + insideShaftStripCount[0] = insideShaftVertexCount; + + TriangleStripArray insideShaft + = new TriangleStripArray(insideShaftVertexCount, + GeometryArray.COORDINATES + | GeometryArray.NORMALS, + insideShaftStripCount); + xShaft3 = shaftRadius * (float)Math.cos(gearStartAngle); + yShaft3 = shaftRadius * (float)Math.sin(gearStartAngle); + + if (normalDirection == OutwardNormals) { + surfaceNormal.set(1.0f, 0.0f, 0.0f); + firstIndex = 1; + secondIndex = 0; + } else { + surfaceNormal.set(-1.0f, 0.0f, 0.0f); + firstIndex = 0; + secondIndex = 1; + } + + // Coordinate labeled 0 in the strip + coordinate.set(shaftRadius, 0.0f, frontZ); + insideShaft.setCoordinate(firstIndex, coordinate); + insideShaft.setNormal(firstIndex, surfaceNormal); + + // Coordinate labeled 1 in the strip + coordinate.set(shaftRadius, 0.0f, rearZ); + insideShaft.setCoordinate(secondIndex, coordinate); + insideShaft.setNormal(secondIndex, surfaceNormal); + + for(int count = 0; count < toothCount; count++) { + index = 2 + count * 4; + + toothStartAngle = circularPitchAngle * (double)count; + toothValleyStartAngle + = toothStartAngle + toothValleyAngleIncrement; + nextToothStartAngle = toothStartAngle + circularPitchAngle; + + xDirection = (float)Math.cos(toothValleyStartAngle); + yDirection = (float)Math.sin(toothValleyStartAngle); + xShaft3 = shaftRadius * xDirection; + yShaft3 = shaftRadius * yDirection; + if (normalDirection == OutwardNormals) + surfaceNormal.set(xDirection, yDirection, 0.0f); + else + surfaceNormal.set(-xDirection, -yDirection, 0.0f); + + // Coordinate labeled 2 in the strip + coordinate.set(xShaft3, yShaft3, frontZ); + insideShaft.setCoordinate(index + firstIndex, coordinate); + insideShaft.setNormal(index + firstIndex, surfaceNormal); + + // Coordinate labeled 3 in the strip + coordinate.set(xShaft3, yShaft3, rearZ); + insideShaft.setCoordinate(index + secondIndex, coordinate); + insideShaft.setNormal(index + secondIndex, surfaceNormal); + + xDirection = (float)Math.cos(nextToothStartAngle); + yDirection = (float)Math.sin(nextToothStartAngle); + xShaft4 = shaftRadius * xDirection; + yShaft4 = shaftRadius * yDirection; + if (normalDirection == OutwardNormals) + surfaceNormal.set(xDirection, yDirection, 0.0f); + else + surfaceNormal.set(-xDirection, -yDirection, 0.0f); + + // Coordinate labeled 4 in the strip + coordinate.set(xShaft4, yShaft4, frontZ); + insideShaft.setCoordinate(index + 2 + firstIndex, coordinate); + insideShaft.setNormal(index + 2 + firstIndex, surfaceNormal); + + // Coordinate labeled 5 in the strip + coordinate.set(xShaft4, yShaft4, rearZ); + insideShaft.setCoordinate(index + 2 + secondIndex, coordinate); + insideShaft.setNormal(index + 2 + secondIndex, surfaceNormal); + + } + newShape = new Shape3D(insideShaft, look); + this.addChild(newShape); + } + + public float getToothTopCenterAngle() { + return toothTopCenterAngle; + } + + public float getValleyCenterAngle() { + return valleyCenterAngle; + } + + public float getCircularPitchAngle() { + return circularPitchAngle; + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/gears/GearBox.form b/src/main/java/org/jdesktop/j3d/examples/gears/GearBox.form new file mode 100644 index 0000000..840732c --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/gears/GearBox.form @@ -0,0 +1,36 @@ +<?xml version="1.0" encoding="UTF-8" ?> + +<Form version="1.0" type="org.netbeans.modules.form.forminfo.JFrameFormInfo"> + <Properties> + <Property name="defaultCloseOperation" type="int" value="3"/> + <Property name="title" type="java.lang.String" value="GearBox"/> + </Properties> + <SyntheticProperties> + <SyntheticProperty name="formSizePolicy" type="int" value="1"/> + </SyntheticProperties> + <AuxValues> + <AuxValue name="FormSettings_generateMnemonicsCode" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_listenerGenerationStyle" type="java.lang.Integer" value="0"/> + <AuxValue name="FormSettings_variablesLocal" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_variablesModifier" type="java.lang.Integer" value="2"/> + <AuxValue name="designerSize" type="java.awt.Dimension" value="-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,1,44,0,0,1,-112"/> + </AuxValues> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + <SubComponents> + <Container class="javax.swing.JPanel" name="drawingPanel"> + <Properties> + <Property name="preferredSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor"> + <Dimension value="[700, 700]"/> + </Property> + </Properties> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout" value="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription"> + <BorderConstraints direction="Center"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + </Container> + </SubComponents> +</Form> diff --git a/src/main/java/org/jdesktop/j3d/examples/gears/GearBox.java b/src/main/java/org/jdesktop/j3d/examples/gears/GearBox.java new file mode 100644 index 0000000..9f3bf6f --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/gears/GearBox.java @@ -0,0 +1,408 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.gears; + +import java.awt.GraphicsConfiguration; + +import org.jogamp.java3d.Alpha; +import org.jogamp.java3d.AmbientLight; +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.Background; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.DirectionalLight; +import org.jogamp.java3d.Material; +import org.jogamp.java3d.RotationInterpolator; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.utils.behaviors.vp.OrbitBehavior; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.java3d.utils.universe.ViewingPlatform; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Vector3d; +import org.jogamp.vecmath.Vector3f; + +/** + * Simple Java 3D example program to display a spinning cube. + */ +public class GearBox extends javax.swing.JFrame { + + private SimpleUniverse univ = null; + private BranchGroup scene = null; + private int toothCount = 48; + + public BranchGroup createSceneGraph() { + Transform3D tempTransform = new Transform3D(); + + // Create the root of the branch graph + BranchGroup branchRoot = createBranchEnvironment(); + + // Create a Transformgroup to scale all objects so they + // appear in the scene. + TransformGroup objScale = new TransformGroup(); + Transform3D t3d = new Transform3D(); + t3d.setScale(0.4); + objScale.setTransform(t3d); + branchRoot.addChild(objScale); + + // Create an Appearance. + Appearance look = new Appearance(); + Color3f objColor = new Color3f(0.5f, 0.5f, 0.6f); + Color3f black = new Color3f(0.0f, 0.0f, 0.0f); + Color3f white = new Color3f(1.0f, 1.0f, 1.0f); + look.setMaterial(new Material(objColor, black, + objColor, white, 100.0f)); + + + // Create the transform group node and initialize it to the + // identity. Enable the TRANSFORM_WRITE capability so that + // our behavior code can modify it at runtime. Add it to the + // root of the subgraph. + TransformGroup gearboxTrans = new TransformGroup(); + gearboxTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + gearboxTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_READ); + objScale.addChild(gearboxTrans); + + // Create a bounds for the mouse behavior methods + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + + // Define the shaft base information + int shaftCount = 4; + int secondsPerRevolution = 8000; + + // Create the Shaft(s) + Shaft shafts[] = new Shaft[shaftCount]; + TransformGroup shaftTGs[] = new TransformGroup[shaftCount]; + Alpha shaftAlphas[] = new Alpha[shaftCount]; + RotationInterpolator shaftRotors[] + = new RotationInterpolator[shaftCount]; + Transform3D shaftAxis[] = new Transform3D[shaftCount]; + + // Note: the following arrays we're incorporated to make changing + // the gearbox easier. + float shaftRatios[] = new float[shaftCount]; + shaftRatios[0] = 1.0f; + shaftRatios[1] = 0.5f; + shaftRatios[2] = 0.75f; + shaftRatios[3] = 5.0f; + + float shaftRadius[] = new float[shaftCount]; + shaftRadius[0] = 0.2f; + shaftRadius[1] = 0.2f; + shaftRadius[2] = 0.2f; + shaftRadius[3] = 0.2f; + + float shaftLength[] = new float[shaftCount]; + shaftLength[0] = 1.8f; + shaftLength[1] = 0.8f; + shaftLength[2] = 0.8f; + shaftLength[3] = 0.8f; + + float shaftDirection[] = new float[shaftCount]; + shaftDirection[0] = 1.0f; + shaftDirection[1] = -1.0f; + shaftDirection[2] = 1.0f; + shaftDirection[3] = -1.0f; + + Vector3d shaftPlacement[] = new Vector3d[shaftCount]; + shaftPlacement[0] = new Vector3d(-0.75, -0.9, 0.0); + shaftPlacement[1] = new Vector3d(0.75, -0.9, 0.0); + shaftPlacement[2] = new Vector3d(0.75, 0.35, 0.0); + shaftPlacement[3] = new Vector3d(-0.75, 0.60, -0.7); + + // Create the shafts. + for(int i = 0; i < shaftCount; i++) { + shafts[i] = new Shaft(shaftRadius[i], shaftLength[i], 25, look); + } + + // Create a transform group node for placing each shaft + for(int i = 0; i < shaftCount; i++) { + shaftTGs[i] = new TransformGroup(); + gearboxTrans.addChild(shaftTGs[i]); + shaftTGs[i].getTransform(tempTransform); + tempTransform.setTranslation(shaftPlacement[i]); + shaftTGs[i].setTransform(tempTransform); + shaftTGs[i].addChild(shafts[i]); + } + + // Add rotation interpolators to rotate the shaft in the appropriate + // direction and at the appropriate rate + for(int i = 0; i < shaftCount; i++) { + shaftAlphas[i] = new Alpha(-1, Alpha.INCREASING_ENABLE, 0, 0, + (long)(secondsPerRevolution + * shaftRatios[i]), + 0, 0, + 0, 0, 0); + shaftAxis[i] = new Transform3D(); + shaftAxis[i].rotX(Math.PI/2.0); + shaftRotors[i] + = new RotationInterpolator(shaftAlphas[i], shafts[i], + shaftAxis[i], + 0.0f, + shaftDirection[i] * + (float) Math.PI * 2.0f); + shaftRotors[i].setSchedulingBounds(bounds); + shaftTGs[i].addChild(shaftRotors[i]); + } + + // Define the gear base information. Again, these arrays exist to + // make the process of changing the GearBox1 via an editor faster + int gearCount = 5; + float valleyToCircularPitchRatio = .15f; + float pitchCircleRadius = 1.0f; + float addendum = 0.05f; + float dedendum = 0.05f; + float gearThickness = 0.3f; + float toothTipThickness = 0.27f; + + // Create an array of gears and their associated information + SpurGear gears[] = new SpurGear[gearCount]; + TransformGroup gearTGs[] = new TransformGroup[gearCount]; + + int gearShaft[] = new int[gearCount]; + gearShaft[0] = 0; + gearShaft[1] = 1; + gearShaft[2] = 2; + gearShaft[3] = 0; + gearShaft[4] = 3; + + float ratio[] = new float[gearCount]; + ratio[0] = 1.0f; + ratio[1] = 0.5f; + ratio[2] = 0.75f; + ratio[3] = 0.25f; + ratio[4] = 1.25f; + + Vector3d placement[] = new Vector3d[gearCount]; + placement[0] = new Vector3d(0.0, 0.0, 0.0); + placement[1] = new Vector3d(0.0, 0.0, 0.0); + placement[2] = new Vector3d(0.0, 0.0, 0.0); + placement[3] = new Vector3d(0.0, 0.0, -0.7); + placement[4] = new Vector3d(0.0, 0.0, 0.0); + + // Create the gears. + for(int i = 0; i < gearCount; i++) { + gears[i] + = new SpurGearThinBody(((int)((float)toothCount * ratio[i])), + pitchCircleRadius * ratio[i], + shaftRadius[0], + addendum, dedendum, + gearThickness, + toothTipThickness, + valleyToCircularPitchRatio, look); + } + + // Create a transform group node for arranging the gears on a shaft + // and attach the gear to its associated shaft + for(int i = 0; i < gearCount; i++) { + gearTGs[i] = new TransformGroup(); + gearTGs[i].getTransform(tempTransform); + tempTransform.rotZ((shaftDirection[gearShaft[i]] == -1.0) ? + gears[i].getCircularPitchAngle()/-2.0f : + 0.0f); + tempTransform.setTranslation(placement[i]); + gearTGs[i].setTransform(tempTransform); + gearTGs[i].addChild(gears[i]); + shafts[gearShaft[i]].addChild(gearTGs[i]); + } + + // Have Java 3D perform optimizations on this scene graph. + branchRoot.compile(); + + return branchRoot; + } + + BranchGroup createBranchEnvironment(){ + // Create the root of the branch graph + BranchGroup branchRoot = new BranchGroup(); + + // Create a bounds for the background and lights + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + + // Set up the background + Color3f bgColor = new Color3f(0.05f, 0.05f, 0.5f); + Background bgNode = new Background(bgColor); + bgNode.setApplicationBounds(bounds); + branchRoot.addChild(bgNode); + + // Set up the ambient light + Color3f ambientColor = new Color3f(0.1f, 0.1f, 0.1f); + AmbientLight ambientLightNode = new AmbientLight(ambientColor); + ambientLightNode.setInfluencingBounds(bounds); + branchRoot.addChild(ambientLightNode); + + // Set up the directional lights + Color3f light1Color = new Color3f(1.0f, 1.0f, 0.9f); + Vector3f light1Direction = new Vector3f(1.0f, 1.0f, 1.0f); + Color3f light2Color = new Color3f(1.0f, 1.0f, 0.9f); + Vector3f light2Direction = new Vector3f(-1.0f, -1.0f, -1.0f); + + DirectionalLight light1 + = new DirectionalLight(light1Color, light1Direction); + light1.setInfluencingBounds(bounds); + branchRoot.addChild(light1); + + DirectionalLight light2 + = new DirectionalLight(light2Color, light2Direction); + light2.setInfluencingBounds(bounds); + branchRoot.addChild(light2); + + return branchRoot; + } + + private Canvas3D createUniverse() { + // Get the preferred graphics configuration for the default screen + GraphicsConfiguration config = + SimpleUniverse.getPreferredConfiguration(); + + // Create a Canvas3D using the preferred configuration + Canvas3D c = new Canvas3D(config); + + // Create simple universe with view branch + univ = new SimpleUniverse(c); + + // add mouse behaviors to the ViewingPlatform + ViewingPlatform viewingPlatform = univ.getViewingPlatform(); + + // add orbit behavior to the ViewingPlatform + OrbitBehavior orbit = new OrbitBehavior(c, OrbitBehavior.REVERSE_ALL); + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0, 0.0, 0.0), 100.0); + orbit.setSchedulingBounds(bounds); + viewingPlatform.setViewPlatformBehavior(orbit); + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + univ.getViewingPlatform().setNominalViewingTransform(); + + // Ensure at least 5 msec per frame (i.e., < 200Hz) + univ.getViewer().getView().setMinimumFrameCycleTime(5); + + return c; + } + + + /** + * Creates new form GearBox + */ + public GearBox(String args[]) { + int value; + + if (args.length > 1) { + System.out.println("Usage: java GearBox #teeth (LCD 4)"); + System.exit(0); + } else if (args.length == 1) { + { + try{ + value = Integer.parseInt(args[0]); + } catch (NumberFormatException e) { + System.out.println("Illegal integer specified"); + System.out.println("Usage: java GearBox #teeth (LCD 4)"); + value = 0; + System.exit(0); + } + if (value <= 0 | (value % 4) != 0) { + System.out.println("Integer not a positive multiple of 4"); + System.out.println("Usage: java GearBox #teeth (LCD 4)"); + System.exit(0); + } + toothCount = value; + } + } + + // Initialize the GUI components + initComponents(); + + // Create Canvas3D and SimpleUniverse; add canvas to drawing panel + Canvas3D c = createUniverse(); + drawingPanel.add(c, java.awt.BorderLayout.CENTER); + + // Create the content branch and add it to the universe + scene = createSceneGraph(); + univ.addBranchGraph(scene); + } + + // ---------------------------------------------------------------- + + /** This method is called from within the constructor to + * initialize the form. + * WARNING: Do NOT modify this code. The content of this method is + * always regenerated by the Form Editor. + */ + // <editor-fold defaultstate="collapsed" desc=" Generated Code ">//GEN-BEGIN:initComponents + private void initComponents() { + drawingPanel = new javax.swing.JPanel(); + + setDefaultCloseOperation(javax.swing.WindowConstants.EXIT_ON_CLOSE); + setTitle("GearBox"); + drawingPanel.setLayout(new java.awt.BorderLayout()); + + drawingPanel.setPreferredSize(new java.awt.Dimension(700, 700)); + getContentPane().add(drawingPanel, java.awt.BorderLayout.CENTER); + + pack(); + }// </editor-fold>//GEN-END:initComponents + + /** + * @param args the command line arguments + */ + public static void main(final String args[]) { + java.awt.EventQueue.invokeLater(new Runnable() { + public void run() { + GearBox gb = new GearBox(args); + gb.setVisible(true); + } + }); + } + + // Variables declaration - do not modify//GEN-BEGIN:variables + private javax.swing.JPanel drawingPanel; + // End of variables declaration//GEN-END:variables + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/gears/GearTest.form b/src/main/java/org/jdesktop/j3d/examples/gears/GearTest.form new file mode 100644 index 0000000..0ba2e64 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/gears/GearTest.form @@ -0,0 +1,36 @@ +<?xml version="1.0" encoding="UTF-8" ?> + +<Form version="1.0" type="org.netbeans.modules.form.forminfo.JFrameFormInfo"> + <Properties> + <Property name="defaultCloseOperation" type="int" value="3"/> + <Property name="title" type="java.lang.String" value="GearTest"/> + </Properties> + <SyntheticProperties> + <SyntheticProperty name="formSizePolicy" type="int" value="1"/> + </SyntheticProperties> + <AuxValues> + <AuxValue name="FormSettings_generateMnemonicsCode" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_listenerGenerationStyle" type="java.lang.Integer" value="0"/> + <AuxValue name="FormSettings_variablesLocal" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_variablesModifier" type="java.lang.Integer" value="2"/> + <AuxValue name="designerSize" type="java.awt.Dimension" value="-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,1,44,0,0,1,-112"/> + </AuxValues> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + <SubComponents> + <Container class="javax.swing.JPanel" name="drawingPanel"> + <Properties> + <Property name="preferredSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor"> + <Dimension value="[700, 700]"/> + </Property> + </Properties> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout" value="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription"> + <BorderConstraints direction="Center"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + </Container> + </SubComponents> +</Form> diff --git a/src/main/java/org/jdesktop/j3d/examples/gears/GearTest.java b/src/main/java/org/jdesktop/j3d/examples/gears/GearTest.java new file mode 100644 index 0000000..d50d7d3 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/gears/GearTest.java @@ -0,0 +1,256 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.gears; + +import java.awt.GraphicsConfiguration; + +import org.jogamp.java3d.Alpha; +import org.jogamp.java3d.AmbientLight; +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.Background; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.DirectionalLight; +import org.jogamp.java3d.Material; +import org.jogamp.java3d.RotationInterpolator; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Vector3f; + +/** + * Simple Java 3D example program to display a spinning cube. + */ +public class GearTest extends javax.swing.JFrame { + + private int toothCount = 24; + private SimpleUniverse univ = null; + private BranchGroup scene = null; + + public BranchGroup createSceneGraph() { + // Create the root of the branch graph + BranchGroup objRoot = new BranchGroup(); + + // Create a Transformgroup to scale all objects so they + // appear in the scene. + TransformGroup objScale = new TransformGroup(); + Transform3D t3d = new Transform3D(); + t3d.setScale(0.4); + objScale.setTransform(t3d); + objRoot.addChild(objScale); + + // Create a bounds for the background and lights + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + + // Set up the background + Color3f bgColor = new Color3f(0.05f, 0.05f, 0.2f); + Background bgNode = new Background(bgColor); + bgNode.setApplicationBounds(bounds); + objScale.addChild(bgNode); + + // Set up the global lights + Color3f light1Color = new Color3f(1.0f, 1.0f, 0.9f); + Vector3f light1Direction = new Vector3f(4.0f, -7.0f, -12.0f); + Color3f light2Color = new Color3f(0.3f, 0.3f, 0.4f); + Vector3f light2Direction = new Vector3f(-6.0f, -2.0f, -1.0f); + Color3f ambientColor = new Color3f(0.1f, 0.1f, 0.1f); + + AmbientLight ambientLightNode = new AmbientLight(ambientColor); + ambientLightNode.setInfluencingBounds(bounds); + objScale.addChild(ambientLightNode); + + DirectionalLight light1 + = new DirectionalLight(light1Color, light1Direction); + light1.setInfluencingBounds(bounds); + objScale.addChild(light1); + + DirectionalLight light2 + = new DirectionalLight(light2Color, light2Direction); + light2.setInfluencingBounds(bounds); + objScale.addChild(light2); + + // Create the transform group node and initialize it to the + // identity. Enable the TRANSFORM_WRITE capability so that + // our behavior code can modify it at runtime. Add it to the + // root of the subgraph. + TransformGroup objTrans = new TransformGroup(); + objTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + objScale.addChild(objTrans); + + // Create an Appearance. + Appearance look = new Appearance(); + Color3f objColor = new Color3f(0.5f, 0.5f, 0.6f); + Color3f black = new Color3f(0.0f, 0.0f, 0.0f); + Color3f white = new Color3f(1.0f, 1.0f, 1.0f); + look.setMaterial(new Material(objColor, black, objColor, white, 100.0f)); + + // Create a gear, add it to the scene graph. + // SpurGear gear = new SpurGear(toothCount, 1.0f, 0.2f, + SpurGear gear = new SpurGearThinBody(toothCount, 1.0f, 0.2f, + 0.05f, 0.05f, 0.3f, 0.28f, look); + objTrans.addChild(gear); + + // Create a new Behavior object that will rotate the object and + // add it into the scene graph. + Transform3D yAxis = new Transform3D(); + Alpha rotationAlpha = new Alpha(-1, Alpha.INCREASING_ENABLE, + 0, 0, + 8000, 0, 0, + 0, 0, 0); + + RotationInterpolator rotator = + new RotationInterpolator(rotationAlpha, objTrans, yAxis, + 0.0f, (float) Math.PI*2.0f); + rotator.setSchedulingBounds(bounds); + objTrans.addChild(rotator); + + // Have Java 3D perform optimizations on this scene graph. + objRoot.compile(); + + return objRoot; + } + + private Canvas3D createUniverse() { + // Get the preferred graphics configuration for the default screen + GraphicsConfiguration config = + SimpleUniverse.getPreferredConfiguration(); + + // Create a Canvas3D using the preferred configuration + Canvas3D c = new Canvas3D(config); + + // Create simple universe with view branch + univ = new SimpleUniverse(c); + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + univ.getViewingPlatform().setNominalViewingTransform(); + + // Ensure at least 5 msec per frame (i.e., < 200Hz) + univ.getViewer().getView().setMinimumFrameCycleTime(5); + + return c; + } + + /** + * Creates new form GearTest + */ + public GearTest(String args[]) { + int value; + + if (args.length > 1) { + System.out.println("Usage: java GearTest [#teeth]"); + System.exit(0); + } else if (args.length == 1) { + try { + value = Integer.parseInt(args[0]); + } catch (NumberFormatException e) { + System.out.println("Illegal integer specified"); + System.out.println("Usage: java GearTest [#teeth]"); + value = 0; + System.exit(0); + } + if (value <= 0) { + System.out.println("Integer must be positive (> 0)"); + System.out.println("Usage: java GearBox [#teeth]"); + System.exit(0); + } + toothCount = value; + + } + + // Initialize the GUI components + initComponents(); + + // Create Canvas3D and SimpleUniverse; add canvas to drawing panel + Canvas3D c = createUniverse(); + drawingPanel.add(c, java.awt.BorderLayout.CENTER); + + // Create the content branch and add it to the universe + scene = createSceneGraph(); + univ.addBranchGraph(scene); + } + + // ---------------------------------------------------------------- + + /** This method is called from within the constructor to + * initialize the form. + * WARNING: Do NOT modify this code. The content of this method is + * always regenerated by the Form Editor. + */ + // <editor-fold defaultstate="collapsed" desc=" Generated Code ">//GEN-BEGIN:initComponents + private void initComponents() { + drawingPanel = new javax.swing.JPanel(); + + setDefaultCloseOperation(javax.swing.WindowConstants.EXIT_ON_CLOSE); + setTitle("GearTest"); + drawingPanel.setLayout(new java.awt.BorderLayout()); + + drawingPanel.setPreferredSize(new java.awt.Dimension(700, 700)); + getContentPane().add(drawingPanel, java.awt.BorderLayout.CENTER); + + pack(); + }// </editor-fold>//GEN-END:initComponents + + /** + * @param args the command line arguments + */ + public static void main(final String args[]) { + java.awt.EventQueue.invokeLater(new Runnable() { + public void run() { + GearTest gt = new GearTest(args); + gt.setVisible(true); + } + }); + } + + // Variables declaration - do not modify//GEN-BEGIN:variables + private javax.swing.JPanel drawingPanel; + // End of variables declaration//GEN-END:variables + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/gears/Shaft.java b/src/main/java/org/jdesktop/j3d/examples/gears/Shaft.java new file mode 100644 index 0000000..18f1c1a --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/gears/Shaft.java @@ -0,0 +1,203 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.gears; + +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.GeometryArray; +import org.jogamp.java3d.Shape3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.TriangleFanArray; +import org.jogamp.java3d.TriangleStripArray; +import org.jogamp.vecmath.Point3f; +import org.jogamp.vecmath.Vector3f; + +public class Shaft extends TransformGroup { + + /** + * Construct a Shaft; + * @return a new shaft that with the specified radius centered about + * the origin an laying in the XY plane and of a specified length + * extending in the Z dimension + * @param radius radius of shaft + * @param length shaft length shaft extends from -length/2 to length/2 in + * the Z dimension + * @param segmentCount number of segments for the shaft face + * @param look the Appearance to associate with this shaft + */ + public Shaft(float radius, float length, int segmentCount, + Appearance look) { + // The direction of the ray from the shaft's center + float xDirection, yDirection; + float xShaft, yShaft; + + // The z coordinates for the shaft's faces (never change) + float frontZ = -0.5f * length; + float rearZ = 0.5f * length; + + int shaftFaceVertexCount; // #(vertices) per shaft face + int shaftFaceTotalVertexCount; // total #(vertices) in all teeth + int shaftFaceStripCount[] = new int[1]; // per shaft vertex count + int shaftVertexCount; // #(vertices) for shaft + int shaftStripCount[] = new int[1]; // #(vertices) in strip/strip + + // Front and rear facing normals for the shaft's faces + Vector3f frontNormal = new Vector3f(0.0f, 0.0f, -1.0f); + Vector3f rearNormal = new Vector3f(0.0f, 0.0f, 1.0f); + // Outward facing normal + Vector3f outNormal = new Vector3f(1.0f, 0.0f, 0.0f); + + // Temporary variables for storing coordinates and vectors + Point3f coordinate = new Point3f(0.0f, 0.0f, 0.0f); + Shape3D newShape; + + // The angle subtended by a single segment + double segmentAngle = 2.0 * Math.PI/segmentCount; + double tempAngle; + + // Allow this object to spin. etc. + this.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + + /* for the forward facing fan: + * ___3___ + * - | - + * / | \ + * 4/\ | /\2 + * / \ | / \ + * / \ | / \ + * : \ | / : + * |--------------- *----------------| + * 5 0 1 + * + * for backward facing fan exchange 1 with 5; 2 with 4, etc. + */ + + // Construct the shaft's front and rear face + shaftFaceVertexCount = segmentCount + 2; + shaftFaceStripCount[0] = shaftFaceVertexCount; + + TriangleFanArray frontShaftFace + = new TriangleFanArray(shaftFaceVertexCount, + GeometryArray.COORDINATES + | GeometryArray.NORMALS, + shaftFaceStripCount); + + TriangleFanArray rearShaftFace + = new TriangleFanArray(shaftFaceVertexCount, + GeometryArray.COORDINATES + | GeometryArray.NORMALS, + shaftFaceStripCount); + + coordinate.set(0.0f, 0.0f, frontZ); + frontShaftFace.setCoordinate(0, coordinate); + frontShaftFace.setNormal(0, frontNormal); + + coordinate.set(0.0f, 0.0f, rearZ); + rearShaftFace.setCoordinate(0, coordinate); + rearShaftFace.setNormal(0, rearNormal); + + for(int index = 1; index < segmentCount+2; index++) { + + tempAngle = segmentAngle * -(double)index; + coordinate.set(radius * (float)Math.cos(tempAngle), + radius * (float)Math.sin(tempAngle), + frontZ); + frontShaftFace.setCoordinate(index, coordinate); + frontShaftFace.setNormal(index, frontNormal); + + tempAngle = -tempAngle; + coordinate.set(radius * (float)Math.cos(tempAngle), + radius * (float)Math.sin(tempAngle), + rearZ); + rearShaftFace.setCoordinate(index, coordinate); + rearShaftFace.setNormal(index, rearNormal); + } + newShape = new Shape3D(frontShaftFace, look); + this.addChild(newShape); + newShape = new Shape3D(rearShaftFace, look); + this.addChild(newShape); + + // Construct shaft's outer skin (the cylinder body) + shaftVertexCount = 2 * segmentCount + 2; + shaftStripCount[0] = shaftVertexCount; + + TriangleStripArray shaft + = new TriangleStripArray(shaftVertexCount, + GeometryArray.COORDINATES + | GeometryArray.NORMALS, + shaftStripCount); + + outNormal.set(1.0f, 0.0f, 0.0f); + + coordinate.set(radius, 0.0f, rearZ); + shaft.setCoordinate(0, coordinate); + shaft.setNormal(0, outNormal); + + coordinate.set(radius, 0.0f, frontZ); + shaft.setCoordinate(1, coordinate); + shaft.setNormal(1, outNormal); + + for(int count = 0; count < segmentCount; count++) { + int index = 2 + count * 2; + + tempAngle = segmentAngle * (double)(count + 1); + xDirection = (float)Math.cos(tempAngle); + yDirection = (float)Math.sin(tempAngle); + xShaft = radius * xDirection; + yShaft = radius * yDirection; + outNormal.set(xDirection, yDirection, 0.0f); + + coordinate.set(xShaft, yShaft, rearZ); + shaft.setCoordinate(index, coordinate); + shaft.setNormal(index, outNormal); + + coordinate.set(xShaft, yShaft, frontZ); + shaft.setCoordinate(index + 1, coordinate); + shaft.setNormal(index + 1, outNormal); + } + newShape = new Shape3D(shaft, look); + this.addChild(newShape); + } +} + diff --git a/src/main/java/org/jdesktop/j3d/examples/gears/SpurGear.java b/src/main/java/org/jdesktop/j3d/examples/gears/SpurGear.java new file mode 100644 index 0000000..0649e96 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/gears/SpurGear.java @@ -0,0 +1,563 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.gears; + +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.GeometryArray; +import org.jogamp.java3d.QuadArray; +import org.jogamp.java3d.Shape3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.TriangleStripArray; +import org.jogamp.vecmath.Point3f; +import org.jogamp.vecmath.Vector3f; + +public class SpurGear extends Gear { + + float toothTopAngleIncrement; + float toothDeclineAngleIncrement; + + float rootRadius; + float outsideRadius; + + //The angle subtended by the ascending or descending portion of a tooth + float circularToothEdgeAngle; + // The angle subtended by a flat (either a tooth top or a valley + // between teeth + float circularToothFlatAngle; + + /** + * internal constructor for SpurGear, used by subclasses to establish + * SpurGear's required state + * @return a new spur gear that contains sufficient information to + * continue building + * @param toothCount number of teeth + * @param pitchCircleRadius radius at center of teeth + * @param addendum distance from pitch circle to top of teeth + * @param dedendum distance from pitch circle to root of teeth + * @param toothToValleyAngleRatio the ratio of the angle subtended by the + * tooth to the angle subtended by the valley (must be <= .25) + */ + SpurGear(int toothCount, float pitchCircleRadius, + float addendum, float dedendum, float toothToValleyAngleRatio) { + + super(toothCount); + + // The angle about Z subtended by one tooth and its associated valley + circularPitchAngle = (float)(2.0 * Math.PI / (double)toothCount); + + // The angle subtended by a flat (either a tooth top or a valley + // between teeth + circularToothFlatAngle = circularPitchAngle * toothToValleyAngleRatio; + + //The angle subtended by the ascending or descending portion of a tooth + circularToothEdgeAngle = circularPitchAngle/2.0f - + circularToothFlatAngle; + + // Increment angles + toothTopAngleIncrement = circularToothEdgeAngle; + toothDeclineAngleIncrement + = toothTopAngleIncrement + circularToothFlatAngle; + toothValleyAngleIncrement + = toothDeclineAngleIncrement + circularToothEdgeAngle; + + // Differential angles for offsetting to the center of tooth's top + // and valley + toothTopCenterAngle + = toothTopAngleIncrement + circularToothFlatAngle/2.0f; + valleyCenterAngle + = toothValleyAngleIncrement + circularToothFlatAngle/2.0f; + + // Gear start differential angle. All gears are constructed with the + // center of a tooth at Z-axis angle = 0. + gearStartAngle = -1.0 * toothTopCenterAngle; + + // The radial distance to the root and top of the teeth, respectively + rootRadius = pitchCircleRadius - dedendum; + outsideRadius = pitchCircleRadius + addendum; + + // Allow this object to spin. etc. + this.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + } + + /** + * Construct a SpurGear; + * @return a new spur gear that conforms to the input paramters + * @param toothCount number of teeth + * @param pitchCircleRadius radius at center of teeth + * @param shaftRadius radius of hole at center + * @param addendum distance from pitch circle to top of teeth + * @param dedendum distance from pitch circle to root of teeth + * @param gearThickness thickness of the gear + */ + public SpurGear(int toothCount, float pitchCircleRadius, float shaftRadius, + float addendum, float dedendum, float gearThickness) { + this(toothCount, pitchCircleRadius, shaftRadius, addendum, dedendum, + gearThickness, gearThickness, 0.25f, null); + } + + /** + * Construct a SpurGear; + * @return a new spur gear that conforms to the input paramters + * @param toothCount number of teeth + * @param pitchCircleRadius radius at center of teeth + * @param shaftRadius radius of hole at center + * @param addendum distance from pitch circle to top of teeth + * @param dedendum distance from pitch circle to root of teeth + * @param gearThickness thickness of the gear + * @param look the gear's appearance + */ + public SpurGear(int toothCount, float pitchCircleRadius, float shaftRadius, + float addendum, float dedendum, float gearThickness, + Appearance look) { + this(toothCount, pitchCircleRadius, shaftRadius, addendum, dedendum, + gearThickness, gearThickness, 0.25f, look); + } + + /** + * Construct a SpurGear; + * @return a new spur gear that conforms to the input paramters + * @param toothCount number of teeth + * @param pitchCircleRadius radius at center of teeth + * @param shaftRadius radius of hole at center + * @param addendum distance from pitch circle to top of teeth + * @param dedendum distance from pitch circle to root of teeth + * @param gearThickness thickness of the gear + * @param toothTipThickness thickness of the tip of the tooth + * @param look the gear's appearance + */ + public SpurGear(int toothCount, float pitchCircleRadius, float shaftRadius, + float addendum, float dedendum, float gearThickness, + float toothTipThickness, Appearance look) { + this(toothCount, pitchCircleRadius, shaftRadius, addendum, dedendum, + gearThickness, toothTipThickness, 0.25f, look); + } + + /** + * Construct a SpurGear; + * @return a new spur gear that conforms to the input paramters + * @param toothCount number of teeth + * @param pitchCircleRadius radius at center of teeth + * @param shaftRadius radius of hole at center + * @param addendum distance from pitch circle to top of teeth + * @param dedendum distance from pitch circle to root of teeth + * @param gearThickness thickness of the gear + * @param toothTipThickness thickness of the tip of the tooth + * @param toothToValleyAngleRatio the ratio of the angle subtended by the + * tooth to the angle subtended by the valley (must be <= .25) + * @param look the gear's appearance object + */ + public SpurGear(int toothCount, float pitchCircleRadius, float shaftRadius, + float addendum, float dedendum, float gearThickness, + float toothTipThickness, float toothToValleyAngleRatio, + Appearance look) { + + this(toothCount, pitchCircleRadius, addendum, dedendum, + toothToValleyAngleRatio); + + // Generate the gear's body disks + addBodyDisks(shaftRadius, rootRadius, gearThickness, look); + + // Generate the gear's interior shaft + addCylinderSkins(shaftRadius, gearThickness, InwardNormals, look); + + // Generate the gear's teeth + addTeeth(pitchCircleRadius, rootRadius, + outsideRadius, gearThickness, toothTipThickness, + toothToValleyAngleRatio, look); + } + + /** + * Construct a SpurGear's teeth by adding the teeth shape nodes + * @param pitchCircleRadius radius at center of teeth + * @param rootRadius distance from pitch circle to top of teeth + * @param outsideRadius distance from pitch circle to root of teeth + * @param gearThickness thickness of the gear + * @param toothTipThickness thickness of the tip of the tooth + * @param toothToValleyAngleRatio the ratio of the angle subtended by the + * tooth to the angle subtended by the valley (must be <= .25) + * @param look the gear's appearance object + */ + void addTeeth(float pitchCircleRadius, float rootRadius, + float outsideRadius, float gearThickness, + float toothTipThickness, float toothToValleyAngleRatio, + Appearance look) { + int index; + Shape3D newShape; + + // Temporaries that store start angle for each portion of tooth facet + double toothStartAngle, toothTopStartAngle, + toothDeclineStartAngle, toothValleyStartAngle, + nextToothStartAngle; + + // The x and y coordinates at each point of a facet and at each + // point on the gear: at the shaft, the root of the teeth, and + // the outer point of the teeth + float xRoot0, yRoot0; + float xOuter1, yOuter1; + float xOuter2, yOuter2; + float xRoot3, yRoot3; + float xRoot4, yRoot4; + + // The z coordinates for the gear + final float frontZ = -0.5f * gearThickness; + final float rearZ = 0.5f * gearThickness; + + // The z coordinates for the tooth tip of the gear + final float toothTipFrontZ = -0.5f * toothTipThickness; + final float toothTipRearZ = 0.5f * toothTipThickness; + + int toothFacetVertexCount; // #(vertices) per tooth facet + int toothFacetCount; // #(facets) per tooth + int toothFaceTotalVertexCount; // #(vertices) in all teeth + int toothFaceStripCount[] = new int[toothCount]; + // per tooth vertex count + int topVertexCount; // #(vertices) for teeth tops + int topStripCount[] = new int[1]; // #(vertices) in strip/strip + + // Front and rear facing normals for the teeth faces + Vector3f frontToothNormal = new Vector3f(0.0f, 0.0f, -1.0f); + Vector3f rearToothNormal = new Vector3f(0.0f, 0.0f, 1.0f); + + // Normals for teeth tops up incline, tooth top, and down incline + Vector3f leftNormal = new Vector3f(-1.0f, 0.0f, 0.0f); + Vector3f rightNormal = new Vector3f(1.0f, 0.0f, 0.0f); + Vector3f outNormal = new Vector3f(1.0f, 0.0f, 0.0f); + Vector3f inNormal = new Vector3f(-1.0f, 0.0f, 0.0f); + + // Temporary variables for storing coordinates and vectors + Point3f coordinate = new Point3f(0.0f, 0.0f, 0.0f); + Point3f tempCoordinate1 = new Point3f(0.0f, 0.0f, 0.0f); + Point3f tempCoordinate2 = new Point3f(0.0f, 0.0f, 0.0f); + Point3f tempCoordinate3 = new Point3f(0.0f, 0.0f, 0.0f); + Vector3f tempVector1 = new Vector3f(0.0f, 0.0f, 0.0f); + Vector3f tempVector2 = new Vector3f(0.0f, 0.0f, 0.0f); + + /* Construct the gear's front facing teeth facets + * 0______2 + * / /\ + * / / \ + * / / \ + * //___________\ + * 1 3 + */ + toothFacetVertexCount = 4; + toothFaceTotalVertexCount = toothFacetVertexCount * toothCount; + for(int i = 0; i < toothCount; i++) + toothFaceStripCount[i] = toothFacetVertexCount; + + TriangleStripArray frontGearTeeth + = new TriangleStripArray(toothFaceTotalVertexCount, + GeometryArray.COORDINATES + | GeometryArray.NORMALS, + toothFaceStripCount); + + for(int count = 0; count < toothCount; count++) { + index = count * toothFacetVertexCount; + + toothStartAngle + = gearStartAngle + circularPitchAngle * (double)count; + toothTopStartAngle = toothStartAngle + toothTopAngleIncrement; + toothDeclineStartAngle + = toothStartAngle + toothDeclineAngleIncrement; + toothValleyStartAngle + = toothStartAngle + toothValleyAngleIncrement; + + xRoot0 = rootRadius * (float)Math.cos(toothStartAngle); + yRoot0 = rootRadius * (float)Math.sin(toothStartAngle); + xOuter1 = outsideRadius * (float)Math.cos(toothTopStartAngle); + yOuter1 = outsideRadius * (float)Math.sin(toothTopStartAngle); + xOuter2 = outsideRadius * (float)Math.cos(toothDeclineStartAngle); + yOuter2 = outsideRadius * (float)Math.sin(toothDeclineStartAngle); + xRoot3 = rootRadius * (float)Math.cos(toothValleyStartAngle); + yRoot3 = rootRadius * (float)Math.sin(toothValleyStartAngle); + + tempCoordinate1.set(xRoot0, yRoot0, frontZ); + tempCoordinate2.set(xRoot3, yRoot3, frontZ); + tempVector1.sub(tempCoordinate2, tempCoordinate1); + + tempCoordinate2.set(xOuter1, yOuter1, toothTipFrontZ); + tempVector2.sub(tempCoordinate2, tempCoordinate1); + + frontToothNormal.cross(tempVector1, tempVector2); + frontToothNormal.normalize(); + + coordinate.set(xOuter1, yOuter1, toothTipFrontZ); + frontGearTeeth.setCoordinate(index, coordinate); + frontGearTeeth.setNormal(index, frontToothNormal); + + coordinate.set(xRoot0, yRoot0, frontZ); + frontGearTeeth.setCoordinate(index + 1, coordinate); + frontGearTeeth.setNormal(index + 1, frontToothNormal); + + coordinate.set(xOuter2, yOuter2, toothTipFrontZ); + frontGearTeeth.setCoordinate(index + 2, coordinate); + frontGearTeeth.setNormal(index + 2, frontToothNormal); + + coordinate.set(xRoot3, yRoot3, frontZ); + frontGearTeeth.setCoordinate(index + 3, coordinate); + frontGearTeeth.setNormal(index + 3, frontToothNormal); + } + newShape = new Shape3D(frontGearTeeth, look); + this.addChild(newShape); + + /* Construct the gear's rear facing teeth facets (Using Quads) + * 1______2 + * / \ + * / \ + * / \ + * /____________\ + * 0 3 + */ + toothFacetVertexCount = 4; + toothFaceTotalVertexCount = toothFacetVertexCount * toothCount; + + QuadArray rearGearTeeth + = new QuadArray(toothCount * toothFacetVertexCount, + GeometryArray.COORDINATES + | GeometryArray.NORMALS); + + for(int count = 0; count < toothCount; count++) { + + index = count * toothFacetVertexCount; + toothStartAngle = + gearStartAngle + circularPitchAngle * (double)count; + toothTopStartAngle = toothStartAngle + toothTopAngleIncrement; + toothDeclineStartAngle + = toothStartAngle + toothDeclineAngleIncrement; + toothValleyStartAngle = toothStartAngle + toothValleyAngleIncrement; + + xRoot0 = rootRadius * (float)Math.cos(toothStartAngle); + yRoot0 = rootRadius * (float)Math.sin(toothStartAngle); + xOuter1 = outsideRadius * (float)Math.cos(toothTopStartAngle); + yOuter1 = outsideRadius * (float)Math.sin(toothTopStartAngle); + xOuter2 = outsideRadius * (float)Math.cos(toothDeclineStartAngle); + yOuter2 = outsideRadius * (float)Math.sin(toothDeclineStartAngle); + xRoot3 = rootRadius * (float)Math.cos(toothValleyStartAngle); + yRoot3 = rootRadius * (float)Math.sin(toothValleyStartAngle); + + tempCoordinate1.set(xRoot0, yRoot0, rearZ); + tempCoordinate2.set(xRoot3, yRoot3, rearZ); + tempVector1.sub(tempCoordinate2, tempCoordinate1); + tempCoordinate2.set(xOuter1, yOuter1, toothTipRearZ); + tempVector2.sub(tempCoordinate2, tempCoordinate1); + rearToothNormal.cross(tempVector2, tempVector1); + rearToothNormal.normalize(); + + coordinate.set(xRoot0, yRoot0, rearZ); + rearGearTeeth.setCoordinate(index, coordinate); + rearGearTeeth.setNormal(index, rearToothNormal); + + coordinate.set(xOuter1, yOuter1, toothTipRearZ); + rearGearTeeth.setCoordinate(index + 1, coordinate); + rearGearTeeth.setNormal(index + 1, rearToothNormal); + + coordinate.set(xOuter2, yOuter2, toothTipRearZ); + rearGearTeeth.setCoordinate(index + 2, coordinate); + rearGearTeeth.setNormal(index + 2, rearToothNormal); + + coordinate.set(xRoot3, yRoot3, rearZ); + rearGearTeeth.setCoordinate(index + 3, coordinate); + rearGearTeeth.setNormal(index + 3, rearToothNormal); + + } + newShape = new Shape3D(rearGearTeeth, look); + this.addChild(newShape); + + /* + * Construct the gear's top teeth faces (As seen from above) + * Root0 Outer1 Outer2 Root3 Root4 (RearZ) + * 0_______3 2_______5 4_______7 6_______9 + * |0 3| |4 7| |8 11| |12 15| + * | | | | | | | | + * | | | | | | | | + * |1_____2| |5_____6| |9____10| |13___14| + * 1 2 3 4 5 6 7 8 + * Root0 Outer1 Outer2 Root3 Root4 (FrontZ) + * + * Quad 0123 uses a left normal + * Quad 2345 uses an out normal + * Quad 4567 uses a right normal + * Quad 6789 uses an out normal + */ + topVertexCount = 8 * toothCount + 2; + topStripCount[0] = topVertexCount; + + toothFacetVertexCount = 4; + toothFacetCount = 4; + + QuadArray topGearTeeth + = new QuadArray(toothCount * toothFacetVertexCount + * toothFacetCount, + GeometryArray.COORDINATES + | GeometryArray.NORMALS); + + for(int count = 0; count < toothCount; count++) { + index = count * toothFacetCount * toothFacetVertexCount; + toothStartAngle = gearStartAngle + + circularPitchAngle * (double)count; + toothTopStartAngle = toothStartAngle + toothTopAngleIncrement; + toothDeclineStartAngle + = toothStartAngle + toothDeclineAngleIncrement; + toothValleyStartAngle + = toothStartAngle + toothValleyAngleIncrement; + nextToothStartAngle = toothStartAngle + circularPitchAngle; + + xRoot0 = rootRadius * (float)Math.cos(toothStartAngle); + yRoot0 = rootRadius * (float)Math.sin(toothStartAngle); + xOuter1 = outsideRadius * (float)Math.cos(toothTopStartAngle); + yOuter1 = outsideRadius * (float)Math.sin(toothTopStartAngle); + xOuter2 = outsideRadius * (float)Math.cos(toothDeclineStartAngle); + yOuter2 = outsideRadius * (float)Math.sin(toothDeclineStartAngle); + xRoot3 = rootRadius * (float)Math.cos(toothValleyStartAngle); + yRoot3 = rootRadius * (float)Math.sin(toothValleyStartAngle); + xRoot4 = rootRadius * (float)Math.cos(nextToothStartAngle); + yRoot4 = rootRadius * (float)Math.sin(nextToothStartAngle); + + // Compute normal for quad 1 + tempCoordinate1.set(xRoot0, yRoot0, frontZ); + tempCoordinate2.set(xOuter1, yOuter1, toothTipFrontZ); + tempVector1.sub(tempCoordinate2, tempCoordinate1); + leftNormal.cross(frontNormal, tempVector1); + leftNormal.normalize(); + + // Coordinate labeled 0 in the quad + coordinate.set(xRoot0, yRoot0, rearZ); + topGearTeeth.setCoordinate(index, coordinate); + topGearTeeth.setNormal(index, leftNormal); + + // Coordinate labeled 1 in the quad + coordinate.set(tempCoordinate1); + topGearTeeth.setCoordinate(index + 1, coordinate); + topGearTeeth.setNormal(index + 1, leftNormal); + + // Coordinate labeled 2 in the quad + topGearTeeth.setCoordinate(index + 2, tempCoordinate2); + topGearTeeth.setNormal(index + 2, leftNormal); + topGearTeeth.setCoordinate(index + 5, tempCoordinate2); + + // Coordinate labeled 3 in the quad + coordinate.set(xOuter1, yOuter1, toothTipRearZ); + topGearTeeth.setCoordinate(index + 3, coordinate); + topGearTeeth.setNormal(index + 3, leftNormal); + topGearTeeth.setCoordinate(index + 4, coordinate); + + // Compute normal for quad 2 + tempCoordinate1.set(xOuter1, yOuter1, toothTipFrontZ); + tempCoordinate2.set(xOuter2, yOuter2, toothTipFrontZ); + tempVector1.sub(tempCoordinate2, tempCoordinate1); + outNormal.cross(frontNormal, tempVector1); + outNormal.normalize(); + + topGearTeeth.setNormal(index + 4, outNormal); + topGearTeeth.setNormal(index + 5, outNormal); + + // Coordinate labeled 4 in the quad + topGearTeeth.setCoordinate(index + 6, tempCoordinate2); + topGearTeeth.setNormal(index + 6, outNormal); + topGearTeeth.setCoordinate(index + 9, tempCoordinate2); + + // Coordinate labeled 5 in the quad + coordinate.set(xOuter2, yOuter2, toothTipRearZ); + topGearTeeth.setCoordinate(index + 7, coordinate); + topGearTeeth.setNormal(index + 7, outNormal); + topGearTeeth.setCoordinate(index + 8, coordinate); + + // Compute normal for quad 3 + tempCoordinate1.set(xOuter2, yOuter2, toothTipFrontZ); + tempCoordinate2.set(xRoot3, yRoot3, frontZ); + tempVector1.sub(tempCoordinate2, tempCoordinate1); + rightNormal.cross(frontNormal, tempVector1); + rightNormal.normalize(); + + topGearTeeth.setNormal(index + 8, rightNormal); + topGearTeeth.setNormal(index + 9, rightNormal); + + // Coordinate labeled 7 in the quad + topGearTeeth.setCoordinate(index + 10, tempCoordinate2); + topGearTeeth.setNormal(index + 10, rightNormal); + topGearTeeth.setCoordinate(index + 13, tempCoordinate2); + + // Coordinate labeled 6 in the quad + coordinate.set(xRoot3, yRoot3, rearZ); + topGearTeeth.setCoordinate(index + 11, coordinate); + topGearTeeth.setNormal(index + 11, rightNormal); + topGearTeeth.setCoordinate(index + 12, coordinate); + + // Compute normal for quad 4 + tempCoordinate1.set(xRoot3, yRoot3, frontZ); + tempCoordinate2.set(xRoot4, yRoot4, frontZ); + tempVector1.sub(tempCoordinate2, tempCoordinate1); + outNormal.cross(frontNormal, tempVector1); + outNormal.normalize(); + + topGearTeeth.setNormal(index + 12, outNormal); + topGearTeeth.setNormal(index + 13, outNormal); + + // Coordinate labeled 9 in the quad + topGearTeeth.setCoordinate(index + 14, tempCoordinate2); + topGearTeeth.setNormal(index + 14, outNormal); + + // Coordinate labeled 8 in the quad + coordinate.set(xRoot4, yRoot4, rearZ); + topGearTeeth.setCoordinate(index + 15, coordinate); + topGearTeeth.setNormal(index + 15, outNormal); + + // Prepare for the loop by computing the new normal + toothTopStartAngle + = nextToothStartAngle + toothTopAngleIncrement; + xOuter1 = outsideRadius * (float)Math.cos(toothTopStartAngle); + yOuter1 = outsideRadius * (float)Math.sin(toothTopStartAngle); + + tempCoordinate1.set(xRoot4, yRoot4, toothTipFrontZ); + tempCoordinate2.set(xOuter1, yOuter1, toothTipFrontZ); + tempVector1.sub(tempCoordinate2, tempCoordinate1); + leftNormal.cross(frontNormal, tempVector1); + leftNormal.normalize(); + } + newShape = new Shape3D(topGearTeeth, look); + this.addChild(newShape); + } + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/gears/SpurGearThinBody.java b/src/main/java/org/jdesktop/j3d/examples/gears/SpurGearThinBody.java new file mode 100644 index 0000000..39a7b20 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/gears/SpurGearThinBody.java @@ -0,0 +1,185 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.gears; + +import org.jogamp.java3d.Appearance; + +public class SpurGearThinBody extends SpurGear { + + /** + * Construct a SpurGearThinBody; + * @return a new spur gear that conforms to the input paramters + * @param toothCount number of teeth + * @param pitchCircleRadius radius at center of teeth + * @param shaftRadius radius of hole at center + * @param addendum distance from pitch circle to top of teeth + * @param dedendum distance from pitch circle to root of teeth + * @param gearThickness thickness of the gear + */ + public SpurGearThinBody(int toothCount, float pitchCircleRadius, + float shaftRadius, float addendum, float dedendum, + float gearThickness) { + this(toothCount, pitchCircleRadius, shaftRadius, + addendum, dedendum, gearThickness, gearThickness, 0.25f, null); + } + + /** + * Construct a SpurGearThinBody; + * @return a new spur gear that conforms to the input paramters + * @param toothCount number of teeth + * @param pitchCircleRadius radius at center of teeth + * @param shaftRadius radius of hole at center + * @param addendum distance from pitch circle to top of teeth + * @param dedendum distance from pitch circle to root of teeth + * @param gearThickness thickness of the gear + * @param look the gear's appearance + */ + public SpurGearThinBody(int toothCount, float pitchCircleRadius, + float shaftRadius, float addendum, float dedendum, + float gearThickness, + Appearance look) { + this(toothCount, pitchCircleRadius, shaftRadius, + addendum, dedendum, gearThickness, gearThickness, 0.25f, look); + } + + /** + * Construct a SpurGearThinBody; + * @return a new spur gear that conforms to the input paramters + * @param toothCount number of teeth + * @param pitchCircleRadius radius at center of teeth + * @param shaftRadius radius of hole at center + * @param addendum distance from pitch circle to top of teeth + * @param dedendum distance from pitch circle to root of teeth + * @param gearThickness thickness of the gear + * @param toothTipThickness thickness of the tip of the tooth + * @param look the gear's appearance + */ + public SpurGearThinBody(int toothCount, float pitchCircleRadius, + float shaftRadius, float addendum, float dedendum, + float gearThickness, float toothTipThickness, + Appearance look) { + this(toothCount, pitchCircleRadius, shaftRadius, addendum, + dedendum, gearThickness, toothTipThickness, 0.25f, look); + } + + /** + * Construct a SpurGearThinBody; + * @return a new spur gear that conforms to the input paramters + * @param toothCount number of teeth + * @param pitchCircleRadius radius at center of teeth + * @param shaftRadius radius of hole at center + * @param addendum distance from pitch circle to top of teeth + * @param dedendum distance from pitch circle to root of teeth + * @param gearThickness thickness of the gear + * @param toothTipThickness thickness of the tip of the tooth + * @param toothToValleyRatio ratio of tooth valley to circular pitch + * (must be <= .25) + * @param look the gear's appearance object + */ + public SpurGearThinBody(int toothCount, float pitchCircleRadius, + float shaftRadius, float addendum, float dedendum, + float gearThickness, float toothTipThickness, + float toothToValleyAngleRatio, Appearance look) { + + this(toothCount, pitchCircleRadius, shaftRadius, addendum, + dedendum, gearThickness, toothTipThickness, 0.25f, look, + 0.6f * gearThickness, 0.75f * (pitchCircleRadius - shaftRadius)); + } + + /** + * Construct a SpurGearThinBody; + * @return a new spur gear that conforms to the input paramters + * @param toothCount number of teeth + * @param pitchCircleRadius radius at center of teeth + * @param shaftRadius radius of hole at center + * @param addendum distance from pitch circle to top of teeth + * @param dedendum distance from pitch circle to root of teeth + * @param gearThickness thickness of the gear + * @param toothTipThickness thickness of the tip of the tooth + * @param toothToValleyRatio ratio of tooth valley to circular pitch + * (must be <= .25) + * @param look the gear's appearance object + * @param bodyThickness the thickness of the gear body + * @param crossSectionWidth the width of the depressed portion of the + * gear's body + */ + public SpurGearThinBody(int toothCount, float pitchCircleRadius, + float shaftRadius, float addendum, float dedendum, + float gearThickness, float toothTipThickness, + float toothToValleyAngleRatio, Appearance look, + float bodyThickness, float crossSectionWidth) { + + super(toothCount, pitchCircleRadius, addendum, dedendum, + toothToValleyAngleRatio); + + float diskCrossSectionWidth = + (rootRadius - shaftRadius - crossSectionWidth)/ 2.0f; + float outerShaftRadius = shaftRadius + diskCrossSectionWidth; + float innerToothRadius = rootRadius - diskCrossSectionWidth; + + // Generate the gear's body disks, first by the shaft, then in + // the body and, lastly, by the teeth + addBodyDisks(shaftRadius, outerShaftRadius, + gearThickness, look); + addBodyDisks(innerToothRadius, rootRadius, + gearThickness, look); + addBodyDisks(outerShaftRadius, innerToothRadius, + bodyThickness, look); + + // Generate the gear's "shaft" equivalents the two at the teeth + // and the two at the shaft + addCylinderSkins(innerToothRadius, gearThickness, InwardNormals, look); + addCylinderSkins(outerShaftRadius, gearThickness, OutwardNormals, look); + + // Generate the gear's interior shaft + addCylinderSkins(shaftRadius, gearThickness, InwardNormals, look); + + // Generate the gear's teeth + addTeeth(pitchCircleRadius, rootRadius, + outsideRadius, gearThickness, toothTipThickness, + toothToValleyAngleRatio, look); + } + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/geometry_by_ref/GeometryByReferenceNIOBuffer.java b/src/main/java/org/jdesktop/j3d/examples/geometry_by_ref/GeometryByReferenceNIOBuffer.java new file mode 100644 index 0000000..ec58e4c --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/geometry_by_ref/GeometryByReferenceNIOBuffer.java @@ -0,0 +1,552 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.geometry_by_ref; + +import java.awt.Container; +import java.awt.Frame; +import java.awt.event.ActionEvent; +import java.awt.event.ActionListener; +import java.nio.ByteBuffer; +import java.nio.ByteOrder; +import java.nio.FloatBuffer; + +import javax.swing.BoxLayout; +import javax.swing.JApplet; +import javax.swing.JCheckBox; +import javax.swing.JComboBox; +import javax.swing.JLabel; +import javax.swing.JPanel; +import javax.swing.border.TitledBorder; + +import org.jogamp.java3d.AmbientLight; +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.ColoringAttributes; +import org.jogamp.java3d.DirectionalLight; +import org.jogamp.java3d.Geometry; +import org.jogamp.java3d.GeometryArray; +import org.jogamp.java3d.GeometryUpdater; +import org.jogamp.java3d.IndexedGeometryArray; +import org.jogamp.java3d.IndexedTriangleArray; +import org.jogamp.java3d.IndexedTriangleStripArray; +import org.jogamp.java3d.J3DBuffer; +import org.jogamp.java3d.Material; +import org.jogamp.java3d.RenderingAttributes; +import org.jogamp.java3d.Shape3D; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.TransparencyAttributes; +import org.jogamp.java3d.TriangleArray; +import org.jogamp.java3d.TriangleStripArray; +import org.jogamp.java3d.utils.applet.MainFrame; +import org.jogamp.java3d.utils.behaviors.vp.OrbitBehavior; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.java3d.utils.universe.ViewingPlatform; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Point3f; +import org.jogamp.vecmath.Vector3f; + +public class GeometryByReferenceNIOBuffer extends JApplet implements ActionListener, +GeometryUpdater { + + RenderingAttributes ra; + ColoringAttributes ca; + Material mat; + Appearance app; + JComboBox geomType; + JComboBox vertexType; + JComboBox colorType; + JCheckBox transparency; + JComboBox updates; + Shape3D shape; + TransparencyAttributes transp; + int updateIndex = 0; + int colorCount = 0, vertexCount = 0; + int vertexIndex = 0, colorIndex = 0; + + GeometryArray tetraRegular, tetraStrip, tetraIndexed, tetraIndexedStrip; + GeometryArray[] geoArrays = new GeometryArray[4]; + + private static final float sqrt3 = (float) Math.sqrt(3.0); + private static final float sqrt3_3 = sqrt3 / 3.0f; + private static final float sqrt24_3 = (float) Math.sqrt(24.0) / 3.0f; + + private static final float ycenter = 0.5f * sqrt24_3; + private static final float zcenter = -sqrt3_3; + + private static final Point3f p1 = + new Point3f(-1.0f, -ycenter, -zcenter); + private static final Point3f p2 = + new Point3f(1.0f, -ycenter, -zcenter); + private static final Point3f p3 = + new Point3f(0.0f, -ycenter, -sqrt3 - zcenter); + private static final Point3f p4 = + new Point3f(0.0f, sqrt24_3 - ycenter, 0.0f); + + private static final float[] floatVerts = { + p1.x, p1.y, p1.z, // front face + p2.x, p2.y, p2.z, + p4.x, p4.y, p4.z, + + p1.x, p1.y, p1.z,// left, back face + p4.x, p4.y, p4.z, + p3.x, p3.y, p3.z, + + p2.x, p2.y, p2.z,// right, back face + p3.x, p3.y, p3.z, + p4.x, p4.y, p4.z, + + p1.x, p1.y, p1.z,// bottom face + p3.x, p3.y, p3.z, + p2.x, p2.y, p2.z, + }; + + private static final Color3f c1 = new Color3f(0.6f, 0.0f, 0.0f); + private static final Color3f c2 = new Color3f(0.0f, 0.6f, 0.0f); + private static final Color3f c3 = new Color3f(0.0f, 0.6f, 0.6f); + private static final Color3f c4 = new Color3f(0.6f, 0.6f, 0.0f); + + + + private static final float[] floatClrs = { + c1.x, c1.y, c1.z, // front face + c2.x, c2.y, c2.z, + c4.x, c4.y, c4.z, + + c1.x, c1.y, c1.z,// left, back face + c4.x, c4.y, c4.z, + c3.x, c3.y, c3.z, + + c2.x, c2.y, c2.z,// right, back face + c3.x, c3.y, c3.z, + c4.x, c4.y, c4.z, + + c1.x, c1.y, c1.z,// bottom face + c3.x, c3.y, c3.z, + c2.x, c2.y, c2.z, + }; + + private static final float[] indexedFloatVerts = { + p1.x,p1.y,p1.z, + p2.x,p2.y,p2.z, + p3.x,p3.y,p3.z, + p4.x,p4.y,p4.z, + + }; + + + private static final float[] indexedFloatClrs = { + c1.x,c1.y,c1.z, + c2.x,c2.y,c2.z, + c3.x,c3.y,c3.z, + c4.x,c4.y,c4.z, + }; + + private static final int[] indices = {0,1,3,0,3,2,1,2,3,0,2,1}; + private int[] stripVertexCounts = {3,3,3,3}; + + private SimpleUniverse u; + + private J3DBuffer floatBufferCoord; + private J3DBuffer floatBufferColor; + private J3DBuffer indexedFloatBufferCoord; + private J3DBuffer indexedFloatBufferColor; + + void createJ3DBuffers() { + int i; + ByteOrder order = ByteOrder.nativeOrder(); + + FloatBuffer coord = ByteBuffer.allocateDirect(36 * 4).order(order).asFloatBuffer(); + coord.put(floatVerts, 0, 36); + floatBufferCoord = new J3DBuffer(coord); + + FloatBuffer color = ByteBuffer.allocateDirect(36 * 4).order(order).asFloatBuffer(); + color.put(floatClrs, 0, 36); + floatBufferColor = new J3DBuffer(color); + + FloatBuffer indexedCoord = ByteBuffer.allocateDirect(12 * 4).order(order).asFloatBuffer(); + indexedCoord.put(indexedFloatVerts, 0, 12); + indexedFloatBufferCoord = new J3DBuffer(indexedCoord); + + FloatBuffer indexedColor = ByteBuffer.allocateDirect(12 * 4).order(order).asFloatBuffer(); + indexedColor.put(indexedFloatClrs, 0, 12); + indexedFloatBufferColor = new J3DBuffer(indexedColor); + } + + BranchGroup createSceneGraph() { + BranchGroup objRoot = new BranchGroup(); + + // Set up attributes to render lines + app = new Appearance(); + + transp = new TransparencyAttributes(); + transp.setTransparency(0.5f); + transp.setCapability(TransparencyAttributes.ALLOW_MODE_WRITE); + transp.setTransparencyMode(TransparencyAttributes.NONE); + app.setTransparencyAttributes(transp); + + //create the direct nio buffer + createJ3DBuffers(); + + tetraRegular = createGeometry(1); + tetraStrip =createGeometry(2); + tetraIndexed = createGeometry(3); + tetraIndexedStrip = createGeometry(4); + + geoArrays[0] = tetraRegular; + geoArrays[1] = tetraStrip; + geoArrays[2] = tetraIndexed; + geoArrays[3] = tetraIndexedStrip; + + shape = new Shape3D(tetraRegular, app); + shape.setCapability(Shape3D.ALLOW_GEOMETRY_WRITE); + shape.setCapability(Shape3D.ALLOW_GEOMETRY_READ); + + Transform3D t = new Transform3D(); + // move the object upwards + t.set(new Vector3f(0.0f, 0.3f, 0.0f)); + + // rotate the shape + Transform3D temp = new Transform3D(); + temp.rotX(Math.PI/4.0d); + t.mul(temp); + temp.rotY(Math.PI/4.0d); + t.mul(temp); + + // Shrink the object + t.setScale(0.6); + + TransformGroup trans = new TransformGroup(t); + trans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + trans.setCapability(TransformGroup.ALLOW_TRANSFORM_READ); + + objRoot.addChild(trans); + trans.addChild(shape); + + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + + // Set up the global lights + Color3f lColor1 = new Color3f(0.7f, 0.7f, 0.7f); + Vector3f lDir1 = new Vector3f(-1.0f, -1.0f, -1.0f); + Color3f alColor = new Color3f(0.2f, 0.2f, 0.2f); + + AmbientLight aLgt = new AmbientLight(alColor); + aLgt.setInfluencingBounds(bounds); + DirectionalLight lgt1 = new DirectionalLight(lColor1, lDir1); + lgt1.setInfluencingBounds(bounds); + objRoot.addChild(aLgt); + objRoot.addChild(lgt1); + + // Let Java 3D perform optimizations on this scene graph. + objRoot.compile(); + + return objRoot; + } + + JPanel createGeometryByReferencePanel() { + JPanel panel = new JPanel(); + panel.setBorder(new TitledBorder("Geometry Type")); + + String values[] = {"Array", "Strip", "Indexed", "IndexedStrip"}; + geomType = new JComboBox(values); + geomType.setLightWeightPopupEnabled(false); + geomType.addActionListener(this); + geomType.setSelectedIndex(0); + panel.add(new JLabel("Geometry Type")); + panel.add(geomType); + + return panel; + } + + JPanel createUpdatePanel() { + + JPanel panel = new JPanel(); + panel.setBorder(new TitledBorder("Other Attributes")); + + String updateComp[] = { "None","Geometry", "Color"}; + + transparency = new JCheckBox("EnableTransparency", + false); + transparency.addActionListener(this); + panel.add(transparency); + + + updates = new JComboBox(updateComp); + updates.setLightWeightPopupEnabled(false); + updates.addActionListener(this); + updates.setSelectedIndex(0); + panel.add(new JLabel("UpdateData")); + panel.add(updates); + + return panel; + } + + + + public GeometryByReferenceNIOBuffer() { + } + + public void init() {System.setProperty("sun.awt.noerasebackground", "true"); + Container contentPane = getContentPane(); + + Canvas3D c = new Canvas3D(SimpleUniverse.getPreferredConfiguration()); + contentPane.add("Center", c); + + BranchGroup scene = createSceneGraph(); + // SimpleUniverse is a Convenience Utility class + u = new SimpleUniverse(c); + + // add mouse behaviors to the viewingPlatform + ViewingPlatform viewingPlatform = u.getViewingPlatform(); + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + viewingPlatform.setNominalViewingTransform(); + u.addBranchGraph(scene); + + // add Orbit behavior to the ViewingPlatform + OrbitBehavior orbit = new OrbitBehavior(c, OrbitBehavior.REVERSE_ALL); + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0, 0.0, 0.0), 100.0); + orbit.setSchedulingBounds(bounds); + viewingPlatform.setViewPlatformBehavior(orbit); + + // Create GUI + JPanel p = new JPanel(); + BoxLayout boxlayout = new BoxLayout(p, + BoxLayout.Y_AXIS); + p.add(createGeometryByReferencePanel()); + p.add(createUpdatePanel()); + p.setLayout(boxlayout); + + contentPane.add("South", p); + } + + public void destroy() { + u.cleanup(); + } + + public void actionPerformed(ActionEvent e) { + Object target = e.getSource(); + GeometryArray geo; + boolean setColor = false, setVertex = false; + if (target == geomType) { + geo = geoArrays[geomType.getSelectedIndex()]; + // Set everything to null, and set it later .. + geo.setColorRefBuffer(null); + geo.setCoordRefBuffer(null); + shape.setGeometry(geoArrays[geomType.getSelectedIndex()]); + + setColor = true; + setVertex= true; + + + } + else if (target == transparency) { + if (transparency.isSelected()) { + transp.setTransparencyMode(TransparencyAttributes.BLENDED); + } + else { + transp.setTransparencyMode(TransparencyAttributes.NONE); + } + + } + else if (target == updates) { + updateIndex = updates.getSelectedIndex(); + if (updateIndex == 1) { + System.out.println("Doing coordinate update"); + ((GeometryArray)(shape.getGeometry())).updateData(this); + } + else if (updateIndex == 2) { + System.out.println("Doing color update"); + ((GeometryArray)(shape.getGeometry())).updateData(this); + } + + } + + if (setVertex) { + geo = (GeometryArray) shape.getGeometry(); + if (geo instanceof IndexedGeometryArray) + geo.setCoordRefBuffer(indexedFloatBufferCoord); + else + geo.setCoordRefBuffer(floatBufferCoord); + + } + if (setColor) { + geo = (GeometryArray) shape.getGeometry(); + if (geo instanceof IndexedGeometryArray) + geo.setColorRefBuffer(indexedFloatBufferColor); + else + geo.setColorRefBuffer(floatBufferColor); + } + } + + + + public static void main(String[] args) {System.setProperty("sun.awt.noerasebackground", "true"); + Frame frame = new MainFrame(new GeometryByReferenceNIOBuffer(), 800, 800); + } + + public GeometryArray createGeometry (int type) { + GeometryArray tetra = null; + if (type == 1) { + tetra =new TriangleArray(12, + TriangleArray.COORDINATES| + TriangleArray.COLOR_3| + TriangleArray.BY_REFERENCE| + TriangleArray.USE_NIO_BUFFER); + + tetra.setCoordRefBuffer(floatBufferCoord); + tetra.setColorRefBuffer(floatBufferColor); + + } + else if (type == 2) { + tetra = new TriangleStripArray(12, + TriangleStripArray.COORDINATES| + TriangleStripArray.COLOR_3| + TriangleStripArray.BY_REFERENCE| + TriangleStripArray.USE_NIO_BUFFER, + stripVertexCounts); + tetra.setCoordRefBuffer(floatBufferCoord); + tetra.setColorRefBuffer(floatBufferColor); + + } + else if (type == 3) { // Indexed Geometry + tetra = new IndexedTriangleArray(4, + IndexedTriangleArray.COORDINATES| + IndexedTriangleArray.COLOR_3| + IndexedTriangleArray.BY_REFERENCE| + IndexedTriangleArray.USE_NIO_BUFFER, + //IndexedTriangleStripArray.USE_COORD_INDEX_ONLY, + 12); + tetra.setCoordRefBuffer(indexedFloatBufferCoord); + tetra.setColorRefBuffer(indexedFloatBufferColor); + ((IndexedTriangleArray)tetra).setCoordinateIndices(0, indices); + ((IndexedTriangleArray)tetra).setColorIndices(0, indices); + } + else if (type == 4) { // Indexed strip geometry + tetra = new IndexedTriangleStripArray(4, + IndexedTriangleStripArray.COORDINATES| + IndexedTriangleStripArray.COLOR_3| + IndexedTriangleStripArray.BY_REFERENCE| + IndexedTriangleStripArray.USE_NIO_BUFFER| + IndexedTriangleStripArray.USE_COORD_INDEX_ONLY, + 12, + stripVertexCounts); + tetra.setCoordRefBuffer(indexedFloatBufferCoord); + tetra.setColorRefBuffer(indexedFloatBufferColor); + ((IndexedTriangleStripArray)tetra).setCoordinateIndices(0, indices); + /* + // Do not set color indices in UCIO mode + ((IndexedTriangleStripArray)tetra).setColorIndices(0, indices); + */ + } + + if (tetra != null) + tetra.setCapability(GeometryArray.ALLOW_REF_DATA_WRITE); + return tetra; + } + + public void updateData(Geometry geometry) { + int i; + float val; + float val1; + if (updateIndex == 1) { // geometry + // Translate the geometry by a small amount in x + vertexCount++; + if ((vertexCount &1) == 1) + val = 0.2f; + else + val = -0.2f; + + FloatBuffer indexedCoord = (FloatBuffer)indexedFloatBufferCoord.getBuffer(); + indexedCoord.rewind(); + FloatBuffer coord = (FloatBuffer)floatBufferCoord.getBuffer(); + coord.rewind(); + + if (vertexIndex == 0) { + // Do Indexed geometry + for (i = 0; i < indexedCoord.limit(); i+=3) { + val1 = indexedCoord.get(i); + indexedCoord.put(i, val1 + val); + } + // Do non-indexed float geometry + for (i = 0; i < coord.limit(); i+=3) { + val1 = coord.get(i); + coord.put(i, val1 + val); + } + } + } + else if (updateIndex == 2) { // colors + colorCount++; + if ((colorCount & 1) == 1) + val = 0.4f; + else + val = -0.4f; + + FloatBuffer indexedColors = (FloatBuffer)indexedFloatBufferColor.getBuffer(); + indexedColors.rewind(); + FloatBuffer colors = (FloatBuffer)floatBufferColor.getBuffer(); + colors.rewind(); + + if (colorIndex == 0) { + // Do Indexed geometry + for (i = 0; i < indexedColors.limit(); i+=3) { + indexedColors.put(i, indexedColors.get(i) + val); + } + // Do non-indexed float geometry + for (i = 0; i < colors.limit(); i+=3) { + colors.put(i, colors.get(i) + val); + } + } + + } + + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/geometry_by_ref/GeometryByReferenceTest.java b/src/main/java/org/jdesktop/j3d/examples/geometry_by_ref/GeometryByReferenceTest.java new file mode 100644 index 0000000..55be4a5 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/geometry_by_ref/GeometryByReferenceTest.java @@ -0,0 +1,584 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.geometry_by_ref; + +import java.awt.Container; +import java.awt.Frame; +import java.awt.event.ActionEvent; +import java.awt.event.ActionListener; + +import javax.swing.BoxLayout; +import javax.swing.JApplet; +import javax.swing.JCheckBox; +import javax.swing.JComboBox; +import javax.swing.JLabel; +import javax.swing.JPanel; +import javax.swing.border.TitledBorder; + +import org.jogamp.java3d.AmbientLight; +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.ColoringAttributes; +import org.jogamp.java3d.DirectionalLight; +import org.jogamp.java3d.Geometry; +import org.jogamp.java3d.GeometryArray; +import org.jogamp.java3d.GeometryUpdater; +import org.jogamp.java3d.IndexedGeometryArray; +import org.jogamp.java3d.IndexedTriangleArray; +import org.jogamp.java3d.IndexedTriangleStripArray; +import org.jogamp.java3d.Material; +import org.jogamp.java3d.RenderingAttributes; +import org.jogamp.java3d.Shape3D; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.TransparencyAttributes; +import org.jogamp.java3d.TriangleArray; +import org.jogamp.java3d.TriangleStripArray; +import org.jogamp.java3d.utils.applet.MainFrame; +import org.jogamp.java3d.utils.behaviors.vp.OrbitBehavior; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.java3d.utils.universe.ViewingPlatform; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Point3f; +import org.jogamp.vecmath.Vector3f; + +public class GeometryByReferenceTest extends JApplet implements ActionListener, +GeometryUpdater { + + RenderingAttributes ra; + ColoringAttributes ca; + Material mat; + Appearance app; + JComboBox geomType; + JComboBox vertexType; + JComboBox colorType; + JCheckBox transparency; + JComboBox updates; + Shape3D shape; + TransparencyAttributes transp; + int updateIndex = 0; + int colorCount = 0, vertexCount = 0; + int vertexIndex = 0, colorIndex = 0; + + GeometryArray tetraRegular, tetraStrip, tetraIndexed, tetraIndexedStrip; + GeometryArray[] geoArrays = new GeometryArray[4]; + + private static final float sqrt3 = (float) Math.sqrt(3.0); + private static final float sqrt3_3 = sqrt3 / 3.0f; + private static final float sqrt24_3 = (float) Math.sqrt(24.0) / 3.0f; + + private static final float ycenter = 0.5f * sqrt24_3; + private static final float zcenter = -sqrt3_3; + + private static final Point3f p1 = + new Point3f(-1.0f, -ycenter, -zcenter); + private static final Point3f p2 = + new Point3f(1.0f, -ycenter, -zcenter); + private static final Point3f p3 = + new Point3f(0.0f, -ycenter, -sqrt3 - zcenter); + private static final Point3f p4 = + new Point3f(0.0f, sqrt24_3 - ycenter, 0.0f); + + + private static final float[] floatVerts = { + p1.x, p1.y, p1.z, // front face + p2.x, p2.y, p2.z, + p4.x, p4.y, p4.z, + + p1.x, p1.y, p1.z,// left, back face + p4.x, p4.y, p4.z, + p3.x, p3.y, p3.z, + + p2.x, p2.y, p2.z,// right, back face + p3.x, p3.y, p3.z, + p4.x, p4.y, p4.z, + + p1.x, p1.y, p1.z,// bottom face + p3.x, p3.y, p3.z, + p2.x, p2.y, p2.z, + }; + + private static final Color3f c1 = new Color3f(0.6f, 0.0f, 0.0f); + private static final Color3f c2 = new Color3f(0.0f, 0.6f, 0.0f); + private static final Color3f c3 = new Color3f(0.0f, 0.6f, 0.6f); + private static final Color3f c4 = new Color3f(0.6f, 0.6f, 0.0f); + + + private static final float[] floatClrs = { + c1.x, c1.y, c1.z, // front face + c2.x, c2.y, c2.z, + c4.x, c4.y, c4.z, + + c1.x, c1.y, c1.z,// left, back face + c4.x, c4.y, c4.z, + c3.x, c3.y, c3.z, + + c2.x, c2.y, c2.z,// right, back face + c3.x, c3.y, c3.z, + c4.x, c4.y, c4.z, + + c1.x, c1.y, c1.z,// bottom face + c3.x, c3.y, c3.z, + c2.x, c2.y, c2.z, + } ; + + private static final float[] indexedFloatVerts = { + p1.x,p1.y,p1.z, + p2.x,p2.y,p2.z, + p3.x,p3.y,p3.z, + p4.x,p4.y,p4.z, + + }; + private static final float[] indexedFloatClrs = { + c1.x,c1.y,c1.z, + c2.x,c2.y,c2.z, + c3.x,c3.y,c3.z, + c4.x,c4.y,c4.z, + }; + private static final Point3f[] p3fVerts = { + p1, p2, p4, p1, p4, p3, p2, p3, p4, p1, p3, p2}; + + private static final Point3f[] indexedP3fVerts = {p1, p2, p3, p4}; + + private static final Color3f[] c3fClrs = { + c1, c2, c4, c1, c4, c3, c2, c3, c4, c1, c3, c2}; + + private static final Color3f[] indexedC3fClrs = {c1, c2, c3, c4}; + + + private static final int[] indices = {0,1,3,0,3,2,1,2,3,0,2,1}; + private int[] stripVertexCounts = {3,3,3,3}; + + private SimpleUniverse u; + + BranchGroup createSceneGraph() { + BranchGroup objRoot = new BranchGroup(); + + // Set up attributes to render lines + app = new Appearance(); + + transp = new TransparencyAttributes(); + transp.setTransparency(0.5f); + transp.setCapability(TransparencyAttributes.ALLOW_MODE_WRITE); + transp.setTransparencyMode(TransparencyAttributes.NONE); + app.setTransparencyAttributes(transp); + + tetraRegular = createGeometry(1); + tetraStrip =createGeometry(2); + tetraIndexed = createGeometry(3); + tetraIndexedStrip = createGeometry(4); + + geoArrays[0] = tetraRegular; + geoArrays[1] = tetraStrip; + geoArrays[2] = tetraIndexed; + geoArrays[3] = tetraIndexedStrip; + + shape = new Shape3D(tetraRegular, app); + shape.setCapability(Shape3D.ALLOW_GEOMETRY_WRITE); + shape.setCapability(Shape3D.ALLOW_GEOMETRY_READ); + + Transform3D t = new Transform3D(); + // move the object upwards + t.set(new Vector3f(0.0f, 0.3f, 0.0f)); + + // rotate the shape + Transform3D temp = new Transform3D(); + temp.rotX(Math.PI/4.0d); + t.mul(temp); + temp.rotY(Math.PI/4.0d); + t.mul(temp); + + // Shrink the object + t.setScale(0.6); + + TransformGroup trans = new TransformGroup(t); + trans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + trans.setCapability(TransformGroup.ALLOW_TRANSFORM_READ); + + objRoot.addChild(trans); + trans.addChild(shape); + + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + + // Set up the global lights + Color3f lColor1 = new Color3f(0.7f, 0.7f, 0.7f); + Vector3f lDir1 = new Vector3f(-1.0f, -1.0f, -1.0f); + Color3f alColor = new Color3f(0.2f, 0.2f, 0.2f); + + AmbientLight aLgt = new AmbientLight(alColor); + aLgt.setInfluencingBounds(bounds); + DirectionalLight lgt1 = new DirectionalLight(lColor1, lDir1); + lgt1.setInfluencingBounds(bounds); + objRoot.addChild(aLgt); + objRoot.addChild(lgt1); + + // Let Java 3D perform optimizations on this scene graph. + objRoot.compile(); + + return objRoot; + } + + JPanel createGeometryByReferencePanel() { + JPanel panel = new JPanel(); + panel.setBorder(new TitledBorder("Geometry Type")); + + String values[] = {"Array", "Strip", "Indexed", "IndexedStrip"}; + geomType = new JComboBox(values); + geomType.setLightWeightPopupEnabled(false); + geomType.addActionListener(this); + geomType.setSelectedIndex(0); + panel.add(new JLabel("Geometry Type")); + panel.add(geomType); + + + String vertex_types[] = { "Float","P3F"}; + + vertexType = new JComboBox(vertex_types); + vertexType.setLightWeightPopupEnabled(false); + vertexType.addActionListener(this); + vertexType.setSelectedIndex(0); + panel.add(new JLabel("VertexType")); + panel.add(vertexType); + + + String color_types[] = { "Float","C3F"}; + + colorType = new JComboBox(color_types); + colorType.setLightWeightPopupEnabled(false); + colorType.addActionListener(this); + colorType.setSelectedIndex(0); + panel.add(new JLabel("ColorType")); + panel.add(colorType); + + + + + return panel; + } + + JPanel createUpdatePanel() { + + JPanel panel = new JPanel(); + panel.setBorder(new TitledBorder("Other Attributes")); + + String updateComp[] = { "None","Geometry", "Color"}; + + transparency = new JCheckBox("EnableTransparency", + false); + transparency.addActionListener(this); + panel.add(transparency); + + + updates = new JComboBox(updateComp); + updates.setLightWeightPopupEnabled(false); + updates.addActionListener(this); + updates.setSelectedIndex(0); + panel.add(new JLabel("UpdateData")); + panel.add(updates); + + return panel; + } + + + + public GeometryByReferenceTest() { + } + + public void init() {System.setProperty("sun.awt.noerasebackground", "true"); + Container contentPane = getContentPane(); + + Canvas3D c = new Canvas3D(SimpleUniverse.getPreferredConfiguration()); + contentPane.add("Center", c); + + BranchGroup scene = createSceneGraph(); + // SimpleUniverse is a Convenience Utility class + u = new SimpleUniverse(c); + + // add mouse behaviors to the viewingPlatform + ViewingPlatform viewingPlatform = u.getViewingPlatform(); + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + viewingPlatform.setNominalViewingTransform(); + u.addBranchGraph(scene); + + // add Orbit behavior to the ViewingPlatform + OrbitBehavior orbit = new OrbitBehavior(c, OrbitBehavior.REVERSE_ALL); + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0, 0.0, 0.0), 100.0); + orbit.setSchedulingBounds(bounds); + viewingPlatform.setViewPlatformBehavior(orbit); + + // Create GUI + JPanel p = new JPanel(); + BoxLayout boxlayout = new BoxLayout(p, + BoxLayout.Y_AXIS); + p.add(createGeometryByReferencePanel()); + p.add(createUpdatePanel()); + p.setLayout(boxlayout); + + contentPane.add("South", p); + } + + public void destroy() { + u.cleanup(); + } + + public void actionPerformed(ActionEvent e) { + Object target = e.getSource(); + GeometryArray geo; + boolean setColor = false, setVertex = false; + if (target == geomType) { + geo = geoArrays[geomType.getSelectedIndex()]; + // Set everything to null, and set it later .. + geo.setColorRefFloat(null); + geo.setColorRef3f(null); + geo.setCoordRefFloat(null); + geo.setCoordRef3f(null); + shape.setGeometry(geoArrays[geomType.getSelectedIndex()]); + + setColor = true; + setVertex= true; + + + } + else if (target == transparency) { + if (transparency.isSelected()) { + transp.setTransparencyMode(TransparencyAttributes.BLENDED); + } + else { + transp.setTransparencyMode(TransparencyAttributes.NONE); + } + + + } + else if (target == updates) { + updateIndex = updates.getSelectedIndex(); + if (updateIndex == 1) { + System.out.println("Doing coordinate update"); + ((GeometryArray)(shape.getGeometry())).updateData(this); + } + else if (updateIndex == 2) { + System.out.println("Doing color update"); + ((GeometryArray)(shape.getGeometry())).updateData(this); + } + + } + else if (target == vertexType) { + geo = ((GeometryArray)shape.getGeometry()); + if (vertexIndex == 0) { + geo.setCoordRefFloat(null); + } + else if (vertexIndex == 1) { + geo.setCoordRef3f(null); + } + vertexIndex = vertexType.getSelectedIndex(); + setVertex = true; + } + else if (target == colorType) { + geo = (GeometryArray) shape.getGeometry(); + if (colorIndex == 0) { + geo.setColorRefFloat(null); + } + else if (colorIndex == 1) { + geo.setColorRef3f(null); + } + colorIndex = colorType.getSelectedIndex(); + setColor = true; + } + + if (setVertex) { + geo = (GeometryArray) shape.getGeometry(); + if (vertexIndex == 0) { + if (geo instanceof IndexedGeometryArray) + geo.setCoordRefFloat(indexedFloatVerts); + else + geo.setCoordRefFloat(floatVerts); + } + else if (vertexIndex == 1) { + if (geo instanceof IndexedGeometryArray) + geo.setCoordRef3f(indexedP3fVerts); + else + geo.setCoordRef3f(p3fVerts); + } + + } + if (setColor) { + geo = (GeometryArray) shape.getGeometry(); + if (colorIndex == 0) { + if (geo instanceof IndexedGeometryArray) + geo.setColorRefFloat(indexedFloatClrs); + else + geo.setColorRefFloat(floatClrs); + } + else if (colorIndex == 1) { + if (geo instanceof IndexedGeometryArray) + geo.setColorRef3f(indexedC3fClrs); + else + geo.setColorRef3f(c3fClrs); + } + } + + } + + + + public static void main(String[] args) {System.setProperty("sun.awt.noerasebackground", "true"); + Frame frame = new MainFrame(new GeometryByReferenceTest(), 800, 800); + } + + public GeometryArray createGeometry (int type) { + GeometryArray tetra = null; + if (type == 1) { + tetra =new TriangleArray(12, + TriangleArray.COORDINATES| + TriangleArray.COLOR_3| + TriangleArray.BY_REFERENCE); + + tetra.setCoordRefFloat(floatVerts); + tetra.setColorRefFloat(floatClrs); + + } + else if (type == 2) { + tetra = new TriangleStripArray(12, + TriangleStripArray.COORDINATES| + TriangleStripArray.COLOR_3| + TriangleStripArray.BY_REFERENCE, + stripVertexCounts); + tetra.setCoordRefFloat(floatVerts); + tetra.setColorRefFloat(floatClrs); + + } + else if (type == 3) { // Indexed Geometry + tetra = new IndexedTriangleArray(4, + IndexedTriangleArray.COORDINATES| + IndexedTriangleArray.COLOR_3| + IndexedTriangleArray.BY_REFERENCE, + 12); + tetra.setCoordRefFloat(indexedFloatVerts); + tetra.setColorRefFloat(indexedFloatClrs); + ((IndexedTriangleArray)tetra).setCoordinateIndices(0, indices); + ((IndexedTriangleArray)tetra).setColorIndices(0, indices); + } + else if (type == 4) { // Indexed strip geometry + tetra = new IndexedTriangleStripArray(4, + IndexedTriangleStripArray.COORDINATES| + IndexedTriangleStripArray.COLOR_3| + IndexedTriangleStripArray.BY_REFERENCE, + 12, + stripVertexCounts); + tetra.setCoordRefFloat(indexedFloatVerts); + tetra.setColorRefFloat(indexedFloatClrs); + ((IndexedTriangleStripArray)tetra).setCoordinateIndices(0, indices); + ((IndexedTriangleStripArray)tetra).setColorIndices(0, indices); + } + + if (tetra != null) + tetra.setCapability(GeometryArray.ALLOW_REF_DATA_WRITE); + return tetra; + } + + public void updateData(Geometry geometry) { + int i; + float val; + + + if (updateIndex == 1) { // geometry + // Translate the geometry by a small amount in x + vertexCount++; + if ((vertexCount &1) == 1) + val = 0.2f; + else + val = -0.2f; + + if (vertexIndex == 0) { + // Do Indexed geometry + for (i = 0; i < indexedFloatVerts.length; i+=3) { + indexedFloatVerts[i] += val; + } + // Do non-indexed float geometry + for (i = 0; i < floatVerts.length; i+=3) { + floatVerts[i] += val; + } + } + else { + // If p3f do each point only once + for (i = 0; i < indexedP3fVerts.length; i++) { + indexedP3fVerts[i].x += val; + } + } + + } + else if (updateIndex == 2) { // colors + colorCount++; + if ((colorCount & 1) == 1) + val = 0.4f; + else + val = -0.4f; + if (colorIndex == 0) { + // Do Indexed geometry + for (i = 0; i < indexedFloatClrs.length; i+=3) { + indexedFloatClrs[i] += val; + } + // Do non-indexed float geometry + for (i = 0; i < floatClrs.length; i+=3) { + floatClrs[i] += val; + } + } + else { + // If c3f do each point only once + for (i = 0; i < indexedC3fClrs.length; i++) { + indexedC3fClrs[i].x += val; + } + } + + } + + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/geometry_by_ref/ImageComponentByReferenceTest.java b/src/main/java/org/jdesktop/j3d/examples/geometry_by_ref/ImageComponentByReferenceTest.java new file mode 100644 index 0000000..6829952 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/geometry_by_ref/ImageComponentByReferenceTest.java @@ -0,0 +1,331 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.geometry_by_ref; + +import java.awt.Container; +import java.awt.event.ActionEvent; +import java.awt.event.ActionListener; +import java.awt.image.BufferedImage; +import java.awt.image.RenderedImage; + +import javax.swing.BoxLayout; +import javax.swing.JApplet; +import javax.swing.JComboBox; +import javax.swing.JLabel; +import javax.swing.JPanel; + +import org.jdesktop.j3d.examples.Resources; +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.Group; +import org.jogamp.java3d.ImageComponent; +import org.jogamp.java3d.ImageComponent2D; +import org.jogamp.java3d.Raster; +import org.jogamp.java3d.Shape3D; +import org.jogamp.java3d.Texture; +import org.jogamp.java3d.Texture2D; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.utils.applet.MainFrame; +import org.jogamp.java3d.utils.geometry.Box; +import org.jogamp.java3d.utils.image.TextureLoader; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Point3f; +import org.jogamp.vecmath.Vector3f; + +public class ImageComponentByReferenceTest extends JApplet implements ActionListener { + + Shape3D s1,s2; + TextureLoader t0, t1, t2; + int count = 0; + + Appearance app = new Appearance(); + BranchGroup objRoot = new BranchGroup(); + TransformGroup objTrans = new TransformGroup(); + BufferedImage bImage1; + TiledImage checkBoard; + boolean yUp = false; + boolean byRef = true; + JComboBox rasterType, texType; + ImageComponent2D[] image = new ImageComponent2D[8]; + Appearance dummyApp = new Appearance(); + Texture2D texOne, texCheckBoard; + Raster raster; + Box textureCube; + Shape3D boxShape; + int w1 = 64, h1 = 32, checkw = 16 , checkh = 16; + + private java.net.URL texImage = null; + + private SimpleUniverse u = null; + + public BranchGroup createSceneGraph() { + objRoot = new BranchGroup(); + + objTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + objTrans.setCapability(Group.ALLOW_CHILDREN_WRITE); + + objRoot.addChild(objTrans); + + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + + app.setCapability(Appearance.ALLOW_TEXTURE_WRITE); + + + textureCube = new Box(0.4f, 0.4f, 0.4f, + Box.GENERATE_TEXTURE_COORDS| + Box.GENERATE_NORMALS, app); + boxShape = textureCube.getShape(Box.FRONT); + boxShape.setCapability(Shape3D.ALLOW_APPEARANCE_WRITE); + objTrans.addChild(textureCube); + + checkBoard = new TiledImage(); + TextureLoader texLoader = new TextureLoader( texImage, this); + ImageComponent2D oneImage = texLoader.getImage(); + bImage1 = oneImage.getImage(); + + int index = 0; + image[index++] = new ImageComponent2D(oneImage.getFormat(), + (RenderedImage)bImage1, + false, + true); + + image[index++] = new ImageComponent2D(oneImage.getFormat(), + (RenderedImage)bImage1, + true, + true); + + + image[index++] = new ImageComponent2D(oneImage.getFormat(), + (RenderedImage)bImage1, + false, + false); + + + image[index++] = new ImageComponent2D(oneImage.getFormat(), + (RenderedImage)bImage1, + true, + false); + + createRaster(objRoot); + + image[index++] = new ImageComponent2D(ImageComponent.FORMAT_RGBA, + checkBoard, + false, + true); + + image[index++] = new ImageComponent2D(ImageComponent.FORMAT_RGBA, + checkBoard, + true, + true); + + + image[index++] = new ImageComponent2D(ImageComponent.FORMAT_RGBA, + checkBoard, + false, + false); + + + image[index++] = new ImageComponent2D(ImageComponent.FORMAT_RGBA, + checkBoard, + true, + false); + + + + texOne = new Texture2D(Texture.BASE_LEVEL, + Texture.RGBA, + image[2].getWidth(), image[2].getHeight()); + + texOne.setCapability(Texture.ALLOW_IMAGE_WRITE); + texOne.setImage(0, image[2]); + + app.setTexture(texOne); + + texCheckBoard = new Texture2D(Texture.BASE_LEVEL, + Texture.RGBA, + image[4].getWidth(), image[4].getHeight()); + + texCheckBoard.setCapability(Texture.ALLOW_IMAGE_WRITE); + objRoot.compile(); + return objRoot; + } + + public void actionPerformed(ActionEvent e ) { + Object target = e.getSource(); + + if (target == rasterType) { + if (rasterType.getSelectedIndex() < 4) { + raster.setSize(w1, h1); + } + else { + raster.setSize(checkw, checkh); + } + raster.setImage(image[rasterType.getSelectedIndex()]); + } + else if (target == texType) { + boxShape.setAppearance(dummyApp); + if (texType.getSelectedIndex() < 4) { + texOne.setImage(0, image[texType.getSelectedIndex()]); + app.setTexture(texOne); + } + else { + texCheckBoard.setImage(0, image[texType.getSelectedIndex()]); + app.setTexture(texCheckBoard); + } + + boxShape.setAppearance(app); + } + + + } + + JPanel createImagePanel() { + JPanel panel = new JPanel(); + String texVals[] = { "One_Yup_ByCopy", + "One_Yup_ByReference", + "One_Ydown_ByCopy", + "One_Ydown_ByReference", + "Checkered_Yup_ByCopy", + "Checkered_Yup_ByReference", + "Checkered_Ydown_ByCopy", + "Checkered_Ydown_ByReference"}; + + rasterType = new JComboBox(texVals); + rasterType.setLightWeightPopupEnabled(false); + rasterType.addActionListener(this); + rasterType.setSelectedIndex(2); + panel.add(new JLabel("Raster Image")); + panel.add(rasterType); + + texType = new JComboBox(texVals); + texType.setLightWeightPopupEnabled(false); + texType.addActionListener(this); + texType.setSelectedIndex(2); + panel.add(new JLabel("Texture Image")); + panel.add(texType); + return panel; + + } + + + + public ImageComponentByReferenceTest() + { + } + + public ImageComponentByReferenceTest(java.net.URL url) { + texImage = url; + } + + public void init() {System.setProperty("sun.awt.noerasebackground", "true"); + + texImage = Resources.getResource("resources/images/one.jpg"); + if (texImage == null) { + System.err.println("resources/images/one.jpg not found"); + System.exit(1); + } + + Canvas3D c = new Canvas3D(SimpleUniverse.getPreferredConfiguration()); + BranchGroup scene = createSceneGraph();u = new SimpleUniverse(c); + u.getViewingPlatform().setNominalViewingTransform(); + u.addBranchGraph(scene); + Container contentPane = getContentPane(); + JPanel p = new JPanel(); + BoxLayout boxlayout = new BoxLayout(p, + BoxLayout.Y_AXIS); + p.setLayout(boxlayout); + contentPane.add("Center", c); + + contentPane.add("South", p); + + p.add(createImagePanel()); + + } + + public void destroy() { + u.cleanup(); + } + + public static void main(String[] args) {System.setProperty("sun.awt.noerasebackground", "true"); + java.net.URL url = null; + // the path to the image file for an application + url = Resources.getResource("resources/images/one.jpg"); + if (url == null) { + System.err.println("resources/images/one.jpg not found"); + System.exit(1); + } + + new MainFrame(new ImageComponentByReferenceTest(url), 800, 700); + } + + void createRaster( BranchGroup scene) { + // Create raster geometries and shapes + Vector3f trans = new Vector3f( ); + Transform3D tr = new Transform3D( ); + TransformGroup tg; + + // Left + raster = new Raster( ); + raster.setCapability(Raster.ALLOW_IMAGE_WRITE); + raster.setCapability(Raster.ALLOW_SIZE_WRITE); + raster.setPosition( new Point3f( -0.9f, 0.75f, 0.0f ) ); + raster.setType( Raster.RASTER_COLOR ); + raster.setOffset( 0, 0 ); + + raster.setSize( image[2].getWidth(), image[2].getHeight() ); + raster.setImage( image[2] ); + Shape3D sh = new Shape3D( raster, new Appearance( ) ); + scene.addChild( sh ); + } +} + + + + diff --git a/src/main/java/org/jdesktop/j3d/examples/geometry_by_ref/InterleavedNIOBuffer.java b/src/main/java/org/jdesktop/j3d/examples/geometry_by_ref/InterleavedNIOBuffer.java new file mode 100644 index 0000000..2d642f2 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/geometry_by_ref/InterleavedNIOBuffer.java @@ -0,0 +1,561 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.geometry_by_ref; + +import java.awt.Container; +import java.awt.Frame; +import java.awt.event.ActionEvent; +import java.awt.event.ActionListener; +import java.nio.ByteBuffer; +import java.nio.ByteOrder; +import java.nio.FloatBuffer; + +import javax.swing.BoxLayout; +import javax.swing.JApplet; +import javax.swing.JCheckBox; +import javax.swing.JComboBox; +import javax.swing.JLabel; +import javax.swing.JPanel; +import javax.swing.border.TitledBorder; + +import org.jdesktop.j3d.examples.Resources; +import org.jogamp.java3d.AmbientLight; +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.ColoringAttributes; +import org.jogamp.java3d.DirectionalLight; +import org.jogamp.java3d.GeometryArray; +import org.jogamp.java3d.IndexedTriangleArray; +import org.jogamp.java3d.IndexedTriangleStripArray; +import org.jogamp.java3d.J3DBuffer; +import org.jogamp.java3d.Material; +import org.jogamp.java3d.RenderingAttributes; +import org.jogamp.java3d.Shape3D; +import org.jogamp.java3d.Texture; +import org.jogamp.java3d.TextureAttributes; +import org.jogamp.java3d.TextureUnitState; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.TransparencyAttributes; +import org.jogamp.java3d.TriangleArray; +import org.jogamp.java3d.TriangleStripArray; +import org.jogamp.java3d.utils.applet.MainFrame; +import org.jogamp.java3d.utils.behaviors.vp.OrbitBehavior; +import org.jogamp.java3d.utils.image.TextureLoader; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.java3d.utils.universe.ViewingPlatform; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point2f; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Point3f; +import org.jogamp.vecmath.Vector3f; + +public class InterleavedNIOBuffer extends JApplet implements ActionListener { + + RenderingAttributes ra; + ColoringAttributes ca; + Material mat; + Appearance app; + JComboBox geomType; + JCheckBox transparency; + JCheckBox textureBox; + Shape3D shape; + TransparencyAttributes transp; + + GeometryArray tetraRegular, tetraStrip, tetraIndexed, tetraIndexedStrip; + GeometryArray[] geoArrays = new GeometryArray[4]; + + // Globally used colors + Color3f white = new Color3f(1.0f, 1.0f, 1.0f); + Color3f red = new Color3f(1.0f, 0.0f, 0.0f); + Color3f green = new Color3f(0.0f, 1.0f, 0.0f); + Color3f blue = new Color3f(0.0f, 0.0f, 1.0f); + Color3f[] colors = {white, red, green, blue}; + + private static final float sqrt3 = (float) Math.sqrt(3.0); + private static final float sqrt3_3 = sqrt3 / 3.0f; + private static final float sqrt24_3 = (float) Math.sqrt(24.0) / 3.0f; + + private static final float ycenter = 0.5f * sqrt24_3; + private static final float zcenter = -sqrt3_3; + + private static final Point3f p1 = + new Point3f(-1.0f, -ycenter, -zcenter); + private static final Point3f p2 = + new Point3f(1.0f, -ycenter, -zcenter); + private static final Point3f p3 = + new Point3f(0.0f, -ycenter, -sqrt3 - zcenter); + private static final Point3f p4 = + new Point3f(0.0f, sqrt24_3 - ycenter, 0.0f); + + private static final Point2f t1 = new Point2f(0.0f, 0.0f); + private static final Point2f t2 = new Point2f(0.5f, 1.0f); + private static final Point2f t3 = new Point2f(1.0f, 0.0f); + private static final Point2f t4 = new Point2f(1.0f, 1.0f); + + private static final Color3f c1 = new Color3f(1.0f, 0.0f, 0.0f); + private static final Color3f c2 = new Color3f(0.0f, 1.0f, 0.0f); + private static final Color3f c3 = new Color3f(0.0f, 1.0f, 1.0f); + private static final Color3f c4 = new Color3f(1.0f, 1.0f, 0.0f); + + + private static final float[] interleaved = { + t1.x, t1.y, + t1.x, t1.y, + c1.x, c1.y, c1.z, // front face + p1.x, p1.y, p1.z, // front face + t2.x, t2.y, + t2.x, t2.y, + c2.x, c2.y, c2.z, + p2.x, p2.y, p2.z, + t4.x, t4.y, + t4.x, t4.y, + c4.x, c4.y, c4.z, + p4.x, p4.y, p4.z, + + t1.x, t1.y, + t1.x, t1.y, + c1.x, c1.y, c1.z,// left, back face + p1.x, p1.y, p1.z,// left, back face + t4.x, t4.y, + t4.x, t4.y, + c4.x, c4.y, c4.z, + p4.x, p4.y, p4.z, + t3.x, t3.y, + t3.x, t3.y, + c3.x, c3.y, c3.z, + p3.x, p3.y, p3.z, + + t2.x, t2.y, + t2.x, t2.y, + c2.x, c2.y, c2.z,// right, back face + p2.x, p2.y, p2.z,// right, back face + t3.x, t3.y, + t3.x, t3.y, + c3.x, c3.y, c3.z, + p3.x, p3.y, p3.z, + t4.x, t4.y, + t4.x, t4.y, + c4.x, c4.y, c4.z, + p4.x, p4.y, p4.z, + + t1.x, t1.y, + t1.x, t1.y, + c1.x, c1.y, c1.z,// bottom face + p1.x, p1.y, p1.z,// bottom face + t3.x, t3.y, + t3.x, t3.y, + c3.x, c3.y, c3.z, + p3.x, p3.y, p3.z, + t2.x, t2.y, + t2.x, t2.y, + c2.x, c2.y, c2.z, + p2.x, p2.y, p2.z, + }; + + private static final float[] indexedInterleaved = { + t1.x,t1.y, + t1.x,t1.y, + c1.x,c1.y,c1.z, + p1.x,p1.y,p1.z, + t2.x,t2.y, + t2.x,t2.y, + c2.x,c2.y,c2.z, + p2.x,p2.y,p2.z, + t3.x,t3.y, + t3.x,t3.y, + c3.x,c3.y,c3.z, + p3.x,p3.y,p3.z, + t4.x,t4.y, + t4.x,t4.y, + c4.x,c4.y,c4.z, + p4.x,p4.y,p4.z, + }; + + + private static final int[] indices = {0,1,3,0,3,2,1,2,3,0,2,1}; + private int[] stripVertexCounts = {3,3,3,3}; + + TextureUnitState textureUnitState[] = new TextureUnitState[2]; + Texture tex1; + Texture tex2; + + private java.net.URL texImage1 = null; + private java.net.URL texImage2 = null; + + private SimpleUniverse u; + + private J3DBuffer interleavedBuffer; + private J3DBuffer indexedInterleavedBuffer; + + void createInterleavedBuffers() { + int size; + ByteOrder order = ByteOrder.nativeOrder(); + + size = (2 + 2 + 3 + 3 ) * 3 * 4; + FloatBuffer vertex = ByteBuffer.allocateDirect(size * 4).order(order).asFloatBuffer(); + vertex.put(interleaved, 0, size); + interleavedBuffer = new J3DBuffer(vertex); + + size = ( 2 + 2 + 3 + 3) * 4; + FloatBuffer indexedVertex = ByteBuffer.allocateDirect(size * 4).order(order).asFloatBuffer(); + indexedVertex.put(indexedInterleaved, 0, size); + indexedInterleavedBuffer = new J3DBuffer(indexedVertex); + } + + BranchGroup createSceneGraph() { + BranchGroup objRoot = new BranchGroup(); + + // Set up attributes to render lines + app = new Appearance(); + app.setCapability(Appearance.ALLOW_TEXTURE_UNIT_STATE_WRITE); + + transp = new TransparencyAttributes(); + transp.setTransparency(0.5f); + transp.setCapability(TransparencyAttributes.ALLOW_MODE_WRITE); + transp.setTransparencyMode(TransparencyAttributes.NONE); + app.setTransparencyAttributes(transp); + + // load textures + TextureAttributes texAttr1 = new TextureAttributes(); + texAttr1.setTextureMode(TextureAttributes.DECAL); + TextureAttributes texAttr2 = new TextureAttributes(); + texAttr2.setTextureMode(TextureAttributes.MODULATE); + + TextureLoader tex = new TextureLoader(texImage1, new String("RGB"), this); + if (tex == null) + return null; + tex1 = tex.getTexture(); + + tex = new TextureLoader(texImage2, new String("RGB"), this); + if (tex == null) + return null; + tex2 = tex.getTexture(); + + textureUnitState[0] = new TextureUnitState(tex1, texAttr1, null); + textureUnitState[1] = new TextureUnitState(tex2, texAttr2, null); + + createInterleavedBuffers(); + + tetraRegular = createGeometry(1); + tetraStrip =createGeometry(2); + tetraIndexed = createGeometry(3); + tetraIndexedStrip = createGeometry(4); + + geoArrays[0] = tetraRegular; + geoArrays[1] = tetraStrip; + geoArrays[2] = tetraIndexed; + geoArrays[3] = tetraIndexedStrip; + + shape = new Shape3D(tetraRegular, app); + shape.setCapability(Shape3D.ALLOW_GEOMETRY_WRITE); + + Transform3D t = new Transform3D(); + // move the object upwards + t.set(new Vector3f(0.0f, 0.3f, 0.0f)); + + // rotate the shape + Transform3D temp = new Transform3D(); + temp.rotX(Math.PI/4.0d); + t.mul(temp); + temp.rotY(Math.PI/4.0d); + t.mul(temp); + + // Shrink the object + t.setScale(0.6); + + TransformGroup trans = new TransformGroup(t); + trans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + trans.setCapability(TransformGroup.ALLOW_TRANSFORM_READ); + + objRoot.addChild(trans); + trans.addChild(shape); + + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + + // Set up the global lights + Color3f lColor1 = new Color3f(0.7f, 0.7f, 0.7f); + Vector3f lDir1 = new Vector3f(-1.0f, -1.0f, -1.0f); + Color3f alColor = new Color3f(0.2f, 0.2f, 0.2f); + + AmbientLight aLgt = new AmbientLight(alColor); + aLgt.setInfluencingBounds(bounds); + DirectionalLight lgt1 = new DirectionalLight(lColor1, lDir1); + lgt1.setInfluencingBounds(bounds); + objRoot.addChild(aLgt); + objRoot.addChild(lgt1); + + // Let Java 3D perform optimizations on this scene graph. + objRoot.compile(); + + return objRoot; + } + + JPanel createGeometryByReferencePanel() { + JPanel panel = new JPanel(); + panel.setBorder(new TitledBorder("Geometry Type")); + + String values[] = {"Array", "Strip", "Indexed", "IndexedStrip"}; + geomType = new JComboBox(values); + geomType.setLightWeightPopupEnabled(false); + geomType.addActionListener(this); + geomType.setSelectedIndex(0); + panel.add(new JLabel("Geometry Type")); + panel.add(geomType); + + transparency = new JCheckBox("EnableTransparency", + false); + transparency.addActionListener(this); + panel.add(transparency); + + textureBox = new JCheckBox("EnableTexture", false); + textureBox.addActionListener(this); + panel.add(textureBox); + + return panel; + } + + public InterleavedNIOBuffer() { + } + + public InterleavedNIOBuffer(java.net.URL texURL1, java.net.URL texURL2) { + texImage1 = texURL1; + texImage2 = texURL2; + } + + public void init() {System.setProperty("sun.awt.noerasebackground", "true"); + + // create textures + texImage1 = Resources.getResource("resources/images/bg.jpg"); + if (texImage1 == null) { + System.err.println("resources/images/bg.jpg not found"); + System.exit(1); + } + + texImage2 = Resources.getResource("resources/images/one.jpg"); + if (texImage2 == null) { + System.err.println("resources/images/one.jpg not found"); + System.exit(1); + } + + Container contentPane = getContentPane(); + + Canvas3D c = new Canvas3D(SimpleUniverse.getPreferredConfiguration()); + contentPane.add("Center", c); + + BranchGroup scene = createSceneGraph(); + // SimpleUniverse is a Convenience Utility class + u = new SimpleUniverse(c); + + // add mouse behaviors to the viewingPlatform + ViewingPlatform viewingPlatform = u.getViewingPlatform(); + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + viewingPlatform.setNominalViewingTransform(); + + // add Orbit behavior to the viewing platform + OrbitBehavior orbit = new OrbitBehavior(c, OrbitBehavior.REVERSE_ALL); + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0, 0.0, 0.0), 100.0); + orbit.setSchedulingBounds(bounds); + viewingPlatform.setViewPlatformBehavior(orbit); + + u.addBranchGraph(scene); + + + // Create GUI + JPanel p = new JPanel(); + BoxLayout boxlayout = new BoxLayout(p, + BoxLayout.Y_AXIS); + p.add(createGeometryByReferencePanel()); + p.setLayout(boxlayout); + + contentPane.add("South", p); + } + + public void destroy() { + u.cleanup(); + } + + public void actionPerformed(ActionEvent e) { + Object target = e.getSource(); + if (target == geomType) { + shape.setGeometry(geoArrays[geomType.getSelectedIndex()]); + + } + else if (target == transparency) { + if (transparency.isSelected()) { + transp.setTransparencyMode(TransparencyAttributes.BLENDED); + } + else { + transp.setTransparencyMode(TransparencyAttributes.NONE); + } + } + else if (target == textureBox) { + if (textureBox.isSelected()) { + app.setTextureUnitState(textureUnitState); + } + else { + app.setTextureUnitState(null); + } + } + } + + + + public static void main(String[] args) {System.setProperty("sun.awt.noerasebackground", "true"); + java.net.URL texURL1 = null; + java.net.URL texURL2 = null; + // the path to the image for an application + texURL1 = Resources.getResource("resources/images/bg.jpg"); + if (texURL1 == null) { + System.err.println("resources/images/bg.jpg not found"); + System.exit(1); + } + + texURL2 = Resources.getResource("resources/images/one.jpg"); + if (texURL2 == null) { + System.err.println("resources/images/one.jpg not found"); + System.exit(1); + } + + Frame frame = new MainFrame(new InterleavedNIOBuffer(texURL1, texURL2), + 800, 800); + } + + public GeometryArray createGeometry (int type) { + GeometryArray tetra = null; + int texCoordSetMap[] = {0, 0}; + + if (type == 1) { + tetra =new TriangleArray(12, + TriangleArray.COORDINATES| + TriangleArray.COLOR_3| + /* + TriangleArray.NORMAL_3| + */ + TriangleArray.TEXTURE_COORDINATE_2 | + TriangleArray.INTERLEAVED| + TriangleArray.BY_REFERENCE| + TriangleArray.USE_NIO_BUFFER, + 2, texCoordSetMap); + + tetra.setInterleavedVertexBuffer(interleavedBuffer); + + } + else if (type == 2) { + tetra = new TriangleStripArray(12, + TriangleStripArray.COORDINATES| + TriangleStripArray.COLOR_3| + /* + TriangleArray.NORMAL_3| + */ + TriangleArray.TEXTURE_COORDINATE_2 | + TriangleStripArray.INTERLEAVED| + TriangleStripArray.BY_REFERENCE| + TriangleStripArray.USE_NIO_BUFFER, + 2, texCoordSetMap, + stripVertexCounts); + tetra.setInterleavedVertexBuffer(interleavedBuffer); + + + } + else if (type == 3) { // Indexed Geometry + tetra = new IndexedTriangleArray(4, + IndexedTriangleArray.COORDINATES| + IndexedTriangleArray.COLOR_3| + /* + IndexedTriangleArray.NORMAL_3| + */ + IndexedTriangleArray.TEXTURE_COORDINATE_2 | + IndexedTriangleArray.INTERLEAVED| + IndexedTriangleArray.BY_REFERENCE| + IndexedTriangleArray.USE_NIO_BUFFER| + IndexedTriangleArray.USE_COORD_INDEX_ONLY, + 2, texCoordSetMap, + 12); + tetra.setInterleavedVertexBuffer(indexedInterleavedBuffer); + ((IndexedTriangleArray)tetra).setCoordinateIndices(0, indices); + /* + // Do not set color or texcoord indices in UCIO mode + ((IndexedTriangleArray)tetra).setColorIndices(0, indices); + ((IndexedTriangleArray)tetra).setTextureCoordinateIndices( + 0, 0, indices); + ((IndexedTriangleArray)tetra).setTextureCoordinateIndices( + 1, 0, indices); + */ + } + else if (type == 4) { // Indexed strip geometry + tetra = new IndexedTriangleStripArray(4, + IndexedTriangleStripArray.COORDINATES| + IndexedTriangleStripArray.COLOR_3| + /* + IndexedTriangleArray.NORMAL_3| + */ + IndexedTriangleArray.TEXTURE_COORDINATE_2 | + IndexedTriangleStripArray.INTERLEAVED| + IndexedTriangleStripArray.BY_REFERENCE| + IndexedTriangleStripArray.USE_NIO_BUFFER, + //IndexedTriangleStripArray.USE_COORD_INDEX_ONLY, + 2, texCoordSetMap, + 12, + stripVertexCounts); + tetra.setInterleavedVertexBuffer(indexedInterleavedBuffer); + ((IndexedTriangleStripArray)tetra).setCoordinateIndices(0, indices); + ((IndexedTriangleStripArray)tetra).setColorIndices(0, indices); + ((IndexedTriangleStripArray)tetra).setTextureCoordinateIndices( + 0, 0, indices); + ((IndexedTriangleStripArray)tetra).setTextureCoordinateIndices( + 1, 0, indices); + } + else if (type == 5) { // Interleaved array + } + return tetra; + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/geometry_by_ref/InterleavedTest.java b/src/main/java/org/jdesktop/j3d/examples/geometry_by_ref/InterleavedTest.java new file mode 100644 index 0000000..0fd0217 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/geometry_by_ref/InterleavedTest.java @@ -0,0 +1,528 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.geometry_by_ref; + +import java.awt.Container; +import java.awt.Frame; +import java.awt.event.ActionEvent; +import java.awt.event.ActionListener; + +import javax.swing.BoxLayout; +import javax.swing.JApplet; +import javax.swing.JCheckBox; +import javax.swing.JComboBox; +import javax.swing.JLabel; +import javax.swing.JPanel; +import javax.swing.border.TitledBorder; + +import org.jdesktop.j3d.examples.Resources; +import org.jogamp.java3d.AmbientLight; +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.ColoringAttributes; +import org.jogamp.java3d.DirectionalLight; +import org.jogamp.java3d.GeometryArray; +import org.jogamp.java3d.IndexedTriangleArray; +import org.jogamp.java3d.IndexedTriangleStripArray; +import org.jogamp.java3d.Material; +import org.jogamp.java3d.RenderingAttributes; +import org.jogamp.java3d.Shape3D; +import org.jogamp.java3d.Texture; +import org.jogamp.java3d.TextureAttributes; +import org.jogamp.java3d.TextureUnitState; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.TransparencyAttributes; +import org.jogamp.java3d.TriangleArray; +import org.jogamp.java3d.TriangleStripArray; +import org.jogamp.java3d.utils.applet.MainFrame; +import org.jogamp.java3d.utils.behaviors.vp.OrbitBehavior; +import org.jogamp.java3d.utils.image.TextureLoader; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.java3d.utils.universe.ViewingPlatform; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point2f; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Point3f; +import org.jogamp.vecmath.Vector3f; + +public class InterleavedTest extends JApplet implements ActionListener { + + RenderingAttributes ra; + ColoringAttributes ca; + Material mat; + Appearance app; + JComboBox geomType; + JCheckBox transparency; + JCheckBox textureBox; + Shape3D shape; + TransparencyAttributes transp; + + GeometryArray tetraRegular, tetraStrip, tetraIndexed, tetraIndexedStrip; + GeometryArray[] geoArrays = new GeometryArray[4]; + + // Globally used colors + Color3f white = new Color3f(1.0f, 1.0f, 1.0f); + Color3f red = new Color3f(1.0f, 0.0f, 0.0f); + Color3f green = new Color3f(0.0f, 1.0f, 0.0f); + Color3f blue = new Color3f(0.0f, 0.0f, 1.0f); + Color3f[] colors = {white, red, green, blue}; + + private static final float sqrt3 = (float) Math.sqrt(3.0); + private static final float sqrt3_3 = sqrt3 / 3.0f; + private static final float sqrt24_3 = (float) Math.sqrt(24.0) / 3.0f; + + private static final float ycenter = 0.5f * sqrt24_3; + private static final float zcenter = -sqrt3_3; + + private static final Point3f p1 = + new Point3f(-1.0f, -ycenter, -zcenter); + private static final Point3f p2 = + new Point3f(1.0f, -ycenter, -zcenter); + private static final Point3f p3 = + new Point3f(0.0f, -ycenter, -sqrt3 - zcenter); + private static final Point3f p4 = + new Point3f(0.0f, sqrt24_3 - ycenter, 0.0f); + + private static final Point2f t1 = new Point2f(0.0f, 0.0f); + private static final Point2f t2 = new Point2f(0.5f, 1.0f); + private static final Point2f t3 = new Point2f(1.0f, 0.0f); + private static final Point2f t4 = new Point2f(1.0f, 1.0f); + + private static final Color3f c1 = new Color3f(1.0f, 0.0f, 0.0f); + private static final Color3f c2 = new Color3f(0.0f, 1.0f, 0.0f); + private static final Color3f c3 = new Color3f(0.0f, 1.0f, 1.0f); + private static final Color3f c4 = new Color3f(1.0f, 1.0f, 0.0f); + + + private static final float[] interleaved = { + t1.x, t1.y, + t1.x, t1.y, + c1.x, c1.y, c1.z, // front face + p1.x, p1.y, p1.z, // front face + t2.x, t2.y, + t2.x, t2.y, + c2.x, c2.y, c2.z, + p2.x, p2.y, p2.z, + t4.x, t4.y, + t4.x, t4.y, + c4.x, c4.y, c4.z, + p4.x, p4.y, p4.z, + + t1.x, t1.y, + t1.x, t1.y, + c1.x, c1.y, c1.z,// left, back face + p1.x, p1.y, p1.z,// left, back face + t4.x, t4.y, + t4.x, t4.y, + c4.x, c4.y, c4.z, + p4.x, p4.y, p4.z, + t3.x, t3.y, + t3.x, t3.y, + c3.x, c3.y, c3.z, + p3.x, p3.y, p3.z, + + t2.x, t2.y, + t2.x, t2.y, + c2.x, c2.y, c2.z,// right, back face + p2.x, p2.y, p2.z,// right, back face + t3.x, t3.y, + t3.x, t3.y, + c3.x, c3.y, c3.z, + p3.x, p3.y, p3.z, + t4.x, t4.y, + t4.x, t4.y, + c4.x, c4.y, c4.z, + p4.x, p4.y, p4.z, + + t1.x, t1.y, + t1.x, t1.y, + c1.x, c1.y, c1.z,// bottom face + p1.x, p1.y, p1.z,// bottom face + t3.x, t3.y, + t3.x, t3.y, + c3.x, c3.y, c3.z, + p3.x, p3.y, p3.z, + t2.x, t2.y, + t2.x, t2.y, + c2.x, c2.y, c2.z, + p2.x, p2.y, p2.z, + }; + + private static final float[] indexedInterleaved = { + t1.x,t1.y, + t1.x,t1.y, + c1.x,c1.y,c1.z, + p1.x,p1.y,p1.z, + t2.x,t2.y, + t2.x,t2.y, + c2.x,c2.y,c2.z, + p2.x,p2.y,p2.z, + t3.x,t3.y, + t3.x,t3.y, + c3.x,c3.y,c3.z, + p3.x,p3.y,p3.z, + t4.x,t4.y, + t4.x,t4.y, + c4.x,c4.y,c4.z, + p4.x,p4.y,p4.z, + }; + + + private static final int[] indices = {0,1,3,0,3,2,1,2,3,0,2,1}; + private int[] stripVertexCounts = {3,3,3,3}; + + TextureUnitState textureUnitState[] = new TextureUnitState[2]; + Texture tex1; + Texture tex2; + + private java.net.URL texImage1 = null; + private java.net.URL texImage2 = null; + + private SimpleUniverse u; + + BranchGroup createSceneGraph() { + BranchGroup objRoot = new BranchGroup(); + + // Set up attributes to render lines + app = new Appearance(); + app.setCapability(Appearance.ALLOW_TEXTURE_UNIT_STATE_WRITE); + + transp = new TransparencyAttributes(); + transp.setTransparency(0.5f); + transp.setCapability(TransparencyAttributes.ALLOW_MODE_WRITE); + transp.setTransparencyMode(TransparencyAttributes.NONE); + app.setTransparencyAttributes(transp); + + // load textures + TextureAttributes texAttr1 = new TextureAttributes(); + texAttr1.setTextureMode(TextureAttributes.DECAL); + TextureAttributes texAttr2 = new TextureAttributes(); + texAttr2.setTextureMode(TextureAttributes.MODULATE); + + TextureLoader tex = new TextureLoader(texImage1, new String("RGB"), this); + if (tex == null) + return null; + tex1 = tex.getTexture(); + + tex = new TextureLoader(texImage2, new String("RGB"), this); + if (tex == null) + return null; + tex2 = tex.getTexture(); + + textureUnitState[0] = new TextureUnitState(tex1, texAttr1, null); + textureUnitState[1] = new TextureUnitState(tex2, texAttr2, null); + + tetraRegular = createGeometry(1); + tetraStrip =createGeometry(2); + tetraIndexed = createGeometry(3); + tetraIndexedStrip = createGeometry(4); + + geoArrays[0] = tetraRegular; + geoArrays[1] = tetraStrip; + geoArrays[2] = tetraIndexed; + geoArrays[3] = tetraIndexedStrip; + + shape = new Shape3D(tetraRegular, app); + shape.setCapability(Shape3D.ALLOW_GEOMETRY_WRITE); + + Transform3D t = new Transform3D(); + // move the object upwards + t.set(new Vector3f(0.0f, 0.3f, 0.0f)); + + // rotate the shape + Transform3D temp = new Transform3D(); + temp.rotX(Math.PI/4.0d); + t.mul(temp); + temp.rotY(Math.PI/4.0d); + t.mul(temp); + + // Shrink the object + t.setScale(0.6); + + TransformGroup trans = new TransformGroup(t); + trans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + trans.setCapability(TransformGroup.ALLOW_TRANSFORM_READ); + + objRoot.addChild(trans); + trans.addChild(shape); + + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + + // Set up the global lights + Color3f lColor1 = new Color3f(0.7f, 0.7f, 0.7f); + Vector3f lDir1 = new Vector3f(-1.0f, -1.0f, -1.0f); + Color3f alColor = new Color3f(0.2f, 0.2f, 0.2f); + + AmbientLight aLgt = new AmbientLight(alColor); + aLgt.setInfluencingBounds(bounds); + DirectionalLight lgt1 = new DirectionalLight(lColor1, lDir1); + lgt1.setInfluencingBounds(bounds); + objRoot.addChild(aLgt); + objRoot.addChild(lgt1); + + // Let Java 3D perform optimizations on this scene graph. + objRoot.compile(); + + return objRoot; + } + + JPanel createGeometryByReferencePanel() { + JPanel panel = new JPanel(); + panel.setBorder(new TitledBorder("Geometry Type")); + + String values[] = {"Array", "Strip", "Indexed", "IndexedStrip"}; + geomType = new JComboBox(values); + geomType.setLightWeightPopupEnabled(false); + geomType.addActionListener(this); + geomType.setSelectedIndex(0); + panel.add(new JLabel("Geometry Type")); + panel.add(geomType); + + transparency = new JCheckBox("EnableTransparency", + false); + transparency.addActionListener(this); + panel.add(transparency); + + textureBox = new JCheckBox("EnableTexture", false); + textureBox.addActionListener(this); + panel.add(textureBox); + + return panel; + } + + public InterleavedTest() { + } + + public InterleavedTest(java.net.URL texURL1, java.net.URL texURL2) { + texImage1 = texURL1; + texImage2 = texURL2; + } + + public void init() {System.setProperty("sun.awt.noerasebackground", "true"); + + // create textures + texImage1 = Resources.getResource("resources/images/bg.jpg"); + if (texImage1 == null) { + System.err.println("resources/images/bg.jpg not found"); + System.exit(1); + } + + texImage2 = Resources.getResource("resources/images/one.jpg"); + if (texImage2 == null) { + System.err.println("resources/images/one.jpg not found"); + System.exit(1); + } + + Container contentPane = getContentPane(); + + Canvas3D c = new Canvas3D(SimpleUniverse.getPreferredConfiguration()); + contentPane.add("Center", c); + + BranchGroup scene = createSceneGraph(); + // SimpleUniverse is a Convenience Utility class + u = new SimpleUniverse(c); + + // add mouse behaviors to the viewingPlatform + ViewingPlatform viewingPlatform = u.getViewingPlatform(); + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + viewingPlatform.setNominalViewingTransform(); + + // add Orbit behavior to the viewing platform + OrbitBehavior orbit = new OrbitBehavior(c, OrbitBehavior.REVERSE_ALL); + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0, 0.0, 0.0), 100.0); + orbit.setSchedulingBounds(bounds); + viewingPlatform.setViewPlatformBehavior(orbit); + + u.addBranchGraph(scene); + + + // Create GUI + JPanel p = new JPanel(); + BoxLayout boxlayout = new BoxLayout(p, + BoxLayout.Y_AXIS); + p.add(createGeometryByReferencePanel()); + p.setLayout(boxlayout); + + contentPane.add("South", p); + } + + public void destroy() { + u.cleanup(); + } + + public void actionPerformed(ActionEvent e) { + Object target = e.getSource(); + if (target == geomType) { + shape.setGeometry(geoArrays[geomType.getSelectedIndex()]); + + } + else if (target == transparency) { + if (transparency.isSelected()) { + transp.setTransparencyMode(TransparencyAttributes.BLENDED); + } + else { + transp.setTransparencyMode(TransparencyAttributes.NONE); + } + } + else if (target == textureBox) { + if (textureBox.isSelected()) { + app.setTextureUnitState(textureUnitState); + } + else { + app.setTextureUnitState(null); + } + } + } + + + + public static void main(String[] args) {System.setProperty("sun.awt.noerasebackground", "true"); + java.net.URL texURL1 = null; + java.net.URL texURL2 = null; + // the path to the image for an application + texURL1 = Resources.getResource("resources/images/bg.jpg"); + if (texURL1 == null) { + System.err.println("resources/images/bg.jpg not found"); + System.exit(1); + } + + texURL2 = Resources.getResource("resources/images/one.jpg"); + if (texURL2 == null) { + System.err.println("resources/images/one.jpg not found"); + System.exit(1); + } + + Frame frame = new MainFrame(new InterleavedTest(texURL1, texURL2), + 800, 800); + } + + public GeometryArray createGeometry (int type) { + GeometryArray tetra = null; + int texCoordSetMap[] = {0, 0}; + + if (type == 1) { + tetra =new TriangleArray(12, + TriangleArray.COORDINATES| + TriangleArray.COLOR_3| + /* + TriangleArray.NORMAL_3| + */ + TriangleArray.TEXTURE_COORDINATE_2 | + TriangleArray.INTERLEAVED| + TriangleArray.BY_REFERENCE, + 2, texCoordSetMap); + + tetra.setInterleavedVertices(interleaved); + + } + else if (type == 2) { + tetra = new TriangleStripArray(12, + TriangleStripArray.COORDINATES| + TriangleStripArray.COLOR_3| + /* + TriangleArray.NORMAL_3| + */ + TriangleArray.TEXTURE_COORDINATE_2 | + TriangleStripArray.INTERLEAVED| + TriangleStripArray.BY_REFERENCE, + 2, texCoordSetMap, + stripVertexCounts); + tetra.setInterleavedVertices(interleaved); + + + } + else if (type == 3) { // Indexed Geometry + tetra = new IndexedTriangleArray(4, + IndexedTriangleArray.COORDINATES| + IndexedTriangleArray.COLOR_3| + /* + IndexedTriangleArray.NORMAL_3| + */ + IndexedTriangleArray.TEXTURE_COORDINATE_2 | + IndexedTriangleArray.INTERLEAVED| + IndexedTriangleArray.BY_REFERENCE, + 2, texCoordSetMap, + 12); + tetra.setInterleavedVertices(indexedInterleaved); + ((IndexedTriangleArray)tetra).setCoordinateIndices(0, indices); + ((IndexedTriangleArray)tetra).setColorIndices(0, indices); + ((IndexedTriangleArray)tetra).setTextureCoordinateIndices( + 0, 0, indices); + ((IndexedTriangleArray)tetra).setTextureCoordinateIndices( + 1, 0, indices); + } + else if (type == 4) { // Indexed strip geometry + tetra = new IndexedTriangleStripArray(4, + IndexedTriangleStripArray.COORDINATES| + IndexedTriangleStripArray.COLOR_3| + /* + IndexedTriangleArray.NORMAL_3| + */ + IndexedTriangleArray.TEXTURE_COORDINATE_2 | + IndexedTriangleStripArray.INTERLEAVED| + IndexedTriangleStripArray.BY_REFERENCE, + 2, texCoordSetMap, + 12, + stripVertexCounts); + tetra.setInterleavedVertices(indexedInterleaved); + ((IndexedTriangleStripArray)tetra).setCoordinateIndices(0, indices); + ((IndexedTriangleStripArray)tetra).setColorIndices(0, indices); + ((IndexedTriangleStripArray)tetra).setTextureCoordinateIndices( + 0, 0, indices); + ((IndexedTriangleStripArray)tetra).setTextureCoordinateIndices( + 1, 0, indices); + } + else if (type == 5) { // Interleaved array + } + return tetra; + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/geometry_by_ref/TiledImage.java b/src/main/java/org/jdesktop/j3d/examples/geometry_by_ref/TiledImage.java new file mode 100644 index 0000000..0e06f0e --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/geometry_by_ref/TiledImage.java @@ -0,0 +1,367 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.geometry_by_ref; + +import java.awt.Rectangle; +import java.awt.Transparency; +import java.awt.color.ColorSpace; +import java.awt.image.BufferedImage; +import java.awt.image.ColorModel; +import java.awt.image.ComponentColorModel; +import java.awt.image.DataBuffer; +import java.awt.image.DataBufferByte; +import java.awt.image.Raster; +import java.awt.image.RenderedImage; +import java.awt.image.SampleModel; +import java.awt.image.WritableRaster; +import java.util.Vector; + +public class TiledImage extends Object implements RenderedImage { + + + WritableRaster[][] tile = new WritableRaster[3][3]; + + WritableRaster bigTile; + ComponentColorModel colorModel; + BufferedImage checkBoard; + int minX = -2; + int minY = -1; + + TiledImage() { + ColorSpace cs = ColorSpace.getInstance(ColorSpace.CS_sRGB); + int[] nBits = {8, 8, 8, 8}; + int i, j, k, cc = 255; + int[] bandOffset = new int[4]; + colorModel = + new ComponentColorModel(cs, nBits, true, false, Transparency.OPAQUE, 0); + // Create 9 tiles + bandOffset[0] = 3; + bandOffset[1] = 2; + bandOffset[2] = 1; + bandOffset[3] = 0; + for (i = 0; i < 3; i++) { + for (j = 0; j < 3; j++) { + tile[i][j] = Raster.createInterleavedRaster(DataBuffer.TYPE_BYTE, 8, 8 , 32, 4, bandOffset, null); + } + } + + // tile {-2, -1} + byte[] byteData = ((DataBufferByte)tile[0][0].getDataBuffer()).getData(); + for (i=4, k = 8 * 4 * 4+4 * 4;i < 8;i++, k+= 16){ + for (j=4;j < 8;j++, k+=4){ + byteData[k] = (byte)0; + byteData[k+1] = (byte)cc; + byteData[k+2] = (byte)0; + byteData[k+3] = (byte)cc ; + } + } + + // tile {-1, -1} + byteData = ((DataBufferByte)tile[1][0].getDataBuffer()).getData(); + for (i=4, k = 8 * 4 * 4;i < 8;i++){ + for (j=4;j < 8;j++, k+=4){ + byteData[k] = (byte)0; + byteData[k+1] = (byte)cc; + byteData[k+2] = (byte)0; + byteData[k+3] = (byte)cc ; + } + for (j=4;j < 8;j++, k+=4){ + byteData[k] = (byte)0; + byteData[k+1] = (byte)0; + byteData[k+2] = (byte)0; + byteData[k+3] = (byte)cc ; + } + } + + // tile {1, -1} + byteData = ((DataBufferByte)tile[2][0].getDataBuffer()).getData(); + for (i=4, k = 8 * 4 * 4;i < 8;i++, k+= 16){ + for (j=0;j < 4;j++, k+=4){ + byteData[k] = (byte)0; + byteData[k+1] = (byte)0; + byteData[k+2] = (byte)0; + byteData[k+3] = (byte)cc ; + } + } + + // tile {-2, 0} + byteData = ((DataBufferByte)tile[0][1].getDataBuffer()).getData(); + for (i=0, k = 16;i < 4;i++, k+=16){ + for (j=4;j < 8;j++, k+=4){ + byteData[k] = (byte)0; + byteData[k+1] = (byte)cc; + byteData[k+2] = (byte)0; + byteData[k+3] = (byte)cc ; + } + } + for (i=4, k = 8*4*4+16;i < 8;i++, k+=16){ + for (j=4;j < 8;j++, k+=4){ + byteData[k] = (byte)0; + byteData[k+1] = (byte)0; + byteData[k+2] = (byte)cc; + byteData[k+3] = (byte)0 ; + } + } + // tile {-1, 0} + byteData = ((DataBufferByte)tile[1][1].getDataBuffer()).getData(); + for (i=0, k = 0;i < 4;i++){ + for (j=4;j < 8;j++, k+=4){ + byteData[k] = (byte)0; + byteData[k+1] = (byte)cc; + byteData[k+2] = (byte)0; + byteData[k+3] = (byte)cc ; + } + for (j=4;j < 8;j++, k+=4){ + byteData[k] = (byte)0; + byteData[k+1] = (byte)0; + byteData[k+2] = (byte)0; + byteData[k+3] = (byte)cc ; + } + } + for (i=0, k = 8 * 4 * 4;i < 4;i++){ + for (j=4;j < 8;j++, k+=4){ + byteData[k] = (byte)0; + byteData[k+1] = (byte)0; + byteData[k+2] = (byte)cc; + byteData[k+3] = (byte)0 ; + } + + for (j=4;j < 8;j++, k+=4){ + byteData[k] = (byte)0; + byteData[k+1] = (byte)0; + byteData[k+2] = (byte)cc; + byteData[k+3] = (byte)cc ; + } + + } + + + // tile {0, 0} + byteData = ((DataBufferByte)tile[2][1].getDataBuffer()).getData(); + for (i=0, k = 0;i < 4;i++, k+= 16) { + for (j=4;j < 8;j++, k+=4){ + byteData[k] = (byte)0; + byteData[k+1] = (byte)0; + byteData[k+2] = (byte)0; + byteData[k+3] = (byte)cc ; + } + } + for (i=4, k = 8 * 4* 4;i < 8;i++, k+= 16) { + for (j=4;j < 8;j++, k+=4){ + byteData[k] = (byte)0; + byteData[k+1] = (byte)0; + byteData[k+2] = (byte)cc; + byteData[k+3] = (byte)cc ; + } + } + + + // tile {-2, 1} + byteData = ((DataBufferByte)tile[0][2].getDataBuffer()).getData(); + for (i=4, k = 16;i < 8;i++, k+= 16) { + for (j=4;j < 8;j++, k+=4){ + byteData[k] = (byte)0; + byteData[k+1] = (byte)0; + byteData[k+2] = (byte)cc; + byteData[k+3] = (byte)0 ; + } + } + + + // tile {-1, 1} + byteData = ((DataBufferByte)tile[1][2].getDataBuffer()).getData(); + for (i=0, k = 0;i < 8;i++) { + for (j=4;j < 8;j++, k+=4){ + byteData[k] = (byte)0; + byteData[k+1] = (byte)0; + byteData[k+2] = (byte)cc; + byteData[k+3] = (byte)0 ; + } + for (j=4;j < 8;j++, k+=4){ + byteData[k] = (byte)0; + byteData[k+1] = (byte)0; + byteData[k+2] = (byte)cc; + byteData[k+3] = (byte)cc ; + } + } + + + + // tile {0, 1} + byteData = ((DataBufferByte)tile[2][2].getDataBuffer()).getData(); + for (i=4, k = 0;i < 8;i++, k+= 16) { + for (j=4;j < 8;j++, k+=4){ + byteData[k] = (byte)0; + byteData[k+1] = (byte)0; + byteData[k+2] = (byte)cc; + byteData[k+3] = (byte)cc ; + } + } + + bigTile = Raster.createInterleavedRaster(DataBuffer.TYPE_BYTE, 16, 16 , 64, 4, bandOffset, null);; + byteData = ((DataBufferByte)bigTile.getDataBuffer()).getData(); + for (i=0, k = 0;i < 8;i++){ + for (j=0;j < 8;j++, k+=4){ + byteData[k] = (byte)0; + byteData[k+1] = (byte)cc; + byteData[k+2] = (byte)0; + byteData[k+3] = (byte)cc ; + } + for (;j < 16;j++, k+=4){ + byteData[k] = (byte)0; + byteData[k+1] = (byte)0; + byteData[k+2] = (byte)0; + byteData[k+3] = (byte)cc ; + } + } + for (;i < 16;i++){ + for (j=0;j < 8;j++, k+=4){ + byteData[k] = (byte)0; + byteData[k+1] = (byte)0; + byteData[k+2] = (byte)cc; + byteData[k+3] = (byte)0; + } + for (;j < 16;j++, k+=4){ + byteData[k] = (byte)0; + byteData[k+1] = (byte)0; + byteData[k+2] = (byte)cc; + byteData[k+3] = (byte)cc ; + } + } + checkBoard = new BufferedImage(colorModel, bigTile, false, null); + } + + + + // create four tiles {r, g, b, y} + public WritableRaster copyData(WritableRaster raster) { + return checkBoard.copyData(raster); + } + + public ColorModel getColorModel() { + return checkBoard.getColorModel(); + } + + public Raster getData() { + return checkBoard.getData(); + } + + public Raster getData(Rectangle rect) { + return checkBoard.getData(rect); + } + + public int getHeight() { + return 16; + } + + public int getMinTileX() { + return minX; + } + + public int getMinTileY() { + return minY; + } + + public int getMinX () { + return -8; + } + + public int getMinY () { + return -8; + } + + public int getNumXTiles() { + return 3; + } + + public int getNumYTiles() { + return 3; + } + + public Object getProperty(String name) { + return checkBoard.getProperty(name); + } + + public String[] getPropertyNames() { + return checkBoard.getPropertyNames(); + } + + + public SampleModel getSampleModel() { + return checkBoard.getSampleModel(); + } + + public Vector getSources() { + return null; + } + + public Raster getTile(int tileX, int tileY) { + return tile[tileX- minX][tileY - minY]; + } + + public int getTileGridXOffset() { + return 4; + } + + public int getTileGridYOffset() { + return -4; + } + + + public int getTileHeight() { + return 8; + } + + + public int getTileWidth() { + return 8; + } + + public int getWidth() { + return 16; + } +} + + diff --git a/src/main/java/org/jdesktop/j3d/examples/geometry_compression/ObjectFileCompressor.java b/src/main/java/org/jdesktop/j3d/examples/geometry_compression/ObjectFileCompressor.java new file mode 100644 index 0000000..15db111 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/geometry_compression/ObjectFileCompressor.java @@ -0,0 +1,255 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.geometry_compression; + +import java.io.FileNotFoundException; +import java.io.IOException; +import java.io.Reader; +import java.net.URL; +import java.util.Hashtable; + +import org.jogamp.java3d.Shape3D; +import org.jogamp.java3d.loaders.IncorrectFormatException; +import org.jogamp.java3d.loaders.ParsingErrorException; +import org.jogamp.java3d.loaders.Scene; +import org.jogamp.java3d.loaders.objectfile.ObjectFile; +import org.jogamp.java3d.utils.geometry.compression.CompressedGeometryData; +import org.jogamp.java3d.utils.geometry.compression.CompressedGeometryFile; +import org.jogamp.java3d.utils.geometry.compression.CompressionStream; +import org.jogamp.java3d.utils.geometry.compression.GeometryCompressor; + +/** + * This extension of ObjectFile provides the methods setQuantization() and + * compress() to compress Wavefront .obj files into the format described by + * appendix B of the Java 3D specification. + */ +public class ObjectFileCompressor extends ObjectFile { + private GeometryCompressor compressor = null ; + + public ObjectFileCompressor() { + super(STRIPIFY | TRIANGULATE) ; + compressor = new GeometryCompressor() ; + } + + public ObjectFileCompressor(int flags) { + super(flags | STRIPIFY | TRIANGULATE) ; + compressor = new GeometryCompressor() ; + } + + public ObjectFileCompressor(int flags, float radians) { + super(flags | STRIPIFY | TRIANGULATE, radians) ; + compressor = new GeometryCompressor() ; + } + + public void setFlags(int flags) { + super.setFlags(flags | STRIPIFY | TRIANGULATE) ; + } + + private int positionQuant = 10 ; + private int colorQuant = 8 ; + private int normalQuant = 3 ; + + /** + * Set the position, normal, and color quantization values for compression. + * @param positionQuant number of bits to quantize each position's X, Y, + * and Z components, ranging from 1 to 16 with a default of 10 + * @param colorQuant number of bits to quantize each color's R, G, B, and + * alpha components, ranging from 2 to 16 with a default of 8 + * @param normalQuant number of bits for quantizing each normal's U and V + * components, ranging from 0 to 6 with a default of 3 + */ + public void setQuantization(int positionQuant, + int colorQuant, + int normalQuant) { + + this.positionQuant = positionQuant ; + this.colorQuant = colorQuant ; + this.normalQuant = normalQuant ; + } + + /** + * Compress the specified .obj file into a CompressedGeometryData node + * component. + * @param objFileName String object representing the path to a .obj file + * @return a CompressedGeometryData node component + */ + public CompressedGeometryData compress(String objFileName) { + return compressScene(getScene(objFileName)) ; + } + + /** + * Compress the specified .obj file and add it to the end of an open + * compressed geometry file. + * @param objFileName String object representing the path to a .obj file + * @param file a currently open CompressedGeometryFile object + * @exception IOException - if write fails + */ + public void compress(String objFileName, CompressedGeometryFile file) + throws IOException { + compressScene(getScene(objFileName), file) ; + } + + /** + * Compress the specified .obj file into a CompressedGeometryData node + * component. + * @param reader an open .obj file + * @return a CompressedGeometryData node component + */ + public CompressedGeometryData compress(Reader reader) { + return compressScene(getScene(reader)) ; + } + + /** + * Compress the specified .obj file and add it to the end of an open + * compressed geometry file. + * @param reader an open .obj file + * @param file an open CompressedGeometryFile object + * @exception IOException - if write fails + */ + public void compress(Reader reader, CompressedGeometryFile file) + throws IOException { + compressScene(getScene(reader), file) ; + } + + /** + * Compress the specified .obj file into a CompressedGeometryData node + * component. + * @param url Uniform Resource Locator for the .obj file + * @return a CompressedGeometryData node component + */ + public CompressedGeometryData compress(URL url) { + return compressScene(getScene(url)) ; + } + + /** + * Compress the specified .obj file and add it to the end of an open + * compressed geometry file. + * @param url Uniform Resource Locator for the .obj file + * @param file a currently open CompressedGeometryFile object + * @exception IOException - if write fails + */ + public void compress(URL url, CompressedGeometryFile file) + throws IOException { + compressScene(getScene(url), file) ; + } + + private CompressedGeometryData compressScene(Scene scene) { + return compressor.compress(getStream(scene)) ; + } + + private void compressScene(Scene scene, CompressedGeometryFile file) + throws IOException { + compressor.compress(getStream(scene), file) ; + } + + private CompressionStream getStream(Scene scene) { + Hashtable objs = scene.getNamedObjects() ; + Shape3D shapes[] = new Shape3D[objs.size()] ; + + objs.values().toArray(shapes) ; + return new CompressionStream(positionQuant, colorQuant, normalQuant, + shapes) ; + } + + private Scene getScene(String objFileName) { + Scene scene = null ; + try { + scene = load(objFileName) ; + } + catch (FileNotFoundException e) { + System.err.println(e) ; + System.exit(1) ; + } + catch (ParsingErrorException e) { + System.err.println(e) ; + System.exit(1) ; + } + catch (IncorrectFormatException e) { + System.err.println(e) ; + System.exit(1) ; + } + return scene ; + } + + private Scene getScene(Reader reader) { + Scene scene = null ; + try { + scene = load(reader) ; + } + catch (FileNotFoundException e) { + System.err.println(e) ; + System.exit(1) ; + } + catch (ParsingErrorException e) { + System.err.println(e) ; + System.exit(1) ; + } + catch (IncorrectFormatException e) { + System.err.println(e) ; + System.exit(1) ; + } + return scene ; + } + + private Scene getScene(URL url) { + Scene scene = null ; + try { + scene = load(url) ; + } + catch (FileNotFoundException e) { + System.err.println(e) ; + System.exit(1) ; + } + catch (ParsingErrorException e) { + System.err.println(e) ; + System.exit(1) ; + } + catch (IncorrectFormatException e) { + System.err.println(e) ; + System.exit(1) ; + } + return scene ; + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/geometry_compression/README.txt b/src/main/java/org/jdesktop/j3d/examples/geometry_compression/README.txt new file mode 100644 index 0000000..345766b --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/geometry_compression/README.txt @@ -0,0 +1,23 @@ +This directory contains example code for using compressed geometry in +Java 3D through the com.sun.j3d.utils.geometry.compression package. + +Applications: + + obj2cg -- takes the names of .obj files to compress followed by the name + of a .cg compressed geometry resource file. If the .cg file + doesn't exist, then an attempt is made to create it; otherwise, + new compressed geometry objects are appended to the end. + + The .obj files are compressed and stored into the .cg file in + the order in which they appear in the command line, and can be + accessed through indices [0 .. fileCount-1] + + cgview -- takes the name of a .cg file and the index of the object to + display, which can range from [0 .. objectCount-1]. The object + may rotated, scaled, and translated in response to mouse drags. + + +Utility classes: + + ObjectFileCompressor.java -- + Extends ObjectFile with compression methods. diff --git a/src/main/java/org/jdesktop/j3d/examples/geometry_compression/cgview.java b/src/main/java/org/jdesktop/j3d/examples/geometry_compression/cgview.java new file mode 100644 index 0000000..e3eae64 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/geometry_compression/cgview.java @@ -0,0 +1,214 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.geometry_compression; + +import java.applet.Applet; +import java.awt.BorderLayout; +import java.io.IOException; + +import org.jogamp.java3d.AmbientLight; +import org.jogamp.java3d.Background; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.DirectionalLight; +import org.jogamp.java3d.Shape3D; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.utils.applet.MainFrame; +import org.jogamp.java3d.utils.behaviors.vp.OrbitBehavior; +import org.jogamp.java3d.utils.geometry.compression.CompressedGeometryData; +import org.jogamp.java3d.utils.geometry.compression.CompressedGeometryFile; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.java3d.utils.universe.ViewingPlatform; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Vector3f; + +public class cgview extends Applet { + + private SimpleUniverse u = null; + + public BranchGroup createSceneGraph(CompressedGeometryData cg) { + // Create the root of the branch graph + BranchGroup objRoot = new BranchGroup() ; + + // Create a Transformgroup to scale all objects so they + // appear in the scene. + TransformGroup objScale = new TransformGroup() ; + Transform3D t3d = new Transform3D() ; + t3d.setScale(0.7) ; + objScale.setTransform(t3d) ; + objRoot.addChild(objScale) ; + + // Create the transform group node and initialize it to the + // identity. Enable the TRANSFORM_WRITE capability so that + // our behavior code can modify it at runtime. Add it to the + // root of the subgraph. + TransformGroup objTrans = new TransformGroup() ; + objTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE) ; + objTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_READ) ; + objScale.addChild(objTrans) ; + + // Add compressed geometry to the scene graph. + CompressedGeometryData.Header hdr = new CompressedGeometryData.Header() ; + cg.getCompressedGeometryHeader(hdr) ; + + Shape3D[] shapes = cg.decompress(); + if (shapes != null) { + for (int i = 0; i < shapes.length; i++) { + objTrans.addChild(shapes[i]); + } + } + + // Create mouse behavior scheduling bounds. + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0) ; + + // Set up the background + Color3f bgColor = new Color3f(0.05f, 0.05f, 0.5f); + Background bgNode = new Background(bgColor) ; + bgNode.setApplicationBounds(bounds) ; + objRoot.addChild(bgNode) ; + + // Set up the ambient light + Color3f ambientColor = new Color3f(0.1f, 0.1f, 0.1f) ; + AmbientLight ambientLightNode = new AmbientLight(ambientColor) ; + ambientLightNode.setInfluencingBounds(bounds) ; + objRoot.addChild(ambientLightNode) ; + + // Set up the directional lights + Color3f light1Color = new Color3f(1.0f, 1.0f, 0.9f) ; + Vector3f light1Direction = new Vector3f(1.0f, 1.0f, 1.0f) ; + Color3f light2Color = new Color3f(1.0f, 1.0f, 0.9f) ; + Vector3f light2Direction = new Vector3f(-1.0f, -1.0f, -0.9f) ; + + DirectionalLight light1 + = new DirectionalLight(light1Color, light1Direction) ; + light1.setInfluencingBounds(bounds) ; + objRoot.addChild(light1) ; + + DirectionalLight light2 + = new DirectionalLight(light2Color, light2Direction) ; + light2.setInfluencingBounds(bounds) ; + objRoot.addChild(light2) ; + + return objRoot ; + } + + private void usage() { + System.out.println("Usage: cgview <.cg file> <object index>") ; + System.exit(0) ; + } + + public cgview(String args[]) { + if (args.length < 1) + usage() ; + + int index ; + if (args.length < 2) + index = 0 ; + else + index = Integer.parseInt(args[1]) ; + + String filename = args[0] ; + if (filename == null) + usage() ; + + // Read the compressed geometry. + CompressedGeometryData cg = null ; + try { + CompressedGeometryFile cgf ; + cgf = new CompressedGeometryFile(filename, false) ; + + if (cgf.getObjectCount() == 0) { + System.out.println("no objects were found in " + filename) ; + System.exit(0) ; + } + + cg = cgf.read(index) ; + cgf.close() ; + + } catch (IOException e) { + System.out.println(e) ; + System.exit(0) ; + } + + setLayout(new BorderLayout()) ; + Canvas3D c = new Canvas3D(SimpleUniverse.getPreferredConfiguration()); + add("Center", c) ; + + // Create a simple scene and attach it to the virtual universe + BranchGroup scene = createSceneGraph(cg) ; + u = new SimpleUniverse(c) ; + + // add mouse behaviors to the ViewingPlatform + ViewingPlatform viewingPlatform = u.getViewingPlatform(); + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + viewingPlatform.setNominalViewingTransform(); + + OrbitBehavior orbit = new OrbitBehavior(c, OrbitBehavior.REVERSE_ALL); + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0, 0.0, 0.0), 100.0); + orbit.setSchedulingBounds(bounds); + viewingPlatform.setViewPlatformBehavior(orbit); + + u.addBranchGraph(scene) ; + } + + public void destroy() { + u.cleanup(); + } + + // + // The following allows cgview to be run as an application + // as well as an applet. + // + public static void main(String[] args) {System.setProperty("sun.awt.noerasebackground", "true"); + new MainFrame(new cgview(args), 700, 700) ; + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/geometry_compression/obj2cg.java b/src/main/java/org/jdesktop/j3d/examples/geometry_compression/obj2cg.java new file mode 100644 index 0000000..c0fea26 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/geometry_compression/obj2cg.java @@ -0,0 +1,73 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.geometry_compression; + +import java.io.IOException; + +import org.jogamp.java3d.utils.geometry.compression.CompressedGeometryFile; + +class obj2cg { + + public static void main(String args[]) throws IOException { + if (args.length < 2) { + System.out.println + ("obj2cg wants the names of .obj files to compress,\n" + + "followed by the name of a .cg file to create or to\n" + + "which to append.") ; + System.exit(0) ; + } + + CompressedGeometryFile file ; + file = new CompressedGeometryFile(args[args.length-1], true) ; + + ObjectFileCompressor compressor ; + compressor = new ObjectFileCompressor() ; + + for (int i = 0 ; i < args.length-1 ; i++) + compressor.compress(args[i], file) ; + + file.close() ; + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/Cube.java b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/Cube.java new file mode 100644 index 0000000..86f02ea --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/Cube.java @@ -0,0 +1,311 @@ +/*
+ * Copyright (c) 2016 JogAmp Community. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation. Sun designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Sun in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ */
+package org.jdesktop.j3d.examples.gl2es2pipeline;
+
+import java.nio.ByteBuffer;
+import java.nio.ByteOrder;
+import java.nio.FloatBuffer;
+
+import org.jogamp.java3d.GeometryArray;
+import org.jogamp.java3d.J3DBuffer;
+import org.jogamp.java3d.Shape3D;
+import org.jogamp.java3d.TriangleArray;
+
+/**
+ * @author Administrator
+ *
+ */
+public class Cube extends Shape3D
+{
+
+ private static final float[] verts = {
+ // front face
+ 1.0f, -1.0f, 1.0f, //1
+ 1.0f, 1.0f, 1.0f, //2
+ -1.0f, 1.0f, 1.0f, //3
+ 1.0f, -1.0f, 1.0f, //1
+ -1.0f, 1.0f, 1.0f, //3
+ -1.0f, -1.0f, 1.0f, //4
+ // back face
+ -1.0f, -1.0f, -1.0f, //1
+ -1.0f, 1.0f, -1.0f, //2
+ 1.0f, 1.0f, -1.0f, //3
+ -1.0f, -1.0f, -1.0f, //1
+ 1.0f, 1.0f, -1.0f, //3
+ 1.0f, -1.0f, -1.0f, //4
+ // right face
+ 1.0f, -1.0f, -1.0f, //1
+ 1.0f, 1.0f, -1.0f, //2
+ 1.0f, 1.0f, 1.0f, //3
+ 1.0f, -1.0f, -1.0f, //1
+ 1.0f, 1.0f, 1.0f, //3
+ 1.0f, -1.0f, 1.0f, //4
+ // left face
+ -1.0f, -1.0f, 1.0f, //1
+ -1.0f, 1.0f, 1.0f, //2
+ -1.0f, 1.0f, -1.0f, //3
+ -1.0f, -1.0f, 1.0f, //1
+ -1.0f, 1.0f, -1.0f, //3
+ -1.0f, -1.0f, -1.0f, //4
+ // top face
+ 1.0f, 1.0f, 1.0f, //1
+ 1.0f, 1.0f, -1.0f, //2
+ -1.0f, 1.0f, -1.0f, //3
+ 1.0f, 1.0f, 1.0f, //1
+ -1.0f, 1.0f, -1.0f, //3
+ -1.0f, 1.0f, 1.0f, //4
+ // bottom face
+ -1.0f, -1.0f, 1.0f, //1
+ -1.0f, -1.0f, -1.0f, //2
+ 1.0f, -1.0f, -1.0f, //3
+ -1.0f, -1.0f, 1.0f, //1
+ 1.0f, -1.0f, -1.0f, //3
+ 1.0f, -1.0f, 1.0f, };//4
+
+ private static final float[] colors = {
+ // front face (red)
+ 1.0f, 0.0f, 0.0f, //1
+ 1.0f, 0.0f, 0.0f, //2
+ 1.0f, 0.0f, 0.0f, //3
+ 1.0f, 0.0f, 0.0f, //1
+ 1.0f, 0.0f, 0.0f, //3
+ 1.0f, 0.0f, 0.0f, //4
+ // back face (green)
+ 0.0f, 1.0f, 0.0f, //1
+ 0.0f, 1.0f, 0.0f, //2
+ 0.0f, 1.0f, 0.0f, //3
+ 0.0f, 1.0f, 0.0f, //1
+ 0.0f, 1.0f, 0.0f, //3
+ 0.0f, 1.0f, 0.0f, //4
+ // right face (blue)
+ 0.0f, 0.0f, 1.0f, //1
+ 0.0f, 0.0f, 1.0f, //2
+ 0.0f, 0.0f, 1.0f, //3
+ 0.0f, 0.0f, 1.0f, //1
+ 0.0f, 0.0f, 1.0f, //3
+ 0.0f, 0.0f, 1.0f, //4
+ // left face (yellow)
+ 1.0f, 1.0f, 0.0f, //1
+ 1.0f, 1.0f, 0.0f, //2
+ 1.0f, 1.0f, 0.0f, //3
+ 1.0f, 1.0f, 0.0f, //1
+ 1.0f, 1.0f, 0.0f, //3
+ 1.0f, 1.0f, 0.0f, //4
+ // top face (magenta)
+ 1.0f, 0.0f, 1.0f, //1
+ 1.0f, 0.0f, 1.0f, //2
+ 1.0f, 0.0f, 1.0f, //3
+ 1.0f, 0.0f, 1.0f, //1
+ 1.0f, 0.0f, 1.0f, //3
+ 1.0f, 0.0f, 1.0f, //4
+ // bottom face (cyan)
+ 0.0f, 1.0f, 1.0f, //1
+ 0.0f, 1.0f, 1.0f, //2
+ 0.0f, 1.0f, 1.0f, //3
+ 0.0f, 1.0f, 1.0f, //1
+ 0.0f, 1.0f, 1.0f, //3
+ 0.0f, 1.0f, 1.0f, };//4
+
+ /**
+ * Constructs a color cube with unit scale. The corners of the
+ * color cube are [-1,-1,-1] and [1,1,1].
+ */
+ public Cube()
+ {
+ TriangleArray cube = new TriangleArray(36,
+ GeometryArray.COORDINATES | GeometryArray.COLOR_3 | GeometryArray.USE_NIO_BUFFER | GeometryArray.BY_REFERENCE);
+
+ cube.setCoordRefBuffer(new J3DBuffer(makeFloatBuffer(verts)));
+ cube.setColorRefBuffer(new J3DBuffer(makeFloatBuffer(colors)));
+
+ this.setGeometry(cube);
+ this.setAppearance(new SimpleShaderAppearance());
+ }
+
+ /**
+ * Constructs a color cube with the specified scale. The corners of the
+ * color cube are [-scale,-scale,-scale] and [scale,scale,scale].
+ * @param scale the scale of the cube
+ */
+ public Cube(double scale)
+ {
+ TriangleArray cube = new TriangleArray(36,
+ GeometryArray.COORDINATES | GeometryArray.COLOR_3 | GeometryArray.USE_NIO_BUFFER | GeometryArray.BY_REFERENCE);
+
+ float scaledVerts[] = new float[verts.length];
+ for (int i = 0; i < verts.length; i++)
+ scaledVerts[i] = verts[i] * (float) scale;
+
+ cube.setCoordRefBuffer(new J3DBuffer(makeFloatBuffer(scaledVerts)));
+ cube.setColorRefBuffer(new J3DBuffer(makeFloatBuffer(colors)));
+
+ this.setGeometry(cube);
+
+ this.setAppearance(new SimpleShaderAppearance());
+ }
+
+ public Cube(double scale, float r, float g, float b)
+ {
+ TriangleArray cube = new TriangleArray(36,
+ GeometryArray.COORDINATES | GeometryArray.COLOR_3 | GeometryArray.USE_NIO_BUFFER | GeometryArray.BY_REFERENCE);
+
+ float scaledVerts[] = new float[verts.length];
+ for (int i = 0; i < verts.length; i++)
+ scaledVerts[i] = verts[i] * (float) scale;
+
+ cube.setCoordRefBuffer(new J3DBuffer(makeFloatBuffer(scaledVerts)));
+
+ float colorsSet[] = new float[36 * 3];
+ for (int i = 0; i < 36; i++)
+ {
+ colorsSet[i * 3 + 0] = r;
+ colorsSet[i * 3 + 1] = g;
+ colorsSet[i * 3 + 2] = b;
+ }
+
+ cube.setColorRefBuffer(new J3DBuffer(makeFloatBuffer(colorsSet)));
+
+ this.setGeometry(cube);
+ this.setAppearance(new SimpleShaderAppearance());
+ }
+
+ /**
+ * Constructs a color cube with the specified scale. The corners of the
+ * color cube are [-scale,-scale,-scale] and [scale,scale,scale].
+ * @param scale the scale of the cube
+ */
+ public Cube(double xScale, double yScale, double zScale)
+ {
+ TriangleArray cube = new TriangleArray(36,
+ GeometryArray.COORDINATES | GeometryArray.COLOR_3 | GeometryArray.USE_NIO_BUFFER | GeometryArray.BY_REFERENCE);
+
+ float scaledVerts[] = new float[verts.length];
+ for (int i = 0; i < verts.length; i += 3)
+ {
+ scaledVerts[i + 0] = verts[i + 0] * (float) xScale;
+ scaledVerts[i + 1] = verts[i + 1] * (float) yScale;
+ scaledVerts[i + 2] = verts[i + 2] * (float) zScale;
+ }
+
+ cube.setCoordRefBuffer(new J3DBuffer(makeFloatBuffer(scaledVerts)));
+ cube.setColorRefBuffer(new J3DBuffer(makeFloatBuffer(colors)));
+
+ this.setGeometry(cube);
+ this.setAppearance(new SimpleShaderAppearance());
+ }
+
+ public Cube(double xScale, double yScale, double zScale, float r, float g, float b)
+ {
+ TriangleArray cube = new TriangleArray(36,
+ GeometryArray.COORDINATES | GeometryArray.COLOR_3 | GeometryArray.USE_NIO_BUFFER | GeometryArray.BY_REFERENCE);
+
+ float scaledVerts[] = new float[verts.length];
+ for (int i = 0; i < verts.length; i += 3)
+ {
+ scaledVerts[i + 0] = verts[i + 0] * (float) xScale;
+ scaledVerts[i + 1] = verts[i + 1] * (float) yScale;
+ scaledVerts[i + 2] = verts[i + 2] * (float) zScale;
+ }
+
+ cube.setCoordRefBuffer(new J3DBuffer(makeFloatBuffer(scaledVerts)));
+
+ float colorsSet[] = new float[36 * 3];
+ for (int i = 0; i < 36; i++)
+ {
+ colorsSet[i * 3 + 0] = r;
+ colorsSet[i * 3 + 1] = g;
+ colorsSet[i * 3 + 2] = b;
+ }
+
+ cube.setColorRefBuffer(new J3DBuffer(makeFloatBuffer(colorsSet)));
+
+ this.setGeometry(cube);
+ this.setAppearance(new SimpleShaderAppearance());
+ }
+
+ public Cube(float xMin, float yMin, float zMin, float xMax, float yMax, float zMax)
+ {
+ TriangleArray cube = new TriangleArray(36,
+ GeometryArray.COORDINATES | GeometryArray.COLOR_3 | GeometryArray.USE_NIO_BUFFER | GeometryArray.BY_REFERENCE);
+
+ float scaledVerts[] = new float[] {
+ // front face
+ xMax, yMin, zMax, //1
+ xMax, yMax, zMax, //2
+ xMin, yMax, zMax, //3
+ xMax, yMin, zMax, //1
+ xMin, yMax, zMax, //3
+ xMin, yMin, zMax, //4
+ // back face
+ xMin, yMin, zMin, //1
+ xMin, yMax, zMin, //2
+ xMax, yMax, zMin, //3
+ xMin, yMin, zMin, //1
+ xMax, yMax, zMin, //3
+ xMax, yMin, zMin, //4
+ // right face
+ xMax, yMin, zMin, //1
+ xMax, yMax, zMin, //2
+ xMax, yMax, zMax, //3
+ xMax, yMin, zMin, //1
+ xMax, yMax, zMax, //3
+ xMax, yMin, zMax, //4
+ // left face
+ xMin, yMin, zMax, //1
+ xMin, yMax, zMax, //2
+ xMin, yMax, zMin, //3
+ xMin, yMin, zMax, //1
+ xMin, yMax, zMin, //3
+ xMin, yMin, zMin, //4
+ // top face
+ xMax, yMax, zMax, //1
+ xMax, yMax, zMin, //2
+ xMin, yMax, zMin, //3
+ xMax, yMax, zMax, //1
+ xMin, yMax, zMin, //3
+ xMin, yMax, zMax, //4
+ // bottom face
+ xMin, yMin, zMax, //1
+ xMin, yMin, zMin, //2
+ xMax, yMin, zMin, //3
+ xMin, yMin, zMax, //1
+ xMax, yMin, zMin, //3
+ xMax, yMin, zMax, };//4
+
+ cube.setCoordRefBuffer(new J3DBuffer(makeFloatBuffer(scaledVerts)));
+ cube.setColorRefBuffer(new J3DBuffer(makeFloatBuffer(colors)));
+
+ this.setGeometry(cube);
+ this.setAppearance(new SimpleShaderAppearance());
+ }
+
+ public static FloatBuffer makeFloatBuffer(float[] arr)
+ {
+ ByteBuffer bb = ByteBuffer.allocateDirect(arr.length * 4);
+ bb.order(ByteOrder.nativeOrder());
+ FloatBuffer fb = bb.asFloatBuffer();
+ fb.put(arr);
+ fb.position(0);
+ return fb;
+ }
+
+}
diff --git a/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/EnvironmentMappingGLSL.form b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/EnvironmentMappingGLSL.form new file mode 100644 index 0000000..b6a3e94 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/EnvironmentMappingGLSL.form @@ -0,0 +1,36 @@ +<?xml version="1.0" encoding="UTF-8" ?> + +<Form version="1.0" type="org.netbeans.modules.form.forminfo.JFrameFormInfo"> + <Properties> + <Property name="defaultCloseOperation" type="int" value="3"/> + <Property name="title" type="java.lang.String" value="EnvironmentMappingGLSL"/> + </Properties> + <SyntheticProperties> + <SyntheticProperty name="formSizePolicy" type="int" value="1"/> + </SyntheticProperties> + <AuxValues> + <AuxValue name="FormSettings_generateMnemonicsCode" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_listenerGenerationStyle" type="java.lang.Integer" value="0"/> + <AuxValue name="FormSettings_variablesLocal" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_variablesModifier" type="java.lang.Integer" value="2"/> + <AuxValue name="designerSize" type="java.awt.Dimension" value="-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,1,44,0,0,1,-112"/> + </AuxValues> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + <SubComponents> + <Container class="javax.swing.JPanel" name="drawingPanel"> + <Properties> + <Property name="preferredSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor"> + <Dimension value="[500, 500]"/> + </Property> + </Properties> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout" value="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription"> + <BorderConstraints direction="Center"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + </Container> + </SubComponents> +</Form> diff --git a/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/EnvironmentMappingGLSL.java b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/EnvironmentMappingGLSL.java new file mode 100644 index 0000000..700df00 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/EnvironmentMappingGLSL.java @@ -0,0 +1,239 @@ +/* + * Copyright (c) 2016 JogAmp Community. All rights reserved. + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * This code is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 only, as + * published by the Free Software Foundation. Sun designates this + * particular file as subject to the "Classpath" exception as provided + * by Sun in the LICENSE file that accompanied this code. + * + * This code is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + * version 2 for more details (a copy is included in the LICENSE file that + * accompanied this code). + * + * You should have received a copy of the GNU General Public License version + * 2 along with this work; if not, write to the Free Software Foundation, + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. + * + */ + +package org.jdesktop.j3d.examples.gl2es2pipeline; + +import java.awt.GraphicsConfiguration; +import java.io.File; +import java.io.IOException; +import java.net.URL; + +import javax.swing.JOptionPane; + +import org.jdesktop.j3d.examples.Resources; +import org.jogamp.java3d.Alpha; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.GLSLShaderProgram; +import org.jogamp.java3d.RotationInterpolator; +import org.jogamp.java3d.Shader; +import org.jogamp.java3d.ShaderAppearance; +import org.jogamp.java3d.ShaderAttribute; +import org.jogamp.java3d.ShaderAttributeSet; +import org.jogamp.java3d.ShaderAttributeValue; +import org.jogamp.java3d.ShaderError; +import org.jogamp.java3d.ShaderErrorListener; +import org.jogamp.java3d.ShaderProgram; +import org.jogamp.java3d.SourceCodeShader; +import org.jogamp.java3d.Texture; +import org.jogamp.java3d.TextureUnitState; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.utils.geometry.Sphere; +import org.jogamp.java3d.utils.image.TextureLoader; +import org.jogamp.java3d.utils.shader.StringIO; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.java3d.utils.universe.ViewingPlatform; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Point3f; + +public class EnvironmentMappingGLSL extends javax.swing.JFrame +{ + + private URL textureURL = null; + private static final int NUM_TEX_UNITS = 1; + private static final int TEX_UNIT = 0; + + SimpleUniverse univ = null; + + public BranchGroup createSceneGraph() + { + // Create the root of the branch graph + BranchGroup objRoot = new BranchGroup(); + + // Create the TransformGroup node and initialize it to the + // identity. Enable the TRANSFORM_WRITE capability so that + // our behavior code can modify it at run time. Add it to + // the root of the subgraph. + TransformGroup objTrans = new TransformGroup(); + objTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + objRoot.addChild(objTrans); + + // Create texture object + textureURL = Resources.getResource("resources/images/duke-gears.jpg"); + Texture tex = new TextureLoader(textureURL, this).getTexture(); + // Create the shader program + String vertexProgram = null; + String fragmentProgram = null; + try + { + vertexProgram = StringIO.readFully( + new File(System.getProperty("user.dir") + "/src/classes/org/jdesktop/j3d/examples/gl2es2pipeline/envmap.vert")); + fragmentProgram = StringIO.readFully( + new File(System.getProperty("user.dir") + "/src/classes/org/jdesktop/j3d/examples/gl2es2pipeline/envmap.frag")); + } + catch (IOException e) + { + System.err.println(e); + } + Shader[] shaders = new Shader[2]; + shaders[0] = new SourceCodeShader(Shader.SHADING_LANGUAGE_GLSL, Shader.SHADER_TYPE_VERTEX, vertexProgram); + shaders[1] = new SourceCodeShader(Shader.SHADING_LANGUAGE_GLSL, Shader.SHADER_TYPE_FRAGMENT, fragmentProgram); + final String[] shaderAttrNames = { "LightPos", "BaseColor", "MixRatio", "EnvMap", }; + final Object[] shaderAttrValues = { new Point3f(1.0f, -1.0f, 2.0f), new Color3f(0.2f, 0.9f, 0.5f), new Float(0.4f), + new Integer(TEX_UNIT), }; + ShaderProgram shaderProgram = new GLSLShaderProgram(); + shaderProgram.setShaders(shaders); + shaderProgram.setShaderAttrNames(shaderAttrNames); + + // Create the shader attribute set + ShaderAttributeSet shaderAttributeSet = new ShaderAttributeSet(); + for (int i = 0; i < shaderAttrNames.length; i++) + { + ShaderAttribute shaderAttribute = new ShaderAttributeValue(shaderAttrNames[i], shaderAttrValues[i]); + shaderAttributeSet.put(shaderAttribute); + } + + // Create shader appearance to hold the shader program and + // shader attributes + ShaderAppearance app = new ShaderAppearance(); + app.setShaderProgram(shaderProgram); + app.setShaderAttributeSet(shaderAttributeSet); + + // Put the texture in specified texture unit + TextureUnitState[] tus = new TextureUnitState[NUM_TEX_UNITS]; + tus[TEX_UNIT] = new TextureUnitState(); + tus[TEX_UNIT].setTexture(tex); + app.setTextureUnitState(tus); + + // Create a Sphere object using the shader appearance, + // and add it into the scene graph. + Sphere sph = new Sphere(0.4f, Sphere.GENERATE_NORMALS, 20, app); + SphereGLSL.makeNIO(sph); + objTrans.addChild(sph); + + // Create a new Behavior object that will perform the + // desired operation on the specified transform and add + // it into the scene graph. + Transform3D yAxis = new Transform3D(); + Alpha rotationAlpha = new Alpha(-1, 4000); + + RotationInterpolator rotator = new RotationInterpolator(rotationAlpha, objTrans, yAxis, 0.0f, (float) Math.PI * 2.0f); + BoundingSphere bounds = new BoundingSphere(new Point3d(0.0, 0.0, 0.0), 100.0); + rotator.setSchedulingBounds(bounds); + objRoot.addChild(rotator); + + // Have Java 3D perform optimizations on this scene graph. + //objRoot.compile(); + + return objRoot; + } + + + + private Canvas3D initScene() + { + GraphicsConfiguration config = SimpleUniverse.getPreferredConfiguration(); + + Canvas3D c = new Canvas3D(config); + + BranchGroup scene = createSceneGraph(); + univ = new SimpleUniverse(c); + + // Add a ShaderErrorListener + univ.addShaderErrorListener(new ShaderErrorListener() { + @Override + public void errorOccurred(ShaderError error) + { + error.printVerbose(); + JOptionPane.showMessageDialog(EnvironmentMappingGLSL.this, error.toString(), "ShaderError", JOptionPane.ERROR_MESSAGE); + } + }); + + ViewingPlatform viewingPlatform = univ.getViewingPlatform(); + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + viewingPlatform.setNominalViewingTransform(); + + univ.addBranchGraph(scene); + + return c; + } + + /** + * Creates new form EnvironmentMappingGLSL + */ + public EnvironmentMappingGLSL() + { + // Initialize the GUI components + initComponents(); + + // Create the scene and add the Canvas3D to the drawing panel + Canvas3D c = initScene(); + drawingPanel.add(c, java.awt.BorderLayout.CENTER); + } + + // ---------------------------------------------------------------- + + /** This method is called from within the constructor to + * initialize the form. + * WARNING: Do NOT modify this code. The content of this method is + * always regenerated by the Form Editor. + */ + // <editor-fold defaultstate="collapsed" desc=" Generated Code ">//GEN-BEGIN:initComponents + private void initComponents() + { + drawingPanel = new javax.swing.JPanel(); + + setDefaultCloseOperation(javax.swing.WindowConstants.EXIT_ON_CLOSE); + setTitle("EnvironmentMappingGLSL"); + drawingPanel.setLayout(new java.awt.BorderLayout()); + + drawingPanel.setPreferredSize(new java.awt.Dimension(500, 500)); + getContentPane().add(drawingPanel, java.awt.BorderLayout.CENTER); + + pack(); + }// </editor-fold>//GEN-END:initComponents + + /** + * @param args the command line arguments + */ + public static void main(String args[]) + { + System.setProperty("sun.awt.noerasebackground", "true"); + System.setProperty("j3d.rend", "jogl2es2"); + java.awt.EventQueue.invokeLater(new Runnable() { + @Override + public void run() + { + new EnvironmentMappingGLSL().setVisible(true); + } + }); + } + + // Variables declaration - do not modify//GEN-BEGIN:variables + private javax.swing.JPanel drawingPanel; + // End of variables declaration//GEN-END:variables + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/ObjLoadGLSL.form b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/ObjLoadGLSL.form new file mode 100644 index 0000000..343b6d5 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/ObjLoadGLSL.form @@ -0,0 +1,36 @@ +<?xml version="1.0" encoding="UTF-8" ?> + +<Form version="1.0" type="org.netbeans.modules.form.forminfo.JFrameFormInfo"> + <Properties> + <Property name="defaultCloseOperation" type="int" value="3"/> + <Property name="title" type="java.lang.String" value="ObjLoadGLSL"/> + </Properties> + <SyntheticProperties> + <SyntheticProperty name="formSizePolicy" type="int" value="1"/> + </SyntheticProperties> + <AuxValues> + <AuxValue name="FormSettings_generateMnemonicsCode" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_listenerGenerationStyle" type="java.lang.Integer" value="0"/> + <AuxValue name="FormSettings_variablesLocal" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_variablesModifier" type="java.lang.Integer" value="2"/> + <AuxValue name="designerSize" type="java.awt.Dimension" value="-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,1,44,0,0,1,-112"/> + </AuxValues> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + <SubComponents> + <Container class="javax.swing.JPanel" name="drawingPanel"> + <Properties> + <Property name="preferredSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor"> + <Dimension value="[700, 700]"/> + </Property> + </Properties> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout" value="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription"> + <BorderConstraints direction="Center"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + </Container> + </SubComponents> +</Form> diff --git a/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/ObjLoadGLSL.java b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/ObjLoadGLSL.java new file mode 100644 index 0000000..2708e58 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/ObjLoadGLSL.java @@ -0,0 +1,424 @@ +/* + * Copyright (c) 2016 JogAmp Community. All rights reserved. + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * This code is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 only, as + * published by the Free Software Foundation. Sun designates this + * particular file as subject to the "Classpath" exception as provided + * by Sun in the LICENSE file that accompanied this code. + * + * This code is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + * version 2 for more details (a copy is included in the LICENSE file that + * accompanied this code). + * + * You should have received a copy of the GNU General Public License version + * 2 along with this work; if not, write to the Free Software Foundation, + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. + * + */ + +package org.jdesktop.j3d.examples.gl2es2pipeline; + +import java.awt.GraphicsConfiguration; +import java.io.File; +import java.io.FileNotFoundException; +import java.io.IOException; +import java.net.MalformedURLException; +import java.net.URL; +import java.util.Enumeration; + +import javax.swing.JOptionPane; + +import org.jdesktop.j3d.examples.Resources; +import org.jogamp.java3d.Alpha; +import org.jogamp.java3d.AmbientLight; +import org.jogamp.java3d.Background; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.DirectionalLight; +import org.jogamp.java3d.GLSLShaderProgram; +import org.jogamp.java3d.Group; +import org.jogamp.java3d.Material; +import org.jogamp.java3d.Node; +import org.jogamp.java3d.RotationInterpolator; +import org.jogamp.java3d.Shader; +import org.jogamp.java3d.ShaderAppearance; +import org.jogamp.java3d.ShaderError; +import org.jogamp.java3d.ShaderErrorListener; +import org.jogamp.java3d.ShaderProgram; +import org.jogamp.java3d.Shape3D; +import org.jogamp.java3d.SourceCodeShader; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.loaders.IncorrectFormatException; +import org.jogamp.java3d.loaders.ParsingErrorException; +import org.jogamp.java3d.loaders.Scene; +import org.jogamp.java3d.loaders.objectfile.ObjectFile; +import org.jogamp.java3d.utils.behaviors.vp.OrbitBehavior; +import org.jogamp.java3d.utils.shader.StringIO; +import org.jogamp.java3d.utils.universe.PlatformGeometry; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.java3d.utils.universe.ViewingPlatform; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Vector3f; + +/** + * Simple Java 3D example program to display an .obj object with shader programs. + */ +public class ObjLoadGLSL extends javax.swing.JFrame +{ + + private String shaderName = "polkadot3d"; + private boolean spin = false; + private boolean noTriangulate = false; + private boolean noStripify = false; + private double creaseAngle = 60.0; + private URL filename = null; + + private SimpleUniverse univ = null; + private BranchGroup scene = null; + + public BranchGroup createSceneGraph() + { + // Create the root of the branch graph + BranchGroup objRoot = new BranchGroup(); + + // Create a Transformgroup to scale all objects so they + // appear in the scene. + TransformGroup objScale = new TransformGroup(); + Transform3D t3d = new Transform3D(); + t3d.setScale(0.7); + objScale.setTransform(t3d); + objRoot.addChild(objScale); + + // Create the transform group node and initialize it to the + // identity. Enable the TRANSFORM_WRITE capability so that + // our behavior code can modify it at runtime. Add it to the + // root of the subgraph. + TransformGroup objTrans = new TransformGroup(); + objTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + objTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_READ); + objScale.addChild(objTrans); + + int flags = ObjectFile.RESIZE; + if (!noTriangulate) + flags |= ObjectFile.TRIANGULATE; + if (!noStripify) + flags |= ObjectFile.STRIPIFY; + ObjectFile f = new ObjectFile(flags, (float) (creaseAngle * Math.PI / 180.0)); + Scene s = null; + try + { + s = f.load(filename); + } + catch (FileNotFoundException e) + { + System.err.println(e); + System.exit(1); + } + catch (ParsingErrorException e) + { + System.err.println(e); + System.exit(1); + } + catch (IncorrectFormatException e) + { + System.err.println(e); + System.exit(1); + } + + // Set vertex and fragment shader program for all Shape3D nodes in scene + String vertexProgram = null; + String fragmentProgram = null; + try + { + vertexProgram = StringIO.readFully(new File( + System.getProperty("user.dir") + "/src/classes/org/jdesktop/j3d/examples/gl2es2pipeline/" + shaderName + ".vert")); + fragmentProgram = StringIO.readFully(new File( + System.getProperty("user.dir") + "/src/classes/org/jdesktop/j3d/examples/gl2es2pipeline/" + shaderName + ".frag")); + } + catch (IOException e) + { + throw new RuntimeException(e); + } + Shader[] shaders = new Shader[2]; + shaders[0] = new SourceCodeShader(Shader.SHADING_LANGUAGE_GLSL, Shader.SHADER_TYPE_VERTEX, vertexProgram); + shaders[1] = new SourceCodeShader(Shader.SHADING_LANGUAGE_GLSL, Shader.SHADER_TYPE_FRAGMENT, fragmentProgram); + ShaderProgram shaderProgram = new GLSLShaderProgram(); + shaderProgram.setShaders(shaders); + setShaderProgram(s.getSceneGroup(), shaderProgram); + + objTrans.addChild(s.getSceneGroup()); + + BoundingSphere bounds = new BoundingSphere(new Point3d(0.0, 0.0, 0.0), 100.0); + + if (spin) + { + Transform3D yAxis = new Transform3D(); + Alpha rotationAlpha = new Alpha(-1, Alpha.INCREASING_ENABLE, 0, 0, 4000, 0, 0, 0, 0, 0); + + RotationInterpolator rotator = new RotationInterpolator(rotationAlpha, objTrans, yAxis, 0.0f, (float) Math.PI * 2.0f); + rotator.setSchedulingBounds(bounds); + objTrans.addChild(rotator); + } + + // Set up the background + Color3f bgColor = new Color3f(0.05f, 0.05f, 0.5f); + Background bgNode = new Background(bgColor); + bgNode.setApplicationBounds(bounds); + objRoot.addChild(bgNode); + + return objRoot; + } + + private Canvas3D createUniverse() + { + // Get the preferred graphics configuration for the default screen + GraphicsConfiguration config = SimpleUniverse.getPreferredConfiguration(); + + // Create a Canvas3D using the preferred configuration + Canvas3D canvas3d = new Canvas3D(config); + + // Create simple universe with view branch + univ = new SimpleUniverse(canvas3d); + BoundingSphere bounds = new BoundingSphere(new Point3d(0.0, 0.0, 0.0), 100.0); + + // Add a ShaderErrorListener + univ.addShaderErrorListener(new ShaderErrorListener() { + @Override + public void errorOccurred(ShaderError error) + { + error.printVerbose(); + JOptionPane.showMessageDialog(ObjLoadGLSL.this, error.toString(), "ShaderError", JOptionPane.ERROR_MESSAGE); + } + }); + + // add mouse behaviors to the ViewingPlatform + ViewingPlatform viewingPlatform = univ.getViewingPlatform(); + + PlatformGeometry pg = new PlatformGeometry(); + + // Set up the ambient light + Color3f ambientColor = new Color3f(0.1f, 0.1f, 0.1f); + AmbientLight ambientLightNode = new AmbientLight(ambientColor); + ambientLightNode.setInfluencingBounds(bounds); + pg.addChild(ambientLightNode); + + // Set up the directional lights + Color3f light1Color = new Color3f(1.0f, 1.0f, 0.9f); + Vector3f light1Direction = new Vector3f(1.0f, 1.0f, 1.0f); + Color3f light2Color = new Color3f(1.0f, 1.0f, 1.0f); + Vector3f light2Direction = new Vector3f(-1.0f, -1.0f, -1.0f); + + DirectionalLight light1 = new DirectionalLight(light1Color, light1Direction); + light1.setInfluencingBounds(bounds); + pg.addChild(light1); + + DirectionalLight light2 = new DirectionalLight(light2Color, light2Direction); + light2.setInfluencingBounds(bounds); + pg.addChild(light2); + + viewingPlatform.setPlatformGeometry(pg); + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + viewingPlatform.setNominalViewingTransform(); + + if (!spin) + { + OrbitBehavior orbit = new OrbitBehavior(canvas3d, OrbitBehavior.REVERSE_ALL); + orbit.setSchedulingBounds(bounds); + viewingPlatform.setViewPlatformBehavior(orbit); + } + + // Ensure at least 5 msec per frame (i.e., < 200Hz) + univ.getViewer().getView().setMinimumFrameCycleTime(5); + + return canvas3d; + } + + private static void usage() + { + System.out.println("Usage: java ObjLoadGLSL [-s] [-S shaderName] [-n] [-t] [-c degrees] <.obj file>"); + System.out.println(" -s Spin (no user interaction)"); + System.out.println(" -S Set shader name (default is 'simple')"); + System.out.println(" -n No triangulation"); + System.out.println(" -t No stripification"); + System.out.println(" -c Set crease angle for normal generation (default is 60 without"); + System.out.println(" smoothing group info, otherwise 180 within smoothing groups)"); + System.exit(0); + } // End of usage + + // Set shader program for all nodes in specified branch graph + private void setShaderProgram(BranchGroup g, ShaderProgram shaderProgram) + { + ShaderAppearance myApp = new ShaderAppearance(); + Material mat = new Material(); + myApp.setShaderProgram(shaderProgram); + myApp.setMaterial(mat); + setShaderProgram(g, myApp); + } + + // Recursively set shader program for all children of specified group + private void setShaderProgram(Group g, ShaderAppearance myApp) + { + + Enumeration<?> e = g.getAllChildren(); + while (e.hasMoreElements()) + { + Node n = (Node) (e.nextElement()); + if (n instanceof Group) + { + setShaderProgram((Group) n, myApp); + } + else if (n instanceof Shape3D) + { + Shape3D s = (Shape3D) n; + s.setAppearance(myApp); + } + } + } + + /** + * Creates new form ObjLoadGLSL + */ + public ObjLoadGLSL(String args[]) + { + if (args.length != 0) + { + for (int i = 0; i < args.length; i++) + { + if (args[i].startsWith("-")) + { + if (args[i].equals("-s")) + { + spin = true; + } + else if (args[i].equals("-n")) + { + noTriangulate = true; + } + else if (args[i].equals("-t")) + { + noStripify = true; + } + else if (args[i].equals("-c")) + { + if (i < args.length - 1) + { + creaseAngle = (new Double(args[++i])).doubleValue(); + } + else + usage(); + } + else if (args[i].equals("-S")) + { + if (i < args.length - 1) + { + shaderName = args[++i]; + } + else + usage(); + } + else + { + usage(); + } + } + else + { + try + { + if ((args[i].indexOf("file:") == 0) || (args[i].indexOf("http") == 0)) + { + filename = new URL(args[i]); + } + else if (args[i].charAt(0) != '/') + { + filename = new URL("file:./" + args[i]); + } + else + { + filename = new URL("file:" + args[i]); + } + } + catch (MalformedURLException e) + { + System.err.println(e); + System.exit(1); + } + } + } + } + + if (filename == null) + { + filename = Resources.getResource("resources/geometry/galleon.obj"); + if (filename == null) + { + System.err.println("resources/geometry/galleon.obj not found"); + System.exit(1); + } + } + + // Initialize the GUI components + initComponents(); + + // Create Canvas3D and SimpleUniverse; add canvas to drawing panel + Canvas3D c = createUniverse(); + drawingPanel.add(c, java.awt.BorderLayout.CENTER); + + // Create the content branch and add it to the universe + scene = createSceneGraph(); + univ.addBranchGraph(scene); + } + + // ---------------------------------------------------------------- + + /** This method is called from within the constructor to + * initialize the form. + * WARNING: Do NOT modify this code. The content of this method is + * always regenerated by the Form Editor. + */ + // <editor-fold defaultstate="collapsed" desc=" Generated Code ">//GEN-BEGIN:initComponents + private void initComponents() + { + drawingPanel = new javax.swing.JPanel(); + + setDefaultCloseOperation(javax.swing.WindowConstants.EXIT_ON_CLOSE); + setTitle("ObjLoadGLSL"); + drawingPanel.setLayout(new java.awt.BorderLayout()); + + drawingPanel.setPreferredSize(new java.awt.Dimension(700, 700)); + getContentPane().add(drawingPanel, java.awt.BorderLayout.CENTER); + + pack(); + }// </editor-fold>//GEN-END:initComponents + + /** + * @param args the command line arguments + */ + public static void main(final String args[]) + { + System.setProperty("sun.awt.noerasebackground", "true"); + System.setProperty("j3d.rend","jogl2es2"); + java.awt.EventQueue.invokeLater(new Runnable() { + @Override + public void run() + { + ObjLoadGLSL objLoadGLSL = new ObjLoadGLSL(args); + objLoadGLSL.setVisible(true); + } + }); + } + + // Variables declaration - do not modify//GEN-BEGIN:variables + private javax.swing.JPanel drawingPanel; + // End of variables declaration//GEN-END:variables + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/PhongShadingGLSL.form b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/PhongShadingGLSL.form new file mode 100644 index 0000000..dcccf73 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/PhongShadingGLSL.form @@ -0,0 +1,138 @@ +<?xml version="1.0" encoding="UTF-8" ?> + +<Form version="1.0" type="org.netbeans.modules.form.forminfo.JFrameFormInfo"> + <NonVisualComponents> + <Component class="javax.swing.ButtonGroup" name="shaderButtonGroup"> + </Component> + <Menu class="javax.swing.JMenuBar" name="jMenuBar1"> + <SubComponents> + <Menu class="javax.swing.JMenu" name="fileMenu"> + <Properties> + <Property name="text" type="java.lang.String" value="File"/> + </Properties> + <SubComponents> + <MenuItem class="javax.swing.JMenuItem" name="exitMenuItem"> + <Properties> + <Property name="text" type="java.lang.String" value="Exit"/> + </Properties> + <Events> + <EventHandler event="actionPerformed" listener="java.awt.event.ActionListener" parameters="java.awt.event.ActionEvent" handler="exitMenuItemActionPerformed"/> + </Events> + </MenuItem> + </SubComponents> + </Menu> + </SubComponents> + </Menu> + </NonVisualComponents> + <Properties> + <Property name="defaultCloseOperation" type="int" value="3"/> + <Property name="title" type="java.lang.String" value="Phong Shading Test"/> + </Properties> + <SyntheticProperties> + <SyntheticProperty name="menuBar" type="java.lang.String" value="jMenuBar1"/> + <SyntheticProperty name="formSizePolicy" type="int" value="1"/> + </SyntheticProperties> + <AuxValues> + <AuxValue name="FormSettings_generateMnemonicsCode" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_listenerGenerationStyle" type="java.lang.Integer" value="0"/> + <AuxValue name="FormSettings_variablesLocal" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_variablesModifier" type="java.lang.Integer" value="2"/> + <AuxValue name="designerSize" type="java.awt.Dimension" value="-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,1,44,0,0,1,-112"/> + </AuxValues> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + <SubComponents> + <Container class="javax.swing.JPanel" name="guiPanel"> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout" value="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription"> + <BorderConstraints direction="North"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout"/> + <SubComponents> + <Container class="javax.swing.JPanel" name="jPanel1"> + <Properties> + <Property name="border" type="javax.swing.border.Border" editor="org.netbeans.modules.form.editors2.BorderEditor"> + <Border info="org.netbeans.modules.form.compat2.border.TitledBorderInfo"> + <TitledBorder title="Shader"/> + </Border> + </Property> + </Properties> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout" value="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription"> + <GridBagConstraints gridX="-1" gridY="-1" gridWidth="1" gridHeight="1" fill="2" ipadX="0" ipadY="0" insetsTop="4" insetsLeft="4" insetsBottom="4" insetsRight="4" anchor="10" weightX="0.0" weightY="0.0"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout"/> + <SubComponents> + <Component class="javax.swing.JRadioButton" name="gouraudButton"> + <Properties> + <Property name="buttonGroup" type="javax.swing.ButtonGroup" editor="org.netbeans.modules.form.RADComponent$ButtonGroupPropertyEditor"> + <ComponentRef name="shaderButtonGroup"/> + </Property> + <Property name="selected" type="boolean" value="true"/> + <Property name="text" type="java.lang.String" value="Per-Vertex Lighting (Gouraud)"/> + <Property name="border" type="javax.swing.border.Border" editor="org.netbeans.modules.form.editors2.BorderEditor"> + <Border info="org.netbeans.modules.form.compat2.border.EmptyBorderInfo"> + <EmptyBorder bottom="0" left="0" right="0" top="0"/> + </Border> + </Property> + <Property name="margin" type="java.awt.Insets" editor="org.netbeans.beaninfo.editors.InsetsEditor"> + <Insets value="[0, 0, 0, 0]"/> + </Property> + </Properties> + <Events> + <EventHandler event="actionPerformed" listener="java.awt.event.ActionListener" parameters="java.awt.event.ActionEvent" handler="gouraudButtonActionPerformed"/> + </Events> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout" value="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription"> + <GridBagConstraints gridX="-1" gridY="-1" gridWidth="1" gridHeight="1" fill="2" ipadX="0" ipadY="0" insetsTop="2" insetsLeft="2" insetsBottom="2" insetsRight="2" anchor="10" weightX="0.0" weightY="0.0"/> + </Constraint> + </Constraints> + </Component> + <Component class="javax.swing.JRadioButton" name="phongButton"> + <Properties> + <Property name="buttonGroup" type="javax.swing.ButtonGroup" editor="org.netbeans.modules.form.RADComponent$ButtonGroupPropertyEditor"> + <ComponentRef name="shaderButtonGroup"/> + </Property> + <Property name="text" type="java.lang.String" value="Per-Pixel Lighting (Phong)"/> + <Property name="border" type="javax.swing.border.Border" editor="org.netbeans.modules.form.editors2.BorderEditor"> + <Border info="org.netbeans.modules.form.compat2.border.EmptyBorderInfo"> + <EmptyBorder bottom="0" left="0" right="0" top="0"/> + </Border> + </Property> + <Property name="margin" type="java.awt.Insets" editor="org.netbeans.beaninfo.editors.InsetsEditor"> + <Insets value="[0, 0, 0, 0]"/> + </Property> + </Properties> + <Events> + <EventHandler event="actionPerformed" listener="java.awt.event.ActionListener" parameters="java.awt.event.ActionEvent" handler="phongButtonActionPerformed"/> + </Events> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout" value="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription"> + <GridBagConstraints gridX="0" gridY="1" gridWidth="1" gridHeight="1" fill="2" ipadX="0" ipadY="0" insetsTop="2" insetsLeft="2" insetsBottom="2" insetsRight="2" anchor="10" weightX="0.0" weightY="0.0"/> + </Constraint> + </Constraints> + </Component> + </SubComponents> + </Container> + </SubComponents> + </Container> + <Container class="javax.swing.JPanel" name="drawingPanel"> + <Properties> + <Property name="preferredSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor"> + <Dimension value="[500, 500]"/> + </Property> + </Properties> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout" value="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription"> + <BorderConstraints direction="Center"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + </Container> + </SubComponents> +</Form> diff --git a/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/PhongShadingGLSL.java b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/PhongShadingGLSL.java new file mode 100644 index 0000000..fa5ba7a --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/PhongShadingGLSL.java @@ -0,0 +1,478 @@ +/* + * Copyright (c) 2016 JogAmp Community. All rights reserved. + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * This code is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 only, as + * published by the Free Software Foundation. Sun designates this + * particular file as subject to the "Classpath" exception as provided + * by Sun in the LICENSE file that accompanied this code. + * + * This code is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + * version 2 for more details (a copy is included in the LICENSE file that + * accompanied this code). + * + * You should have received a copy of the GNU General Public License version + * 2 along with this work; if not, write to the Free Software Foundation, + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. + * + */ + +package org.jdesktop.j3d.examples.gl2es2pipeline; + +import java.awt.GraphicsConfiguration; +import java.io.File; +import java.io.IOException; + +import javax.swing.JOptionPane; + +import org.jogamp.java3d.Alpha; +import org.jogamp.java3d.AmbientLight; +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.Background; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.ColoringAttributes; +import org.jogamp.java3d.DirectionalLight; +import org.jogamp.java3d.GLSLShaderProgram; +import org.jogamp.java3d.Light; +import org.jogamp.java3d.Material; +import org.jogamp.java3d.PointLight; +import org.jogamp.java3d.RotationInterpolator; +import org.jogamp.java3d.Shader; +import org.jogamp.java3d.ShaderAppearance; +import org.jogamp.java3d.ShaderError; +import org.jogamp.java3d.ShaderErrorListener; +import org.jogamp.java3d.ShaderProgram; +import org.jogamp.java3d.SourceCodeShader; +import org.jogamp.java3d.SpotLight; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.utils.geometry.Sphere; +import org.jogamp.java3d.utils.shader.StringIO; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Point3f; +import org.jogamp.vecmath.Vector3d; +import org.jogamp.vecmath.Vector3f; + +/** + * + * @author kcr + */ +public class PhongShadingGLSL extends javax.swing.JFrame +{ + + // Constants for type of light to use + private static final int DIRECTIONAL_LIGHT = 0; + private static final int POINT_LIGHT = 1; + private static final int SPOT_LIGHT = 2; + + // Flag indicates type of lights: directional, point, or spot lights. + private static int lightType = DIRECTIONAL_LIGHT; + + private SimpleUniverse univ = null; + + private ShaderAppearance sApp = null; + private ShaderProgram gouraudSP = null; + private ShaderProgram phongSP = null; + + public BranchGroup createSceneGraph() + { + Color3f eColor = new Color3f(0.0f, 0.0f, 0.0f); + Color3f sColor = new Color3f(1.0f, 1.0f, 1.0f); + Color3f objColor = new Color3f(0.6f, 0.6f, 0.6f); + // Color3f lColor1 = new Color3f(1.0f, 0.0f, 0.0f); + // Color3f lColor2 = new Color3f(0.0f, 1.0f, 0.0f); + Color3f lColor1 = new Color3f(1.0f, 1.0f, 0.5f); + Color3f alColor = new Color3f(0.2f, 0.2f, 0.2f); + Color3f bgColor = new Color3f(0.05f, 0.05f, 0.2f); + + Transform3D t; + + // Create the root of the branch graph + BranchGroup objRoot = new BranchGroup(); + + // Create a Transformgroup to scale all objects so they + // appear in the scene. + TransformGroup objScale = new TransformGroup(); + Transform3D t3d = new Transform3D(); + t3d.setScale(0.5); + objScale.setTransform(t3d); + objRoot.addChild(objScale); + + // Create a bounds for the background and lights + BoundingSphere bounds = new BoundingSphere(new Point3d(0.0, 0.0, 0.0), 100.0); + + // Set up the background + Background bg = new Background(bgColor); + bg.setApplicationBounds(bounds); + objRoot.addChild(bg); + + // Create the TransformGroup node and initialize it to the + // identity. Enable the TRANSFORM_WRITE capability so that + // our behavior code can modify it at run time. Add it to + // the root of the subgraph. + TransformGroup objTrans = new TransformGroup(); + objTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + objScale.addChild(objTrans); + + // Create a Sphere object, generate one copy of the sphere, + // and add it into the scene graph. + sApp = new ShaderAppearance(); + sApp.setCapability(ShaderAppearance.ALLOW_SHADER_PROGRAM_WRITE); + Material m = new Material(objColor, eColor, objColor, sColor, 100.0f); + sApp.setMaterial(m); + + // Create Gouraud and Phong shader programs + String vertexProgram = null; + String fragmentProgram = null; + Shader[] shaders = new Shader[2]; + //String[] attrNames = { "numLights" }; + + try + { + vertexProgram = StringIO.readFully( + new File(System.getProperty("user.dir") + "/src/classes/org/jdesktop/j3d/examples/gl2es2pipeline/gouraud.vert")); + fragmentProgram = StringIO.readFully( + new File(System.getProperty("user.dir") + "/src/classes/org/jdesktop/j3d/examples/gl2es2pipeline/gouraud.frag")); + } + catch (IOException e) + { + throw new RuntimeException(e); + } + shaders[0] = new SourceCodeShader(Shader.SHADING_LANGUAGE_GLSL, Shader.SHADER_TYPE_VERTEX, vertexProgram); + shaders[1] = new SourceCodeShader(Shader.SHADING_LANGUAGE_GLSL, Shader.SHADER_TYPE_FRAGMENT, fragmentProgram); + gouraudSP = new GLSLShaderProgram(); + gouraudSP.setShaders(shaders); + + try + { + vertexProgram = StringIO.readFully( + new File(System.getProperty("user.dir") + "/src/classes/org/jdesktop/j3d/examples/gl2es2pipeline/phong.vert")); + fragmentProgram = StringIO.readFully( + new File(System.getProperty("user.dir") + "/src/classes/org/jdesktop/j3d/examples/gl2es2pipeline/phong.frag")); + } + catch (IOException e) + { + throw new RuntimeException(e); + } + shaders[0] = new SourceCodeShader(Shader.SHADING_LANGUAGE_GLSL, Shader.SHADER_TYPE_VERTEX, vertexProgram); + shaders[1] = new SourceCodeShader(Shader.SHADING_LANGUAGE_GLSL, Shader.SHADER_TYPE_FRAGMENT, fragmentProgram); + phongSP = new GLSLShaderProgram(); + phongSP.setShaders(shaders); + + if (gouraudButton.isSelected()) + { + sApp.setShaderProgram(gouraudSP); + } + else if (phongButton.isSelected()) + { + sApp.setShaderProgram(phongSP); + } + Sphere sph = new Sphere(1.0f, Sphere.GENERATE_NORMALS, 30, sApp); + SphereGLSL.makeNIO(sph); + objTrans.addChild(sph); + + // Create a new Behavior object that will perform the + // desired operation on the specified transform and add + // it into the scene graph. + Transform3D yAxis = new Transform3D(); + yAxis.rotZ(Math.PI); + Alpha rotationAlpha = new Alpha(-1, 10000); + + RotationInterpolator rotator = new RotationInterpolator(rotationAlpha, objTrans, yAxis, 0.0f, (float) Math.PI * 2.0f); + rotator.setSchedulingBounds(bounds); + objRoot.addChild(rotator); + + // Create the transform group node for the each light and initialize + // it to the identity. Enable the TRANSFORM_WRITE capability so that + // our behavior code can modify it at runtime. Add them to the root + // of the subgraph. + TransformGroup l1RotTrans = new TransformGroup(); + l1RotTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + objScale.addChild(l1RotTrans); + + TransformGroup l2RotTrans = new TransformGroup(); + l2RotTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + objScale.addChild(l2RotTrans); + + // Create transformations for the positional lights + t = new Transform3D(); + Vector3d lPos1 = new Vector3d(0.0, 0.0, 2.0); + t.set(lPos1); + TransformGroup l1Trans = new TransformGroup(t); + l1RotTrans.addChild(l1Trans); + + // t = new Transform3D(); + // Vector3d lPos2 = new Vector3d(0.5, 0.8, 2.0); + // t.set(lPos2); + // TransformGroup l2Trans = new TransformGroup(t); + // l2RotTrans.addChild(l2Trans); + + // Create Geometry for point lights + ColoringAttributes caL1 = new ColoringAttributes(); + // ColoringAttributes caL2 = new ColoringAttributes(); + caL1.setColor(lColor1); + // caL2.setColor(lColor2); + Appearance appL1 = new Appearance(); + // Appearance appL2 = new Appearance(); + appL1.setColoringAttributes(caL1); + // appL2.setColoringAttributes(caL2); + + Sphere sph2 = new Sphere(0.05f, appL1); + SphereGLSL.makeNIO(sph2); + l1Trans.addChild(sph2); + // l2Trans.addChild(new Sphere(0.05f, appL2)); + + // Create lights + AmbientLight aLgt = new AmbientLight(alColor); + + Light lgt1 = null; + // Light lgt2 = null; + + Point3f lPoint = new Point3f(0.0f, 0.0f, 0.0f); + Point3f atten = new Point3f(1.0f, 0.0f, 0.0f); + Vector3f lDirect1 = new Vector3f(lPos1); + // Vector3f lDirect2 = new Vector3f(lPos2); + lDirect1.negate(); + // lDirect2.negate(); + + switch (lightType) + { + case DIRECTIONAL_LIGHT: + lgt1 = new DirectionalLight(lColor1, lDirect1); + // lgt2 = new DirectionalLight(lColor2, lDirect2); + break; + case POINT_LIGHT: + assert false : "can't get here"; + lgt1 = new PointLight(lColor1, lPoint, atten); + // lgt2 = new PointLight(lColor2, lPoint, atten); + break; + case SPOT_LIGHT: + assert false : "can't get here"; + lgt1 = new SpotLight(lColor1, lPoint, atten, lDirect1, 25.0f * (float) Math.PI / 180.0f, 10.0f); + // lgt2 = new SpotLight(lColor2, lPoint, atten, lDirect2, + // 25.0f * (float)Math.PI / 180.0f, 10.0f); + break; + } + + // Set the influencing bounds + aLgt.setInfluencingBounds(bounds); + lgt1.setInfluencingBounds(bounds); + // lgt2.setInfluencingBounds(bounds); + + // Add the lights into the scene graph + objScale.addChild(aLgt); + l1Trans.addChild(lgt1); + // l2Trans.addChild(lgt2); + + // Create a new Behavior object that will perform the desired + // operation on the specified transform object and add it into the + // scene graph. + yAxis = new Transform3D(); + Alpha rotor1Alpha = new Alpha(-1, Alpha.INCREASING_ENABLE, 0, 0, 4000, 0, 0, 0, 0, 0); + RotationInterpolator rotator1 = new RotationInterpolator(rotor1Alpha, l1RotTrans, yAxis, 0.0f, (float) Math.PI * 2.0f); + rotator1.setSchedulingBounds(bounds); + l1RotTrans.addChild(rotator1); + + // Create a new Behavior object that will perform the desired + // operation on the specified transform object and add it into the + // scene graph. + Alpha rotor2Alpha = new Alpha(-1, Alpha.INCREASING_ENABLE, 0, 0, 1000, 0, 0, 0, 0, 0); + RotationInterpolator rotator2 = new RotationInterpolator(rotor2Alpha, l2RotTrans, yAxis, 0.0f, 0.0f); + bounds = new BoundingSphere(new Point3d(0.0, 0.0, 0.0), 100.0); + rotator2.setSchedulingBounds(bounds); + l2RotTrans.addChild(rotator2); + + return objRoot; + } + + + + private Canvas3D initScene() + { + GraphicsConfiguration config = SimpleUniverse.getPreferredConfiguration(); + + Canvas3D c = new Canvas3D(config); + + univ = new SimpleUniverse(c); + + // Add a ShaderErrorListener + univ.addShaderErrorListener(new ShaderErrorListener() { + @Override + public void errorOccurred(ShaderError error) + { + error.printVerbose(); + JOptionPane.showMessageDialog(PhongShadingGLSL.this, error.toString(), "ShaderError", JOptionPane.ERROR_MESSAGE); + } + }); + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + univ.getViewingPlatform().setNominalViewingTransform(); + + BranchGroup scene = createSceneGraph(); + univ.addBranchGraph(scene); + + return c; + } + + /** + * Creates new form PhongShadingGLSL + */ + public PhongShadingGLSL() + { + // Initialize the GUI components + initComponents(); + + // Create the scene and add the Canvas3D to the drawing panel + Canvas3D c = initScene(); + drawingPanel.add(c, java.awt.BorderLayout.CENTER); + } + + // ---------------------------------------------------------------- + + /** This method is called from within the constructor to + * initialize the form. + * WARNING: Do NOT modify this code. The content of this method is + * always regenerated by the Form Editor. + */ + // <editor-fold defaultstate="collapsed" desc=" Generated Code ">//GEN-BEGIN:initComponents + private void initComponents() + { + java.awt.GridBagConstraints gridBagConstraints; + + shaderButtonGroup = new javax.swing.ButtonGroup(); + guiPanel = new javax.swing.JPanel(); + jPanel1 = new javax.swing.JPanel(); + gouraudButton = new javax.swing.JRadioButton(); + phongButton = new javax.swing.JRadioButton(); + drawingPanel = new javax.swing.JPanel(); + jMenuBar1 = new javax.swing.JMenuBar(); + fileMenu = new javax.swing.JMenu(); + exitMenuItem = new javax.swing.JMenuItem(); + + setDefaultCloseOperation(javax.swing.WindowConstants.EXIT_ON_CLOSE); + setTitle("Phong Shading Test"); + guiPanel.setLayout(new java.awt.GridBagLayout()); + + jPanel1.setLayout(new java.awt.GridBagLayout()); + + jPanel1.setBorder(javax.swing.BorderFactory.createTitledBorder("Shader")); + shaderButtonGroup.add(gouraudButton); + gouraudButton.setSelected(true); + gouraudButton.setText("Per-Vertex Lighting (Gouraud)"); + gouraudButton.setBorder(javax.swing.BorderFactory.createEmptyBorder(0, 0, 0, 0)); + gouraudButton.setMargin(new java.awt.Insets(0, 0, 0, 0)); + gouraudButton.addActionListener(new java.awt.event.ActionListener() { + @Override + public void actionPerformed(java.awt.event.ActionEvent evt) + { + gouraudButtonActionPerformed(evt); + } + }); + + gridBagConstraints = new java.awt.GridBagConstraints(); + gridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL; + gridBagConstraints.insets = new java.awt.Insets(2, 2, 2, 2); + jPanel1.add(gouraudButton, gridBagConstraints); + + shaderButtonGroup.add(phongButton); + phongButton.setText("Per-Pixel Lighting (Phong)"); + phongButton.setBorder(javax.swing.BorderFactory.createEmptyBorder(0, 0, 0, 0)); + phongButton.setMargin(new java.awt.Insets(0, 0, 0, 0)); + phongButton.addActionListener(new java.awt.event.ActionListener() { + @Override + public void actionPerformed(java.awt.event.ActionEvent evt) + { + phongButtonActionPerformed(evt); + } + }); + + gridBagConstraints = new java.awt.GridBagConstraints(); + gridBagConstraints.gridx = 0; + gridBagConstraints.gridy = 1; + gridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL; + gridBagConstraints.insets = new java.awt.Insets(2, 2, 2, 2); + jPanel1.add(phongButton, gridBagConstraints); + + gridBagConstraints = new java.awt.GridBagConstraints(); + gridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL; + gridBagConstraints.insets = new java.awt.Insets(4, 4, 4, 4); + guiPanel.add(jPanel1, gridBagConstraints); + + getContentPane().add(guiPanel, java.awt.BorderLayout.NORTH); + + drawingPanel.setLayout(new java.awt.BorderLayout()); + + drawingPanel.setPreferredSize(new java.awt.Dimension(500, 500)); + getContentPane().add(drawingPanel, java.awt.BorderLayout.CENTER); + + fileMenu.setText("File"); + exitMenuItem.setText("Exit"); + exitMenuItem.addActionListener(new java.awt.event.ActionListener() { + @Override + public void actionPerformed(java.awt.event.ActionEvent evt) + { + exitMenuItemActionPerformed(evt); + } + }); + + fileMenu.add(exitMenuItem); + + jMenuBar1.add(fileMenu); + + setJMenuBar(jMenuBar1); + + pack(); + }// </editor-fold>//GEN-END:initComponents + + private void phongButtonActionPerformed(java.awt.event.ActionEvent evt) + {//GEN-FIRST:event_phongButtonActionPerformed + sApp.setShaderProgram(phongSP); + }//GEN-LAST:event_phongButtonActionPerformed + + private void gouraudButtonActionPerformed(java.awt.event.ActionEvent evt) + {//GEN-FIRST:event_gouraudButtonActionPerformed + sApp.setShaderProgram(gouraudSP); + }//GEN-LAST:event_gouraudButtonActionPerformed + + private static void exitMenuItemActionPerformed(java.awt.event.ActionEvent evt) + {//GEN-FIRST:event_exitMenuItemActionPerformed + System.exit(0); + }//GEN-LAST:event_exitMenuItemActionPerformed + + /** + * @param args the command line arguments + */ + public static void main(String args[]) + { + System.setProperty("sun.awt.noerasebackground", "true"); + System.setProperty("j3d.rend", "jogl2es2"); + java.awt.EventQueue.invokeLater(new Runnable() { + @Override + public void run() + { + new PhongShadingGLSL().setVisible(true); + } + }); + } + + // Variables declaration - do not modify//GEN-BEGIN:variables + private javax.swing.JPanel drawingPanel; + private javax.swing.JMenuItem exitMenuItem; + private javax.swing.JMenu fileMenu; + private javax.swing.JRadioButton gouraudButton; + private javax.swing.JPanel guiPanel; + private javax.swing.JMenuBar jMenuBar1; + private javax.swing.JPanel jPanel1; + private javax.swing.JRadioButton phongButton; + private javax.swing.ButtonGroup shaderButtonGroup; + // End of variables declaration//GEN-END:variables + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/SamplerTestGLSL.form b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/SamplerTestGLSL.form new file mode 100644 index 0000000..6a1a031 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/SamplerTestGLSL.form @@ -0,0 +1,36 @@ +<?xml version="1.0" encoding="UTF-8" ?> + +<Form version="1.0" type="org.netbeans.modules.form.forminfo.JFrameFormInfo"> + <Properties> + <Property name="defaultCloseOperation" type="int" value="3"/> + <Property name="title" type="java.lang.String" value="SamplerTestGLSL"/> + </Properties> + <SyntheticProperties> + <SyntheticProperty name="formSizePolicy" type="int" value="1"/> + </SyntheticProperties> + <AuxValues> + <AuxValue name="FormSettings_generateMnemonicsCode" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_listenerGenerationStyle" type="java.lang.Integer" value="0"/> + <AuxValue name="FormSettings_variablesLocal" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_variablesModifier" type="java.lang.Integer" value="2"/> + <AuxValue name="designerSize" type="java.awt.Dimension" value="-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,1,44,0,0,1,-112"/> + </AuxValues> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + <SubComponents> + <Container class="javax.swing.JPanel" name="drawingPanel"> + <Properties> + <Property name="preferredSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor"> + <Dimension value="[500, 500]"/> + </Property> + </Properties> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout" value="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription"> + <BorderConstraints direction="Center"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + </Container> + </SubComponents> +</Form> diff --git a/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/SamplerTestGLSL.java b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/SamplerTestGLSL.java new file mode 100644 index 0000000..1cb2904 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/SamplerTestGLSL.java @@ -0,0 +1,261 @@ +/* + * Copyright (c) 2016 JogAmp Community. All rights reserved. + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * This code is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 only, as + * published by the Free Software Foundation. Sun designates this + * particular file as subject to the "Classpath" exception as provided + * by Sun in the LICENSE file that accompanied this code. + * + * This code is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + * version 2 for more details (a copy is included in the LICENSE file that + * accompanied this code). + * + * You should have received a copy of the GNU General Public License version + * 2 along with this work; if not, write to the Free Software Foundation, + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. + * + */ + +package org.jdesktop.j3d.examples.gl2es2pipeline; + +import java.awt.GraphicsConfiguration; +import java.io.File; +import java.io.IOException; +import java.net.URL; + +import javax.swing.JOptionPane; + +import org.jdesktop.j3d.examples.Resources; +import org.jogamp.java3d.Alpha; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.GLSLShaderProgram; +import org.jogamp.java3d.RotationInterpolator; +import org.jogamp.java3d.Shader; +import org.jogamp.java3d.ShaderAppearance; +import org.jogamp.java3d.ShaderAttribute; +import org.jogamp.java3d.ShaderAttributeSet; +import org.jogamp.java3d.ShaderAttributeValue; +import org.jogamp.java3d.ShaderError; +import org.jogamp.java3d.ShaderErrorListener; +import org.jogamp.java3d.ShaderProgram; +import org.jogamp.java3d.SourceCodeShader; +import org.jogamp.java3d.Texture; +import org.jogamp.java3d.TextureUnitState; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.utils.geometry.Sphere; +import org.jogamp.java3d.utils.image.TextureLoader; +import org.jogamp.java3d.utils.shader.StringIO; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.java3d.utils.universe.ViewingPlatform; +import org.jogamp.vecmath.Point3d; + +public class SamplerTestGLSL extends javax.swing.JFrame +{ + + private static String cloudTexName = "resources/images/bg.jpg"; + private static String earthTexName = "resources/images/earth.jpg"; + + private URL cloudURL = null; + private URL earthURL = null; + private static final int CLOUD = 0; + private static final int EARTH = 1; + + SimpleUniverse univ = null; + + public BranchGroup createSceneGraph() + { + // Create the root of the branch graph + BranchGroup objRoot = new BranchGroup(); + + // Create the TransformGroup node and initialize it to the + // identity. Enable the TRANSFORM_WRITE capability so that + // our behavior code can modify it at run time. Add it to + // the root of the subgraph. + TransformGroup objTrans = new TransformGroup(); + objTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + objRoot.addChild(objTrans); + + // Create texture objects + cloudURL = Resources.getResource(cloudTexName); + Texture cloudTex = new TextureLoader(cloudURL, this).getTexture(); + earthURL = Resources.getResource(earthTexName); + Texture earthTex = new TextureLoader(earthURL, this).getTexture(); + + // Create the shader program + String vertexProgram = null; + String fragmentProgram = null; + try + { + vertexProgram = StringIO.readFully( + new File(System.getProperty("user.dir") + "/src/classes/org/jdesktop/j3d/examples/gl2es2pipeline/multitex.vert")); + fragmentProgram = StringIO.readFully( + new File(System.getProperty("user.dir") + "/src/classes/org/jdesktop/j3d/examples/gl2es2pipeline/multitex.frag")); + } + catch (IOException e) + { + System.err.println(e); + } + Shader[] shaders = new Shader[2]; + shaders[0] = new SourceCodeShader(Shader.SHADING_LANGUAGE_GLSL, Shader.SHADER_TYPE_VERTEX, vertexProgram); + shaders[1] = new SourceCodeShader(Shader.SHADING_LANGUAGE_GLSL, Shader.SHADER_TYPE_FRAGMENT, fragmentProgram); + final String[] shaderAttrNames = { "cloudFactor", "cloudTex", "earthTex", }; + final Object[] shaderAttrValues = { new Float(0.6f), new Integer(0), new Integer(1), }; + ShaderProgram shaderProgram = new GLSLShaderProgram(); + shaderProgram.setShaders(shaders); + shaderProgram.setShaderAttrNames(shaderAttrNames); + + // Create the shader attribute set + ShaderAttributeSet shaderAttributeSet = new ShaderAttributeSet(); + for (int i = 0; i < shaderAttrNames.length; i++) + { + ShaderAttribute shaderAttribute = new ShaderAttributeValue(shaderAttrNames[i], shaderAttrValues[i]); + shaderAttributeSet.put(shaderAttribute); + } + + // Create shader appearance to hold the shader program and + // shader attributes + ShaderAppearance app = new ShaderAppearance(); + app.setShaderProgram(shaderProgram); + app.setShaderAttributeSet(shaderAttributeSet); + + // GL2ES2: Tex coord gen done in shader now + //Vector4f plane0S = new Vector4f(3.0f, 1.5f, 0.3f, 0.0f); + //Vector4f plane0T = new Vector4f(1.0f, 2.5f, 0.24f, 0.0f); + //TexCoordGeneration tcg0 = new TexCoordGeneration(TexCoordGeneration.OBJECT_LINEAR, TexCoordGeneration.TEXTURE_COORDINATE_2, plane0S, + // plane0T); + //TexCoordGeneration tcg1 = new TexCoordGeneration(TexCoordGeneration.SPHERE_MAP, TexCoordGeneration.TEXTURE_COORDINATE_2); + + // Put the textures in unit 0,1 + TextureUnitState[] tus = new TextureUnitState[2]; + tus[CLOUD] = new TextureUnitState(); + tus[CLOUD].setTexture(cloudTex); + + // GL2ES2: Tex coord gen done in shader now + //tus[CLOUD].setTexCoordGeneration(tcg0); + + tus[EARTH] = new TextureUnitState(); + tus[EARTH].setTexture(earthTex); + + // GL2ES2: Tex coord gen done in shader now + //tus[EARTH].setTexCoordGeneration(tcg1); + + app.setTextureUnitState(tus); + + // Create a Sphere object using the shader appearance, + // and add it into the scene graph. + Sphere sph = new Sphere(0.4f, Sphere.GENERATE_NORMALS, 30, app); + + SphereGLSL.makeNIO(sph); + objTrans.addChild(sph); + + + // Create a new Behavior object that will perform the + // desired operation on the specified transform and add + // it into the scene graph. + Transform3D yAxis = new Transform3D(); + Alpha rotationAlpha = new Alpha(-1, 4000); + + RotationInterpolator rotator = new RotationInterpolator(rotationAlpha, objTrans, yAxis, 0.0f, (float) Math.PI * 2.0f); + BoundingSphere bounds = new BoundingSphere(new Point3d(0.0, 0.0, 0.0), 100.0); + rotator.setSchedulingBounds(bounds); + objRoot.addChild(rotator); + + // Have Java 3D perform optimizations on this scene graph. + //objRoot.compile(); + + return objRoot; + } + + + private Canvas3D initScene() + { + GraphicsConfiguration config = SimpleUniverse.getPreferredConfiguration(); + + Canvas3D c = new Canvas3D(config); + + BranchGroup scene = createSceneGraph(); + univ = new SimpleUniverse(c); + + // Add a ShaderErrorListener + univ.addShaderErrorListener(new ShaderErrorListener() { + @Override + public void errorOccurred(ShaderError error) + { + error.printVerbose(); + JOptionPane.showMessageDialog(SamplerTestGLSL.this, error.toString(), "ShaderError", JOptionPane.ERROR_MESSAGE); + } + }); + + ViewingPlatform viewingPlatform = univ.getViewingPlatform(); + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + viewingPlatform.setNominalViewingTransform(); + + univ.addBranchGraph(scene); + + return c; + } + + /** + * Creates new form SamplerTestGLSL + */ + public SamplerTestGLSL() + { + // Initialize the GUI components + initComponents(); + + // Create the scene and add the Canvas3D to the drawing panel + Canvas3D c = initScene(); + drawingPanel.add(c, java.awt.BorderLayout.CENTER); + } + + // ---------------------------------------------------------------- + + /** This method is called from within the constructor to + * initialize the form. + * WARNING: Do NOT modify this code. The content of this method is + * always regenerated by the Form Editor. + */ + // <editor-fold defaultstate="collapsed" desc=" Generated Code ">//GEN-BEGIN:initComponents + private void initComponents() + { + drawingPanel = new javax.swing.JPanel(); + + setDefaultCloseOperation(javax.swing.WindowConstants.EXIT_ON_CLOSE); + setTitle("SamplerTestGLSL"); + drawingPanel.setLayout(new java.awt.BorderLayout()); + + drawingPanel.setPreferredSize(new java.awt.Dimension(500, 500)); + getContentPane().add(drawingPanel, java.awt.BorderLayout.CENTER); + + pack(); + }// </editor-fold>//GEN-END:initComponents + + /** + * @param args the command line arguments + */ + public static void main(String args[]) + { + System.setProperty("sun.awt.noerasebackground", "true"); + System.setProperty("j3d.rend","jogl2es2"); + java.awt.EventQueue.invokeLater(new Runnable() { + @Override + public void run() + { + new SamplerTestGLSL().setVisible(true); + } + }); + } + + // Variables declaration - do not modify//GEN-BEGIN:variables + private javax.swing.JPanel drawingPanel; + // End of variables declaration//GEN-END:variables + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/ShaderTestGLSL.form b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/ShaderTestGLSL.form new file mode 100644 index 0000000..714273d --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/ShaderTestGLSL.form @@ -0,0 +1,266 @@ +<?xml version="1.0" encoding="UTF-8" ?> + +<Form version="1.2" type="org.netbeans.modules.form.forminfo.JFrameFormInfo"> + <NonVisualComponents> + <Component class="javax.swing.ButtonGroup" name="densityButtonGroup"> + </Component> + <Component class="javax.swing.ButtonGroup" name="colorButtonGroup"> + </Component> + <Component class="javax.swing.ButtonGroup" name="sceneGraphButtonGroup"> + </Component> + <Menu class="javax.swing.JMenuBar" name="jMenuBar1"> + <SubComponents> + <Menu class="javax.swing.JMenu" name="fileMenu"> + <Properties> + <Property name="text" type="java.lang.String" value="File"/> + </Properties> + <SubComponents> + <MenuItem class="javax.swing.JMenuItem" name="exitMenuItem"> + <Properties> + <Property name="text" type="java.lang.String" value="Exit"/> + </Properties> + <Events> + <EventHandler event="actionPerformed" listener="java.awt.event.ActionListener" parameters="java.awt.event.ActionEvent" handler="exitMenuItemActionPerformed"/> + </Events> + </MenuItem> + </SubComponents> + </Menu> + </SubComponents> + </Menu> + </NonVisualComponents> + <Properties> + <Property name="title" type="java.lang.String" value="Window Title"/> + </Properties> + <SyntheticProperties> + <SyntheticProperty name="menuBar" type="java.lang.String" value="jMenuBar1"/> + <SyntheticProperty name="formSizePolicy" type="int" value="1"/> + </SyntheticProperties> + <Events> + <EventHandler event="windowClosing" listener="java.awt.event.WindowListener" parameters="java.awt.event.WindowEvent" handler="exitForm"/> + </Events> + <AuxValues> + <AuxValue name="FormSettings_generateMnemonicsCode" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_listenerGenerationStyle" type="java.lang.Integer" value="0"/> + <AuxValue name="FormSettings_variablesLocal" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_variablesModifier" type="java.lang.Integer" value="2"/> + <AuxValue name="designerSize" type="java.awt.Dimension" value="-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,1,-85,0,0,2,0"/> + </AuxValues> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + <SubComponents> + <Container class="javax.swing.JPanel" name="mainPanel"> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout" value="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription"> + <BorderConstraints direction="Center"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + <SubComponents> + <Container class="javax.swing.JPanel" name="guiPanel"> + <Properties> + <Property name="border" type="javax.swing.border.Border" editor="org.netbeans.modules.form.editors2.BorderEditor"> + <Border info="org.netbeans.modules.form.compat2.border.LineBorderInfo"> + <LineBorder/> + </Border> + </Property> + </Properties> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout" value="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription"> + <BorderConstraints direction="North"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBoxLayout"/> + <SubComponents> + <Container class="javax.swing.JPanel" name="densityPanel"> + <Properties> + <Property name="border" type="javax.swing.border.Border" editor="org.netbeans.modules.form.editors2.BorderEditor"> + <Border info="org.netbeans.modules.form.compat2.border.TitledBorderInfo"> + <TitledBorder title="Density"/> + </Border> + </Property> + </Properties> + <AccessibilityProperties> + <Property name="AccessibleContext.accessibleName" type="java.lang.String" value="ShaderAttributeValue 
"/> + </AccessibilityProperties> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout"/> + <SubComponents> + <Component class="javax.swing.JRadioButton" name="zeroButton"> + <Properties> + <Property name="buttonGroup" type="javax.swing.ButtonGroup" editor="org.netbeans.modules.form.RADComponent$ButtonGroupPropertyEditor"> + <ComponentRef name="densityButtonGroup"/> + </Property> + <Property name="text" type="java.lang.String" value="Zero"/> + </Properties> + <Events> + <EventHandler event="actionPerformed" listener="java.awt.event.ActionListener" parameters="java.awt.event.ActionEvent" handler="zeroButtonActionPerformed"/> + </Events> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout" value="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription"> + <GridBagConstraints gridX="-1" gridY="-1" gridWidth="1" gridHeight="1" fill="2" ipadX="0" ipadY="0" insetsTop="0" insetsLeft="0" insetsBottom="0" insetsRight="0" anchor="10" weightX="0.0" weightY="0.0"/> + </Constraint> + </Constraints> + </Component> + <Component class="javax.swing.JRadioButton" name="halfButton"> + <Properties> + <Property name="buttonGroup" type="javax.swing.ButtonGroup" editor="org.netbeans.modules.form.RADComponent$ButtonGroupPropertyEditor"> + <ComponentRef name="densityButtonGroup"/> + </Property> + <Property name="text" type="java.lang.String" value="Half"/> + </Properties> + <Events> + <EventHandler event="actionPerformed" listener="java.awt.event.ActionListener" parameters="java.awt.event.ActionEvent" handler="halfButtonActionPerformed"/> + </Events> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout" value="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription"> + <GridBagConstraints gridX="0" gridY="1" gridWidth="1" gridHeight="1" fill="2" ipadX="0" ipadY="0" insetsTop="0" insetsLeft="0" insetsBottom="0" insetsRight="0" anchor="10" weightX="0.0" weightY="0.0"/> + </Constraint> + </Constraints> + </Component> + <Component class="javax.swing.JRadioButton" name="fullButton"> + <Properties> + <Property name="buttonGroup" type="javax.swing.ButtonGroup" editor="org.netbeans.modules.form.RADComponent$ButtonGroupPropertyEditor"> + <ComponentRef name="densityButtonGroup"/> + </Property> + <Property name="selected" type="boolean" value="true"/> + <Property name="text" type="java.lang.String" value="Full"/> + </Properties> + <Events> + <EventHandler event="actionPerformed" listener="java.awt.event.ActionListener" parameters="java.awt.event.ActionEvent" handler="fullButtonActionPerformed"/> + </Events> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout" value="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription"> + <GridBagConstraints gridX="0" gridY="2" gridWidth="1" gridHeight="1" fill="2" ipadX="0" ipadY="0" insetsTop="0" insetsLeft="0" insetsBottom="0" insetsRight="0" anchor="10" weightX="0.0" weightY="0.0"/> + </Constraint> + </Constraints> + </Component> + </SubComponents> + </Container> + <Container class="javax.swing.JPanel" name="colorPanel"> + <Properties> + <Property name="border" type="javax.swing.border.Border" editor="org.netbeans.modules.form.editors2.BorderEditor"> + <Border info="org.netbeans.modules.form.compat2.border.TitledBorderInfo"> + <TitledBorder title="Color"/> + </Border> + </Property> + </Properties> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout"/> + <SubComponents> + <Component class="javax.swing.JRadioButton" name="goldButton"> + <Properties> + <Property name="buttonGroup" type="javax.swing.ButtonGroup" editor="org.netbeans.modules.form.RADComponent$ButtonGroupPropertyEditor"> + <ComponentRef name="colorButtonGroup"/> + </Property> + <Property name="selected" type="boolean" value="true"/> + <Property name="text" type="java.lang.String" value="Gold"/> + </Properties> + <Events> + <EventHandler event="actionPerformed" listener="java.awt.event.ActionListener" parameters="java.awt.event.ActionEvent" handler="goldButtonActionPerformed"/> + </Events> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout" value="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription"> + <GridBagConstraints gridX="-1" gridY="-1" gridWidth="1" gridHeight="1" fill="2" ipadX="0" ipadY="0" insetsTop="0" insetsLeft="0" insetsBottom="0" insetsRight="0" anchor="10" weightX="0.0" weightY="0.0"/> + </Constraint> + </Constraints> + </Component> + <Component class="javax.swing.JRadioButton" name="silverButton"> + <Properties> + <Property name="buttonGroup" type="javax.swing.ButtonGroup" editor="org.netbeans.modules.form.RADComponent$ButtonGroupPropertyEditor"> + <ComponentRef name="colorButtonGroup"/> + </Property> + <Property name="text" type="java.lang.String" value="Silver"/> + </Properties> + <Events> + <EventHandler event="actionPerformed" listener="java.awt.event.ActionListener" parameters="java.awt.event.ActionEvent" handler="silverButtonActionPerformed"/> + </Events> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout" value="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription"> + <GridBagConstraints gridX="0" gridY="1" gridWidth="1" gridHeight="1" fill="2" ipadX="0" ipadY="0" insetsTop="0" insetsLeft="0" insetsBottom="0" insetsRight="0" anchor="10" weightX="0.0" weightY="0.0"/> + </Constraint> + </Constraints> + </Component> + </SubComponents> + </Container> + <Container class="javax.swing.JPanel" name="sceneGraphPanel"> + <Properties> + <Property name="border" type="javax.swing.border.Border" editor="org.netbeans.modules.form.editors2.BorderEditor"> + <Border info="org.netbeans.modules.form.compat2.border.TitledBorderInfo"> + <TitledBorder title="Scene Graph"/> + </Border> + </Property> + </Properties> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout"/> + <SubComponents> + <Component class="javax.swing.JToggleButton" name="DetachButton"> + <Properties> + <Property name="buttonGroup" type="javax.swing.ButtonGroup" editor="org.netbeans.modules.form.RADComponent$ButtonGroupPropertyEditor"> + <ComponentRef name="sceneGraphButtonGroup"/> + </Property> + <Property name="selected" type="boolean" value="true"/> + <Property name="text" type="java.lang.String" value="Detach"/> + </Properties> + <Events> + <EventHandler event="actionPerformed" listener="java.awt.event.ActionListener" parameters="java.awt.event.ActionEvent" handler="DetachButtonActionPerformed"/> + </Events> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout" value="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription"> + <GridBagConstraints gridX="-1" gridY="-1" gridWidth="1" gridHeight="1" fill="2" ipadX="0" ipadY="0" insetsTop="0" insetsLeft="0" insetsBottom="0" insetsRight="0" anchor="10" weightX="0.0" weightY="0.0"/> + </Constraint> + </Constraints> + </Component> + <Component class="javax.swing.JToggleButton" name="AttachButton"> + <Properties> + <Property name="buttonGroup" type="javax.swing.ButtonGroup" editor="org.netbeans.modules.form.RADComponent$ButtonGroupPropertyEditor"> + <ComponentRef name="sceneGraphButtonGroup"/> + </Property> + <Property name="text" type="java.lang.String" value="Create"/> + </Properties> + <Events> + <EventHandler event="actionPerformed" listener="java.awt.event.ActionListener" parameters="java.awt.event.ActionEvent" handler="AttachButtonActionPerformed"/> + </Events> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout" value="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription"> + <GridBagConstraints gridX="0" gridY="1" gridWidth="1" gridHeight="1" fill="2" ipadX="0" ipadY="0" insetsTop="0" insetsLeft="0" insetsBottom="0" insetsRight="0" anchor="10" weightX="0.0" weightY="0.0"/> + </Constraint> + </Constraints> + </Component> + <Component class="javax.swing.JButton" name="replaceSPButton"> + <Properties> + <Property name="text" type="java.lang.String" value="Replace Shader"/> + <Property name="enabled" type="boolean" value="false"/> + </Properties> + <Events> + <EventHandler event="actionPerformed" listener="java.awt.event.ActionListener" parameters="java.awt.event.ActionEvent" handler="replaceSPButtonActionPerformed"/> + </Events> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout" value="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription"> + <GridBagConstraints gridX="0" gridY="2" gridWidth="1" gridHeight="1" fill="2" ipadX="0" ipadY="0" insetsTop="0" insetsLeft="0" insetsBottom="0" insetsRight="0" anchor="10" weightX="0.0" weightY="0.0"/> + </Constraint> + </Constraints> + </Component> + </SubComponents> + </Container> + </SubComponents> + </Container> + <Container class="javax.swing.JPanel" name="drawingPanel"> + <Properties> + <Property name="preferredSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor"> + <Dimension value="[500, 500]"/> + </Property> + </Properties> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout" value="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription"> + <BorderConstraints direction="Center"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + </Container> + </SubComponents> + </Container> + </SubComponents> +</Form> diff --git a/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/ShaderTestGLSL.java b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/ShaderTestGLSL.java new file mode 100644 index 0000000..ac0282e --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/ShaderTestGLSL.java @@ -0,0 +1,727 @@ +/* + * Copyright (c) 2016 JogAmp Community. All rights reserved. + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * This code is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 only, as + * published by the Free Software Foundation. Sun designates this + * particular file as subject to the "Classpath" exception as provided + * by Sun in the LICENSE file that accompanied this code. + * + * This code is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + * version 2 for more details (a copy is included in the LICENSE file that + * accompanied this code). + * + * You should have received a copy of the GNU General Public License version + * 2 along with this work; if not, write to the Free Software Foundation, + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. + * + */ + +package org.jdesktop.j3d.examples.gl2es2pipeline; + +import java.awt.GraphicsConfiguration; +import java.io.File; +import java.io.IOException; + +import javax.swing.JOptionPane; + +import org.jogamp.java3d.Alpha; +import org.jogamp.java3d.Background; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.GLSLShaderProgram; +import org.jogamp.java3d.Material; +import org.jogamp.java3d.PositionInterpolator; +import org.jogamp.java3d.Shader; +import org.jogamp.java3d.ShaderAppearance; +import org.jogamp.java3d.ShaderAttributeObject; +import org.jogamp.java3d.ShaderAttributeSet; +import org.jogamp.java3d.ShaderAttributeValue; +import org.jogamp.java3d.ShaderError; +import org.jogamp.java3d.ShaderErrorListener; +import org.jogamp.java3d.ShaderProgram; +import org.jogamp.java3d.Shape3D; +import org.jogamp.java3d.SourceCodeShader; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.utils.geometry.Sphere; +import org.jogamp.java3d.utils.shader.StringIO; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.java3d.utils.universe.ViewingPlatform; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Point3f; +import org.jogamp.vecmath.Vector3d; + +public class ShaderTestGLSL extends javax.swing.JFrame +{ + + static final int GOLD = 1; + static final int SILVER = 2; + + static final int DIMPLE_SHADER = 1; + static final int BRICK_SHADER = 2; + static final int WOOD_SHADER = 3; + static final int POLKADOT3D_SHADER = 4; + + static final String[] shaderAttrNames1 = { "Density", "Size", "LightPosition", "Color" }; + + static final String[] shaderAttrNames2 = { "BrickColor", "LightPosition" }; + + private SimpleUniverse univ = null; + //private View view; + //private BranchGroup transpObj; + private BranchGroup scene = null; + private int shaderSelected = DIMPLE_SHADER; + private float density = 16.0f; + private int color = GOLD; + + private Color3f eColor = new Color3f(0.2f, 0.2f, 0.2f); + private Color3f sColor = new Color3f(0.8f, 0.8f, 0.8f); + private Color3f objColor = new Color3f(0.6f, 0.6f, 0.6f); + private Color3f bgColor = new Color3f(0.05f, 0.05f, 0.2f); + private Color3f gold = new Color3f(0.7f, 0.6f, 0.18f); + private Color3f silver = new Color3f(0.75f, 0.75f, 0.75f); + + // Handlers for doing update + private ShaderAppearance sApp1 = null; + private ShaderAppearance sApp2 = null; + private ShaderAppearance sApp3 = null; + private ShaderAppearance sApp4 = null; + private ShaderProgram sp1 = null; + private ShaderProgram sp2 = null; + private ShaderProgram sp3 = null; + private ShaderProgram sp4 = null; + private ShaderAttributeSet sas1 = null; + private ShaderAttributeSet sas2 = null; + private ShaderAttributeObject sao1 = null; + private ShaderAttributeObject sao2 = null; + private Sphere sphere = null; + private Shape3D s3d = null; + + private Material createMaterial() + { + Material m; + m = new Material(objColor, eColor, objColor, sColor, 100.0f); + m.setLightingEnable(true); + return m; + } + + private static ShaderProgram createGLSLShaderProgram(int index) + { + String vertexProgram = null; + String fragmentProgram = null; + + try + { + switch (index) + { + case DIMPLE_SHADER: + vertexProgram = StringIO.readFully( + new File(System.getProperty("user.dir") + "/src/classes/org/jdesktop/j3d/examples/gl2es2pipeline/dimple.vert")); + fragmentProgram = StringIO.readFully( + new File(System.getProperty("user.dir") + "/src/classes/org/jdesktop/j3d/examples/gl2es2pipeline/dimple.frag")); + break; + case BRICK_SHADER: + vertexProgram = StringIO.readFully( + new File(System.getProperty("user.dir") + "/src/classes/org/jdesktop/j3d/examples/gl2es2pipeline/aabrick.vert")); + fragmentProgram = StringIO.readFully( + new File(System.getProperty("user.dir") + "/src/classes/org/jdesktop/j3d/examples/gl2es2pipeline/aabrick.frag")); + break; + case WOOD_SHADER: + vertexProgram = StringIO.readFully( + new File(System.getProperty("user.dir") + "/src/classes/org/jdesktop/j3d/examples/gl2es2pipeline/wood.vert")); + fragmentProgram = StringIO.readFully( + new File(System.getProperty("user.dir") + "/src/classes/org/jdesktop/j3d/examples/gl2es2pipeline/wood.frag")); + break; + case POLKADOT3D_SHADER: + vertexProgram = StringIO.readFully( + new File(System.getProperty("user.dir") + "/src/classes/org/jdesktop/j3d/examples/gl2es2pipeline/polkadot3d.vert")); + fragmentProgram = StringIO.readFully( + new File(System.getProperty("user.dir") + "/src/classes/org/jdesktop/j3d/examples/gl2es2pipeline/polkadot3d.frag")); + break; + default: + } + } + catch (IOException e) + { + throw new RuntimeException(e); + } + Shader[] shaders = new Shader[2]; + shaders[0] = new SourceCodeShader(Shader.SHADING_LANGUAGE_GLSL, Shader.SHADER_TYPE_VERTEX, vertexProgram); + shaders[1] = new SourceCodeShader(Shader.SHADING_LANGUAGE_GLSL, Shader.SHADER_TYPE_FRAGMENT, fragmentProgram); + ShaderProgram shaderProgram = new GLSLShaderProgram(); + shaderProgram.setShaders(shaders); + return shaderProgram; + } + + private ShaderAttributeSet createShaderAttributeSet(int index) + { + ShaderAttributeSet shaderAttributeSet = new ShaderAttributeSet(); + ShaderAttributeObject shaderAttribute = null; + + switch (index) + { + case DIMPLE_SHADER: + // "Density", "Size", "Scale", "Color", "LightPosition" + shaderAttribute = new ShaderAttributeValue("Size", new Float(0.25)); + shaderAttributeSet.put(shaderAttribute); + shaderAttribute = new ShaderAttributeValue("LightPosition", new Point3f(0.0f, 0.0f, 0.5f)); + shaderAttributeSet.put(shaderAttribute); + + sao1 = new ShaderAttributeValue("Density", new Float(density)); + sao1.setCapability(ShaderAttributeObject.ALLOW_VALUE_READ); + sao1.setCapability(ShaderAttributeObject.ALLOW_VALUE_WRITE); + shaderAttributeSet.put(sao1); + + if (color == GOLD) + { + sao2 = new ShaderAttributeValue("Color", gold); + } + else if (color == SILVER) + { + sao2 = new ShaderAttributeValue("Color", silver); + } + sao2.setCapability(ShaderAttributeObject.ALLOW_VALUE_READ); + sao2.setCapability(ShaderAttributeObject.ALLOW_VALUE_WRITE); + shaderAttributeSet.put(sao2); + break; + + case BRICK_SHADER: + // "BrickColor", "LightPosition" + shaderAttribute = new ShaderAttributeValue("BrickColor", new Color3f(1.0f, 0.3f, 0.2f)); + shaderAttributeSet.put(shaderAttribute); + shaderAttribute = new ShaderAttributeValue("LightPosition", new Point3f(0.0f, 0.0f, 0.5f)); + shaderAttributeSet.put(shaderAttribute); + break; + default: + assert false; + } + return shaderAttributeSet; + } + + private ShaderAppearance createShaderAppearance() + { + ShaderAppearance sApp = new ShaderAppearance(); + sApp.setMaterial(createMaterial()); + return sApp; + } + + private BranchGroup createSubSceneGraph() + { + // Create the sub-root of the branch graph + BranchGroup subRoot = new BranchGroup(); + + // + // Create 1 spheres with a GLSLShader and add it into the scene graph. + // + sApp1 = createShaderAppearance(); + sApp1.setCapability(ShaderAppearance.ALLOW_SHADER_PROGRAM_READ); + sApp1.setCapability(ShaderAppearance.ALLOW_SHADER_PROGRAM_WRITE); + sApp1.setCapability(ShaderAppearance.ALLOW_SHADER_ATTRIBUTE_SET_READ); + sApp1.setCapability(ShaderAppearance.ALLOW_SHADER_ATTRIBUTE_SET_WRITE); + + sp1 = createGLSLShaderProgram(1); + sp1.setShaderAttrNames(shaderAttrNames1); + sas1 = createShaderAttributeSet(1); + sas1.setCapability(ShaderAttributeSet.ALLOW_ATTRIBUTES_READ); + sas1.setCapability(ShaderAttributeSet.ALLOW_ATTRIBUTES_WRITE); + sApp1.setShaderProgram(sp1); + sApp1.setShaderAttributeSet(sas1); + + // Setup Brick shader + sp2 = createGLSLShaderProgram(2); + sp2.setShaderAttrNames(shaderAttrNames2); + sas2 = createShaderAttributeSet(2); + sApp2 = createShaderAppearance(); + sApp2.setShaderProgram(sp2); + sApp2.setShaderAttributeSet(sas2); + + // Setup Wood shader + sp3 = createGLSLShaderProgram(3); + sApp3 = createShaderAppearance(); + sApp3.setShaderProgram(sp3); + + // Setup Polkadot3d shader + sp4 = createGLSLShaderProgram(4); + sApp4 = createShaderAppearance(); + sApp4.setShaderProgram(sp4); + + sphere = new Sphere(1.5f, Sphere.GENERATE_NORMALS, 200, null); + SphereGLSL.makeNIO(sphere); + s3d = sphere.getShape(); + s3d.setCapability(Shape3D.ALLOW_APPEARANCE_READ); + s3d.setCapability(Shape3D.ALLOW_APPEARANCE_WRITE); + s3d.setAppearance(sApp1); + + TransformGroup objTG; + Transform3D t = new Transform3D(); + t.set(new Vector3d(0.0, 0.0, 0.0)); + objTG = new TransformGroup(t); + objTG.addChild(sphere); + subRoot.addChild(objTG); + + return subRoot; + } + + + private BranchGroup createSceneGraph(int selectedScene) + { + // Create the root of the branch graph + BranchGroup objRoot = new BranchGroup(); + objRoot.setCapability(BranchGroup.ALLOW_DETACH); + + // Create a Transformgroup to scale all objects so they + // appear in the scene. + TransformGroup objScale = new TransformGroup(); + Transform3D t3d = new Transform3D(); + t3d.setScale(0.4); + objScale.setTransform(t3d); + objRoot.addChild(objScale); + + // Create a bounds for the background and lights + BoundingSphere bounds = new BoundingSphere(new Point3d(0.0, 0.0, 0.0), 100.0); + + // Set up the background + Background bg = new Background(bgColor); + bg.setApplicationBounds(bounds); + objScale.addChild(bg); + + objScale.addChild(createSubSceneGraph()); + + // Create a position interpolator and attach it to the view + // platform + TransformGroup vpTrans = univ.getViewingPlatform().getViewPlatformTransform(); + Transform3D axisOfTranslation = new Transform3D(); + Alpha transAlpha = new Alpha(-1, Alpha.INCREASING_ENABLE | Alpha.DECREASING_ENABLE, 0, 0, 5000, 0, 0, 5000, 0, 0); + axisOfTranslation.rotY(-Math.PI / 2.0); + PositionInterpolator translator = new PositionInterpolator(transAlpha, vpTrans, axisOfTranslation, 2.0f, 3.5f); + translator.setSchedulingBounds(bounds); + objScale.addChild(translator); + + // Let Java 3D perform optimizations on this scene graph. + objRoot.compile(); + + return objRoot; + } + + private Canvas3D initScene() + { + GraphicsConfiguration config = SimpleUniverse.getPreferredConfiguration(); + + Canvas3D c = new Canvas3D(config); + + univ = new SimpleUniverse(c); + + // Add a ShaderErrorListener + univ.addShaderErrorListener(new ShaderErrorListener() { + @Override + public void errorOccurred(ShaderError error) + { + error.printVerbose(); + JOptionPane.showMessageDialog(ShaderTestGLSL.this, error.toString(), "ShaderError", JOptionPane.ERROR_MESSAGE); + } + }); + + ViewingPlatform viewingPlatform = univ.getViewingPlatform(); + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + viewingPlatform.setNominalViewingTransform(); + + //view = univ.getViewer().getView(); + + return c; + } + + /** + * Creates new form ShaderTestGLSL + */ + public ShaderTestGLSL() + { + // Initialize the GUI components + initComponents(); + + // Create the scene and add the Canvas3D to the drawing panel + Canvas3D c = initScene(); + drawingPanel.add(c, java.awt.BorderLayout.CENTER); + } + + // ---------------------------------------------------------------- + + /** This method is called from within the constructor to + * initialize the form. + * WARNING: Do NOT modify this code. The content of this method is + * always regenerated by the Form Editor. + */ + // <editor-fold defaultstate="collapsed" desc=" Generated Code ">//GEN-BEGIN:initComponents + private void initComponents() + { + java.awt.GridBagConstraints gridBagConstraints; + + densityButtonGroup = new javax.swing.ButtonGroup(); + colorButtonGroup = new javax.swing.ButtonGroup(); + sceneGraphButtonGroup = new javax.swing.ButtonGroup(); + mainPanel = new javax.swing.JPanel(); + guiPanel = new javax.swing.JPanel(); + densityPanel = new javax.swing.JPanel(); + zeroButton = new javax.swing.JRadioButton(); + halfButton = new javax.swing.JRadioButton(); + fullButton = new javax.swing.JRadioButton(); + colorPanel = new javax.swing.JPanel(); + goldButton = new javax.swing.JRadioButton(); + silverButton = new javax.swing.JRadioButton(); + sceneGraphPanel = new javax.swing.JPanel(); + DetachButton = new javax.swing.JToggleButton(); + AttachButton = new javax.swing.JToggleButton(); + replaceSPButton = new javax.swing.JButton(); + drawingPanel = new javax.swing.JPanel(); + jMenuBar1 = new javax.swing.JMenuBar(); + fileMenu = new javax.swing.JMenu(); + exitMenuItem = new javax.swing.JMenuItem(); + + setTitle("Window Title"); + addWindowListener(new java.awt.event.WindowAdapter() { + @Override + public void windowClosing(java.awt.event.WindowEvent evt) + { + exitForm(evt); + } + }); + + mainPanel.setLayout(new java.awt.BorderLayout()); + + guiPanel.setLayout(new javax.swing.BoxLayout(guiPanel, javax.swing.BoxLayout.X_AXIS)); + + guiPanel.setBorder(new javax.swing.border.LineBorder(new java.awt.Color(0, 0, 0))); + densityPanel.setLayout(new java.awt.GridBagLayout()); + + densityPanel.setBorder(new javax.swing.border.TitledBorder("Density")); + densityButtonGroup.add(zeroButton); + zeroButton.setText("Zero"); + zeroButton.addActionListener(new java.awt.event.ActionListener() { + @Override + public void actionPerformed(java.awt.event.ActionEvent evt) + { + zeroButtonActionPerformed(evt); + } + }); + + gridBagConstraints = new java.awt.GridBagConstraints(); + gridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL; + densityPanel.add(zeroButton, gridBagConstraints); + + densityButtonGroup.add(halfButton); + halfButton.setText("Half"); + halfButton.addActionListener(new java.awt.event.ActionListener() { + @Override + public void actionPerformed(java.awt.event.ActionEvent evt) + { + halfButtonActionPerformed(evt); + } + }); + + gridBagConstraints = new java.awt.GridBagConstraints(); + gridBagConstraints.gridx = 0; + gridBagConstraints.gridy = 1; + gridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL; + densityPanel.add(halfButton, gridBagConstraints); + + densityButtonGroup.add(fullButton); + fullButton.setSelected(true); + fullButton.setText("Full"); + fullButton.addActionListener(new java.awt.event.ActionListener() { + @Override + public void actionPerformed(java.awt.event.ActionEvent evt) + { + fullButtonActionPerformed(evt); + } + }); + + gridBagConstraints = new java.awt.GridBagConstraints(); + gridBagConstraints.gridx = 0; + gridBagConstraints.gridy = 2; + gridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL; + densityPanel.add(fullButton, gridBagConstraints); + + guiPanel.add(densityPanel); + densityPanel.getAccessibleContext().setAccessibleName("ShaderAttributeValue \n"); + + colorPanel.setLayout(new java.awt.GridBagLayout()); + + colorPanel.setBorder(new javax.swing.border.TitledBorder("Color")); + colorButtonGroup.add(goldButton); + goldButton.setSelected(true); + goldButton.setText("Gold"); + goldButton.addActionListener(new java.awt.event.ActionListener() { + @Override + public void actionPerformed(java.awt.event.ActionEvent evt) + { + goldButtonActionPerformed(evt); + } + }); + + gridBagConstraints = new java.awt.GridBagConstraints(); + gridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL; + colorPanel.add(goldButton, gridBagConstraints); + + colorButtonGroup.add(silverButton); + silverButton.setText("Silver"); + silverButton.addActionListener(new java.awt.event.ActionListener() { + @Override + public void actionPerformed(java.awt.event.ActionEvent evt) + { + silverButtonActionPerformed(evt); + } + }); + + gridBagConstraints = new java.awt.GridBagConstraints(); + gridBagConstraints.gridx = 0; + gridBagConstraints.gridy = 1; + gridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL; + colorPanel.add(silverButton, gridBagConstraints); + + guiPanel.add(colorPanel); + + sceneGraphPanel.setLayout(new java.awt.GridBagLayout()); + + sceneGraphPanel.setBorder(new javax.swing.border.TitledBorder("Scene Graph")); + sceneGraphButtonGroup.add(DetachButton); + DetachButton.setSelected(true); + DetachButton.setText("Detach"); + DetachButton.addActionListener(new java.awt.event.ActionListener() { + @Override + public void actionPerformed(java.awt.event.ActionEvent evt) + { + DetachButtonActionPerformed(evt); + } + }); + + gridBagConstraints = new java.awt.GridBagConstraints(); + gridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL; + sceneGraphPanel.add(DetachButton, gridBagConstraints); + + sceneGraphButtonGroup.add(AttachButton); + AttachButton.setText("Create"); + AttachButton.addActionListener(new java.awt.event.ActionListener() { + @Override + public void actionPerformed(java.awt.event.ActionEvent evt) + { + AttachButtonActionPerformed(evt); + } + }); + + gridBagConstraints = new java.awt.GridBagConstraints(); + gridBagConstraints.gridx = 0; + gridBagConstraints.gridy = 1; + gridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL; + sceneGraphPanel.add(AttachButton, gridBagConstraints); + + replaceSPButton.setText("Replace Shader"); + replaceSPButton.setEnabled(false); + replaceSPButton.addActionListener(new java.awt.event.ActionListener() { + @Override + public void actionPerformed(java.awt.event.ActionEvent evt) + { + replaceSPButtonActionPerformed(evt); + } + }); + + gridBagConstraints = new java.awt.GridBagConstraints(); + gridBagConstraints.gridx = 0; + gridBagConstraints.gridy = 2; + gridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL; + sceneGraphPanel.add(replaceSPButton, gridBagConstraints); + + guiPanel.add(sceneGraphPanel); + + mainPanel.add(guiPanel, java.awt.BorderLayout.NORTH); + + drawingPanel.setLayout(new java.awt.BorderLayout()); + + drawingPanel.setPreferredSize(new java.awt.Dimension(500, 500)); + mainPanel.add(drawingPanel, java.awt.BorderLayout.CENTER); + + getContentPane().add(mainPanel, java.awt.BorderLayout.CENTER); + + fileMenu.setText("File"); + exitMenuItem.setText("Exit"); + exitMenuItem.addActionListener(new java.awt.event.ActionListener() { + @Override + public void actionPerformed(java.awt.event.ActionEvent evt) + { + exitMenuItemActionPerformed(evt); + } + }); + + fileMenu.add(exitMenuItem); + + jMenuBar1.add(fileMenu); + + setJMenuBar(jMenuBar1); + + pack(); + } + // </editor-fold>//GEN-END:initComponents + + private void silverButtonActionPerformed(java.awt.event.ActionEvent evt) + {//GEN-FIRST:event_silverButtonActionPerformed + color = SILVER; + if (scene != null) + { + sao2.setValue(silver); + } + }//GEN-LAST:event_silverButtonActionPerformed + + private void goldButtonActionPerformed(java.awt.event.ActionEvent evt) + {//GEN-FIRST:event_goldButtonActionPerformed + color = GOLD; + if (scene != null) + { + sao2.setValue(gold); + } + }//GEN-LAST:event_goldButtonActionPerformed + + private void replaceSPButtonActionPerformed(java.awt.event.ActionEvent evt) + {//GEN-FIRST:event_replaceSPButtonActionPerformed + if (shaderSelected != DIMPLE_SHADER) + { + goldButton.setEnabled(false); + silverButton.setEnabled(false); + zeroButton.setEnabled(false); + halfButton.setEnabled(false); + fullButton.setEnabled(false); + } + + switch (shaderSelected) + { + case DIMPLE_SHADER: + s3d.setAppearance(sApp1); + goldButton.setEnabled(true); + silverButton.setEnabled(true); + zeroButton.setEnabled(true); + halfButton.setEnabled(true); + fullButton.setEnabled(true); + shaderSelected = BRICK_SHADER; + break; + case BRICK_SHADER: + s3d.setAppearance(sApp2); + shaderSelected = WOOD_SHADER; + break; + case WOOD_SHADER: + s3d.setAppearance(sApp3); + shaderSelected = POLKADOT3D_SHADER; + break; + case POLKADOT3D_SHADER: + s3d.setAppearance(sApp4); + shaderSelected = DIMPLE_SHADER; + break; + default: + assert false; + } + + }//GEN-LAST:event_replaceSPButtonActionPerformed + + private void fullButtonActionPerformed(java.awt.event.ActionEvent evt) + {//GEN-FIRST:event_fullButtonActionPerformed + density = 16.0f; + if (scene != null) + { + sao1.setValue(new Float(density)); + } + }//GEN-LAST:event_fullButtonActionPerformed + + private void DetachButtonActionPerformed(java.awt.event.ActionEvent evt) + {//GEN-FIRST:event_DetachButtonActionPerformed + if (scene != null) + { + scene.detach(); + scene = null; + replaceSPButton.setEnabled(false); + goldButton.setEnabled(true); + silverButton.setEnabled(true); + zeroButton.setEnabled(true); + halfButton.setEnabled(true); + fullButton.setEnabled(true); + shaderSelected = DIMPLE_SHADER; + } + }//GEN-LAST:event_DetachButtonActionPerformed + + private void AttachButtonActionPerformed(java.awt.event.ActionEvent evt) + {//GEN-FIRST:event_AttachButtonActionPerformed + if (scene == null) + { + scene = createSceneGraph(1); + univ.addBranchGraph(scene); + replaceSPButton.setEnabled(true); + shaderSelected = BRICK_SHADER; + } + }//GEN-LAST:event_AttachButtonActionPerformed + + private void halfButtonActionPerformed(java.awt.event.ActionEvent evt) + {//GEN-FIRST:event_halfButtonActionPerformed + density = 8.0f; + if (scene != null) + { + sao1.setValue(new Float(density)); + } + }//GEN-LAST:event_halfButtonActionPerformed + + private void zeroButtonActionPerformed(java.awt.event.ActionEvent evt) + {//GEN-FIRST:event_zeroButtonActionPerformed + density = 0.0f; + if (scene != null) + { + sao1.setValue(new Float(density)); + } + + }//GEN-LAST:event_zeroButtonActionPerformed + + private static void exitMenuItemActionPerformed(java.awt.event.ActionEvent evt) + {//GEN-FIRST:event_exitMenuItemActionPerformed + System.exit(0); + }//GEN-LAST:event_exitMenuItemActionPerformed + + /** Exit the Application */ + private static void exitForm(java.awt.event.WindowEvent evt) + {//GEN-FIRST:event_exitForm + System.exit(0); + }//GEN-LAST:event_exitForm + + /** + * @param args the command line arguments + */ + public static void main(String args[]) + { + System.setProperty("sun.awt.noerasebackground", "true"); + System.setProperty("j3d.rend","jogl2es2"); + new ShaderTestGLSL().setVisible(true); + } + + // Variables declaration - do not modify//GEN-BEGIN:variables + private javax.swing.JToggleButton AttachButton; + private javax.swing.JToggleButton DetachButton; + private javax.swing.ButtonGroup colorButtonGroup; + private javax.swing.JPanel colorPanel; + private javax.swing.ButtonGroup densityButtonGroup; + private javax.swing.JPanel densityPanel; + private javax.swing.JPanel drawingPanel; + private javax.swing.JMenuItem exitMenuItem; + private javax.swing.JMenu fileMenu; + private javax.swing.JRadioButton fullButton; + private javax.swing.JRadioButton goldButton; + private javax.swing.JPanel guiPanel; + private javax.swing.JRadioButton halfButton; + private javax.swing.JMenuBar jMenuBar1; + private javax.swing.JPanel mainPanel; + private javax.swing.JButton replaceSPButton; + private javax.swing.ButtonGroup sceneGraphButtonGroup; + private javax.swing.JPanel sceneGraphPanel; + private javax.swing.JRadioButton silverButton; + private javax.swing.JRadioButton zeroButton; + // End of variables declaration//GEN-END:variables + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/SimpleShaderAppearance.java b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/SimpleShaderAppearance.java new file mode 100644 index 0000000..5b7be75 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/SimpleShaderAppearance.java @@ -0,0 +1,474 @@ +/*
+ * Copyright (c) 2016 JogAmp Community. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation. Sun designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Sun in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ */
+package org.jdesktop.j3d.examples.gl2es2pipeline;
+
+import org.jogamp.java3d.ColoringAttributes;
+import org.jogamp.java3d.GLSLShaderProgram;
+import org.jogamp.java3d.LineAttributes;
+import org.jogamp.java3d.Material;
+import org.jogamp.java3d.PolygonAttributes;
+import org.jogamp.java3d.RenderingAttributes;
+import org.jogamp.java3d.Shader;
+import org.jogamp.java3d.ShaderAppearance;
+import org.jogamp.java3d.ShaderAttributeSet;
+import org.jogamp.java3d.ShaderAttributeValue;
+import org.jogamp.java3d.SourceCodeShader;
+import org.jogamp.vecmath.Color3f;
+
+/**
+ * @author phil
+ *
+ */
+public class SimpleShaderAppearance extends ShaderAppearance
+{
+ private static GLSLShaderProgram flatShaderProgram;
+ private static GLSLShaderProgram textureShaderProgram;
+ private static GLSLShaderProgram colorLineShaderProgram;
+ private static GLSLShaderProgram litFlatShaderProgram;
+ private static GLSLShaderProgram litTextureShaderProgram;
+
+ public static String alphaTestUniforms = "uniform int alphaTestEnabled;\n" + //
+ "uniform int alphaTestFunction;\n" + //
+ "uniform float alphaTestValue;\n";
+
+ public static String alphaTestMethod = "if(alphaTestEnabled != 0)\n" + //
+ "{ \n" + //
+ " if(alphaTestFunction==516)//>\n" + //
+ " if(baseMap.a<=alphaTestValue)discard;\n" + //
+ " else if(alphaTestFunction==518)//>=\n" + //
+ " if(baseMap.a<alphaTestValue)discard;\n" + //
+ " else if(alphaTestFunction==514)//==\n" + //
+ " if(baseMap.a!=alphaTestValue)discard;\n" + //
+ " else if(alphaTestFunction==517)//!=\n" + //
+ " if(baseMap.a==alphaTestValue)discard;\n" + //
+ " else if(alphaTestFunction==513)//<\n" + //
+ " if(baseMap.a>=alphaTestValue)discard;\n" + //
+ " else if(alphaTestFunction==515)//<=\n" + //
+ " if(baseMap.a>alphaTestValue)discard;\n" + //
+ " else if(alphaTestFunction==512)//never \n" + //
+ " discard; \n" + //
+ "}\n";
+
+ /**
+ * Polygons no texture, no single color, must have color vertex attribute
+ */
+ public SimpleShaderAppearance()
+ {
+ this(null, false, false);
+ }
+
+ /**
+ * Lines with a single color no texture, ignores vertex attribute of color
+ * @param color
+ */
+ public SimpleShaderAppearance(Color3f color)
+ {
+ this(color, false, false);
+ }
+
+ /**
+ * Polygons if hasTexture is true a texture otherwise vertex attribute colors for face color
+ */
+ public SimpleShaderAppearance(boolean hasTexture)
+ {
+ this(null, false, hasTexture);
+ }
+
+ public SimpleShaderAppearance(boolean lit, boolean hasTexture)
+ {
+ this(null, lit, hasTexture);
+ }
+
+ /** if color is not null then a line appearance
+ * otherwise simple poly appearance
+ * @param color
+ */
+ private SimpleShaderAppearance(Color3f color, boolean lit, boolean hasTexture)
+ {
+ if (lit)
+ {
+ String vertexProgram = "#version 120\n";
+ vertexProgram += "attribute vec4 glVertex;\n";
+ vertexProgram += "attribute vec4 glColor;\n";
+ vertexProgram += "attribute vec3 glNormal; \n";
+ if (hasTexture)
+ {
+ vertexProgram += "attribute vec2 glMultiTexCoord0;\n";
+ }
+ vertexProgram += "uniform mat4 glModelViewProjectionMatrix;\n";
+ vertexProgram += "uniform mat4 glModelViewMatrix;\n";
+ vertexProgram += "uniform mat3 glNormalMatrix;\n";
+ vertexProgram += "uniform int ignoreVertexColors;\n";
+ vertexProgram += "uniform vec4 glLightModelambient;\n";
+ vertexProgram += "struct material\n";
+ vertexProgram += "{\n";
+ vertexProgram += " int lightEnabled;\n";
+ vertexProgram += " vec4 ambient;\n";
+ vertexProgram += " vec4 diffuse;\n";
+ vertexProgram += " vec4 emission; \n";
+ vertexProgram += " vec3 specular;\n";
+ vertexProgram += " float shininess;\n";
+ vertexProgram += "};\n";
+ vertexProgram += "uniform material glFrontMaterial;\n";
+ vertexProgram += "struct lightSource\n";
+ vertexProgram += " {\n";
+ vertexProgram += " int enabled;\n";
+ vertexProgram += " vec4 position;\n";
+ vertexProgram += " vec4 diffuse;\n";
+ vertexProgram += " vec4 specular;\n";
+ vertexProgram += " float constantAttenuation, linearAttenuation, quadraticAttenuation;\n";
+ vertexProgram += " float spotCutoff, spotExponent;\n";
+ vertexProgram += " vec3 spotDirection;\n";
+ vertexProgram += " };\n";
+ vertexProgram += "\n";
+ vertexProgram += " uniform int numberOfLights;\n";
+ vertexProgram += " const int maxLights = 1;\n";
+ vertexProgram += " uniform lightSource glLightSource[maxLights];\n";
+ if (hasTexture)
+ {
+ vertexProgram += "varying vec2 glTexCoord0;\n";
+ }
+ vertexProgram += "varying vec3 LightDir;\n";
+ vertexProgram += "varying vec3 ViewDir;\n";
+ vertexProgram += "varying vec3 N;\n";
+ vertexProgram += "varying vec4 A;\n";
+ vertexProgram += "varying vec4 C;\n";
+ vertexProgram += "varying vec4 D;\n";
+ vertexProgram += "varying vec3 emissive;\n";
+ vertexProgram += "varying vec3 specular;\n";
+ vertexProgram += "varying float shininess;\n";
+ vertexProgram += "void main( void ){\n";
+ vertexProgram += "gl_Position = glModelViewProjectionMatrix * glVertex;\n";
+ if (hasTexture)
+ {
+ vertexProgram += "glTexCoord0 = glMultiTexCoord0.st;\n";
+ }
+
+ vertexProgram += "N = normalize(glNormalMatrix * glNormal);\n";
+
+ vertexProgram += "vec3 v = vec3(glModelViewMatrix * glVertex);\n";
+
+ vertexProgram += "ViewDir = -v.xyz;\n";
+ vertexProgram += "LightDir = glLightSource[0].position.xyz;\n";
+
+ vertexProgram += "A = glLightModelambient * glFrontMaterial.ambient;\n";
+ vertexProgram += "if( ignoreVertexColors != 0) \n";
+ // objectColor should be used if it is no lighting, and reusing material diffuse appears wrong
+ vertexProgram += " C = vec4(1,1,1,1);//glFrontMaterial.diffuse; \n";
+ vertexProgram += "else \n";
+ vertexProgram += " C = glColor; \n";
+
+ vertexProgram += "D = glLightSource[0].diffuse * glFrontMaterial.diffuse;\n";
+
+ vertexProgram += "emissive = glFrontMaterial.emission.rgb;\n";
+ vertexProgram += "specular = glFrontMaterial.specular;\n";
+ vertexProgram += "shininess = glFrontMaterial.shininess;\n";
+ vertexProgram += "}";
+
+ String fragmentProgram = "#version 120\n";
+ fragmentProgram += "precision mediump float;\n";
+ if (hasTexture)
+ {
+ fragmentProgram += alphaTestUniforms;
+
+ fragmentProgram += "varying vec2 glTexCoord0;\n";
+ fragmentProgram += "uniform sampler2D BaseMap;\n";
+ }
+
+ fragmentProgram += "in vec3 LightDir;\n";
+ fragmentProgram += "in vec3 ViewDir;\n";
+
+ fragmentProgram += "in vec3 N;\n";
+
+ fragmentProgram += "in vec4 A;\n";
+ fragmentProgram += "in vec4 C;\n";
+ fragmentProgram += "in vec4 D;\n";
+
+ fragmentProgram += "in vec3 emissive;\n";
+ fragmentProgram += "in vec3 specular;\n";
+ fragmentProgram += "in float shininess;\n";
+ fragmentProgram += "void main( void ){\n ";
+ if (hasTexture)
+ {
+ fragmentProgram += "vec4 baseMap = texture2D( BaseMap, glTexCoord0.st );\n";
+ }
+ if (hasTexture)
+ {
+ fragmentProgram += alphaTestMethod;
+ }
+ fragmentProgram += "vec3 normal = N;\n";
+
+ fragmentProgram += "vec3 L = normalize(LightDir);\n";
+ fragmentProgram += "vec3 E = normalize(ViewDir);\n";
+ fragmentProgram += "vec3 R = reflect(-L, normal);\n";
+ fragmentProgram += "vec3 H = normalize( L + E );\n";
+
+ fragmentProgram += "float NdotL = max( dot(normal, L), 0.0 );\n";
+ fragmentProgram += "float NdotH = max( dot(normal, H), 0.0 );\n";
+ fragmentProgram += "float EdotN = max( dot(normal, E), 0.0 );\n";
+ fragmentProgram += "float NdotNegL = max( dot(normal, -L), 0.0 );\n";
+
+ fragmentProgram += "vec4 color;\n";
+ if (hasTexture)
+ {
+ fragmentProgram += "vec3 albedo = baseMap.rgb * C.rgb;\n";
+ }
+ else
+ {
+ fragmentProgram += "vec3 albedo = C.rgb;\n";
+ }
+ fragmentProgram += "vec3 diffuse = A.rgb + (D.rgb * NdotL);\n";
+
+ // 0.3 is just what the calc is
+ fragmentProgram += "vec3 spec = specular * pow(NdotH, 0.3*shininess);\n";
+ // D is not right it should be the light source spec color, probably just 1,1,1 but java3d has no spec on lights
+ //fragmentProgram += "spec *= D.rgb;\n";
+
+ fragmentProgram += "color.rgb = albedo * (diffuse + emissive) + spec;\n";
+ if (hasTexture)
+ {
+ fragmentProgram += "color.a = C.a * baseMap.a;\n";
+ }
+ else
+ {
+ fragmentProgram += "color.a = C.a;\n";
+ }
+
+ fragmentProgram += "gl_FragColor = color;\n";
+
+ fragmentProgram += "}";
+ if (hasTexture)
+ {
+ if (litTextureShaderProgram == null)
+ {
+ litTextureShaderProgram = new GLSLShaderProgram() {
+ @Override
+ public String toString()
+ {
+ return "SimpleShaderAppearance litTextureShaderProgram";
+ }
+ };
+ litTextureShaderProgram.setShaders(makeShaders(vertexProgram, fragmentProgram));
+ litTextureShaderProgram.setShaderAttrNames(new String[] { "BaseMap" });
+
+ }
+
+ setShaderProgram(litTextureShaderProgram);
+
+ ShaderAttributeSet shaderAttributeSet = new ShaderAttributeSet();
+ shaderAttributeSet.put(new ShaderAttributeValue("BaseMap", new Integer(0)));
+ setShaderAttributeSet(shaderAttributeSet);
+ }
+ else
+ {
+ if (litFlatShaderProgram == null)
+ {
+ litFlatShaderProgram = new GLSLShaderProgram() {
+ @Override
+ public String toString()
+ {
+ return "SimpleShaderAppearance litFlatShaderProgram";
+ }
+ };
+ litFlatShaderProgram.setShaders(makeShaders(vertexProgram, fragmentProgram));
+
+ //System.out.println("vertexProgram " + vertexProgram);
+ //System.out.println("fragmentProgram " + fragmentProgram);
+
+ }
+
+ setShaderProgram(litFlatShaderProgram);
+
+ }
+ }
+ else
+ {
+ if (hasTexture)
+ {
+ if (textureShaderProgram == null)
+ {
+ textureShaderProgram = new GLSLShaderProgram() {
+ @Override
+ public String toString()
+ {
+ return "SimpleShaderAppearance textureShaderProgram";
+ }
+ };
+ String vertexProgram = "#version 120\n";
+ vertexProgram += "attribute vec4 glVertex;\n";
+ vertexProgram += "attribute vec2 glMultiTexCoord0;\n";
+ vertexProgram += "uniform mat4 glModelViewProjectionMatrix;\n";
+ vertexProgram += "varying vec2 glTexCoord0;\n";
+ vertexProgram += "void main( void ){\n";
+ vertexProgram += "gl_Position = glModelViewProjectionMatrix * glVertex;\n";
+ vertexProgram += "glTexCoord0 = glMultiTexCoord0.st;\n";
+ vertexProgram += "}";
+
+ String fragmentProgram = "#version 120\n";
+ fragmentProgram += "precision mediump float;\n";
+ fragmentProgram += alphaTestUniforms;
+ fragmentProgram += "varying vec2 glTexCoord0;\n";
+ fragmentProgram += "uniform sampler2D BaseMap;\n";
+ fragmentProgram += "void main( void ){\n ";
+ fragmentProgram += "vec4 baseMap = texture2D( BaseMap, glTexCoord0.st );\n";
+ fragmentProgram += alphaTestMethod;
+ fragmentProgram += "gl_FragColor = baseMap;\n";
+ fragmentProgram += "}";
+
+ textureShaderProgram.setShaders(makeShaders(vertexProgram, fragmentProgram));
+ textureShaderProgram.setShaderAttrNames(new String[] { "BaseMap" });
+ }
+
+ setShaderProgram(textureShaderProgram);
+
+ ShaderAttributeSet shaderAttributeSet = new ShaderAttributeSet();
+ shaderAttributeSet.put(new ShaderAttributeValue("BaseMap", new Integer(0)));
+ setShaderAttributeSet(shaderAttributeSet);
+
+ }
+ else
+
+ {
+ if (color != null)
+ {
+ PolygonAttributes polyAtt = new PolygonAttributes(PolygonAttributes.POLYGON_LINE, PolygonAttributes.CULL_NONE, 0.0f);
+ polyAtt.setPolygonOffset(0.1f);
+ setPolygonAttributes(polyAtt);
+ LineAttributes lineAtt = new LineAttributes(1, LineAttributes.PATTERN_SOLID, false);
+ setLineAttributes(lineAtt);
+
+ ColoringAttributes colorAtt = new ColoringAttributes(color, ColoringAttributes.FASTEST);
+ setColoringAttributes(colorAtt);
+
+ RenderingAttributes ra = new RenderingAttributes();
+ ra.setIgnoreVertexColors(true);
+ setRenderingAttributes(ra);
+
+ Material mat = new Material();
+ setMaterial(mat);
+
+ if (colorLineShaderProgram == null)
+ {
+ colorLineShaderProgram = new GLSLShaderProgram() {
+ @Override
+ public String toString()
+ {
+ return "SimpleShaderAppearance colorLineShaderProgram";
+ }
+ };
+ String vertexProgram = "#version 120\n";
+ vertexProgram += "attribute vec4 glVertex;\n";
+ vertexProgram += "attribute vec4 glColor;\n";
+ vertexProgram += "uniform int ignoreVertexColors;\n";
+ vertexProgram += "uniform vec4 objectColor;\n";
+ vertexProgram += "uniform mat4 glModelViewProjectionMatrix;\n";
+ vertexProgram += "varying vec4 glFrontColor;\n";
+ vertexProgram += "void main( void ){\n";
+ vertexProgram += "gl_Position = glModelViewProjectionMatrix * glVertex;\n";
+ vertexProgram += "if( ignoreVertexColors != 0 )\n";
+ vertexProgram += " glFrontColor = objectColor;\n";
+ vertexProgram += "else\n";
+ vertexProgram += " glFrontColor = glColor;\n";
+ vertexProgram += "}";
+
+ String fragmentProgram = "#version 120\n";
+ fragmentProgram += "precision mediump float;\n";
+ fragmentProgram += "varying vec4 glFrontColor;\n";
+ fragmentProgram += "void main( void ){\n";
+ fragmentProgram += "gl_FragColor = glFrontColor;\n";
+ fragmentProgram += "}";
+
+ colorLineShaderProgram.setShaders(makeShaders(vertexProgram, fragmentProgram));
+ }
+
+ setShaderProgram(colorLineShaderProgram);
+
+ }
+ else
+ {
+ RenderingAttributes ra = new RenderingAttributes();
+ setRenderingAttributes(ra);
+
+ if (flatShaderProgram == null)
+ {
+ flatShaderProgram = new GLSLShaderProgram() {
+ @Override
+ public String toString()
+ {
+ return "SimpleShaderAppearance flatShaderProgram";
+ }
+ };
+ String vertexProgram = "#version 120\n";
+ vertexProgram += "attribute vec4 glVertex;\n";
+ vertexProgram += "attribute vec4 glColor;\n";
+ vertexProgram += "uniform int ignoreVertexColors;\n";
+ vertexProgram += "uniform vec4 objectColor;\n";
+ vertexProgram += "uniform mat4 glModelViewProjectionMatrix;\n";
+ vertexProgram += "varying vec4 glFrontColor;\n";
+ vertexProgram += "void main( void ){\n";
+ vertexProgram += "gl_Position = glModelViewProjectionMatrix * glVertex;\n";
+ vertexProgram += "if( ignoreVertexColors != 0 )\n";
+ vertexProgram += " glFrontColor = objectColor;\n";
+ vertexProgram += "else\n";
+ vertexProgram += " glFrontColor = glColor;\n";
+ vertexProgram += "}";
+
+ String fragmentProgram = "#version 120\n";
+ fragmentProgram += "precision mediump float;\n";
+ fragmentProgram += "varying vec4 glFrontColor;\n";
+ fragmentProgram += "void main( void ){\n";
+ fragmentProgram += "gl_FragColor = glFrontColor;\n";
+ fragmentProgram += "}";
+
+ flatShaderProgram.setShaders(makeShaders(vertexProgram, fragmentProgram));
+
+ }
+
+ setShaderProgram(flatShaderProgram);
+
+ }
+ }
+
+ }
+
+ }
+
+ private static Shader[] makeShaders(String vertexProgram, String fragmentProgram)
+ {
+ Shader[] shaders = new Shader[2];
+ shaders[0] = new SourceCodeShader(Shader.SHADING_LANGUAGE_GLSL, Shader.SHADER_TYPE_VERTEX, vertexProgram) {
+ @Override
+ public String toString()
+ {
+ return "vertexProgram";
+ }
+ };
+ shaders[1] = new SourceCodeShader(Shader.SHADING_LANGUAGE_GLSL, Shader.SHADER_TYPE_FRAGMENT, fragmentProgram) {
+ @Override
+ public String toString()
+ {
+ return "fragmentProgram";
+ }
+ };
+ return shaders;
+ }
+}
diff --git a/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/SphereGLSL.form b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/SphereGLSL.form new file mode 100644 index 0000000..26e9b32 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/SphereGLSL.form @@ -0,0 +1,36 @@ +<?xml version="1.0" encoding="UTF-8" ?> + +<Form version="1.0" type="org.netbeans.modules.form.forminfo.JFrameFormInfo"> + <Properties> + <Property name="defaultCloseOperation" type="int" value="3"/> + <Property name="title" type="java.lang.String" value="SphereGLSL"/> + </Properties> + <SyntheticProperties> + <SyntheticProperty name="formSizePolicy" type="int" value="1"/> + </SyntheticProperties> + <AuxValues> + <AuxValue name="FormSettings_generateMnemonicsCode" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_listenerGenerationStyle" type="java.lang.Integer" value="0"/> + <AuxValue name="FormSettings_variablesLocal" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_variablesModifier" type="java.lang.Integer" value="2"/> + <AuxValue name="designerSize" type="java.awt.Dimension" value="-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,1,44,0,0,1,-112"/> + </AuxValues> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + <SubComponents> + <Container class="javax.swing.JPanel" name="drawingPanel"> + <Properties> + <Property name="preferredSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor"> + <Dimension value="[700, 700]"/> + </Property> + </Properties> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout" value="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription"> + <BorderConstraints direction="Center"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + </Container> + </SubComponents> +</Form> diff --git a/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/SphereGLSL.java b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/SphereGLSL.java new file mode 100644 index 0000000..8a59c5f --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/SphereGLSL.java @@ -0,0 +1,388 @@ +/* + * Copyright (c) 2016 JogAmp Community. All rights reserved. + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * This code is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 only, as + * published by the Free Software Foundation. Sun designates this + * particular file as subject to the "Classpath" exception as provided + * by Sun in the LICENSE file that accompanied this code. + * + * This code is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + * version 2 for more details (a copy is included in the LICENSE file that + * accompanied this code). + * + * You should have received a copy of the GNU General Public License version + * 2 along with this work; if not, write to the Free Software Foundation, + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. + * + */ + +package org.jdesktop.j3d.examples.gl2es2pipeline; + +import java.awt.GraphicsConfiguration; +import java.io.File; +import java.io.IOException; +import java.nio.ByteBuffer; +import java.nio.ByteOrder; +import java.nio.FloatBuffer; + +import javax.swing.JOptionPane; + +import org.jogamp.java3d.Alpha; +import org.jogamp.java3d.AmbientLight; +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.Background; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.ColoringAttributes; +import org.jogamp.java3d.DirectionalLight; +import org.jogamp.java3d.GLSLShaderProgram; +import org.jogamp.java3d.GeometryArray; +import org.jogamp.java3d.J3DBuffer; +import org.jogamp.java3d.Light; +import org.jogamp.java3d.Material; +import org.jogamp.java3d.PointLight; +import org.jogamp.java3d.PositionInterpolator; +import org.jogamp.java3d.RotationInterpolator; +import org.jogamp.java3d.Shader; +import org.jogamp.java3d.ShaderAppearance; +import org.jogamp.java3d.ShaderError; +import org.jogamp.java3d.ShaderErrorListener; +import org.jogamp.java3d.ShaderProgram; +import org.jogamp.java3d.SourceCodeShader; +import org.jogamp.java3d.SpotLight; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.TriangleStripArray; +import org.jogamp.java3d.utils.geometry.Sphere; +import org.jogamp.java3d.utils.shader.StringIO; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Point3f; +import org.jogamp.vecmath.Vector3d; +import org.jogamp.vecmath.Vector3f; + +/** + * Simple Java 3D example program with programmable shader. + */ +public class SphereGLSL extends javax.swing.JFrame +{ + + // Constants for type of light to use + private static final int DIRECTIONAL_LIGHT = 0; + private static final int POINT_LIGHT = 1; + private static final int SPOT_LIGHT = 2; + + // Flag indicates type of lights: directional, point, or spot + // lights. This flag is set based on command line argument + private static int lightType = POINT_LIGHT;//DIRECTIONAL_LIGHT; + private SimpleUniverse univ = null; + private BranchGroup scene = null; + + public BranchGroup createSceneGraph() + { + Color3f eColor = new Color3f(0.0f, 0.0f, 0.0f); + Color3f sColor = new Color3f(1.0f, 1.0f, 1.0f); + Color3f objColor = new Color3f(0.6f, 0.6f, 0.6f); + Color3f lColor1 = new Color3f(1.0f, 0.0f, 0.0f); + Color3f lColor2 = new Color3f(0.0f, 1.0f, 0.0f); + Color3f alColor = new Color3f(0.2f, 0.2f, 0.2f); + Color3f bgColor = new Color3f(0.05f, 0.05f, 0.2f); + + Transform3D t; + + // Create the root of the branch graph + BranchGroup objRoot = new BranchGroup(); + + // Create a Transformgroup to scale all objects so they + // appear in the scene. + TransformGroup objScale = new TransformGroup(); + Transform3D t3d = new Transform3D(); + t3d.setScale(0.4); + objScale.setTransform(t3d); + objRoot.addChild(objScale); + + // Create a bounds for the background and lights + BoundingSphere bounds = new BoundingSphere(new Point3d(0.0, 0.0, 0.0), 100.0); + + // Set up the background + Background bg = new Background(bgColor); + bg.setApplicationBounds(bounds); + objScale.addChild(bg); + + // Create a Sphere object, generate one copy of the sphere, + // and add it into the scene graph. + ShaderAppearance a = new ShaderAppearance(); + Material m = new Material(objColor, eColor, objColor, sColor, 100.0f); + m.setLightingEnable(true); + String vertexProgram = null; + String fragmentProgram = null; + try + { + vertexProgram = StringIO.readFully( + new File(System.getProperty("user.dir") + "/src/classes/org/jdesktop/j3d/examples/gl2es2pipeline/simple.vert")); + fragmentProgram = StringIO.readFully( + new File(System.getProperty("user.dir") + "/src/classes/org/jdesktop/j3d/examples/gl2es2pipeline/simple.frag")); + } + catch (IOException e) + { + throw new RuntimeException(e); + } + Shader[] shaders = new Shader[2]; + shaders[0] = new SourceCodeShader(Shader.SHADING_LANGUAGE_GLSL, Shader.SHADER_TYPE_VERTEX, vertexProgram); + shaders[1] = new SourceCodeShader(Shader.SHADING_LANGUAGE_GLSL, Shader.SHADER_TYPE_FRAGMENT, fragmentProgram); + ShaderProgram shaderProgram = new GLSLShaderProgram(); + shaderProgram.setShaders(shaders); + + a.setShaderProgram(shaderProgram); + a.setMaterial(m); + Sphere sph = new Sphere(1.0f, Sphere.GENERATE_NORMALS, 200, a); + makeNIO(sph); + objScale.addChild(sph); + + // Create the transform group node for the each light and initialize + // it to the identity. Enable the TRANSFORM_WRITE capability so that + // our behavior code can modify it at runtime. Add them to the root + // of the subgraph. + TransformGroup l1RotTrans = new TransformGroup(); + l1RotTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + objScale.addChild(l1RotTrans); + + TransformGroup l2RotTrans = new TransformGroup(); + l2RotTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + objScale.addChild(l2RotTrans); + + // Create transformations for the positional lights + t = new Transform3D(); + Vector3d lPos1 = new Vector3d(0.0, 0.0, 2.0); + t.set(lPos1); + TransformGroup l1Trans = new TransformGroup(t); + l1RotTrans.addChild(l1Trans); + + t = new Transform3D(); + Vector3d lPos2 = new Vector3d(0.5, 0.8, 2.0); + t.set(lPos2); + TransformGroup l2Trans = new TransformGroup(t); + l2RotTrans.addChild(l2Trans); + + // Create Geometry for point lights + ColoringAttributes caL1 = new ColoringAttributes(); + ColoringAttributes caL2 = new ColoringAttributes(); + caL1.setColor(lColor1); + caL2.setColor(lColor2); + + Appearance appL1 = new SimpleShaderAppearance(false, false); + Appearance appL2 = new SimpleShaderAppearance(false, false); + appL1.setColoringAttributes(caL1); + appL2.setColoringAttributes(caL2); + + Sphere sph2 = new Sphere(0.05f, appL1); + makeNIO(sph2); + + l1Trans.addChild(sph2); + Sphere sph3 = new Sphere(0.05f, appL2); + makeNIO(sph3); + + l2Trans.addChild(sph3); + + // Create lights + AmbientLight aLgt = new AmbientLight(alColor); + + Light lgt1 = null; + Light lgt2 = null; + + Point3f lPoint = new Point3f(0.0f, 0.0f, 0.0f); + Point3f atten = new Point3f(1.0f, 0.0f, 0.0f); + Vector3f lDirect1 = new Vector3f(lPos1); + Vector3f lDirect2 = new Vector3f(lPos2); + lDirect1.negate(); + lDirect2.negate(); + + switch (lightType) + { + case DIRECTIONAL_LIGHT: + lgt1 = new DirectionalLight(lColor1, lDirect1); + lgt2 = new DirectionalLight(lColor2, lDirect2); + break; + case POINT_LIGHT: + lgt1 = new PointLight(lColor1, lPoint, atten); + lgt2 = new PointLight(lColor2, lPoint, atten); + break; + case SPOT_LIGHT: + lgt1 = new SpotLight(lColor1, lPoint, atten, lDirect1, 25.0f * (float) Math.PI / 180.0f, 10.0f); + lgt2 = new SpotLight(lColor2, lPoint, atten, lDirect2, 25.0f * (float) Math.PI / 180.0f, 10.0f); + break; + } + + // Set the influencing bounds + aLgt.setInfluencingBounds(bounds); + lgt1.setInfluencingBounds(bounds); + lgt2.setInfluencingBounds(bounds); + + // Add the lights into the scene graph + objScale.addChild(aLgt); + l1Trans.addChild(lgt1); + l2Trans.addChild(lgt2); + + // Create a new Behavior object that will perform the desired + // operation on the specified transform object and add it into the + // scene graph. + Transform3D yAxis = new Transform3D(); + Alpha rotor1Alpha = new Alpha(-1, Alpha.INCREASING_ENABLE, 0, 0, 4000, 0, 0, 0, 0, 0); + RotationInterpolator rotator1 = new RotationInterpolator(rotor1Alpha, l1RotTrans, yAxis, 0.0f, (float) Math.PI * 2.0f); + rotator1.setSchedulingBounds(bounds); + l1RotTrans.addChild(rotator1); + + // Create a new Behavior object that will perform the desired + // operation on the specified transform object and add it into the + // scene graph. + Alpha rotor2Alpha = new Alpha(-1, Alpha.INCREASING_ENABLE, 0, 0, 1000, 0, 0, 0, 0, 0); + RotationInterpolator rotator2 = new RotationInterpolator(rotor2Alpha, l2RotTrans, yAxis, 0.0f, 0.0f); + bounds = new BoundingSphere(new Point3d(0.0, 0.0, 0.0), 100.0); + rotator2.setSchedulingBounds(bounds); + l2RotTrans.addChild(rotator2); + + // Create a position interpolator and attach it to the view + // platform + TransformGroup vpTrans = univ.getViewingPlatform().getViewPlatformTransform(); + Transform3D axisOfTranslation = new Transform3D(); + Alpha transAlpha = new Alpha(-1, Alpha.INCREASING_ENABLE | Alpha.DECREASING_ENABLE, 0, 0, 5000, 0, 0, 5000, 0, 0); + axisOfTranslation.rotY(-Math.PI / 2.0); + PositionInterpolator translator = new PositionInterpolator(transAlpha, vpTrans, axisOfTranslation, 2.0f, 3.5f); + translator.setSchedulingBounds(bounds); + objScale.addChild(translator); + + // Let Java 3D perform optimizations on this scene graph. + objRoot.compile(); + + return objRoot; + } + + private Canvas3D createUniverse() + { + // Get the preferred graphics configuration for the default screen + GraphicsConfiguration config = SimpleUniverse.getPreferredConfiguration(); + + // Create a Canvas3D using the preferred configuration + Canvas3D canvas3d = new Canvas3D(config); + + // Create simple universe with view branch + univ = new SimpleUniverse(canvas3d); + //BoundingSphere bounds = new BoundingSphere(new Point3d(0.0, 0.0, 0.0), 100.0); + + // Add a ShaderErrorListener + univ.addShaderErrorListener(new ShaderErrorListener() { + @Override + public void errorOccurred(ShaderError error) + { + error.printVerbose(); + JOptionPane.showMessageDialog(SphereGLSL.this, error.toString(), "ShaderError", JOptionPane.ERROR_MESSAGE); + } + }); + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + univ.getViewingPlatform().setNominalViewingTransform(); + + // Ensure at least 5 msec per frame (i.e., < 200Hz) + univ.getViewer().getView().setMinimumFrameCycleTime(5); + + return canvas3d; + } + + /** + * Creates new form SphereGLSL + */ + public SphereGLSL() + { + + // Initialize the GUI components + initComponents(); + + // Create Canvas3D and SimpleUniverse; add canvas to drawing panel + Canvas3D c = createUniverse(); + drawingPanel.add(c, java.awt.BorderLayout.CENTER); + + // Create the content branch and add it to the universe + scene = createSceneGraph(); + univ.addBranchGraph(scene); + } + + // ---------------------------------------------------------------- + + /** This method is called from within the constructor to + * initialize the form. + * WARNING: Do NOT modify this code. The content of this method is + * always regenerated by the Form Editor. + */ + // <editor-fold defaultstate="collapsed" desc=" Generated Code ">//GEN-BEGIN:initComponents + private void initComponents() + { + drawingPanel = new javax.swing.JPanel(); + + setDefaultCloseOperation(javax.swing.WindowConstants.EXIT_ON_CLOSE); + setTitle("SphereGLSL"); + drawingPanel.setLayout(new java.awt.BorderLayout()); + + drawingPanel.setPreferredSize(new java.awt.Dimension(700, 700)); + getContentPane().add(drawingPanel, java.awt.BorderLayout.CENTER); + + pack(); + }// </editor-fold>//GEN-END:initComponents + + /** + * @param args the command line arguments + */ + public static void main(final String args[]) + { + System.setProperty("sun.awt.noerasebackground", "true"); + System.setProperty("j3d.rend", "jogl2es2"); + java.awt.EventQueue.invokeLater(new Runnable() { + @Override + public void run() + { + SphereGLSL sphereGLSL = new SphereGLSL(); + sphereGLSL.setVisible(true); + } + }); + } + + // Variables declaration - do not modify//GEN-BEGIN:variables + private javax.swing.JPanel drawingPanel; + + // End of variables declaration//GEN-END:variables + public static void makeNIO(Sphere sph) + { + //Make it NIO + TriangleStripArray geo = (TriangleStripArray) sph.getShape().getGeometry(); + int[] stripVertexCounts = new int[geo.getNumStrips()]; + geo.getStripVertexCounts(stripVertexCounts); + TriangleStripArray newGeo = new TriangleStripArray(geo.getVertexCount(), GeometryArray.COORDINATES | GeometryArray.NORMALS + //| GeometryArray.TEXTURE_COORDINATE_2 + | GeometryArray.USE_NIO_BUFFER | GeometryArray.BY_REFERENCE, stripVertexCounts); + + float[] coords = new float[geo.getValidVertexCount() * 3]; + geo.getCoordinates(0, coords); + newGeo.setCoordRefBuffer(new J3DBuffer(makeFloatBuffer(coords))); + float[] norms = new float[geo.getValidVertexCount() * 3]; + geo.getNormals(0, norms); + newGeo.setNormalRefBuffer(new J3DBuffer(makeFloatBuffer(norms))); + sph.getShape().setGeometry(newGeo); + + } + + private static FloatBuffer makeFloatBuffer(float[] arr) + { + ByteBuffer bb = ByteBuffer.allocateDirect(arr.length * 4); + bb.order(ByteOrder.nativeOrder()); + FloatBuffer fb = bb.asFloatBuffer(); + fb.put(arr); + fb.position(0); + return fb; + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/VertexAttrTestGLSL.form b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/VertexAttrTestGLSL.form new file mode 100644 index 0000000..6e31a8f --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/VertexAttrTestGLSL.form @@ -0,0 +1,203 @@ +<?xml version="1.0" encoding="UTF-8" ?> + +<Form version="1.0" type="org.netbeans.modules.form.forminfo.JFrameFormInfo"> + <NonVisualComponents> + <Menu class="javax.swing.JMenuBar" name="jMenuBar1"> + <SubComponents> + <Menu class="javax.swing.JMenu" name="fileMenu"> + <Properties> + <Property name="text" type="java.lang.String" value="File"/> + </Properties> + <SubComponents> + <MenuItem class="javax.swing.JMenuItem" name="exitMenuItem"> + <Properties> + <Property name="text" type="java.lang.String" value="Exit"/> + </Properties> + <Events> + <EventHandler event="actionPerformed" listener="java.awt.event.ActionListener" parameters="java.awt.event.ActionEvent" handler="exitMenuItemActionPerformed"/> + </Events> + </MenuItem> + </SubComponents> + </Menu> + </SubComponents> + </Menu> + </NonVisualComponents> + <Properties> + <Property name="title" type="java.lang.String" value="VertexAttrTestGLSL"/> + </Properties> + <SyntheticProperties> + <SyntheticProperty name="menuBar" type="java.lang.String" value="jMenuBar1"/> + <SyntheticProperty name="formSizePolicy" type="int" value="1"/> + </SyntheticProperties> + <Events> + <EventHandler event="windowClosing" listener="java.awt.event.WindowListener" parameters="java.awt.event.WindowEvent" handler="exitForm"/> + </Events> + <AuxValues> + <AuxValue name="FormSettings_generateMnemonicsCode" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_listenerGenerationStyle" type="java.lang.Integer" value="0"/> + <AuxValue name="FormSettings_variablesLocal" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_variablesModifier" type="java.lang.Integer" value="2"/> + <AuxValue name="designerSize" type="java.awt.Dimension" value="-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,1,44,0,0,1,-112"/> + </AuxValues> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + <SubComponents> + <Container class="javax.swing.JPanel" name="mainPanel"> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout" value="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription"> + <BorderConstraints direction="Center"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + <SubComponents> + <Container class="javax.swing.JPanel" name="guiPanel"> + <Properties> + <Property name="border" type="javax.swing.border.Border" editor="org.netbeans.modules.form.editors2.BorderEditor"> + <Border info="org.netbeans.modules.form.compat2.border.LineBorderInfo"> + <LineBorder/> + </Border> + </Property> + </Properties> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout" value="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription"> + <BorderConstraints direction="North"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout"/> + <SubComponents> + <Container class="javax.swing.JPanel" name="vertexCheckBoxPanel"> + <Properties> + <Property name="border" type="javax.swing.border.Border" editor="org.netbeans.modules.form.editors2.BorderEditor"> + <Border info="org.netbeans.modules.form.compat2.border.TitledBorderInfo"> + <TitledBorder title="vertexFormat"> + <Font PropertyName="font" name="Lucida Sans" size="10" style="0"/> + </TitledBorder> + </Border> + </Property> + </Properties> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout" value="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription"> + <GridBagConstraints gridX="-1" gridY="0" gridWidth="1" gridHeight="1" fill="0" ipadX="0" ipadY="0" insetsTop="2" insetsLeft="2" insetsBottom="2" insetsRight="2" anchor="10" weightX="0.0" weightY="0.0"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout"/> + <SubComponents> + <Container class="javax.swing.JPanel" name="jPanel1"> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout" value="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription"> + <GridBagConstraints gridX="-1" gridY="-1" gridWidth="1" gridHeight="1" fill="0" ipadX="0" ipadY="0" insetsTop="0" insetsLeft="0" insetsBottom="0" insetsRight="0" anchor="11" weightX="0.0" weightY="0.0"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout"/> + <SubComponents> + <Component class="javax.swing.JSeparator" name="jSeparator1"> + <Properties> + <Property name="preferredSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor"> + <Dimension value="[0, 4]"/> + </Property> + </Properties> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout" value="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription"> + <GridBagConstraints gridX="0" gridY="1" gridWidth="1" gridHeight="1" fill="0" ipadX="0" ipadY="0" insetsTop="0" insetsLeft="0" insetsBottom="0" insetsRight="0" anchor="10" weightX="0.0" weightY="0.0"/> + </Constraint> + </Constraints> + </Component> + <Component class="javax.swing.JSeparator" name="jSeparator2"> + <Properties> + <Property name="preferredSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor"> + <Dimension value="[0, 4]"/> + </Property> + </Properties> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout" value="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription"> + <GridBagConstraints gridX="0" gridY="3" gridWidth="1" gridHeight="1" fill="0" ipadX="0" ipadY="0" insetsTop="0" insetsLeft="0" insetsBottom="0" insetsRight="0" anchor="10" weightX="0.0" weightY="0.0"/> + </Constraint> + </Constraints> + </Component> + </SubComponents> + </Container> + <Container class="javax.swing.JPanel" name="jPanel2"> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout" value="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription"> + <GridBagConstraints gridX="-1" gridY="-1" gridWidth="1" gridHeight="1" fill="0" ipadX="0" ipadY="0" insetsTop="0" insetsLeft="0" insetsBottom="0" insetsRight="0" anchor="11" weightX="0.0" weightY="0.0"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout"/> + <SubComponents> + <Component class="javax.swing.JCheckBox" name="vertexAttrsBox"> + <Properties> + <Property name="selected" type="boolean" value="true"/> + <Property name="text" type="java.lang.String" value="VertexAttrs"/> + </Properties> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout" value="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription"> + <GridBagConstraints gridX="0" gridY="4" gridWidth="1" gridHeight="1" fill="2" ipadX="0" ipadY="0" insetsTop="0" insetsLeft="0" insetsBottom="0" insetsRight="0" anchor="10" weightX="0.0" weightY="0.0"/> + </Constraint> + </Constraints> + </Component> + </SubComponents> + </Container> + </SubComponents> + </Container> + <Container class="javax.swing.JPanel" name="geometryPanel"> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout" value="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription"> + <GridBagConstraints gridX="-1" gridY="0" gridWidth="1" gridHeight="1" fill="0" ipadX="0" ipadY="0" insetsTop="2" insetsLeft="2" insetsBottom="2" insetsRight="2" anchor="10" weightX="0.0" weightY="0.0"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout"/> + <SubComponents> + <Component class="javax.swing.JButton" name="createButton"> + <Properties> + <Property name="text" type="java.lang.String" value="Create Geometry"/> + </Properties> + <Events> + <EventHandler event="actionPerformed" listener="java.awt.event.ActionListener" parameters="java.awt.event.ActionEvent" handler="createButtonActionPerformed"/> + </Events> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout" value="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription"> + <GridBagConstraints gridX="-1" gridY="-1" gridWidth="1" gridHeight="1" fill="2" ipadX="0" ipadY="0" insetsTop="0" insetsLeft="0" insetsBottom="0" insetsRight="0" anchor="10" weightX="0.0" weightY="0.0"/> + </Constraint> + </Constraints> + </Component> + <Component class="javax.swing.JButton" name="destroyButton"> + <Properties> + <Property name="text" type="java.lang.String" value="Destroy Geometry"/> + </Properties> + <Events> + <EventHandler event="actionPerformed" listener="java.awt.event.ActionListener" parameters="java.awt.event.ActionEvent" handler="destroyButtonActionPerformed"/> + </Events> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout" value="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription"> + <GridBagConstraints gridX="0" gridY="-1" gridWidth="1" gridHeight="1" fill="2" ipadX="0" ipadY="0" insetsTop="0" insetsLeft="0" insetsBottom="2" insetsRight="0" anchor="10" weightX="0.0" weightY="0.0"/> + </Constraint> + </Constraints> + </Component> + </SubComponents> + </Container> + </SubComponents> + </Container> + <Container class="javax.swing.JPanel" name="drawingPanel"> + <Properties> + <Property name="preferredSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor"> + <Dimension value="[500, 500]"/> + </Property> + </Properties> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout" value="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription"> + <BorderConstraints direction="Center"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + </Container> + </SubComponents> + </Container> + </SubComponents> +</Form> diff --git a/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/VertexAttrTestGLSL.java b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/VertexAttrTestGLSL.java new file mode 100644 index 0000000..f80ac11 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/VertexAttrTestGLSL.java @@ -0,0 +1,435 @@ +/* + * Copyright (c) 2016 JogAmp Community. All rights reserved. + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * This code is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 only, as + * published by the Free Software Foundation. Sun designates this + * particular file as subject to the "Classpath" exception as provided + * by Sun in the LICENSE file that accompanied this code. + * + * This code is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + * version 2 for more details (a copy is included in the LICENSE file that + * accompanied this code). + * + * You should have received a copy of the GNU General Public License version + * 2 along with this work; if not, write to the Free Software Foundation, + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. + * + */ + +package org.jdesktop.j3d.examples.gl2es2pipeline; + +import java.awt.GraphicsConfiguration; +import java.io.File; +import java.io.IOException; +import java.nio.ByteBuffer; +import java.nio.ByteOrder; +import java.nio.FloatBuffer; + +import javax.swing.JFrame; +import javax.swing.JOptionPane; + +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.Background; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.GLSLShaderProgram; +import org.jogamp.java3d.GeometryArray; +import org.jogamp.java3d.J3DBuffer; +import org.jogamp.java3d.Shader; +import org.jogamp.java3d.ShaderAppearance; +import org.jogamp.java3d.ShaderError; +import org.jogamp.java3d.ShaderErrorListener; +import org.jogamp.java3d.ShaderProgram; +import org.jogamp.java3d.Shape3D; +import org.jogamp.java3d.SourceCodeShader; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.TriangleArray; +import org.jogamp.java3d.utils.shader.StringIO; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.java3d.utils.universe.ViewingPlatform; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3d; + +public class VertexAttrTestGLSL extends javax.swing.JFrame +{ + + SimpleUniverse univ = null; + BranchGroup scene = null; + + public BranchGroup createSceneGraph(boolean hasVertexAttrs) + { + + // Bounds for BG and behavior + BoundingSphere bounds = new BoundingSphere(new Point3d(0.0, 0.0, 0.0), 100.0); + + // Create the root of the branch graph + BranchGroup objRoot = new BranchGroup(); + objRoot.setCapability(BranchGroup.ALLOW_DETACH); + + // Set up the background + Color3f bgColor = new Color3f(0.1f, 0.1f, 0.1f); + Background bg = new Background(bgColor); + bg.setApplicationBounds(bounds); + objRoot.addChild(bg); + + // Create the TransformGroup node and initialize it to the + // identity. Enable the TRANSFORM_WRITE capability so that + // our behavior code can modify it at run time. Add it to + // the root of the subgraph. + TransformGroup objTrans = new TransformGroup(); + objTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + objRoot.addChild(objTrans); + + // Create a simple Shape3D node; add it to the scene graph. + objTrans.addChild(new MyShape(this, hasVertexAttrs)); + + return objRoot; + } + + private Canvas3D initScene() + { + GraphicsConfiguration config = SimpleUniverse.getPreferredConfiguration(); + + Canvas3D c = new Canvas3D(config); + univ = new SimpleUniverse(c); + + // Add a ShaderErrorListener + univ.addShaderErrorListener(new ShaderErrorListener() { + @Override + public void errorOccurred(ShaderError error) + { + error.printVerbose(); + JOptionPane.showMessageDialog(VertexAttrTestGLSL.this, error.toString(), "ShaderError", JOptionPane.ERROR_MESSAGE); + } + }); + + ViewingPlatform viewingPlatform = univ.getViewingPlatform(); + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + viewingPlatform.setNominalViewingTransform(); + + return c; + } + + /** + * Creates new form VertexAttrTestGLSL + */ + public VertexAttrTestGLSL() + { + // Initialize the GUI components + initComponents(); + + // Create the scene and add the Canvas3D to the drawing panel + Canvas3D c = initScene(); + drawingPanel.add(c, java.awt.BorderLayout.CENTER); + } + + static class MyShape extends Shape3D + { + + // Coordinate data + private static final float[] coords = { 0.0f, 0.0f, 0.0f, 0.5f, 0.0f, 0.0f, 0.0f, 0.5f, 0.0f, }; + + private static final int[] sizes = { 1, 3 }; + private static final float[] weights = { 0.45f, 0.15f, 0.95f, }; + private static final float[] temps = { 1.0f, 0.5f, 0.5f, 0.5f, 1.0f, 0.5f, 0.5f, 0.5f, 1.0f, }; + + private static final String[] vaNames = { "weight", "temperature" }; + + J3DBuffer createDirectFloatBuffer(float[] arr) + { + ByteOrder order = ByteOrder.nativeOrder(); + + FloatBuffer nioBuf = ByteBuffer.allocateDirect(arr.length * 4).order(order).asFloatBuffer(); + nioBuf.put(arr); + return new J3DBuffer(nioBuf); + } + + MyShape(JFrame frame, boolean hasVertexAttrs) + { + + int vertexFormat = GeometryArray.COORDINATES; + int vertexAttrCount = 0; + int[] vertexAttrSizes = null; + String[] vertexAttrNames = null; + String[] shaderAttrNames = null; + + if (hasVertexAttrs) + { + vertexFormat |= GeometryArray.VERTEX_ATTRIBUTES; + vertexAttrCount = vaNames.length; + vertexAttrSizes = sizes; + vertexAttrNames = vaNames; + } + + //GL2ES2: requires by reference + vertexFormat |= GeometryArray.BY_REFERENCE; + + TriangleArray tri = new TriangleArray(6, vertexFormat, 0, null, vertexAttrCount, vertexAttrSizes); + tri.setValidVertexCount(3); + //tri.setCoordinates(0, coords); + tri.setCoordRefFloat(coords); + + if (hasVertexAttrs) + { + //tri.setVertexAttrs(0, 0, weights); + //tri.setVertexAttrs(1, 0, temps); + + tri.setVertexAttrRefFloat(0, weights); + tri.setVertexAttrRefFloat(1, temps); + + String vertexProgram = null; + String fragmentProgram = null; + try + { + vertexProgram = StringIO.readFully(new File( + System.getProperty("user.dir") + "/src/classes/org/jdesktop/j3d/examples/gl2es2pipeline/vertexshader.vert")); + fragmentProgram = StringIO.readFully(new File( + System.getProperty("user.dir") + "/src/classes/org/jdesktop/j3d/examples/gl2es2pipeline/vertexshader.frag")); + } + catch (IOException e) + { + throw new RuntimeException(e); + } + + Shader[] shaders = new Shader[2]; + shaders[0] = new SourceCodeShader(Shader.SHADING_LANGUAGE_GLSL, Shader.SHADER_TYPE_VERTEX, vertexProgram); + shaders[1] = new SourceCodeShader(Shader.SHADING_LANGUAGE_GLSL, Shader.SHADER_TYPE_FRAGMENT, fragmentProgram); + + ShaderProgram shaderProgram = new GLSLShaderProgram(); + shaderProgram.setShaders(shaders); + shaderProgram.setVertexAttrNames(vertexAttrNames); + shaderProgram.setShaderAttrNames(shaderAttrNames); + + ShaderAppearance app = new ShaderAppearance(); + app.setShaderProgram(shaderProgram); + + this.setGeometry(tri); + + this.setAppearance(app); + } + else + { + this.setGeometry(tri); + this.setAppearance(new Appearance()); + } + } + } + + // ---------------------------------------------------------------- + + /** This method is called from within the constructor to + * initialize the form. + * WARNING: Do NOT modify this code. The content of this method is + * always regenerated by the Form Editor. + */ + // <editor-fold defaultstate="collapsed" desc=" Generated Code ">//GEN-BEGIN:initComponents + private void initComponents() + { + java.awt.GridBagConstraints gridBagConstraints; + + mainPanel = new javax.swing.JPanel(); + guiPanel = new javax.swing.JPanel(); + vertexCheckBoxPanel = new javax.swing.JPanel(); + jPanel1 = new javax.swing.JPanel(); + jSeparator1 = new javax.swing.JSeparator(); + jSeparator2 = new javax.swing.JSeparator(); + jPanel2 = new javax.swing.JPanel(); + vertexAttrsBox = new javax.swing.JCheckBox(); + geometryPanel = new javax.swing.JPanel(); + createButton = new javax.swing.JButton(); + destroyButton = new javax.swing.JButton(); + drawingPanel = new javax.swing.JPanel(); + jMenuBar1 = new javax.swing.JMenuBar(); + fileMenu = new javax.swing.JMenu(); + exitMenuItem = new javax.swing.JMenuItem(); + + setTitle("VertexAttrTestGLSL"); + addWindowListener(new java.awt.event.WindowAdapter() { + @Override + public void windowClosing(java.awt.event.WindowEvent evt) + { + exitForm(evt); + } + }); + + mainPanel.setLayout(new java.awt.BorderLayout()); + + guiPanel.setLayout(new java.awt.GridBagLayout()); + + guiPanel.setBorder(javax.swing.BorderFactory.createLineBorder(new java.awt.Color(0, 0, 0))); + vertexCheckBoxPanel.setLayout(new java.awt.GridBagLayout()); + + vertexCheckBoxPanel.setBorder( + javax.swing.BorderFactory.createTitledBorder(null, "vertexFormat", javax.swing.border.TitledBorder.DEFAULT_JUSTIFICATION, + javax.swing.border.TitledBorder.DEFAULT_POSITION, new java.awt.Font("Lucida Sans", 0, 10))); + jPanel1.setLayout(new java.awt.GridBagLayout()); + + jSeparator1.setPreferredSize(new java.awt.Dimension(0, 4)); + gridBagConstraints = new java.awt.GridBagConstraints(); + gridBagConstraints.gridx = 0; + gridBagConstraints.gridy = 1; + jPanel1.add(jSeparator1, gridBagConstraints); + + jSeparator2.setPreferredSize(new java.awt.Dimension(0, 4)); + gridBagConstraints = new java.awt.GridBagConstraints(); + gridBagConstraints.gridx = 0; + gridBagConstraints.gridy = 3; + jPanel1.add(jSeparator2, gridBagConstraints); + + gridBagConstraints = new java.awt.GridBagConstraints(); + gridBagConstraints.anchor = java.awt.GridBagConstraints.NORTH; + vertexCheckBoxPanel.add(jPanel1, gridBagConstraints); + + jPanel2.setLayout(new java.awt.GridBagLayout()); + + vertexAttrsBox.setSelected(true); + vertexAttrsBox.setText("VertexAttrs"); + gridBagConstraints = new java.awt.GridBagConstraints(); + gridBagConstraints.gridx = 0; + gridBagConstraints.gridy = 4; + gridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL; + jPanel2.add(vertexAttrsBox, gridBagConstraints); + + gridBagConstraints = new java.awt.GridBagConstraints(); + gridBagConstraints.anchor = java.awt.GridBagConstraints.NORTH; + vertexCheckBoxPanel.add(jPanel2, gridBagConstraints); + + gridBagConstraints = new java.awt.GridBagConstraints(); + gridBagConstraints.gridy = 0; + gridBagConstraints.insets = new java.awt.Insets(2, 2, 2, 2); + guiPanel.add(vertexCheckBoxPanel, gridBagConstraints); + + geometryPanel.setLayout(new java.awt.GridBagLayout()); + + createButton.setText("Create Geometry"); + createButton.addActionListener(new java.awt.event.ActionListener() { + @Override + public void actionPerformed(java.awt.event.ActionEvent evt) + { + createButtonActionPerformed(evt); + } + }); + + gridBagConstraints = new java.awt.GridBagConstraints(); + gridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL; + geometryPanel.add(createButton, gridBagConstraints); + + destroyButton.setText("Destroy Geometry"); + destroyButton.addActionListener(new java.awt.event.ActionListener() { + @Override + public void actionPerformed(java.awt.event.ActionEvent evt) + { + destroyButtonActionPerformed(evt); + } + }); + + gridBagConstraints = new java.awt.GridBagConstraints(); + gridBagConstraints.gridx = 0; + gridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL; + gridBagConstraints.insets = new java.awt.Insets(0, 0, 2, 0); + geometryPanel.add(destroyButton, gridBagConstraints); + + gridBagConstraints = new java.awt.GridBagConstraints(); + gridBagConstraints.gridy = 0; + gridBagConstraints.insets = new java.awt.Insets(2, 2, 2, 2); + guiPanel.add(geometryPanel, gridBagConstraints); + + mainPanel.add(guiPanel, java.awt.BorderLayout.NORTH); + + drawingPanel.setLayout(new java.awt.BorderLayout()); + + drawingPanel.setPreferredSize(new java.awt.Dimension(500, 500)); + mainPanel.add(drawingPanel, java.awt.BorderLayout.CENTER); + + getContentPane().add(mainPanel, java.awt.BorderLayout.CENTER); + + fileMenu.setText("File"); + exitMenuItem.setText("Exit"); + exitMenuItem.addActionListener(new java.awt.event.ActionListener() { + @Override + public void actionPerformed(java.awt.event.ActionEvent evt) + { + exitMenuItemActionPerformed(evt); + } + }); + + fileMenu.add(exitMenuItem); + + jMenuBar1.add(fileMenu); + + setJMenuBar(jMenuBar1); + + pack(); + }// </editor-fold>//GEN-END:initComponents + + private void destroyButtonActionPerformed(java.awt.event.ActionEvent evt) + {//GEN-FIRST:event_destroyButtonActionPerformed + if (scene != null) + { + univ.getLocale().removeBranchGraph(scene); + scene = null; + } + }//GEN-LAST:event_destroyButtonActionPerformed + + private void createButtonActionPerformed(java.awt.event.ActionEvent evt) + {//GEN-FIRST:event_createButtonActionPerformed + if (scene == null) + { + boolean hasVertexAttrs = vertexAttrsBox.isSelected(); + scene = createSceneGraph(hasVertexAttrs); + univ.addBranchGraph(scene); + } + }//GEN-LAST:event_createButtonActionPerformed + + private static void exitMenuItemActionPerformed(java.awt.event.ActionEvent evt) + {//GEN-FIRST:event_exitMenuItemActionPerformed + System.exit(0); + }//GEN-LAST:event_exitMenuItemActionPerformed + + /** Exit the Application */ + private static void exitForm(java.awt.event.WindowEvent evt) + {//GEN-FIRST:event_exitForm + System.exit(0); + }//GEN-LAST:event_exitForm + + /** + * @param args the command line arguments + */ + public static void main(String args[]) + { + System.setProperty("sun.awt.noerasebackground", "true"); + System.setProperty("j3d.rend","jogl2es2"); + java.awt.EventQueue.invokeLater(new Runnable() { + @Override + public void run() + { + new VertexAttrTestGLSL().setVisible(true); + } + }); + } + + // Variables declaration - do not modify//GEN-BEGIN:variables + private javax.swing.JButton createButton; + private javax.swing.JButton destroyButton; + private javax.swing.JPanel drawingPanel; + private javax.swing.JMenuItem exitMenuItem; + private javax.swing.JMenu fileMenu; + private javax.swing.JPanel geometryPanel; + private javax.swing.JPanel guiPanel; + private javax.swing.JMenuBar jMenuBar1; + private javax.swing.JPanel jPanel1; + private javax.swing.JPanel jPanel2; + private javax.swing.JSeparator jSeparator1; + private javax.swing.JSeparator jSeparator2; + private javax.swing.JPanel mainPanel; + private javax.swing.JCheckBox vertexAttrsBox; + private javax.swing.JPanel vertexCheckBoxPanel; + // End of variables declaration//GEN-END:variables + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/aabrick.frag b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/aabrick.frag new file mode 100644 index 0000000..030b811 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/aabrick.frag @@ -0,0 +1,56 @@ +// +// Fragment shader for antialiased procedural bricks +// +// Authors: Dave Baldwin, Randi Rost +// based on a shader by Darwyn Peachey +// +// Copyright (c) 2002-2004 3Dlabs Inc. Ltd. +// +// See 3Dlabs-License.txt for license information +// + +uniform vec3 BrickColor; +//uniform vec3 MortarColor; +//uniform vec2 BrickSize; +//uniform vec2 BrickPct; +//uniform vec2 MortarPct; + +//const vec3 BrickColor = vec3 (1, 0.3, 0.2); +const vec3 MortarColor = vec3 (0.85, 0.86, 0.84); +const vec2 BrickSize = vec2 (0.3, 0.15); +const vec2 BrickPct = vec2 (0.9, 0.85); +const vec2 MortarPct = vec2 (0.1, 0.15); + +varying vec2 MCposition; +varying float LightIntensity; + +#define Integral(x, p, notp) ((floor(x)*(p)) + max(fract(x)-(notp), 0.0)) + +void main(void) +{ + vec2 position, fw, useBrick; + vec3 color; + + // Determine position within the brick pattern + position = MCposition / BrickSize; + + // Adjust every other row by an offset of half a brick + if (fract(position.y * 0.5) > 0.5) + position.x += 0.5; + + // Calculate filter size + //fw = fwidth(position); //fwidth not implemented on WildcatVP + fw = (abs(dFdx(MCposition)) + abs(dFdy(MCposition))) / BrickSize; + + // Perform filtering by integrating the 2D pulse made by the + // brick pattern over the filter width and height + useBrick = (Integral(position + fw, BrickPct, MortarPct) - + Integral(position, BrickPct, MortarPct)) / fw; + + // Determine final color + color = mix(MortarColor, BrickColor, useBrick.x * useBrick.y); + color *= LightIntensity; + + // GL2ES2: gl_FragColor is unchanged + gl_FragColor = vec4 (color, 1.0); +} diff --git a/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/aabrick.vert b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/aabrick.vert new file mode 100644 index 0000000..9b96195 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/aabrick.vert @@ -0,0 +1,64 @@ +// +// Vertex shader for antialiased procedural bricks +// +// Authors: Dave Baldwin, Steve Koren, Randi Rost +// based on a shader by Darwyn Peachey +// +// Copyright (c) 2002-2004 3Dlabs Inc. Ltd. +// +// See 3Dlabs-License.txt for license information +// + +// GL2ES2: Java3D built-in attributes, these are calculated and passsed in if declared here +attribute vec4 glVertex; +attribute vec3 glNormal; + +// GL2ES2: Java3D built-in uniforms, these are calculated and passsed in if declared here +uniform mat4 glModelViewMatrix; +uniform mat4 glModelViewProjectionMatrix; +uniform mat3 glNormalMatrix; + + +uniform vec3 LightPosition; +//const vec3 LightPosition = vec3 (0, 4, 4); + +const float SpecularContribution = 0.3; +const float DiffuseContribution = 1.0 - SpecularContribution; + +varying float LightIntensity; +varying vec2 MCposition; + +void main(void) +{ + // GL2ES2: swap built-in variable for Java3d built-in uniforms and attributes gl_* = gl* + declaration (at top) + //vec3 ecPosition = vec3 (gl_ModelViewMatrix * gl_Vertex); + vec3 ecPosition = vec3 (glModelViewMatrix * glVertex); + // GL2ES2: swap built-in variable for Java3d built-in uniforms and attributes gl_* = gl* + declaration (at top) + //vec3 tnorm = normalize(gl_NormalMatrix * glNormal); + vec3 tnorm = normalize(glNormalMatrix * glNormal); + + + vec3 lightVec = normalize(LightPosition - ecPosition); + vec3 reflectVec = reflect(-lightVec, tnorm); + vec3 viewVec = normalize(-ecPosition); + float diffuse = max(dot(lightVec, tnorm), 0.0); + float spec = 0.0; + + if (diffuse > 0.0) + { + spec = max(dot(reflectVec, viewVec), 0.0); + spec = pow(spec, 16.0); + } + + LightIntensity = DiffuseContribution * diffuse + + SpecularContribution * spec; + + // GL2ES2: swap built-in variable for Java3d built-in uniforms and attributes gl_* = gl* + declaration (at top) + //MCposition = gl_Vertex.xy; + MCposition = glVertex.xy; + + // GL2ES2: ftransform() no longer exists, but it is simple (note use of Java3D built-in uniforms and attributes) + // GL2ES2: gl_Position is unchanged + //gl_Position = ftransform(); + gl_Position = glModelViewProjectionMatrix * glVertex; +} diff --git a/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/dimple.frag b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/dimple.frag new file mode 100644 index 0000000..b2a2ef7 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/dimple.frag @@ -0,0 +1,68 @@ + +// +// dimple.frag: Fragment shader for bump mapping dimples (bumps) +// +// author: John Kessenich +// +// Copyright (c) 2002: 3Dlabs, Inc. +// +// + +// GL2ES2: non buit-in varyings +varying vec2 glTexCoord0; +varying vec4 C; + +varying vec3 LightDir; +varying vec3 EyeDir; +varying vec3 Normal; + +//const vec3 Color = vec3(0.7, 0.6, 0.18); + +//const float Density = 16.0; +//const float Size = 0.25; + +uniform vec3 Color; +uniform float Density; +uniform float Size; +// uniform float SpecularFactor; + +//float Density = 27.6; +//float Size = 0.13025; + + +//uniform float Scale; + +const float SpecularFactor = 0.4; + +void main (void) +{ + vec3 litColor; + + // GL2ES2: non buit-in varying + vec2 c = Density * (glTexCoord0.xy); + vec2 p = fract(c) - vec2(0.5); + float d = (p.x * p.x) + (p.y * p.y); + if (d >= Size) + p = vec2(0.0); + + vec3 normDelta = vec3(-p.x, -p.y, 1.0); + + litColor = Color * max(0.0, dot(normDelta, LightDir)); + + float t = 2.0 * dot(LightDir, normDelta); + vec3 reflectDir = t * normDelta; + reflectDir = LightDir - reflectDir; + +// vec3 reflectDir = LightDir - 2.0 * dot(LightDir, normDelta) * normDelta; + + float spec = max(dot(EyeDir, reflectDir), 0.0); + spec = spec * spec; + spec = spec * spec; + spec *= SpecularFactor; + + litColor = min(litColor + spec, vec3(1.0)); + // GL2ES2: gl_FragColor is unchanged, C is a non built-in varying + gl_FragColor = vec4(litColor, C.a); +// gl_FragColor = vec4(litColor, 1.0); +// gl_FragColor = vec4(Scale); +} diff --git a/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/dimple.vert b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/dimple.vert new file mode 100644 index 0000000..ebbfdc9 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/dimple.vert @@ -0,0 +1,75 @@ +#version 120 +// +// dimple.vert: Vertex shader for bump mapping dimples (bumps) +// +// author: John Kessenich +// +// Copyright (c) 2002: 3Dlabs, Inc. +// + + +// GL2ES2: Java3D built-in attributes, these are calculated and passsed in if declared here +attribute vec4 glVertex; +attribute vec3 glNormal; +attribute vec4 glColor; + +// GL2ES2: Java3D built-in uniforms, these are calculated and passsed in if declared here +uniform mat4 glModelViewMatrix; +uniform mat4 glModelViewProjectionMatrix; +uniform mat3 glNormalMatrix; + +uniform int ignoreVertexColors; + +// GL2ES2: new output varyings, these replace gl_TexCoord[] and gl_FrontColor (along with A and D) +varying vec2 glTexCoord0; +varying vec4 C; + +varying vec3 LightDir; +varying vec3 EyeDir; +varying vec3 Normal; + +uniform vec3 LightPosition; +// uniform float Scale; +// vec3 LightPosition = vec3(0.0, 0.0, 5.0); +float Scale = 1.0; + + + +void main(void) +{ + // GL2ES2: swap built-in variable for Java3d built-in uniforms and attributes gl_* = gl* + declaration (at top) + vec4 pos = glModelViewMatrix * glVertex; + // GL2ES2: swap built-in variable for Java3d built-in uniforms and attributes gl_* = gl* + declaration (at top) + gl_Position = glModelViewProjectionMatrix * glVertex; + vec3 eyeDir = vec3(pos); + // GL2ES2: swap built-in variable for Java3d built-in uniforms and attributes gl_* = gl* + declaration (at top) + // GL2ES2: swap built-in varying for declared varying + //gl_TexCoord[0] = gl_MultiTexCoord0; + glTexCoord0 = glVertex.xy; + // GL2ES2: swap built-in variable for Java3d built-in uniforms and attributes gl_* = gl* + declaration (at top) + // GL2ES2: swap built-in varying for declared varying + //gl_FrontColor = gl_Color; + + if( ignoreVertexColors != 0) + C = vec4(1,1,1,1); + else + C = glColor; + + vec3 n = normalize(glNormalMatrix * glNormal); + vec3 t = normalize(cross(vec3(1.141, 2.78, 3.14), n)); + vec3 b = cross(n, t); + + vec3 v; + v.x = dot(LightPosition, t); + v.y = dot(LightPosition, b); + v.z = dot(LightPosition, n); + LightDir = normalize(v); + + v.x = dot(eyeDir, t); + v.y = dot(eyeDir, b); + v.z = dot(eyeDir, n); + EyeDir = normalize(v); + + + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/envmap.frag b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/envmap.frag new file mode 100644 index 0000000..3e298f8 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/envmap.frag @@ -0,0 +1,61 @@ +// +// Fragment shader for environment mapping with an +// equirectangular 2D texture +// +// Authors: John Kessenich, Randi Rost +// +// Copyright (c) 2002-2004 3Dlabs Inc. Ltd. +// +// See 3Dlabs-License.txt for license information +// + +const vec3 Xunitvec = vec3 (1.0, 0.0, 0.0); +const vec3 Yunitvec = vec3 (0.0, 1.0, 0.0); + +uniform vec3 BaseColor; +uniform float MixRatio; + +uniform sampler2D EnvMap; + +varying vec3 Normal; +varying vec3 EyeDir; +varying float LightIntensity; + +void main (void) +{ + // Compute reflection vector + vec3 reflectDir = reflect(EyeDir, Normal); + + // Compute altitude and azimuth angles + + vec2 index; + + index.y = dot(normalize(reflectDir), Yunitvec); + reflectDir.y = 0.0; + index.x = dot(normalize(reflectDir), Xunitvec) * 0.5; + + // Translate index values into proper range + + if (reflectDir.z >= 0.0) + index = (index + 1.0) * 0.5; + else + { + index.t = (index.t + 1.0) * 0.5; + index.s = (-index.s) * 0.5 + 1.0; + } + + // if reflectDir.z >= 0.0, s will go from 0.25 to 0.75 + // if reflectDir.z < 0.0, s will go from 0.75 to 1.25, and + // that's OK, because we've set the texture to wrap. + + // Do a lookup into the environment map. + + vec3 envColor = vec3 (texture2D(EnvMap, index)); + + // Add lighting to base color and mix + + vec3 base = LightIntensity * BaseColor; + envColor = mix(envColor, base, MixRatio); + + gl_FragColor = vec4 (envColor, 1.0); +} diff --git a/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/envmap.vert b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/envmap.vert new file mode 100644 index 0000000..2296c83 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/envmap.vert @@ -0,0 +1,46 @@ +// +// Vertex shader for environment mapping with an +// equirectangular 2D texture +// +// Authors: John Kessenich, Randi Rost +// +// Copyright (c) 2002-2004 3Dlabs Inc. Ltd. +// +// See 3Dlabs-License.txt for license information +// + +// GL2ES2: Java3D built-in attributes, these are calculated and passsed in if declared here +attribute vec4 glVertex; +attribute vec3 glNormal; + +// GL2ES2: Java3D built-in uniforms, these are calculated and passsed in if declared here +uniform mat4 glModelViewMatrix; +uniform mat4 glModelViewProjectionMatrix; +uniform mat3 glNormalMatrix; + + +varying vec3 Normal; +varying vec3 EyeDir; +varying float LightIntensity; + +uniform vec3 LightPos; + +void main(void) +{ + // GL2ES2: ftransform() no longer exists, but it is simple (note use of Java3D built-in uniforms and attributes) + // GL2ES2: gl_Position is unchanged + //gl_Position = ftransform(); + gl_Position = glModelViewProjectionMatrix * glVertex; + + // compute the transformed normal + // GL2ES2: swap built-in variable for Java3d built-in uniforms and attributes gl_* = gl* + declaration (at top) + //vec3 Normal = normalize(gl_NormalMatrix * gl_Normal); + Normal = normalize(glNormalMatrix * glNormal); + + // GL2ES2: swap built-in variable for Java3d built-in uniforms and attributes gl_* = gl* + declaration (at top) + //vec4 pos = gl_ModelViewMatrix * gl_Vertex; + vec4 pos = glModelViewMatrix * glVertex; + + EyeDir = pos.xyz; + LightIntensity = max(dot(normalize(LightPos - EyeDir), Normal), 0.0); +} diff --git a/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/fixed_function_shader.frag b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/fixed_function_shader.frag new file mode 100644 index 0000000..3da3ef6 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/fixed_function_shader.frag @@ -0,0 +1,108 @@ +#version 140
+
+precision mediump float;
+
+
+uniform int alphaTestEnabled;
+uniform int alphaTestFunction;
+uniform float alphaTestValue;
+
+struct fogData
+{
+ int fogEnabled;
+ vec4 expColor;
+ float expDensity;
+ vec4 linearColor;
+ float linearStart;
+ float linearEnd;
+};
+uniform fogData fogData;
+
+in vec2 glTexCoord0;
+
+uniform sampler2D BaseMap;
+
+in vec3 LightDir;
+in vec3 ViewDir;
+
+in vec3 N;
+
+in vec4 A;
+in vec4 C;
+in vec4 D;
+in vec3 S;
+in vec3 emissive;
+
+in float shininess;
+
+out vec4 glFragColor;
+
+void main( void )
+{
+ vec4 baseMap = texture( BaseMap, glTexCoord0.st );
+
+ //web says the keyword discard in a shader is bad
+ //I could just gl_FragColor=vec(0,0,0,0); return;
+ if(alphaTestEnabled != 0)
+ {
+ if(alphaTestFunction==516)//>
+ if(baseMap.a<=alphaTestValue)discard;
+ else if(alphaTestFunction==518)//>=
+ if(baseMap.a<alphaTestValue)discard;
+ else if(alphaTestFunction==514)//==
+ if(baseMap.a!=alphaTestValue)discard;
+ else if(alphaTestFunction==517)//!=
+ if(baseMap.a==alphaTestValue)discard;
+ else if(alphaTestFunction==513)//<
+ if(baseMap.a>=alphaTestValue)discard;
+ else if(alphaTestFunction==515)//<=
+ if(baseMap.a>alphaTestValue)discard;
+ else if(alphaTestFunction==512)//never
+ discard;
+ }
+
+ vec3 normal = N;
+
+ vec3 L = normalize(LightDir);
+ vec3 E = normalize(ViewDir);
+ vec3 R = reflect(-L, normal);
+ vec3 H = normalize( L + E );
+
+ float NdotL = max( dot(normal, L), 0.0 );
+ float NdotH = max( dot(normal, H), 0.0 );
+ float EdotN = max( dot(normal, E), 0.0 );
+ float NdotNegL = max( dot(normal, -L), 0.0 );
+
+ vec4 color;
+ vec3 albedo = baseMap.rgb * C.rgb;
+ vec3 diffuse = A.rgb + (D.rgb * NdotL);
+
+ // Specular
+ vec3 spec = S * pow(NdotH, 0.3*shininess);
+
+ color.rgb = albedo * (diffuse + emissive) + spec;
+ color.a = C.a * baseMap.a;
+
+ if(fogData.fogEnabled == 1)
+ {
+ //compute distance used in fog equations
+ float dist = length(ViewVec);
+ float fogFactor = 0.0;
+
+ if(fogData.linearEnd > 0.0)//linear fog
+ {
+ fogFactor = 1.0-((fogData.linearEnd - dist)/(fogData.linearEnd - fogData.linearStart));
+ fogFactor = clamp( fogFactor, 0.0, 1.0 );
+ color = mix(color, fogData.linearColor, fogFactor);
+ }
+ else if( fogData.expDensity > 0.0)// exponential fog
+ {
+ fogFactor = 1.0-(1.0 /exp(dist * fogData.expDensity));
+ fogFactor = clamp( fogFactor, 0.0, 1.0 );
+ color = mix(color, fogData.expColor, fogFactor);
+ }
+ color.a = color.a + fogFactor;
+ }
+
+ glFragColor = color;
+}
diff --git a/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/fixed_function_shader.vert b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/fixed_function_shader.vert new file mode 100644 index 0000000..354c004 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/fixed_function_shader.vert @@ -0,0 +1,142 @@ +#version 150
+
+in vec4 glVertex;
+in vec4 glColor;
+in vec3 glNormal;
+in vec2 glMultiTexCoord0;
+
+uniform mat4 glProjectionMatrix;
+//uniform mat4 glProjectionMatrixInverse;
+uniform mat4 glViewMatrix;
+uniform mat4 glModelMatrix;
+//uniform mat4 glModelViewMatrix;
+//uniform mat4 glModelViewMatrixInverse;
+//uniform mat4 glModelViewProjectionMatrix;
+
+//uniform mat3 glNormalMatrix;
+
+uniform int ignoreVertexColors;
+
+uniform vec4 glLightModelambient;
+
+struct material
+{
+ int lightEnabled;
+ vec4 ambient;
+ vec4 diffuse;
+ vec4 emission;
+ vec3 specular;
+ float shininess;
+};
+uniform material glFrontMaterial;
+
+struct lightSource
+{
+ int enabled;
+ vec4 position;
+ vec4 diffuse;
+ vec4 specular;
+ float constantAttenuation, linearAttenuation, quadraticAttenuation;
+ float spotCutoff, spotExponent;
+ vec3 spotDirection;
+};
+
+uniform int numberOfLights;// numberOfLights will be set to how many the pipeline can send
+const int maxLights = 1;// this is for the shader, it will process no more than this, must be a const
+uniform lightSource glLightSource[maxLights];
+
+uniform mat4 textureTransform;
+
+// alpha testing is normally done in frag versus the texture alpha
+//uniform int alphaTestEnabled;
+//uniform int alphaTestFunction;
+//uniform float alphaTestValue;
+
+
+// struct fogData
+// {
+// int fogEnabled = -1;
+// vec4 expColor;
+// float expDensity;
+// vec4 linearColor;
+// float linearStart;
+// float linearEnd;
+// };
+// uniform fogData fogData;
+
+
+// Fixed function pipeline pre-calculated values not available:
+// Note:
+// A,D,S = Ambient,Diffuse,Specular
+// cm, cli = glFrontMaterial, glLightSource
+
+
+// gl_LightSource[i].halfVector
+// http://stackoverflow.com/questions/3744038/what-is-half-vector-in-modern-glsl
+// vec3 ecPos = vec3(glModelViewMatrix * glVertex);
+// vec3 ecL;
+// if( glLightSource[i].position.w == 0.0)
+// ecL = vec3(glLightSource0position.xyz);// no -ecPos in case of dir lights?
+// else
+// ecL = vec3(glLightSource0position.xyz - ecPos);
+// vec3 L = normalize(ecL.xyz);
+// vec3 V = -ecPos.xyz;
+// vec3 halfVector = normalize(L + V);
+
+//gl_LightSource[i].ambient
+//use glLightModelambient
+
+// gl_FrontLightModelProduct.sceneColor
+// Derived. Ecm + Acm * Acs (Acs is normal glLightModelambient)
+// use vec4 sceneColor = glFrontMaterial.emission + glFrontMaterial.ambient * glLightModelambient;
+
+
+//gl_FrontLightProduct[i]
+//vec4 ambient; // Acm * Acli (Acli does not exist use glLightModelambient)
+//vec4 diffuse; // Dcm * Dcli
+//vec4 specular; // Scm * Scli
+// calculate yourself
+
+
+out vec2 glTexCoord0;
+
+out vec3 LightDir;
+out vec3 ViewVec;
+
+out vec3 N;
+
+out vec4 A;
+out vec4 C;
+out vec4 D;
+out vec3 S;
+out vec3 E;
+
+out float shininess;
+
+void main( void )
+{
+ mat4 glModelViewMatrix = glViewMatrix * glModelMatrix;
+ gl_Position = glProjectionMatrix * glModelViewMatrix * glVertex;//glModelViewProjectionMatrix * glVertex;
+
+ glTexCoord0 = (textureTransform * vec4(glMultiTexCoord0,0,1)).st;
+
+ mat3 glNormalMatrix = mat3(transpose(inverse(glModelViewMatrix)));
+ N = normalize(glNormalMatrix * glNormal);
+
+ vec3 v = vec3(glModelViewMatrix * glVertex);
+
+ ViewVec = -v.xyz;
+ LightDir = glLightSource[0].position.xyz;
+
+ A = glLightModelambient;
+ if( ignoreVertexColors != 0)
+ C = vec4(1,1,1,1);//glFrontMaterialdiffuse; // objectColor should be used if it is no lighting
+ else
+ C = glColor;
+ D = glLightSource[0].diffuse * glFrontMaterial.diffuse;
+ S = glLightSource[0].specular.rgb * glFrontMaterial.specular;
+ E = glFrontMaterial.emission.rgb;
+
+ shininess = glFrontMaterial.shininess;
+
+}
diff --git a/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/gouraud.frag b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/gouraud.frag new file mode 100644 index 0000000..c02a268 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/gouraud.frag @@ -0,0 +1,54 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +// Simple GLSL fragment program to add the primary and secondary (specular) colors + +//GL2ES2: varying color data needs to be defined +varying vec4 glFrontColor; +varying vec4 glFrontSecondaryColor; + +void main() +{ + gl_FragColor = glFrontColor + glFrontSecondaryColor; +} diff --git a/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/gouraud.vert b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/gouraud.vert new file mode 100644 index 0000000..771afce --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/gouraud.vert @@ -0,0 +1,158 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +// A GLSL vertex program for handling 1 directional light with specular. +// This implements per-vertex lighting (Gouraud shading). + +// GL2ES2: Java3D built-in attributes, these are calculated and passsed in if declared here +attribute vec4 glVertex; +attribute vec3 glNormal; + +// GL2ES2: Java3D built-in uniforms, these are calculated and passsed in if declared here +uniform mat4 glModelViewMatrix; +uniform mat4 glModelViewProjectionMatrix; +uniform mat3 glNormalMatrix; + + + +uniform vec4 glLightModelambient; + +struct material +{ + int lightEnabled; + vec4 ambient; + vec4 diffuse; + vec4 emission;// note vec4 extra 1.0 sent through for ease + vec3 specular; + float shininess; +}; +uniform material glFrontMaterial; + +struct lightSource +{ + int enabled; + vec4 position; + vec4 diffuse; + vec4 specular; + float constantAttenuation, linearAttenuation, quadraticAttenuation; + float spotCutoff, spotExponent; + vec3 spotDirection; +}; + +uniform int numberOfLights; +const int maxLights = 1; +uniform lightSource glLightSource[maxLights]; + +//GL2ES2: varying color data needs to be defined +varying vec4 glFrontColor; +varying vec4 glFrontSecondaryColor; + +void directionalLight0( + in vec3 normal, + inout vec4 ambient, + inout vec4 diffuse, + inout vec3 specular) +{ + // Normalized light direction and half vector + vec3 lightDirection = normalize(vec3(glLightSource[0].position)); + + //GL2ES2: half vector must be calculated + //vec3 halfVector = normalize(vec3(gl_LightSource[0].halfVector)); + //http://stackoverflow.com/questions/3744038/what-is-half-vector-in-modern-glsl + vec3 ecPos = vec3(glModelViewMatrix * glVertex); + vec3 ecL; + if( glLightSource[0].position.w == 0.0) + ecL = vec3(glLightSource[0].position.xyz);// no -ecPos in case of dir lights? + else + ecL = vec3(glLightSource[0].position.xyz - ecPos); + vec3 L = normalize(ecL.xyz); + vec3 V = -ecPos.xyz; + vec3 halfVector = normalize(L + V); + + float nDotVP; // normal . light_direction + float nDotHV; // normal . light_half_vector + float pf; // power factor + + nDotVP = max(0.0, dot(normal, lightDirection)); + nDotHV = max(0.0, dot(normal, halfVector)); + + if (nDotVP == 0.0) { + pf = 0.0; + } + else { + pf = pow(nDotHV, glFrontMaterial.shininess); + } + + ambient += glLightModelambient; + diffuse += glLightSource[0].diffuse * nDotVP; + specular += glFrontMaterial.specular * pf; +} + + +void main() +{ + vec3 tnorm = normalize(vec3(glNormalMatrix * glNormal)); + vec4 amb = vec4(0.0); + vec4 diff = vec4(0.0); + vec3 spec = vec3(0.0); + int i; + + // Transform the vertex + vec4 outPosition = glModelViewProjectionMatrix * glVertex; + + directionalLight0(tnorm, amb, diff, spec); + + //GL2ES2: sceneColor Derived. Ecm + Acm * Acs (Acs is normal glLightModelambient) + vec4 sceneColor = glFrontMaterial.emission + glFrontMaterial.ambient * glLightModelambient; + + // Apply the result of the lighting equation + vec4 outSecondaryColor = vec4(vec3(spec * glFrontMaterial.specular), 1.0); + vec4 outColor = vec4(vec3( sceneColor + + amb * glFrontMaterial.ambient + + diff * glFrontMaterial.diffuse), 1.0); + + glFrontColor = outColor; + glFrontSecondaryColor = outSecondaryColor; + gl_Position = outPosition; +} diff --git a/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/multitex.frag b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/multitex.frag new file mode 100644 index 0000000..db24f68 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/multitex.frag @@ -0,0 +1,67 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +uniform float cloudFactor; +uniform sampler2D earthTex; +uniform sampler2D cloudTex; + +uniform sampler2D EnvMap; + +varying vec2 texCoord0; +varying vec2 texCoord1; + +void main (void) +{ + vec2 tc0 = texCoord0.xy; + vec2 tc1 = texCoord1.xy; + + vec3 color0 = vec3(texture2D(cloudTex, tc0)); + vec3 color1 = vec3(texture2D(earthTex, tc1)); + vec3 finalColor = color0*cloudFactor + color1; + + gl_FragColor = vec4(finalColor, 1.0); + + // if(tc1.x > 0.0) + // gl_FragColor = vec4(tc1.y,0.0,0.0,1.0); +} diff --git a/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/multitex.vert b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/multitex.vert new file mode 100644 index 0000000..5c25c11 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/multitex.vert @@ -0,0 +1,68 @@ +// tex coord gen sample from http://www.ogre3d.org/forums/viewtopic.php?f=4&t=59737 + + + + +// GL2ES2: Java3D built-in attributes, these are calculated and passsed in if declared here +attribute vec4 glVertex; +attribute vec3 glNormal; + +// GL2ES2: Java3D built-in uniforms, these are calculated and passsed in if declared here +uniform mat4 glModelViewProjectionMatrix; +uniform mat4 glModelViewMatrix; +uniform mat3 glNormalMatrix; + +// Per-pixel normal (output to fragment shader) +varying vec3 Normal; + +varying vec2 texCoord0; +varying vec2 texCoord1; + + //Example 8-4 Sphere Map Texture Coordinate Generation + // position is the normalized position coordinate in eye space + // normal is the normalized normal coordinate in eye space + // returns a vec2 texture coordinate +vec2 sphere_map(vec3 position, vec3 normal) +{ + vec3 reflection = reflect(position, normal); + float m = 2.0 * sqrt(reflection.x * reflection.x + reflection.y * reflection.y + (reflection.z + 1.0) * (reflection.z + 1.0)); + return vec2((reflection.x / m + 0.5), (reflection.y / m + 0.5)); +} + + //Example 8-5 Cube Map Texture Coordinate Generation + + // position is the normalized position coordinate in eye space + // normal is the normalized normal coordinate in eye space + // returns the reflection vector as a vec3 texture coordinate +vec3 cube_map(vec3 position, vec3 normal) +{ + return reflect(position, normal); +} + +//Object Linear Mapping +//When the texture generation mode is set to GL_OBJECT_LINEAR, texture coordinates are generated using the following function: +//coord = P1*X + P2*Y + P3*Z + P4*W +// The X, Y, Z, and W values are the vertex coordinates from the object being textured, and the P1–P4 values are the coefficients for a plane equation. + +//For this shader in my code I have: +//Vector4f plane0S = new Vector4f(3.0f, 1.5f, 0.3f, 0.0f); //to calc coord S +//Vector4f plane0T = new Vector4f(1.0f, 2.5f, 0.24f, 0.0f); //to calc coord T +//I could hand them is as uniforms, but I choose to hard code them + + +vec2 object_linear(vec4 pos, vec4 planeOS, vec4 planeOT) +{ + return vec2(pos.x*planeOS.x+pos.y*planeOS.y+pos.z*planeOS.z+ pos.w*planeOS.w,pos.x*planeOT.x+pos.y*planeOT.y+pos.z*planeOT.z+pos.w*planeOT.w); +} + + +void main() +{ + Normal = normalize(vec3(glNormalMatrix * glNormal)); + + // Transform the vertex + gl_Position = glModelViewProjectionMatrix * glVertex; + + texCoord0 = object_linear(glVertex, vec4(3.0, 1.5, 0.3, 0.0),vec4(1.0, 2.5, 0.24, 0.0)); + texCoord1 = sphere_map(normalize(vec3(glModelViewMatrix*glVertex)), Normal); +} diff --git a/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/phong.frag b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/phong.frag new file mode 100644 index 0000000..7cb6388 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/phong.frag @@ -0,0 +1,154 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +// A GLSL fragment program for handling 1 directional light with specular. +// This implements per-pixel lighting (Phong shading) + +// GL2ES2: Java3D built-in uniforms, these are calculated and passsed in if declared here +uniform mat4 glModelViewMatrix; + + + +uniform vec4 glLightModelambient; + +struct material +{ + int lightEnabled; + vec4 ambient; + vec4 diffuse; + vec4 emission; + vec3 specular; + float shininess; +}; +uniform material glFrontMaterial; + +struct lightSource +{ + int enabled; + vec4 position; + vec4 diffuse; + vec4 specular; + float constantAttenuation, linearAttenuation, quadraticAttenuation; + float spotCutoff, spotExponent; + vec3 spotDirection; +}; + +uniform int numberOfLights; +const int maxLights = 1; +uniform lightSource glLightSource[maxLights]; + +varying vec3 worldPos; + +varying vec4 sceneColor; + +void directionalLight0(in vec3 normal, inout vec4 ambient, inout vec4 diffuse, inout vec3 specular) +{ + // Normalized light direction and half vector + vec3 lightDirection = normalize(vec3(glLightSource[0].position)); + + + //GL2ES2: half vector must be calculated + //vec3 halfVector = normalize(vec3(gl_LightSource[0].halfVector)); + //http://stackoverflow.com/questions/3744038/what-is-half-vector-in-modern-glsl + vec3 ecPos = vec3(glModelViewMatrix * vec4(worldPos,1.0)); + vec3 ecL; + if( glLightSource[0].position.w == 0.0) + ecL = vec3(glLightSource[0].position.xyz);// no -ecPos in case of dir lights? + else + ecL = vec3(glLightSource[0].position.xyz - ecPos); + vec3 L = normalize(ecL.xyz); + vec3 V = -ecPos.xyz; + vec3 halfVector = normalize(L + V); + + + float nDotVP; // normal . light_direction + float nDotHV; // normal . light_half_vector + float pf; // power factor + + nDotVP = max(0.0, dot(normal, lightDirection)); + nDotHV = max(0.0, dot(normal, halfVector)); + + if (nDotVP == 0.0) { + pf = 0.0; + } + else { + pf = pow(nDotHV, glFrontMaterial.shininess); + } + + // GL2ES2: ambient is part of light model + //ambient += gl_LightSource[0].ambient; + ambient += glLightModelambient; + diffuse += glLightSource[0].diffuse * nDotVP; + + // GL2ES2: specular is part of material + //specular += gl_LightSource[0].specular * pf; + specular += glFrontMaterial.specular * pf; +} + + +// Per-pixel normal (input from vertex shader) +varying vec3 Normal; + +void main() +{ + vec3 unitNorm = normalize(Normal); + vec4 amb = vec4(0.0); + vec4 diff = vec4(0.0); + vec3 spec = vec3(0.0); + int i; + + + directionalLight0(unitNorm, amb, diff, spec); + + + // Apply the result of the lighting equation + vec4 secondaryColor = vec4(spec * glFrontMaterial.specular, 1.0); + // GL2ES2: change to calc'ed sceneColor + //vec4 color = vec4(vec3(gl_FrontLightModelProduct.sceneColor + + vec4 color = vec4(vec3(sceneColor + + amb * glLightModelambient + + diff * glFrontMaterial.diffuse), 1.0); + + gl_FragColor = color + secondaryColor; +} diff --git a/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/phong.vert b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/phong.vert new file mode 100644 index 0000000..780c2bd --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/phong.vert @@ -0,0 +1,89 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +// A GLSL vertex program for doing Phone shading (per-fragment lighting) + + +// GL2ES2: Java3D built-in attributes, these are calculated and passsed in if declared here +attribute vec4 glVertex; +attribute vec3 glNormal; + +// GL2ES2: Java3D built-in uniforms, these are calculated and passsed in if declared here +uniform mat4 glModelViewProjectionMatrix; +uniform mat4 glModelViewMatrix; +uniform mat3 glNormalMatrix; + +uniform vec4 glLightModelambient; + +struct material +{ + int lightEnabled; + vec4 ambient; + vec4 diffuse; + vec4 emission; + vec3 specular; + float shininess; +}; +uniform material glFrontMaterial; + +// Per-pixel normal (output to fragment shader) +varying vec3 Normal; +varying vec3 worldPos; + +varying vec4 sceneColor; + + +void main() +{ + + //GL2ES2: sceneColor Derived. Ecm + Acm * Acs (Acs is normal glLightModelambient) + sceneColor = glFrontMaterial.emission + glFrontMaterial.ambient * glLightModelambient; + + Normal = normalize(vec3(glNormalMatrix * glNormal)); + + worldPos = vec3(glModelViewMatrix * glVertex); + + // Transform the vertex + gl_Position = glModelViewProjectionMatrix * glVertex; +} diff --git a/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/polkadot3d.frag b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/polkadot3d.frag new file mode 100644 index 0000000..605cb5f --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/polkadot3d.frag @@ -0,0 +1,49 @@ +// +// Fragment shader for 3 dimensional polka dot shader. +// +// Author: Joshua Doss +// +// Copyright (C) 2002-2004 3Dlabs Inc. Ltd. +// +// See 3Dlabs-License.txt for license information +// +varying float LightIntensity; +varying vec3 MCPosition; + +//Create uniform variables so dots can be spaced and scaled by user +//uniform vec3 Spacing; +//uniform float DotSize; +const vec3 Spacing = vec3 (0.314, 0.36, 0.261); +const float DotSize = 0.123; + +//Create colors as uniform variables so they can be easily changed +//uniform vec3 ModelColor, PolkaDotColor; +const vec3 ModelColor = vec3 (0.75, 0.2, 0.1); +const vec3 PolkaDotColor = vec3 (1, 1, 1); + +void main(void) +{ + float insidesphere, sphereradius, scaledpointlength; + vec3 scaledpoint, finalcolor; + + // Scale the coordinate system + // The following line of code is not yet implemented in current drivers: + // mcpos = mod(Spacing, MCposition); + // We will use a workaround found below for now + scaledpoint = MCPosition - (Spacing * floor(MCPosition/Spacing)); + + // Bring the scaledpoint vector into the center of the scaled coordinate system + scaledpoint = scaledpoint - Spacing/2.0; + + // Find the length of the scaledpoint vector and compare it to the dotsize + scaledpointlength = length(scaledpoint); + insidesphere = step(scaledpointlength,DotSize); + + // Determine final output color before lighting + finalcolor = vec3(mix(ModelColor, PolkaDotColor, insidesphere)); + + // Output final color and factor in lighting + // GL2ES2: gl_FragColor is unchanged + gl_FragColor = clamp((vec4( finalcolor, 1.0 ) * LightIntensity), vec4(0.0), vec4(1.0)); +} + diff --git a/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/polkadot3d.vert b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/polkadot3d.vert new file mode 100644 index 0000000..0422670 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/polkadot3d.vert @@ -0,0 +1,75 @@ +// This is the Vertex Shader for three dimensional polka dots. +// +// author(s): Joshua Doss +// +// Copyright (C) 2002-2004 3Dlabs Inc. Ltd. + +// GL2ES2: Java3D built-in attributes, these are calculated and passsed in if declared here +attribute vec4 glVertex; +attribute vec3 glNormal; + +// GL2ES2: Java3D built-in uniforms, these are calculated and passsed in if declared here +uniform mat4 glModelViewMatrix; +uniform mat4 glModelViewProjectionMatrix; +uniform mat3 glNormalMatrix; + +//Create uniform variables for lighting to allow user interaction +//uniform float SpecularContribution; +//uniform vec3 LightPosition; + +const float SpecularContribution = 0.36; +const vec3 LightPosition = vec3 (0, 4, 5); + +varying vec3 MCPosition; +varying float LightIntensity; + +void main(void) +{ + float diffusecontribution = 1.0 - SpecularContribution; + + // compute the vertex position in eye coordinates + // GL2ES2: swap built-in variable for Java3d built-in uniforms and attributes gl_* = gl* + declaration (at top) + //vec3 ecPosition = vec3(gl_ModelViewMatrix * gl_Vertex); + vec3 ecPosition = vec3(glModelViewMatrix * glVertex); + + // compute the transformed normal + // GL2ES2: swap built-in variable for Java3d built-in uniforms and attributes gl_* = gl* + declaration (at top) + //vec3 tnorm = normalize(gl_NormalMatrix * gl_Normal); + vec3 tnorm = normalize(glNormalMatrix * glNormal); + + // compute a vector from the model to the light position + vec3 lightVec = normalize(LightPosition - ecPosition); + + // compute the reflection vector + vec3 reflectVec = reflect(-lightVec, tnorm); + + // compute a unit vector in direction of viewing position + vec3 viewVec = normalize(-ecPosition); + + // calculate amount of diffuse light based on normal and light angle + float diffuse = max(dot(lightVec, tnorm), 0.0); + float spec = 0.0; + + // if there is diffuse lighting, calculate specular + if(diffuse > 0.0) + { + spec = max(dot(reflectVec, viewVec), 0.0); + spec = pow(spec, 16.0); + } + + // add up the light sources, since this is a varying (global) it will pass to frag shader + LightIntensity = diffusecontribution * diffuse * 1.5 + + SpecularContribution * spec; + + // the varying variable MCPosition will be used by the fragment shader to determine where + // in model space the current pixel is + // GL2ES2: swap built-in variable for Java3d built-in uniforms and attributes gl_* = gl* + declaration (at top) + //MCPosition = vec3 (gl_Vertex); + MCPosition = vec3 (glVertex); + + // send vertex information + // GL2ES2: swap built-in variable for Java3d built-in uniforms and attributes gl_* = gl* + declaration (at top) + //gl_Position = gl_ModelViewProjectionMatrix * gl_Vertex; + gl_Position = glModelViewProjectionMatrix * glVertex; +} + diff --git a/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/simple.frag b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/simple.frag new file mode 100644 index 0000000..092a110 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/simple.frag @@ -0,0 +1,68 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +// Simple GLSL fragment program to attenuate the input fragment color as a +// function of the distance of the fragment position from the center +// of the window + +//GL2ES2: varying color data needs to be defined +varying vec4 glFrontColor; +varying vec4 glFrontSecondaryColor; + +//GL2ES2: see particle system point size for mechanism +const float windowSize = 700.0; // TODO: this should be a built-in parameter! + +void main() +{ + // Compute distance from center in range [0.0, 1.0] + //GL2ES2: gl_FragCoord still exists + vec2 dist = min(abs((gl_FragCoord.xy - (windowSize)/2.0) / windowSize), 1.0); + vec2 invDist = 1.0 - dist; + + // Compute attenuation + float atten = invDist.x * invDist.y; + vec4 outcolor = (glFrontColor + glFrontSecondaryColor) * atten; + + gl_FragColor = outcolor; +} diff --git a/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/simple.vert b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/simple.vert new file mode 100644 index 0000000..4c5f3c9 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/simple.vert @@ -0,0 +1,189 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +// A simple GLSL vertex program for handling 2 directional lights with +// separate specular + +// GL2ES2: Java3D built-in attributes, these are calculated and passsed in if declared here +attribute vec4 glVertex; +attribute vec3 glNormal; +attribute vec4 glColor; + +// GL2ES2: Java3D built-in uniforms, these are calculated and passsed in if declared here +uniform mat4 glModelViewMatrix; +uniform mat4 glModelViewProjectionMatrix; +uniform mat3 glNormalMatrix; + +uniform vec4 glLightModelambient; + + +struct material +{ + int lightEnabled; + vec4 ambient; + vec4 diffuse; + vec4 emission; + vec3 specular; + float shininess; +}; +uniform material glFrontMaterial; + +struct lightSource +{ + int enabled; + vec4 position; + vec4 diffuse; + vec4 specular; + float constantAttenuation, linearAttenuation, quadraticAttenuation; + float spotCutoff, spotExponent; + vec3 spotDirection; +}; + +uniform int numberOfLights; +const int maxLights = 1; +uniform lightSource glLightSource[maxLights]; + +//GL2ES2: varying color data needs to be defined +varying vec4 glFrontColor; +varying vec4 glFrontSecondaryColor; + +void directionalLight( + in int i, + in vec3 normal, + inout vec4 ambient, + inout vec4 diffuse, + inout vec3 specular) +{ + // Normalized light direction and half vector + // (shouldn't they be pre-normalized?!) + + //GL2ES2 notice not using the i parameter but hard coded to 0 + vec3 lightDirection = normalize(vec3(glLightSource[0].position)); + + //GL2ES2: half vector must be calculated + //vec3 halfVector = normalize(vec3(gl_LightSource[0].halfVector)); + vec3 worldPos = vec3(glModelViewMatrix * glVertex); + vec3 L = normalize(glLightSource[0].position.xyz - worldPos); + vec3 V = vec3(0,0,1);//eye position + vec3 halfVector = (L + V); + + + + float nDotVP; // normal . light_direction + float nDotHV; // normal . light_half_vector + float pf; // power factor + + nDotVP = max(0.0, dot(normal, lightDirection)); + nDotHV = max(0.0, dot(normal, halfVector)); + + if (nDotVP == 0.0) { + pf = 0.0; + } + else { + pf = pow(nDotHV, glFrontMaterial.shininess); + } + + ambient += glLightModelambient; + diffuse += glLightSource[0].diffuse * nDotVP; + specular += glFrontMaterial.specular * pf; +} + +//GL2ES2: only a single light for now +const int numEnabledLights = 1; // TODO: this should be a built-in parameter! + +void main() +{ + //vec4 ecPosition = gl_ModelViewMatrix * gl_Vertex; + //vec3 ecPosition3 = ecPosition.xyz / ecPosition.w; + // GL2ES2: swap built-in variable for Java3d built-in uniforms and attributes gl_* = gl* + declaration (at top) + //vec3 tnorm = normalize(vec3(gl_NormalMatrix * gl_Normal)); + vec3 tnorm = normalize(vec3(glNormalMatrix * glNormal)); + vec4 amb = vec4(0.0); + vec4 diff = vec4(0.0); + vec3 spec = vec3(0.0); + int i; + + // Transform the vertex + // GL2ES2: swap built-in variable for Java3d built-in uniforms and attributes gl_* = gl* + declaration (at top) + //vec4 outPosition = gl_ModelViewProjectionMatrix * gl_Vertex; + vec4 outPosition = glModelViewProjectionMatrix * glVertex; + + for (i = 0; i < numEnabledLights; i++) { + directionalLight(i, tnorm, amb, diff, spec); + } + + //GL2ES2: sceneColor Derived. Ecm + Acm * Acs (Acs is normal glLightModelambient) + vec4 sceneColor = glFrontMaterial.emission + glFrontMaterial.ambient * glLightModelambient; + + // Apply the result of the lighting equation + vec4 outSecondaryColor = vec4(vec3(spec * glFrontMaterial.specular), 1.0); + vec3 color0 = vec3(sceneColor + + amb * glLightModelambient + + diff * glFrontMaterial.diffuse); + + // Generate a pseudo-random noise pattern + vec3 xyz = clamp((outPosition.xyz + 1.0) * 0.5, 0.0, 1.0); + + xyz = fract(xyz * 262144.0); + float randSeed = fract(3.0 * xyz.x + 5.0 * xyz.y + 7.0 * xyz.z); + + vec3 altColor; + + randSeed = fract(37.0 * randSeed); + altColor.x = randSeed * 0.5 + 0.5; + randSeed = fract(37.0 * randSeed); + altColor.y = randSeed * 0.5 + 0.5; + randSeed = fract(37.0 * randSeed); + altColor.z = randSeed * 0.5 + 0.5; + randSeed = fract(37.0 * randSeed); + float altAlpha = randSeed * 0.5; + + // Apply noise and output final vertex color + vec4 outColor; + outColor = vec4(mix(color0, altColor, altAlpha), 1.0); + + glFrontColor = outColor; + glFrontSecondaryColor = outSecondaryColor; + gl_Position = outPosition; +} diff --git a/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/toon.frag b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/toon.frag new file mode 100644 index 0000000..fa50453 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/toon.frag @@ -0,0 +1,34 @@ +// +// Fragment shader for cartoon-style shading +// +// Author: Philip Rideout +// +// Copyright (c) 2004 3Dlabs Inc. Ltd. +// +// See 3Dlabs-License.txt for license information +// + +//uniform vec3 DiffuseColor; +//uniform vec3 PhongColor; +//uniform float Edge; +//uniform float Phong; + +vec3 DiffuseColor = vec3(0.5,0.5,1.0); +vec3 PhongColor = vec3(0.75,0.75,1.0); +float Edge = 0.64; +float Phong = 0.90; + +varying vec3 Normal; +varying vec3 LightDir; + +void main (void) +{ + vec3 color = DiffuseColor; + float f = max( 0.0, dot(LightDir,Normal)); + if (abs(f) < Edge) + color = DiffuseColor * 0.2; + if (f > Phong) + color = PhongColor; + + gl_FragColor = vec4(color, 1); +} diff --git a/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/toon.vert b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/toon.vert new file mode 100644 index 0000000..d044af7 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/toon.vert @@ -0,0 +1,19 @@ +// +// Vertex shader for cartoon-style shading +// +// Author: Philip Rideout +// +// Copyright (c) 2004 3Dlabs Inc. Ltd. +// +// See 3Dlabs-License.txt for license information +// + +varying vec3 Normal; +varying vec3 LightDir; + +void main(void) +{ + Normal = normalize(gl_NormalMatrix * gl_Normal); + gl_Position = gl_ModelViewProjectionMatrix * gl_Vertex; + LightDir = vec3(normalize(gl_LightSource[0].position)); +} diff --git a/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/vertexshader.frag b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/vertexshader.frag new file mode 100644 index 0000000..029b044 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/vertexshader.frag @@ -0,0 +1,52 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + + +//GL2ES2: varying color data needs to be defined +varying vec4 glFrontColor; + +void main() +{ + gl_FragColor = glFrontColor; +} diff --git a/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/vertexshader.vert b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/vertexshader.vert new file mode 100644 index 0000000..12f3662 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/vertexshader.vert @@ -0,0 +1,70 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +// GL2ES2: Java3D built-in attributes, these are calculated and passsed in if declared here +attribute vec4 glVertex; + +// GL2ES2: Java3D built-in uniforms, these are calculated and passsed in if declared here +uniform mat4 glModelViewProjectionMatrix; + +// A simple GLSL vertex program for demo. vertex attributes + +attribute float weight; +attribute vec3 temperature; + +//GL2ES2: varying color data needs to be defined +varying vec4 glFrontColor; + +void main() +{ + // Transform the vertex + vec4 outPosition = glModelViewProjectionMatrix * glVertex; + + // Compute color from temperature + vec4 outColor; + outColor = vec4(temperature * weight, 1); + // Assign output parameters + glFrontColor = outColor; + gl_Position = outPosition; +} diff --git a/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/wood.frag b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/wood.frag new file mode 100644 index 0000000..6686190 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/wood.frag @@ -0,0 +1,67 @@ +// +// Simple fragment shader for wood +// +// Author: John Kessenich +// +// Copyright (c) 2002-2004 3Dlabs Inc. Ltd. +// +// See 3Dlabs-License.txt for license information +// + +//uniform float GrainSizeRecip; +//uniform vec3 DarkColor; +//uniform vec3 spread; +const float GrainSizeRecip = 1.0; +const vec3 DarkColor = vec3 (0.6, 0.3, 0.1); +const vec3 spread = vec3 (0.15, 0.075, 0.0); + +varying float lightIntensity; +varying vec3 Position; + +void main (void) +{ + // + // cheap noise + // + vec3 location = Position; + vec3 floorvec = vec3(floor(10.0 * Position.x), 0.0, floor(10.0 * Position.z)); + vec3 noise = Position * 10.0 - floorvec - 0.5; + noise *= noise; + location += noise * 0.12; + + // + // distance from axis + // + float dist = location.x * location.x + location.z * location.z; + float grain = dist * GrainSizeRecip; + + // + // grain effects as function of distance + // + float brightness = fract(grain); + if (brightness > 0.5) + brightness = (1.0 - brightness); + vec3 color = DarkColor + brightness * spread; + + brightness = fract(grain * 7.0); + if (brightness > 0.5) + brightness = 1.0 - brightness; + color -= brightness * spread; + + // + // also as a function of lines parallel to the axis + // + brightness = fract(grain * 47.0) * 0.60; + float line = fract(Position.z + Position.x); + float snap = floor(line * 20.0) * (1.0/20.0); + if (line < snap + 0.006) + color -= brightness * spread; + + // + // apply lighting effects from vertex processor + // + color = clamp(color * lightIntensity, 0.0, 1.0); + + // GL2ES2: gl_FragColor is unchanged + gl_FragColor = vec4(color, 1.0); +} diff --git a/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/wood.vert b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/wood.vert new file mode 100644 index 0000000..e04ba6d --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/gl2es2pipeline/wood.vert @@ -0,0 +1,43 @@ +// +// Simple vertex shader for wood +// +// Author: John Kessenich +// +// Copyright (c) 2002-2004 3Dlabs Inc. Ltd. +// +// See 3Dlabs-License.txt for license information +// + +// GL2ES2: Java3D built-in attributes, these are calculated and passsed in if declared here +attribute vec4 glVertex; +attribute vec3 glNormal; + +// GL2ES2: Java3D built-in uniforms, these are calculated and passsed in if declared here +uniform mat4 glModelViewMatrix; +uniform mat4 glModelViewProjectionMatrix; +uniform mat3 glNormalMatrix; + +varying float lightIntensity; +varying vec3 Position; +//uniform vec3 LightPosition; +//uniform float Scale; +const vec3 LightPosition = vec3 (0.0,0.0,0.4); +const float Scale = 1.0; + +void main(void) +{ + // GL2ES2: swap built-in variable for Java3d built-in uniforms and attributes gl_* = gl* + declaration (at top) + //vec4 pos = glModelViewMatrix * glVertex; + vec4 pos = glModelViewMatrix * glVertex; + // GL2ES2: swap built-in variable for Java3d built-in uniforms and attributes gl_* = gl* + declaration (at top) + //Position = vec3(glVertex) * Scale; + Position = vec3(glVertex) * Scale; + // GL2ES2: swap built-in variable for Java3d built-in uniforms and attributes gl_* = gl* + declaration (at top) + //vec3 tnorm = normalize(gl_NormalMatrix * gl_Normal); + vec3 tnorm = normalize(glNormalMatrix * glNormal); + lightIntensity = max(dot(normalize(LightPosition - vec3(pos)), tnorm), 0.0) * 1.5; + + // GL2ES2: swap built-in variable for Java3d built-in uniforms and attributes gl_* = gl* + declaration (at top) + //gl_Position = gl_ModelViewProjectionMatrix * gl_Vertex; + gl_Position = glModelViewProjectionMatrix * glVertex; +} diff --git a/src/main/java/org/jdesktop/j3d/examples/glsl_shader/EnvironmentMappingGLSL.form b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/EnvironmentMappingGLSL.form new file mode 100644 index 0000000..b6a3e94 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/EnvironmentMappingGLSL.form @@ -0,0 +1,36 @@ +<?xml version="1.0" encoding="UTF-8" ?> + +<Form version="1.0" type="org.netbeans.modules.form.forminfo.JFrameFormInfo"> + <Properties> + <Property name="defaultCloseOperation" type="int" value="3"/> + <Property name="title" type="java.lang.String" value="EnvironmentMappingGLSL"/> + </Properties> + <SyntheticProperties> + <SyntheticProperty name="formSizePolicy" type="int" value="1"/> + </SyntheticProperties> + <AuxValues> + <AuxValue name="FormSettings_generateMnemonicsCode" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_listenerGenerationStyle" type="java.lang.Integer" value="0"/> + <AuxValue name="FormSettings_variablesLocal" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_variablesModifier" type="java.lang.Integer" value="2"/> + <AuxValue name="designerSize" type="java.awt.Dimension" value="-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,1,44,0,0,1,-112"/> + </AuxValues> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + <SubComponents> + <Container class="javax.swing.JPanel" name="drawingPanel"> + <Properties> + <Property name="preferredSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor"> + <Dimension value="[500, 500]"/> + </Property> + </Properties> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout" value="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription"> + <BorderConstraints direction="Center"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + </Container> + </SubComponents> +</Form> diff --git a/src/main/java/org/jdesktop/j3d/examples/glsl_shader/EnvironmentMappingGLSL.java b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/EnvironmentMappingGLSL.java new file mode 100644 index 0000000..ff5e9cd --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/EnvironmentMappingGLSL.java @@ -0,0 +1,261 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.glsl_shader; + +import java.awt.GraphicsConfiguration; +import java.io.IOException; +import java.net.URL; + +import javax.swing.JOptionPane; + +import org.jdesktop.j3d.examples.Resources; +import org.jogamp.java3d.Alpha; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.GLSLShaderProgram; +import org.jogamp.java3d.RotationInterpolator; +import org.jogamp.java3d.Shader; +import org.jogamp.java3d.ShaderAppearance; +import org.jogamp.java3d.ShaderAttribute; +import org.jogamp.java3d.ShaderAttributeSet; +import org.jogamp.java3d.ShaderAttributeValue; +import org.jogamp.java3d.ShaderError; +import org.jogamp.java3d.ShaderErrorListener; +import org.jogamp.java3d.ShaderProgram; +import org.jogamp.java3d.SourceCodeShader; +import org.jogamp.java3d.Texture; +import org.jogamp.java3d.TextureUnitState; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.utils.geometry.Sphere; +import org.jogamp.java3d.utils.image.TextureLoader; +import org.jogamp.java3d.utils.shader.StringIO; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.java3d.utils.universe.ViewingPlatform; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Point3f; + +public class EnvironmentMappingGLSL extends javax.swing.JFrame { + + private URL textureURL = null; + private static final int NUM_TEX_UNITS = 1; + private static final int TEX_UNIT = 0; + + SimpleUniverse univ = null; + + public BranchGroup createSceneGraph() { + // Create the root of the branch graph + BranchGroup objRoot = new BranchGroup(); + + // Create the TransformGroup node and initialize it to the + // identity. Enable the TRANSFORM_WRITE capability so that + // our behavior code can modify it at run time. Add it to + // the root of the subgraph. + TransformGroup objTrans = new TransformGroup(); + objTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + objRoot.addChild(objTrans); + + // Create texture object + textureURL = Resources.getResource("resources/images/duke-gears.jpg"); + Texture tex = new TextureLoader(textureURL, this).getTexture(); + // Create the shader program + String vertexProgram = null; + String fragmentProgram = null; + try { + vertexProgram = StringIO.readFully(Resources.getResource("glsl_shader/envmap.vert")); + fragmentProgram = StringIO.readFully(Resources.getResource("glsl_shader/envmap.frag")); + } + catch (IOException e) { + System.err.println(e); + } + Shader[] shaders = new Shader[2]; + shaders[0] = new SourceCodeShader(Shader.SHADING_LANGUAGE_GLSL, + Shader.SHADER_TYPE_VERTEX, + vertexProgram); + shaders[1] = new SourceCodeShader(Shader.SHADING_LANGUAGE_GLSL, + Shader.SHADER_TYPE_FRAGMENT, + fragmentProgram); + final String[] shaderAttrNames = { + "LightPos", + "BaseColor", + "MixRatio", + "EnvMap", + }; + final Object[] shaderAttrValues = { + new Point3f(1.0f, -1.0f, 2.0f), + new Color3f(0.2f, 0.9f, 0.5f), + new Float(0.4f), + new Integer(TEX_UNIT), + }; + ShaderProgram shaderProgram = new GLSLShaderProgram(); + shaderProgram.setShaders(shaders); + shaderProgram.setShaderAttrNames(shaderAttrNames); + + // Create the shader attribute set + ShaderAttributeSet shaderAttributeSet = new ShaderAttributeSet(); + for (int i = 0; i < shaderAttrNames.length; i++) { + ShaderAttribute shaderAttribute = + new ShaderAttributeValue(shaderAttrNames[i], shaderAttrValues[i]); + shaderAttributeSet.put(shaderAttribute); + } + + // Create shader appearance to hold the shader program and + // shader attributes + ShaderAppearance app = new ShaderAppearance(); + app.setShaderProgram(shaderProgram); + app.setShaderAttributeSet(shaderAttributeSet); + + // Put the texture in specified texture unit + TextureUnitState[] tus = new TextureUnitState[NUM_TEX_UNITS]; + tus[TEX_UNIT] = new TextureUnitState(); + tus[TEX_UNIT].setTexture(tex); + app.setTextureUnitState(tus); + + // Create a Sphere object using the shader appearance, + // and add it into the scene graph. + Sphere sph = new Sphere(0.4f, Sphere.GENERATE_NORMALS, 20, app); + objTrans.addChild(sph); + + // Create a new Behavior object that will perform the + // desired operation on the specified transform and add + // it into the scene graph. + Transform3D yAxis = new Transform3D(); + Alpha rotationAlpha = new Alpha(-1, 4000); + + RotationInterpolator rotator = + new RotationInterpolator(rotationAlpha, objTrans, yAxis, + 0.0f, (float) Math.PI*2.0f); + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + rotator.setSchedulingBounds(bounds); + objRoot.addChild(rotator); + + // Have Java 3D perform optimizations on this scene graph. + //objRoot.compile(); + + return objRoot; + } + + private Canvas3D initScene() { + GraphicsConfiguration config = + SimpleUniverse.getPreferredConfiguration(); + + Canvas3D c = new Canvas3D(config); + + BranchGroup scene = createSceneGraph(); + univ = new SimpleUniverse(c); + + // Add a ShaderErrorListener + univ.addShaderErrorListener(new ShaderErrorListener() { + public void errorOccurred(ShaderError error) { + error.printVerbose(); + JOptionPane.showMessageDialog(EnvironmentMappingGLSL.this, + error.toString(), + "ShaderError", + JOptionPane.ERROR_MESSAGE); + } + }); + + ViewingPlatform viewingPlatform = univ.getViewingPlatform(); + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + viewingPlatform.setNominalViewingTransform(); + + univ.addBranchGraph(scene); + + return c; + } + + /** + * Creates new form EnvironmentMappingGLSL + */ + public EnvironmentMappingGLSL() { + // Initialize the GUI components + initComponents(); + + // Create the scene and add the Canvas3D to the drawing panel + Canvas3D c = initScene(); + drawingPanel.add(c, java.awt.BorderLayout.CENTER); + } + + // ---------------------------------------------------------------- + + /** This method is called from within the constructor to + * initialize the form. + * WARNING: Do NOT modify this code. The content of this method is + * always regenerated by the Form Editor. + */ + // <editor-fold defaultstate="collapsed" desc=" Generated Code ">//GEN-BEGIN:initComponents + private void initComponents() { + drawingPanel = new javax.swing.JPanel(); + + setDefaultCloseOperation(javax.swing.WindowConstants.EXIT_ON_CLOSE); + setTitle("EnvironmentMappingGLSL"); + drawingPanel.setLayout(new java.awt.BorderLayout()); + + drawingPanel.setPreferredSize(new java.awt.Dimension(500, 500)); + getContentPane().add(drawingPanel, java.awt.BorderLayout.CENTER); + + pack(); + }// </editor-fold>//GEN-END:initComponents + + /** + * @param args the command line arguments + */ + public static void main(String args[]) { + java.awt.EventQueue.invokeLater(new Runnable() { + public void run() { + new EnvironmentMappingGLSL().setVisible(true); + } + }); + } + + // Variables declaration - do not modify//GEN-BEGIN:variables + private javax.swing.JPanel drawingPanel; + // End of variables declaration//GEN-END:variables + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/glsl_shader/ObjLoadGLSL.form b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/ObjLoadGLSL.form new file mode 100644 index 0000000..343b6d5 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/ObjLoadGLSL.form @@ -0,0 +1,36 @@ +<?xml version="1.0" encoding="UTF-8" ?> + +<Form version="1.0" type="org.netbeans.modules.form.forminfo.JFrameFormInfo"> + <Properties> + <Property name="defaultCloseOperation" type="int" value="3"/> + <Property name="title" type="java.lang.String" value="ObjLoadGLSL"/> + </Properties> + <SyntheticProperties> + <SyntheticProperty name="formSizePolicy" type="int" value="1"/> + </SyntheticProperties> + <AuxValues> + <AuxValue name="FormSettings_generateMnemonicsCode" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_listenerGenerationStyle" type="java.lang.Integer" value="0"/> + <AuxValue name="FormSettings_variablesLocal" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_variablesModifier" type="java.lang.Integer" value="2"/> + <AuxValue name="designerSize" type="java.awt.Dimension" value="-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,1,44,0,0,1,-112"/> + </AuxValues> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + <SubComponents> + <Container class="javax.swing.JPanel" name="drawingPanel"> + <Properties> + <Property name="preferredSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor"> + <Dimension value="[700, 700]"/> + </Property> + </Properties> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout" value="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription"> + <BorderConstraints direction="Center"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + </Container> + </SubComponents> +</Form> diff --git a/src/main/java/org/jdesktop/j3d/examples/glsl_shader/ObjLoadGLSL.java b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/ObjLoadGLSL.java new file mode 100644 index 0000000..2feb50a --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/ObjLoadGLSL.java @@ -0,0 +1,404 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.glsl_shader; + +import java.awt.GraphicsConfiguration; +import java.io.FileNotFoundException; +import java.io.IOException; +import java.net.MalformedURLException; +import java.net.URL; +import java.util.Enumeration; + +import javax.swing.JOptionPane; + +import org.jdesktop.j3d.examples.Resources; +import org.jogamp.java3d.Alpha; +import org.jogamp.java3d.AmbientLight; +import org.jogamp.java3d.Background; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.DirectionalLight; +import org.jogamp.java3d.GLSLShaderProgram; +import org.jogamp.java3d.Group; +import org.jogamp.java3d.Material; +import org.jogamp.java3d.Node; +import org.jogamp.java3d.RotationInterpolator; +import org.jogamp.java3d.Shader; +import org.jogamp.java3d.ShaderAppearance; +import org.jogamp.java3d.ShaderError; +import org.jogamp.java3d.ShaderErrorListener; +import org.jogamp.java3d.ShaderProgram; +import org.jogamp.java3d.Shape3D; +import org.jogamp.java3d.SourceCodeShader; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.loaders.IncorrectFormatException; +import org.jogamp.java3d.loaders.ParsingErrorException; +import org.jogamp.java3d.loaders.Scene; +import org.jogamp.java3d.loaders.objectfile.ObjectFile; +import org.jogamp.java3d.utils.behaviors.vp.OrbitBehavior; +import org.jogamp.java3d.utils.shader.StringIO; +import org.jogamp.java3d.utils.universe.PlatformGeometry; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.java3d.utils.universe.ViewingPlatform; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Vector3f; + +/** + * Simple Java 3D example program to display an .obj object with shader programs. + */ +public class ObjLoadGLSL extends javax.swing.JFrame { + + private String shaderName = "polkadot3d"; + private boolean spin = false; + private boolean noTriangulate = false; + private boolean noStripify = false; + private double creaseAngle = 60.0; + private URL filename = null; + + private SimpleUniverse univ = null; + private BranchGroup scene = null; + + public BranchGroup createSceneGraph() { + // Create the root of the branch graph + BranchGroup objRoot = new BranchGroup(); + + // Create a Transformgroup to scale all objects so they + // appear in the scene. + TransformGroup objScale = new TransformGroup(); + Transform3D t3d = new Transform3D(); + t3d.setScale(0.7); + objScale.setTransform(t3d); + objRoot.addChild(objScale); + + // Create the transform group node and initialize it to the + // identity. Enable the TRANSFORM_WRITE capability so that + // our behavior code can modify it at runtime. Add it to the + // root of the subgraph. + TransformGroup objTrans = new TransformGroup(); + objTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + objTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_READ); + objScale.addChild(objTrans); + + int flags = ObjectFile.RESIZE; + if (!noTriangulate) flags |= ObjectFile.TRIANGULATE; + if (!noStripify) flags |= ObjectFile.STRIPIFY; + ObjectFile f = new ObjectFile(flags, + (float)(creaseAngle * Math.PI / 180.0)); + Scene s = null; + try { + s = f.load(filename); + } + catch (FileNotFoundException e) { + System.err.println(e); + System.exit(1); + } + catch (ParsingErrorException e) { + System.err.println(e); + System.exit(1); + } + catch (IncorrectFormatException e) { + System.err.println(e); + System.exit(1); + } + + // Set vertex and fragment shader program for all Shape3D nodes in scene + String vertexProgram = null; + String fragmentProgram = null; + try { + vertexProgram = StringIO.readFully(Resources.getResource("glsl_shader/" + shaderName + ".vert")); + fragmentProgram = StringIO.readFully(Resources.getResource("glsl_shader/" + shaderName + ".frag")); + } + catch (IOException e) { + throw new RuntimeException(e); + } + Shader[] shaders = new Shader[2]; + shaders[0] = new SourceCodeShader(Shader.SHADING_LANGUAGE_GLSL, + Shader.SHADER_TYPE_VERTEX, + vertexProgram); + shaders[1] = new SourceCodeShader(Shader.SHADING_LANGUAGE_GLSL, + Shader.SHADER_TYPE_FRAGMENT, + fragmentProgram); + ShaderProgram shaderProgram = new GLSLShaderProgram(); + shaderProgram.setShaders(shaders); + setShaderProgram(s.getSceneGroup(), shaderProgram); + + objTrans.addChild(s.getSceneGroup()); + + BoundingSphere bounds = new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + + if (spin) { + Transform3D yAxis = new Transform3D(); + Alpha rotationAlpha = new Alpha(-1, Alpha.INCREASING_ENABLE, + 0, 0, + 4000, 0, 0, + 0, 0, 0); + + RotationInterpolator rotator = + new RotationInterpolator(rotationAlpha, objTrans, yAxis, + 0.0f, (float) Math.PI*2.0f); + rotator.setSchedulingBounds(bounds); + objTrans.addChild(rotator); + } + + // Set up the background + Color3f bgColor = new Color3f(0.05f, 0.05f, 0.5f); + Background bgNode = new Background(bgColor); + bgNode.setApplicationBounds(bounds); + objRoot.addChild(bgNode); + + return objRoot; + } + + private Canvas3D createUniverse() { + // Get the preferred graphics configuration for the default screen + GraphicsConfiguration config = + SimpleUniverse.getPreferredConfiguration(); + + // Create a Canvas3D using the preferred configuration + Canvas3D canvas3d = new Canvas3D(config); + + // Create simple universe with view branch + univ = new SimpleUniverse(canvas3d); + BoundingSphere bounds = new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + + // Add a ShaderErrorListener + univ.addShaderErrorListener(new ShaderErrorListener() { + public void errorOccurred(ShaderError error) { + error.printVerbose(); + JOptionPane.showMessageDialog(ObjLoadGLSL.this, + error.toString(), + "ShaderError", + JOptionPane.ERROR_MESSAGE); + } + }); + + // add mouse behaviors to the ViewingPlatform + ViewingPlatform viewingPlatform = univ.getViewingPlatform(); + + PlatformGeometry pg = new PlatformGeometry(); + + // Set up the ambient light + Color3f ambientColor = new Color3f(0.1f, 0.1f, 0.1f); + AmbientLight ambientLightNode = new AmbientLight(ambientColor); + ambientLightNode.setInfluencingBounds(bounds); + pg.addChild(ambientLightNode); + + // Set up the directional lights + Color3f light1Color = new Color3f(1.0f, 1.0f, 0.9f); + Vector3f light1Direction = new Vector3f(1.0f, 1.0f, 1.0f); + Color3f light2Color = new Color3f(1.0f, 1.0f, 1.0f); + Vector3f light2Direction = new Vector3f(-1.0f, -1.0f, -1.0f); + + DirectionalLight light1 + = new DirectionalLight(light1Color, light1Direction); + light1.setInfluencingBounds(bounds); + pg.addChild(light1); + + DirectionalLight light2 + = new DirectionalLight(light2Color, light2Direction); + light2.setInfluencingBounds(bounds); + pg.addChild(light2); + + viewingPlatform.setPlatformGeometry( pg ); + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + viewingPlatform.setNominalViewingTransform(); + + if (!spin) { + OrbitBehavior orbit = new OrbitBehavior(canvas3d, + OrbitBehavior.REVERSE_ALL); + orbit.setSchedulingBounds(bounds); + viewingPlatform.setViewPlatformBehavior(orbit); + } + + // Ensure at least 5 msec per frame (i.e., < 200Hz) + univ.getViewer().getView().setMinimumFrameCycleTime(5); + + return canvas3d; + } + + private void usage() { + System.out.println("Usage: java ObjLoadGLSL [-s] [-S shaderName] [-n] [-t] [-c degrees] <.obj file>"); + System.out.println(" -s Spin (no user interaction)"); + System.out.println(" -S Set shader name (default is 'simple')"); + System.out.println(" -n No triangulation"); + System.out.println(" -t No stripification"); + System.out.println( + " -c Set crease angle for normal generation (default is 60 without"); + System.out.println( + " smoothing group info, otherwise 180 within smoothing groups)"); + System.exit(0); + } // End of usage + + // Set shader program for all nodes in specified branch graph + private void setShaderProgram(BranchGroup g, ShaderProgram shaderProgram) { + ShaderAppearance myApp = new ShaderAppearance(); + Material mat = new Material(); + myApp.setShaderProgram(shaderProgram); + myApp.setMaterial(mat); + setShaderProgram(g, myApp); + } + + // Recursively set shader program for all children of specified group + private void setShaderProgram(Group g, + ShaderAppearance myApp) { + + Enumeration e = g.getAllChildren(); + while (e.hasMoreElements()) { + Node n = (Node)(e.nextElement()); + if (n instanceof Group) { + setShaderProgram((Group)n, myApp); + } + else if (n instanceof Shape3D) { + Shape3D s = (Shape3D)n; + s.setAppearance(myApp); + } + } + } + + /** + * Creates new form ObjLoadGLSL + */ + public ObjLoadGLSL(String args[]) { + if (args.length != 0) { + for (int i = 0 ; i < args.length ; i++) { + if (args[i].startsWith("-")) { + if (args[i].equals("-s")) { + spin = true; + } else if (args[i].equals("-n")) { + noTriangulate = true; + } else if (args[i].equals("-t")) { + noStripify = true; + } else if (args[i].equals("-c")) { + if (i < args.length - 1) { + creaseAngle = (new Double(args[++i])).doubleValue(); + } else usage(); + } else if (args[i].equals("-S")) { + if (i < args.length - 1) { + shaderName = args[++i]; + } else usage(); + } else { + usage(); + } + } else { + try { + if ((args[i].indexOf("file:") == 0) || + (args[i].indexOf("http") == 0)) { + filename = new URL(args[i]); + } else if (args[i].charAt(0) != '/') { + filename = new URL("file:./" + args[i]); + } else { + filename = new URL("file:" + args[i]); + } + } catch (MalformedURLException e) { + System.err.println(e); + System.exit(1); + } + } + } + } + + if (filename == null) { + filename = Resources.getResource("resources/geometry/galleon.obj"); + if (filename == null) { + System.err.println("resources/geometry/galleon.obj not found"); + System.exit(1); + } + } + + // Initialize the GUI components + initComponents(); + + // Create Canvas3D and SimpleUniverse; add canvas to drawing panel + Canvas3D c = createUniverse(); + drawingPanel.add(c, java.awt.BorderLayout.CENTER); + + // Create the content branch and add it to the universe + scene = createSceneGraph(); + univ.addBranchGraph(scene); + } + + // ---------------------------------------------------------------- + + /** This method is called from within the constructor to + * initialize the form. + * WARNING: Do NOT modify this code. The content of this method is + * always regenerated by the Form Editor. + */ + // <editor-fold defaultstate="collapsed" desc=" Generated Code ">//GEN-BEGIN:initComponents + private void initComponents() { + drawingPanel = new javax.swing.JPanel(); + + setDefaultCloseOperation(javax.swing.WindowConstants.EXIT_ON_CLOSE); + setTitle("ObjLoadGLSL"); + drawingPanel.setLayout(new java.awt.BorderLayout()); + + drawingPanel.setPreferredSize(new java.awt.Dimension(700, 700)); + getContentPane().add(drawingPanel, java.awt.BorderLayout.CENTER); + + pack(); + }// </editor-fold>//GEN-END:initComponents + + /** + * @param args the command line arguments + */ + public static void main(final String args[]) { + java.awt.EventQueue.invokeLater(new Runnable() { + public void run() { + ObjLoadGLSL objLoadGLSL = new ObjLoadGLSL(args); + objLoadGLSL.setVisible(true); + } + }); + } + + // Variables declaration - do not modify//GEN-BEGIN:variables + private javax.swing.JPanel drawingPanel; + // End of variables declaration//GEN-END:variables + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/glsl_shader/PhongShadingGLSL.form b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/PhongShadingGLSL.form new file mode 100644 index 0000000..dcccf73 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/PhongShadingGLSL.form @@ -0,0 +1,138 @@ +<?xml version="1.0" encoding="UTF-8" ?> + +<Form version="1.0" type="org.netbeans.modules.form.forminfo.JFrameFormInfo"> + <NonVisualComponents> + <Component class="javax.swing.ButtonGroup" name="shaderButtonGroup"> + </Component> + <Menu class="javax.swing.JMenuBar" name="jMenuBar1"> + <SubComponents> + <Menu class="javax.swing.JMenu" name="fileMenu"> + <Properties> + <Property name="text" type="java.lang.String" value="File"/> + </Properties> + <SubComponents> + <MenuItem class="javax.swing.JMenuItem" name="exitMenuItem"> + <Properties> + <Property name="text" type="java.lang.String" value="Exit"/> + </Properties> + <Events> + <EventHandler event="actionPerformed" listener="java.awt.event.ActionListener" parameters="java.awt.event.ActionEvent" handler="exitMenuItemActionPerformed"/> + </Events> + </MenuItem> + </SubComponents> + </Menu> + </SubComponents> + </Menu> + </NonVisualComponents> + <Properties> + <Property name="defaultCloseOperation" type="int" value="3"/> + <Property name="title" type="java.lang.String" value="Phong Shading Test"/> + </Properties> + <SyntheticProperties> + <SyntheticProperty name="menuBar" type="java.lang.String" value="jMenuBar1"/> + <SyntheticProperty name="formSizePolicy" type="int" value="1"/> + </SyntheticProperties> + <AuxValues> + <AuxValue name="FormSettings_generateMnemonicsCode" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_listenerGenerationStyle" type="java.lang.Integer" value="0"/> + <AuxValue name="FormSettings_variablesLocal" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_variablesModifier" type="java.lang.Integer" value="2"/> + <AuxValue name="designerSize" type="java.awt.Dimension" value="-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,1,44,0,0,1,-112"/> + </AuxValues> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + <SubComponents> + <Container class="javax.swing.JPanel" name="guiPanel"> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout" value="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription"> + <BorderConstraints direction="North"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout"/> + <SubComponents> + <Container class="javax.swing.JPanel" name="jPanel1"> + <Properties> + <Property name="border" type="javax.swing.border.Border" editor="org.netbeans.modules.form.editors2.BorderEditor"> + <Border info="org.netbeans.modules.form.compat2.border.TitledBorderInfo"> + <TitledBorder title="Shader"/> + </Border> + </Property> + </Properties> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout" value="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription"> + <GridBagConstraints gridX="-1" gridY="-1" gridWidth="1" gridHeight="1" fill="2" ipadX="0" ipadY="0" insetsTop="4" insetsLeft="4" insetsBottom="4" insetsRight="4" anchor="10" weightX="0.0" weightY="0.0"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout"/> + <SubComponents> + <Component class="javax.swing.JRadioButton" name="gouraudButton"> + <Properties> + <Property name="buttonGroup" type="javax.swing.ButtonGroup" editor="org.netbeans.modules.form.RADComponent$ButtonGroupPropertyEditor"> + <ComponentRef name="shaderButtonGroup"/> + </Property> + <Property name="selected" type="boolean" value="true"/> + <Property name="text" type="java.lang.String" value="Per-Vertex Lighting (Gouraud)"/> + <Property name="border" type="javax.swing.border.Border" editor="org.netbeans.modules.form.editors2.BorderEditor"> + <Border info="org.netbeans.modules.form.compat2.border.EmptyBorderInfo"> + <EmptyBorder bottom="0" left="0" right="0" top="0"/> + </Border> + </Property> + <Property name="margin" type="java.awt.Insets" editor="org.netbeans.beaninfo.editors.InsetsEditor"> + <Insets value="[0, 0, 0, 0]"/> + </Property> + </Properties> + <Events> + <EventHandler event="actionPerformed" listener="java.awt.event.ActionListener" parameters="java.awt.event.ActionEvent" handler="gouraudButtonActionPerformed"/> + </Events> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout" value="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription"> + <GridBagConstraints gridX="-1" gridY="-1" gridWidth="1" gridHeight="1" fill="2" ipadX="0" ipadY="0" insetsTop="2" insetsLeft="2" insetsBottom="2" insetsRight="2" anchor="10" weightX="0.0" weightY="0.0"/> + </Constraint> + </Constraints> + </Component> + <Component class="javax.swing.JRadioButton" name="phongButton"> + <Properties> + <Property name="buttonGroup" type="javax.swing.ButtonGroup" editor="org.netbeans.modules.form.RADComponent$ButtonGroupPropertyEditor"> + <ComponentRef name="shaderButtonGroup"/> + </Property> + <Property name="text" type="java.lang.String" value="Per-Pixel Lighting (Phong)"/> + <Property name="border" type="javax.swing.border.Border" editor="org.netbeans.modules.form.editors2.BorderEditor"> + <Border info="org.netbeans.modules.form.compat2.border.EmptyBorderInfo"> + <EmptyBorder bottom="0" left="0" right="0" top="0"/> + </Border> + </Property> + <Property name="margin" type="java.awt.Insets" editor="org.netbeans.beaninfo.editors.InsetsEditor"> + <Insets value="[0, 0, 0, 0]"/> + </Property> + </Properties> + <Events> + <EventHandler event="actionPerformed" listener="java.awt.event.ActionListener" parameters="java.awt.event.ActionEvent" handler="phongButtonActionPerformed"/> + </Events> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout" value="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription"> + <GridBagConstraints gridX="0" gridY="1" gridWidth="1" gridHeight="1" fill="2" ipadX="0" ipadY="0" insetsTop="2" insetsLeft="2" insetsBottom="2" insetsRight="2" anchor="10" weightX="0.0" weightY="0.0"/> + </Constraint> + </Constraints> + </Component> + </SubComponents> + </Container> + </SubComponents> + </Container> + <Container class="javax.swing.JPanel" name="drawingPanel"> + <Properties> + <Property name="preferredSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor"> + <Dimension value="[500, 500]"/> + </Property> + </Properties> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout" value="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription"> + <BorderConstraints direction="Center"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + </Container> + </SubComponents> +</Form> diff --git a/src/main/java/org/jdesktop/j3d/examples/glsl_shader/PhongShadingGLSL.java b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/PhongShadingGLSL.java new file mode 100644 index 0000000..45b4b94 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/PhongShadingGLSL.java @@ -0,0 +1,492 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.glsl_shader; + +import java.awt.GraphicsConfiguration; +import java.io.IOException; + +import javax.swing.JOptionPane; + +import org.jdesktop.j3d.examples.Resources; +import org.jogamp.java3d.Alpha; +import org.jogamp.java3d.AmbientLight; +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.Background; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.ColoringAttributes; +import org.jogamp.java3d.DirectionalLight; +import org.jogamp.java3d.GLSLShaderProgram; +import org.jogamp.java3d.Light; +import org.jogamp.java3d.Material; +import org.jogamp.java3d.PointLight; +import org.jogamp.java3d.RotationInterpolator; +import org.jogamp.java3d.Shader; +import org.jogamp.java3d.ShaderAppearance; +import org.jogamp.java3d.ShaderError; +import org.jogamp.java3d.ShaderErrorListener; +import org.jogamp.java3d.ShaderProgram; +import org.jogamp.java3d.SourceCodeShader; +import org.jogamp.java3d.SpotLight; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.utils.geometry.Sphere; +import org.jogamp.java3d.utils.shader.StringIO; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Point3f; +import org.jogamp.vecmath.Vector3d; +import org.jogamp.vecmath.Vector3f; + +/** + * + * @author kcr + */ +public class PhongShadingGLSL extends javax.swing.JFrame { + + // Constants for type of light to use + private static final int DIRECTIONAL_LIGHT = 0; + private static final int POINT_LIGHT = 1; + private static final int SPOT_LIGHT = 2; + + // Flag indicates type of lights: directional, point, or spot lights. + private static int lightType = DIRECTIONAL_LIGHT; + + private SimpleUniverse univ = null; + + private ShaderAppearance sApp = null; + private ShaderProgram gouraudSP = null; + private ShaderProgram phongSP = null; + + public BranchGroup createSceneGraph() { + Color3f eColor = new Color3f(0.0f, 0.0f, 0.0f); + Color3f sColor = new Color3f(1.0f, 1.0f, 1.0f); + Color3f objColor = new Color3f(0.6f, 0.6f, 0.6f); +// Color3f lColor1 = new Color3f(1.0f, 0.0f, 0.0f); +// Color3f lColor2 = new Color3f(0.0f, 1.0f, 0.0f); + Color3f lColor1 = new Color3f(1.0f, 1.0f, 0.5f); + Color3f alColor = new Color3f(0.2f, 0.2f, 0.2f); + Color3f bgColor = new Color3f(0.05f, 0.05f, 0.2f); + + Transform3D t; + + // Create the root of the branch graph + BranchGroup objRoot = new BranchGroup(); + + // Create a Transformgroup to scale all objects so they + // appear in the scene. + TransformGroup objScale = new TransformGroup(); + Transform3D t3d = new Transform3D(); + t3d.setScale(0.5); + objScale.setTransform(t3d); + objRoot.addChild(objScale); + + // Create a bounds for the background and lights + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + + // Set up the background + Background bg = new Background(bgColor); + bg.setApplicationBounds(bounds); + objRoot.addChild(bg); + + // Create the TransformGroup node and initialize it to the + // identity. Enable the TRANSFORM_WRITE capability so that + // our behavior code can modify it at run time. Add it to + // the root of the subgraph. + TransformGroup objTrans = new TransformGroup(); + objTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + objScale.addChild(objTrans); + + // Create a Sphere object, generate one copy of the sphere, + // and add it into the scene graph. + sApp = new ShaderAppearance(); + sApp.setCapability(ShaderAppearance.ALLOW_SHADER_PROGRAM_WRITE); + Material m = new Material(objColor, eColor, objColor, sColor, 100.0f); + sApp.setMaterial(m); + + // Create Gouraud and Phong shader programs + String vertexProgram = null; + String fragmentProgram = null; + Shader[] shaders = new Shader[2]; + String[] attrNames = { "numLights" }; + + try { + vertexProgram = StringIO.readFully(Resources.getResource("glsl_shader/gouraud.vert")); + fragmentProgram = StringIO.readFully(Resources.getResource("glsl_shader/gouraud.frag")); + } + catch (IOException e) { + throw new RuntimeException(e); + } + shaders[0] = new SourceCodeShader(Shader.SHADING_LANGUAGE_GLSL, + Shader.SHADER_TYPE_VERTEX, + vertexProgram); + shaders[1] = new SourceCodeShader(Shader.SHADING_LANGUAGE_GLSL, + Shader.SHADER_TYPE_FRAGMENT, + fragmentProgram); + gouraudSP = new GLSLShaderProgram(); + gouraudSP.setShaders(shaders); + + try { + vertexProgram = StringIO.readFully(Resources.getResource("glsl_shader/phong.vert")); + fragmentProgram = StringIO.readFully(Resources.getResource("glsl_shader/phong.frag")); + } + catch (IOException e) { + throw new RuntimeException(e); + } + shaders[0] = new SourceCodeShader(Shader.SHADING_LANGUAGE_GLSL, + Shader.SHADER_TYPE_VERTEX, + vertexProgram); + shaders[1] = new SourceCodeShader(Shader.SHADING_LANGUAGE_GLSL, + Shader.SHADER_TYPE_FRAGMENT, + fragmentProgram); + phongSP = new GLSLShaderProgram(); + phongSP.setShaders(shaders); + + if (gouraudButton.isSelected()) { + sApp.setShaderProgram(gouraudSP); + } else if (phongButton.isSelected()) { + sApp.setShaderProgram(phongSP); + } + Sphere sph = new Sphere(1.0f, Sphere.GENERATE_NORMALS, 30, sApp); + objTrans.addChild(sph); + + // Create a new Behavior object that will perform the + // desired operation on the specified transform and add + // it into the scene graph. + Transform3D yAxis = new Transform3D(); + yAxis.rotZ(Math.PI); + Alpha rotationAlpha = new Alpha(-1, 10000); + + RotationInterpolator rotator = + new RotationInterpolator(rotationAlpha, objTrans, yAxis, + 0.0f, (float) Math.PI*2.0f); + rotator.setSchedulingBounds(bounds); + objRoot.addChild(rotator); + + // Create the transform group node for the each light and initialize + // it to the identity. Enable the TRANSFORM_WRITE capability so that + // our behavior code can modify it at runtime. Add them to the root + // of the subgraph. + TransformGroup l1RotTrans = new TransformGroup(); + l1RotTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + objScale.addChild(l1RotTrans); + + TransformGroup l2RotTrans = new TransformGroup(); + l2RotTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + objScale.addChild(l2RotTrans); + + // Create transformations for the positional lights + t = new Transform3D(); + Vector3d lPos1 = new Vector3d(0.0, 0.0, 2.0); + t.set(lPos1); + TransformGroup l1Trans = new TransformGroup(t); + l1RotTrans.addChild(l1Trans); + +// t = new Transform3D(); +// Vector3d lPos2 = new Vector3d(0.5, 0.8, 2.0); +// t.set(lPos2); +// TransformGroup l2Trans = new TransformGroup(t); +// l2RotTrans.addChild(l2Trans); + + // Create Geometry for point lights + ColoringAttributes caL1 = new ColoringAttributes(); +// ColoringAttributes caL2 = new ColoringAttributes(); + caL1.setColor(lColor1); +// caL2.setColor(lColor2); + Appearance appL1 = new Appearance(); +// Appearance appL2 = new Appearance(); + appL1.setColoringAttributes(caL1); +// appL2.setColoringAttributes(caL2); + l1Trans.addChild(new Sphere(0.05f, appL1)); +// l2Trans.addChild(new Sphere(0.05f, appL2)); + + // Create lights + AmbientLight aLgt = new AmbientLight(alColor); + + Light lgt1 = null; +// Light lgt2 = null; + + Point3f lPoint = new Point3f(0.0f, 0.0f, 0.0f); + Point3f atten = new Point3f(1.0f, 0.0f, 0.0f); + Vector3f lDirect1 = new Vector3f(lPos1); +// Vector3f lDirect2 = new Vector3f(lPos2); + lDirect1.negate(); +// lDirect2.negate(); + + switch (lightType) { + case DIRECTIONAL_LIGHT: + lgt1 = new DirectionalLight(lColor1, lDirect1); +// lgt2 = new DirectionalLight(lColor2, lDirect2); + break; + case POINT_LIGHT: + assert false : "can't get here"; + lgt1 = new PointLight(lColor1, lPoint, atten); +// lgt2 = new PointLight(lColor2, lPoint, atten); + break; + case SPOT_LIGHT: + assert false : "can't get here"; + lgt1 = new SpotLight(lColor1, lPoint, atten, lDirect1, + 25.0f * (float)Math.PI / 180.0f, 10.0f); +// lgt2 = new SpotLight(lColor2, lPoint, atten, lDirect2, +// 25.0f * (float)Math.PI / 180.0f, 10.0f); + break; + } + + // Set the influencing bounds + aLgt.setInfluencingBounds(bounds); + lgt1.setInfluencingBounds(bounds); +// lgt2.setInfluencingBounds(bounds); + + // Add the lights into the scene graph + objScale.addChild(aLgt); + l1Trans.addChild(lgt1); +// l2Trans.addChild(lgt2); + + // Create a new Behavior object that will perform the desired + // operation on the specified transform object and add it into the + // scene graph. + yAxis = new Transform3D(); + Alpha rotor1Alpha = new Alpha(-1, Alpha.INCREASING_ENABLE, + 0, 0, + 4000, 0, 0, + 0, 0, 0); + RotationInterpolator rotator1 = + new RotationInterpolator(rotor1Alpha, + l1RotTrans, + yAxis, + 0.0f, (float) Math.PI*2.0f); + rotator1.setSchedulingBounds(bounds); + l1RotTrans.addChild(rotator1); + + // Create a new Behavior object that will perform the desired + // operation on the specified transform object and add it into the + // scene graph. + Alpha rotor2Alpha = new Alpha(-1, Alpha.INCREASING_ENABLE, + 0, 0, + 1000, 0, 0, + 0, 0, 0); + RotationInterpolator rotator2 = + new RotationInterpolator(rotor2Alpha, + l2RotTrans, + yAxis, + 0.0f, 0.0f); + bounds = new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + rotator2.setSchedulingBounds(bounds); + l2RotTrans.addChild(rotator2); + + return objRoot; + } + + private Canvas3D initScene() { + GraphicsConfiguration config = + SimpleUniverse.getPreferredConfiguration(); + + Canvas3D c = new Canvas3D(config); + + univ = new SimpleUniverse(c); + + // Add a ShaderErrorListener + univ.addShaderErrorListener(new ShaderErrorListener() { + public void errorOccurred(ShaderError error) { + error.printVerbose(); + JOptionPane.showMessageDialog(PhongShadingGLSL.this, + error.toString(), + "ShaderError", + JOptionPane.ERROR_MESSAGE); + } + }); + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + univ.getViewingPlatform().setNominalViewingTransform(); + + BranchGroup scene = createSceneGraph(); + univ.addBranchGraph(scene); + + return c; + } + + /** + * Creates new form PhongShadingGLSL + */ + public PhongShadingGLSL() { + // Initialize the GUI components + initComponents(); + + // Create the scene and add the Canvas3D to the drawing panel + Canvas3D c = initScene(); + drawingPanel.add(c, java.awt.BorderLayout.CENTER); + } + + + // ---------------------------------------------------------------- + + /** This method is called from within the constructor to + * initialize the form. + * WARNING: Do NOT modify this code. The content of this method is + * always regenerated by the Form Editor. + */ + // <editor-fold defaultstate="collapsed" desc=" Generated Code ">//GEN-BEGIN:initComponents + private void initComponents() { + java.awt.GridBagConstraints gridBagConstraints; + + shaderButtonGroup = new javax.swing.ButtonGroup(); + guiPanel = new javax.swing.JPanel(); + jPanel1 = new javax.swing.JPanel(); + gouraudButton = new javax.swing.JRadioButton(); + phongButton = new javax.swing.JRadioButton(); + drawingPanel = new javax.swing.JPanel(); + jMenuBar1 = new javax.swing.JMenuBar(); + fileMenu = new javax.swing.JMenu(); + exitMenuItem = new javax.swing.JMenuItem(); + + setDefaultCloseOperation(javax.swing.WindowConstants.EXIT_ON_CLOSE); + setTitle("Phong Shading Test"); + guiPanel.setLayout(new java.awt.GridBagLayout()); + + jPanel1.setLayout(new java.awt.GridBagLayout()); + + jPanel1.setBorder(javax.swing.BorderFactory.createTitledBorder("Shader")); + shaderButtonGroup.add(gouraudButton); + gouraudButton.setSelected(true); + gouraudButton.setText("Per-Vertex Lighting (Gouraud)"); + gouraudButton.setBorder(javax.swing.BorderFactory.createEmptyBorder(0, 0, 0, 0)); + gouraudButton.setMargin(new java.awt.Insets(0, 0, 0, 0)); + gouraudButton.addActionListener(new java.awt.event.ActionListener() { + public void actionPerformed(java.awt.event.ActionEvent evt) { + gouraudButtonActionPerformed(evt); + } + }); + + gridBagConstraints = new java.awt.GridBagConstraints(); + gridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL; + gridBagConstraints.insets = new java.awt.Insets(2, 2, 2, 2); + jPanel1.add(gouraudButton, gridBagConstraints); + + shaderButtonGroup.add(phongButton); + phongButton.setText("Per-Pixel Lighting (Phong)"); + phongButton.setBorder(javax.swing.BorderFactory.createEmptyBorder(0, 0, 0, 0)); + phongButton.setMargin(new java.awt.Insets(0, 0, 0, 0)); + phongButton.addActionListener(new java.awt.event.ActionListener() { + public void actionPerformed(java.awt.event.ActionEvent evt) { + phongButtonActionPerformed(evt); + } + }); + + gridBagConstraints = new java.awt.GridBagConstraints(); + gridBagConstraints.gridx = 0; + gridBagConstraints.gridy = 1; + gridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL; + gridBagConstraints.insets = new java.awt.Insets(2, 2, 2, 2); + jPanel1.add(phongButton, gridBagConstraints); + + gridBagConstraints = new java.awt.GridBagConstraints(); + gridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL; + gridBagConstraints.insets = new java.awt.Insets(4, 4, 4, 4); + guiPanel.add(jPanel1, gridBagConstraints); + + getContentPane().add(guiPanel, java.awt.BorderLayout.NORTH); + + drawingPanel.setLayout(new java.awt.BorderLayout()); + + drawingPanel.setPreferredSize(new java.awt.Dimension(500, 500)); + getContentPane().add(drawingPanel, java.awt.BorderLayout.CENTER); + + fileMenu.setText("File"); + exitMenuItem.setText("Exit"); + exitMenuItem.addActionListener(new java.awt.event.ActionListener() { + public void actionPerformed(java.awt.event.ActionEvent evt) { + exitMenuItemActionPerformed(evt); + } + }); + + fileMenu.add(exitMenuItem); + + jMenuBar1.add(fileMenu); + + setJMenuBar(jMenuBar1); + + pack(); + }// </editor-fold>//GEN-END:initComponents + + private void phongButtonActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_phongButtonActionPerformed + sApp.setShaderProgram(phongSP); + }//GEN-LAST:event_phongButtonActionPerformed + + private void gouraudButtonActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_gouraudButtonActionPerformed + sApp.setShaderProgram(gouraudSP); + }//GEN-LAST:event_gouraudButtonActionPerformed + + private void exitMenuItemActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_exitMenuItemActionPerformed + System.exit(0); + }//GEN-LAST:event_exitMenuItemActionPerformed + + /** + * @param args the command line arguments + */ + public static void main(String args[]) { + java.awt.EventQueue.invokeLater(new Runnable() { + public void run() { + new PhongShadingGLSL().setVisible(true); + } + }); + } + + // Variables declaration - do not modify//GEN-BEGIN:variables + private javax.swing.JPanel drawingPanel; + private javax.swing.JMenuItem exitMenuItem; + private javax.swing.JMenu fileMenu; + private javax.swing.JRadioButton gouraudButton; + private javax.swing.JPanel guiPanel; + private javax.swing.JMenuBar jMenuBar1; + private javax.swing.JPanel jPanel1; + private javax.swing.JRadioButton phongButton; + private javax.swing.ButtonGroup shaderButtonGroup; + // End of variables declaration//GEN-END:variables + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/glsl_shader/SamplerTestGLSL.form b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/SamplerTestGLSL.form new file mode 100644 index 0000000..6a1a031 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/SamplerTestGLSL.form @@ -0,0 +1,36 @@ +<?xml version="1.0" encoding="UTF-8" ?> + +<Form version="1.0" type="org.netbeans.modules.form.forminfo.JFrameFormInfo"> + <Properties> + <Property name="defaultCloseOperation" type="int" value="3"/> + <Property name="title" type="java.lang.String" value="SamplerTestGLSL"/> + </Properties> + <SyntheticProperties> + <SyntheticProperty name="formSizePolicy" type="int" value="1"/> + </SyntheticProperties> + <AuxValues> + <AuxValue name="FormSettings_generateMnemonicsCode" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_listenerGenerationStyle" type="java.lang.Integer" value="0"/> + <AuxValue name="FormSettings_variablesLocal" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_variablesModifier" type="java.lang.Integer" value="2"/> + <AuxValue name="designerSize" type="java.awt.Dimension" value="-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,1,44,0,0,1,-112"/> + </AuxValues> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + <SubComponents> + <Container class="javax.swing.JPanel" name="drawingPanel"> + <Properties> + <Property name="preferredSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor"> + <Dimension value="[500, 500]"/> + </Property> + </Properties> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout" value="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription"> + <BorderConstraints direction="Center"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + </Container> + </SubComponents> +</Form> diff --git a/src/main/java/org/jdesktop/j3d/examples/glsl_shader/SamplerTestGLSL.java b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/SamplerTestGLSL.java new file mode 100644 index 0000000..d2c3265 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/SamplerTestGLSL.java @@ -0,0 +1,278 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.glsl_shader; + +import java.awt.GraphicsConfiguration; +import java.io.IOException; +import java.net.URL; + +import javax.swing.JOptionPane; + +import org.jdesktop.j3d.examples.Resources; +import org.jogamp.java3d.Alpha; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.GLSLShaderProgram; +import org.jogamp.java3d.RotationInterpolator; +import org.jogamp.java3d.Shader; +import org.jogamp.java3d.ShaderAppearance; +import org.jogamp.java3d.ShaderAttribute; +import org.jogamp.java3d.ShaderAttributeSet; +import org.jogamp.java3d.ShaderAttributeValue; +import org.jogamp.java3d.ShaderError; +import org.jogamp.java3d.ShaderErrorListener; +import org.jogamp.java3d.ShaderProgram; +import org.jogamp.java3d.SourceCodeShader; +import org.jogamp.java3d.TexCoordGeneration; +import org.jogamp.java3d.Texture; +import org.jogamp.java3d.TextureUnitState; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.utils.geometry.Sphere; +import org.jogamp.java3d.utils.image.TextureLoader; +import org.jogamp.java3d.utils.shader.StringIO; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.java3d.utils.universe.ViewingPlatform; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Vector4f; + +public class SamplerTestGLSL extends javax.swing.JFrame { + + private static String cloudTexName = "resources/images/bg.jpg"; + private static String earthTexName = "resources/images/earth.jpg"; + private static String fragmentProgName = "glsl_shader/multitex.frag"; + private URL cloudURL = null; + private URL earthURL = null; + private static final int CLOUD = 0; + private static final int EARTH = 1; + + SimpleUniverse univ = null; + + public BranchGroup createSceneGraph() { + // Create the root of the branch graph + BranchGroup objRoot = new BranchGroup(); + + // Create the TransformGroup node and initialize it to the + // identity. Enable the TRANSFORM_WRITE capability so that + // our behavior code can modify it at run time. Add it to + // the root of the subgraph. + TransformGroup objTrans = new TransformGroup(); + objTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + objRoot.addChild(objTrans); + + // Create texture objects + cloudURL = Resources.getResource(cloudTexName); + Texture cloudTex = new TextureLoader(cloudURL, this).getTexture(); + earthURL = Resources.getResource(earthTexName); + Texture earthTex = new TextureLoader(earthURL, this).getTexture(); + + // Create the shader program + String vertexProgram = null; + String fragmentProgram = null; + try { + fragmentProgram = StringIO.readFully(Resources.getResource(fragmentProgName)); + } + catch (IOException e) { + System.err.println(e); + } + Shader[] shaders = new Shader[1]; + shaders[0] = new SourceCodeShader(Shader.SHADING_LANGUAGE_GLSL, + Shader.SHADER_TYPE_FRAGMENT, + fragmentProgram); + final String[] shaderAttrNames = { + "cloudFactor", + "cloudTex", + "earthTex", + }; + final Object[] shaderAttrValues = { + new Float(0.6f), + new Integer(0), + new Integer(1), + }; + ShaderProgram shaderProgram = new GLSLShaderProgram(); + shaderProgram.setShaders(shaders); + shaderProgram.setShaderAttrNames(shaderAttrNames); + + // Create the shader attribute set + ShaderAttributeSet shaderAttributeSet = new ShaderAttributeSet(); + for (int i = 0; i < shaderAttrNames.length; i++) { + ShaderAttribute shaderAttribute = + new ShaderAttributeValue(shaderAttrNames[i], shaderAttrValues[i]); + shaderAttributeSet.put(shaderAttribute); + } + + // Create shader appearance to hold the shader program and + // shader attributes + ShaderAppearance app = new ShaderAppearance(); + app.setShaderProgram(shaderProgram); + app.setShaderAttributeSet(shaderAttributeSet); + + // Setup texture coordinate generation + Vector4f plane0S = new Vector4f(3.0f, 1.5f, 0.3f, 0.0f); + Vector4f plane0T = new Vector4f(1.0f, 2.5f, 0.24f, 0.0f); + TexCoordGeneration tcg0 = + new TexCoordGeneration(TexCoordGeneration.OBJECT_LINEAR, + TexCoordGeneration.TEXTURE_COORDINATE_2, plane0S, plane0T); + + // Setup texture coordinate generation + TexCoordGeneration tcg1 = + new TexCoordGeneration(TexCoordGeneration.SPHERE_MAP, + TexCoordGeneration.TEXTURE_COORDINATE_2); + + // Put the textures in unit 0,1 + TextureUnitState[] tus = new TextureUnitState[2]; + tus[CLOUD] = new TextureUnitState(); + tus[CLOUD].setTexture(cloudTex); + tus[CLOUD].setTexCoordGeneration(tcg0); + tus[EARTH] = new TextureUnitState(); + tus[EARTH].setTexture(earthTex); + tus[EARTH].setTexCoordGeneration(tcg1); + app.setTextureUnitState(tus); + + // Create a Sphere object using the shader appearance, + // and add it into the scene graph. + Sphere sph = new Sphere(0.4f, Sphere.GENERATE_NORMALS, 30, app); + objTrans.addChild(sph); + + // Create a new Behavior object that will perform the + // desired operation on the specified transform and add + // it into the scene graph. + Transform3D yAxis = new Transform3D(); + Alpha rotationAlpha = new Alpha(-1, 4000); + + RotationInterpolator rotator = + new RotationInterpolator(rotationAlpha, objTrans, yAxis, + 0.0f, (float) Math.PI*2.0f); + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + rotator.setSchedulingBounds(bounds); + objRoot.addChild(rotator); + + // Have Java 3D perform optimizations on this scene graph. + //objRoot.compile(); + + return objRoot; + } + + private Canvas3D initScene() { + GraphicsConfiguration config = + SimpleUniverse.getPreferredConfiguration(); + + Canvas3D c = new Canvas3D(config); + + BranchGroup scene = createSceneGraph(); + univ = new SimpleUniverse(c); + + // Add a ShaderErrorListener + univ.addShaderErrorListener(new ShaderErrorListener() { + public void errorOccurred(ShaderError error) { + error.printVerbose(); + JOptionPane.showMessageDialog(SamplerTestGLSL.this, + error.toString(), + "ShaderError", + JOptionPane.ERROR_MESSAGE); + } + }); + + ViewingPlatform viewingPlatform = univ.getViewingPlatform(); + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + viewingPlatform.setNominalViewingTransform(); + + univ.addBranchGraph(scene); + + return c; + } + + /** + * Creates new form SamplerTestGLSL + */ + public SamplerTestGLSL() { + // Initialize the GUI components + initComponents(); + + // Create the scene and add the Canvas3D to the drawing panel + Canvas3D c = initScene(); + drawingPanel.add(c, java.awt.BorderLayout.CENTER); + } + + // ---------------------------------------------------------------- + + /** This method is called from within the constructor to + * initialize the form. + * WARNING: Do NOT modify this code. The content of this method is + * always regenerated by the Form Editor. + */ + // <editor-fold defaultstate="collapsed" desc=" Generated Code ">//GEN-BEGIN:initComponents + private void initComponents() { + drawingPanel = new javax.swing.JPanel(); + + setDefaultCloseOperation(javax.swing.WindowConstants.EXIT_ON_CLOSE); + setTitle("SamplerTestGLSL"); + drawingPanel.setLayout(new java.awt.BorderLayout()); + + drawingPanel.setPreferredSize(new java.awt.Dimension(500, 500)); + getContentPane().add(drawingPanel, java.awt.BorderLayout.CENTER); + + pack(); + }// </editor-fold>//GEN-END:initComponents + + /** + * @param args the command line arguments + */ + public static void main(String args[]) { + java.awt.EventQueue.invokeLater(new Runnable() { + public void run() { + new SamplerTestGLSL().setVisible(true); + } + }); + } + + // Variables declaration - do not modify//GEN-BEGIN:variables + private javax.swing.JPanel drawingPanel; + // End of variables declaration//GEN-END:variables + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/glsl_shader/ShaderTestGLSL.form b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/ShaderTestGLSL.form new file mode 100644 index 0000000..714273d --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/ShaderTestGLSL.form @@ -0,0 +1,266 @@ +<?xml version="1.0" encoding="UTF-8" ?> + +<Form version="1.2" type="org.netbeans.modules.form.forminfo.JFrameFormInfo"> + <NonVisualComponents> + <Component class="javax.swing.ButtonGroup" name="densityButtonGroup"> + </Component> + <Component class="javax.swing.ButtonGroup" name="colorButtonGroup"> + </Component> + <Component class="javax.swing.ButtonGroup" name="sceneGraphButtonGroup"> + </Component> + <Menu class="javax.swing.JMenuBar" name="jMenuBar1"> + <SubComponents> + <Menu class="javax.swing.JMenu" name="fileMenu"> + <Properties> + <Property name="text" type="java.lang.String" value="File"/> + </Properties> + <SubComponents> + <MenuItem class="javax.swing.JMenuItem" name="exitMenuItem"> + <Properties> + <Property name="text" type="java.lang.String" value="Exit"/> + </Properties> + <Events> + <EventHandler event="actionPerformed" listener="java.awt.event.ActionListener" parameters="java.awt.event.ActionEvent" handler="exitMenuItemActionPerformed"/> + </Events> + </MenuItem> + </SubComponents> + </Menu> + </SubComponents> + </Menu> + </NonVisualComponents> + <Properties> + <Property name="title" type="java.lang.String" value="Window Title"/> + </Properties> + <SyntheticProperties> + <SyntheticProperty name="menuBar" type="java.lang.String" value="jMenuBar1"/> + <SyntheticProperty name="formSizePolicy" type="int" value="1"/> + </SyntheticProperties> + <Events> + <EventHandler event="windowClosing" listener="java.awt.event.WindowListener" parameters="java.awt.event.WindowEvent" handler="exitForm"/> + </Events> + <AuxValues> + <AuxValue name="FormSettings_generateMnemonicsCode" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_listenerGenerationStyle" type="java.lang.Integer" value="0"/> + <AuxValue name="FormSettings_variablesLocal" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_variablesModifier" type="java.lang.Integer" value="2"/> + <AuxValue name="designerSize" type="java.awt.Dimension" value="-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,1,-85,0,0,2,0"/> + </AuxValues> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + <SubComponents> + <Container class="javax.swing.JPanel" name="mainPanel"> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout" value="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription"> + <BorderConstraints direction="Center"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + <SubComponents> + <Container class="javax.swing.JPanel" name="guiPanel"> + <Properties> + <Property name="border" type="javax.swing.border.Border" editor="org.netbeans.modules.form.editors2.BorderEditor"> + <Border info="org.netbeans.modules.form.compat2.border.LineBorderInfo"> + <LineBorder/> + </Border> + </Property> + </Properties> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout" value="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription"> + <BorderConstraints direction="North"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBoxLayout"/> + <SubComponents> + <Container class="javax.swing.JPanel" name="densityPanel"> + <Properties> + <Property name="border" type="javax.swing.border.Border" editor="org.netbeans.modules.form.editors2.BorderEditor"> + <Border info="org.netbeans.modules.form.compat2.border.TitledBorderInfo"> + <TitledBorder title="Density"/> + </Border> + </Property> + </Properties> + <AccessibilityProperties> + <Property name="AccessibleContext.accessibleName" type="java.lang.String" value="ShaderAttributeValue 
"/> + </AccessibilityProperties> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout"/> + <SubComponents> + <Component class="javax.swing.JRadioButton" name="zeroButton"> + <Properties> + <Property name="buttonGroup" type="javax.swing.ButtonGroup" editor="org.netbeans.modules.form.RADComponent$ButtonGroupPropertyEditor"> + <ComponentRef name="densityButtonGroup"/> + </Property> + <Property name="text" type="java.lang.String" value="Zero"/> + </Properties> + <Events> + <EventHandler event="actionPerformed" listener="java.awt.event.ActionListener" parameters="java.awt.event.ActionEvent" handler="zeroButtonActionPerformed"/> + </Events> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout" value="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription"> + <GridBagConstraints gridX="-1" gridY="-1" gridWidth="1" gridHeight="1" fill="2" ipadX="0" ipadY="0" insetsTop="0" insetsLeft="0" insetsBottom="0" insetsRight="0" anchor="10" weightX="0.0" weightY="0.0"/> + </Constraint> + </Constraints> + </Component> + <Component class="javax.swing.JRadioButton" name="halfButton"> + <Properties> + <Property name="buttonGroup" type="javax.swing.ButtonGroup" editor="org.netbeans.modules.form.RADComponent$ButtonGroupPropertyEditor"> + <ComponentRef name="densityButtonGroup"/> + </Property> + <Property name="text" type="java.lang.String" value="Half"/> + </Properties> + <Events> + <EventHandler event="actionPerformed" listener="java.awt.event.ActionListener" parameters="java.awt.event.ActionEvent" handler="halfButtonActionPerformed"/> + </Events> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout" value="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription"> + <GridBagConstraints gridX="0" gridY="1" gridWidth="1" gridHeight="1" fill="2" ipadX="0" ipadY="0" insetsTop="0" insetsLeft="0" insetsBottom="0" insetsRight="0" anchor="10" weightX="0.0" weightY="0.0"/> + </Constraint> + </Constraints> + </Component> + <Component class="javax.swing.JRadioButton" name="fullButton"> + <Properties> + <Property name="buttonGroup" type="javax.swing.ButtonGroup" editor="org.netbeans.modules.form.RADComponent$ButtonGroupPropertyEditor"> + <ComponentRef name="densityButtonGroup"/> + </Property> + <Property name="selected" type="boolean" value="true"/> + <Property name="text" type="java.lang.String" value="Full"/> + </Properties> + <Events> + <EventHandler event="actionPerformed" listener="java.awt.event.ActionListener" parameters="java.awt.event.ActionEvent" handler="fullButtonActionPerformed"/> + </Events> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout" value="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription"> + <GridBagConstraints gridX="0" gridY="2" gridWidth="1" gridHeight="1" fill="2" ipadX="0" ipadY="0" insetsTop="0" insetsLeft="0" insetsBottom="0" insetsRight="0" anchor="10" weightX="0.0" weightY="0.0"/> + </Constraint> + </Constraints> + </Component> + </SubComponents> + </Container> + <Container class="javax.swing.JPanel" name="colorPanel"> + <Properties> + <Property name="border" type="javax.swing.border.Border" editor="org.netbeans.modules.form.editors2.BorderEditor"> + <Border info="org.netbeans.modules.form.compat2.border.TitledBorderInfo"> + <TitledBorder title="Color"/> + </Border> + </Property> + </Properties> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout"/> + <SubComponents> + <Component class="javax.swing.JRadioButton" name="goldButton"> + <Properties> + <Property name="buttonGroup" type="javax.swing.ButtonGroup" editor="org.netbeans.modules.form.RADComponent$ButtonGroupPropertyEditor"> + <ComponentRef name="colorButtonGroup"/> + </Property> + <Property name="selected" type="boolean" value="true"/> + <Property name="text" type="java.lang.String" value="Gold"/> + </Properties> + <Events> + <EventHandler event="actionPerformed" listener="java.awt.event.ActionListener" parameters="java.awt.event.ActionEvent" handler="goldButtonActionPerformed"/> + </Events> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout" value="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription"> + <GridBagConstraints gridX="-1" gridY="-1" gridWidth="1" gridHeight="1" fill="2" ipadX="0" ipadY="0" insetsTop="0" insetsLeft="0" insetsBottom="0" insetsRight="0" anchor="10" weightX="0.0" weightY="0.0"/> + </Constraint> + </Constraints> + </Component> + <Component class="javax.swing.JRadioButton" name="silverButton"> + <Properties> + <Property name="buttonGroup" type="javax.swing.ButtonGroup" editor="org.netbeans.modules.form.RADComponent$ButtonGroupPropertyEditor"> + <ComponentRef name="colorButtonGroup"/> + </Property> + <Property name="text" type="java.lang.String" value="Silver"/> + </Properties> + <Events> + <EventHandler event="actionPerformed" listener="java.awt.event.ActionListener" parameters="java.awt.event.ActionEvent" handler="silverButtonActionPerformed"/> + </Events> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout" value="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription"> + <GridBagConstraints gridX="0" gridY="1" gridWidth="1" gridHeight="1" fill="2" ipadX="0" ipadY="0" insetsTop="0" insetsLeft="0" insetsBottom="0" insetsRight="0" anchor="10" weightX="0.0" weightY="0.0"/> + </Constraint> + </Constraints> + </Component> + </SubComponents> + </Container> + <Container class="javax.swing.JPanel" name="sceneGraphPanel"> + <Properties> + <Property name="border" type="javax.swing.border.Border" editor="org.netbeans.modules.form.editors2.BorderEditor"> + <Border info="org.netbeans.modules.form.compat2.border.TitledBorderInfo"> + <TitledBorder title="Scene Graph"/> + </Border> + </Property> + </Properties> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout"/> + <SubComponents> + <Component class="javax.swing.JToggleButton" name="DetachButton"> + <Properties> + <Property name="buttonGroup" type="javax.swing.ButtonGroup" editor="org.netbeans.modules.form.RADComponent$ButtonGroupPropertyEditor"> + <ComponentRef name="sceneGraphButtonGroup"/> + </Property> + <Property name="selected" type="boolean" value="true"/> + <Property name="text" type="java.lang.String" value="Detach"/> + </Properties> + <Events> + <EventHandler event="actionPerformed" listener="java.awt.event.ActionListener" parameters="java.awt.event.ActionEvent" handler="DetachButtonActionPerformed"/> + </Events> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout" value="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription"> + <GridBagConstraints gridX="-1" gridY="-1" gridWidth="1" gridHeight="1" fill="2" ipadX="0" ipadY="0" insetsTop="0" insetsLeft="0" insetsBottom="0" insetsRight="0" anchor="10" weightX="0.0" weightY="0.0"/> + </Constraint> + </Constraints> + </Component> + <Component class="javax.swing.JToggleButton" name="AttachButton"> + <Properties> + <Property name="buttonGroup" type="javax.swing.ButtonGroup" editor="org.netbeans.modules.form.RADComponent$ButtonGroupPropertyEditor"> + <ComponentRef name="sceneGraphButtonGroup"/> + </Property> + <Property name="text" type="java.lang.String" value="Create"/> + </Properties> + <Events> + <EventHandler event="actionPerformed" listener="java.awt.event.ActionListener" parameters="java.awt.event.ActionEvent" handler="AttachButtonActionPerformed"/> + </Events> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout" value="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription"> + <GridBagConstraints gridX="0" gridY="1" gridWidth="1" gridHeight="1" fill="2" ipadX="0" ipadY="0" insetsTop="0" insetsLeft="0" insetsBottom="0" insetsRight="0" anchor="10" weightX="0.0" weightY="0.0"/> + </Constraint> + </Constraints> + </Component> + <Component class="javax.swing.JButton" name="replaceSPButton"> + <Properties> + <Property name="text" type="java.lang.String" value="Replace Shader"/> + <Property name="enabled" type="boolean" value="false"/> + </Properties> + <Events> + <EventHandler event="actionPerformed" listener="java.awt.event.ActionListener" parameters="java.awt.event.ActionEvent" handler="replaceSPButtonActionPerformed"/> + </Events> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout" value="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription"> + <GridBagConstraints gridX="0" gridY="2" gridWidth="1" gridHeight="1" fill="2" ipadX="0" ipadY="0" insetsTop="0" insetsLeft="0" insetsBottom="0" insetsRight="0" anchor="10" weightX="0.0" weightY="0.0"/> + </Constraint> + </Constraints> + </Component> + </SubComponents> + </Container> + </SubComponents> + </Container> + <Container class="javax.swing.JPanel" name="drawingPanel"> + <Properties> + <Property name="preferredSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor"> + <Dimension value="[500, 500]"/> + </Property> + </Properties> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout" value="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription"> + <BorderConstraints direction="Center"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + </Container> + </SubComponents> + </Container> + </SubComponents> +</Form> diff --git a/src/main/java/org/jdesktop/j3d/examples/glsl_shader/ShaderTestGLSL.java b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/ShaderTestGLSL.java new file mode 100644 index 0000000..f7f82e9 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/ShaderTestGLSL.java @@ -0,0 +1,707 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.glsl_shader; + +import java.awt.GraphicsConfiguration; +import java.io.IOException; + +import javax.swing.JOptionPane; + +import org.jdesktop.j3d.examples.Resources; +import org.jogamp.java3d.Alpha; +import org.jogamp.java3d.Background; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.GLSLShaderProgram; +import org.jogamp.java3d.Material; +import org.jogamp.java3d.PositionInterpolator; +import org.jogamp.java3d.Shader; +import org.jogamp.java3d.ShaderAppearance; +import org.jogamp.java3d.ShaderAttributeObject; +import org.jogamp.java3d.ShaderAttributeSet; +import org.jogamp.java3d.ShaderAttributeValue; +import org.jogamp.java3d.ShaderError; +import org.jogamp.java3d.ShaderErrorListener; +import org.jogamp.java3d.ShaderProgram; +import org.jogamp.java3d.Shape3D; +import org.jogamp.java3d.SourceCodeShader; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.View; +import org.jogamp.java3d.utils.geometry.Sphere; +import org.jogamp.java3d.utils.shader.StringIO; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.java3d.utils.universe.ViewingPlatform; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Point3f; +import org.jogamp.vecmath.Vector3d; + +public class ShaderTestGLSL extends javax.swing.JFrame { + + static final int GOLD = 1; + static final int SILVER = 2; + + static final int DIMPLE_SHADER = 1; + static final int BRICK_SHADER = 2; + static final int WOOD_SHADER = 3; + static final int POLKADOT3D_SHADER = 4; + + static final String[] shaderAttrNames1 = { + "Density", "Size", "LightPosition", "Color" + }; + + static final String[] shaderAttrNames2 = { + "BrickColor", "LightPosition" + }; + + private SimpleUniverse univ = null; + private View view; + private BranchGroup transpObj; + private BranchGroup scene = null; + private int shaderSelected = DIMPLE_SHADER; + private float density = 16.0f; + private int color = GOLD; + + private Color3f eColor = new Color3f(0.2f, 0.2f, 0.2f); + private Color3f sColor = new Color3f(0.8f, 0.8f, 0.8f); + private Color3f objColor = new Color3f(0.6f, 0.6f, 0.6f); + private Color3f bgColor = new Color3f(0.05f, 0.05f, 0.2f); + private Color3f gold = new Color3f(0.7f, 0.6f, 0.18f); + private Color3f silver = new Color3f(0.75f, 0.75f, 0.75f); + + // Handlers for doing update + private ShaderAppearance sApp1 = null; + private ShaderAppearance sApp2 = null; + private ShaderAppearance sApp3 = null; + private ShaderAppearance sApp4 = null; + private ShaderProgram sp1 = null; + private ShaderProgram sp2 = null; + private ShaderProgram sp3 = null; + private ShaderProgram sp4 = null; + private ShaderAttributeSet sas1 = null; + private ShaderAttributeSet sas2 = null; + private ShaderAttributeObject sao1 = null; + private ShaderAttributeObject sao2 = null; + private Sphere sphere = null; + private Shape3D s3d = null; + + private Material createMaterial() { + Material m; + m = new Material(objColor, eColor, objColor, sColor, 100.0f); + m.setLightingEnable(true); + return m; + } + + private ShaderProgram createGLSLShaderProgram(int index) { + String vertexProgram = null; + String fragmentProgram = null; + try { + switch (index) { + case DIMPLE_SHADER: + vertexProgram = StringIO.readFully(Resources.getResource("glsl_shader/dimple.vert")); + fragmentProgram = StringIO.readFully(Resources.getResource("glsl_shader/dimple.frag")); + break; + case BRICK_SHADER: + vertexProgram = StringIO.readFully(Resources.getResource("glsl_shader/aabrick.vert")); + fragmentProgram = StringIO.readFully(Resources.getResource("glsl_shader/aabrick.frag")); + break; + case WOOD_SHADER: + vertexProgram = StringIO.readFully(Resources.getResource("glsl_shader/wood.vert")); + fragmentProgram = StringIO.readFully(Resources.getResource("glsl_shader/wood.frag")); + break; + case POLKADOT3D_SHADER: + vertexProgram = StringIO.readFully(Resources.getResource("glsl_shader/polkadot3d.vert")); + fragmentProgram = StringIO.readFully(Resources.getResource("glsl_shader/polkadot3d.frag")); + break; + default: + } + } + catch (IOException e) { + throw new RuntimeException(e); + } + Shader[] shaders = new Shader[2]; + shaders[0] = new SourceCodeShader(Shader.SHADING_LANGUAGE_GLSL, + Shader.SHADER_TYPE_VERTEX, + vertexProgram); + shaders[1] = new SourceCodeShader(Shader.SHADING_LANGUAGE_GLSL, + Shader.SHADER_TYPE_FRAGMENT, + fragmentProgram); + ShaderProgram shaderProgram = new GLSLShaderProgram(); + shaderProgram.setShaders(shaders); + return shaderProgram; + } + + private ShaderAttributeSet createShaderAttributeSet(int index) { + ShaderAttributeSet shaderAttributeSet = new ShaderAttributeSet(); + ShaderAttributeObject shaderAttribute = null; + + switch (index) { + case DIMPLE_SHADER: + // "Density", "Size", "Scale", "Color", "LightPosition" + shaderAttribute = new ShaderAttributeValue("Size", new Float(0.25)); + shaderAttributeSet.put(shaderAttribute); + shaderAttribute = new ShaderAttributeValue("LightPosition", + new Point3f(0.0f, 0.0f, 0.5f)); + shaderAttributeSet.put(shaderAttribute); + + sao1 = new ShaderAttributeValue("Density", new Float(density)); + sao1.setCapability(ShaderAttributeObject.ALLOW_VALUE_READ); + sao1.setCapability(ShaderAttributeObject.ALLOW_VALUE_WRITE); + shaderAttributeSet.put(sao1); + + if(color == GOLD) { + sao2 = new ShaderAttributeValue("Color", gold); + } + else if (color == SILVER) { + sao2 = new ShaderAttributeValue("Color", silver); + } + sao2.setCapability(ShaderAttributeObject.ALLOW_VALUE_READ); + sao2.setCapability(ShaderAttributeObject.ALLOW_VALUE_WRITE); + shaderAttributeSet.put(sao2); + break; + + case BRICK_SHADER: + // "BrickColor", "LightPosition" + shaderAttribute = new ShaderAttributeValue("BrickColor", + new Color3f(1.0f, 0.3f, 0.2f)); + shaderAttributeSet.put(shaderAttribute); + shaderAttribute = new ShaderAttributeValue("LightPosition", + new Point3f(0.0f, 0.0f, 0.5f)); + shaderAttributeSet.put(shaderAttribute); + break; + default: + assert false; + } + return shaderAttributeSet; + } + + private ShaderAppearance createShaderAppearance() { + ShaderAppearance sApp = new ShaderAppearance(); + sApp.setMaterial(createMaterial()); + return sApp; + } + + + private BranchGroup createSubSceneGraph() { + // Create the sub-root of the branch graph + BranchGroup subRoot = new BranchGroup(); + + // + // Create 1 spheres with a GLSLShader and add it into the scene graph. + // + sApp1 = createShaderAppearance(); + sApp1.setCapability(ShaderAppearance.ALLOW_SHADER_PROGRAM_READ); + sApp1.setCapability(ShaderAppearance.ALLOW_SHADER_PROGRAM_WRITE); + sApp1.setCapability(ShaderAppearance.ALLOW_SHADER_ATTRIBUTE_SET_READ); + sApp1.setCapability(ShaderAppearance.ALLOW_SHADER_ATTRIBUTE_SET_WRITE); + + sp1 = createGLSLShaderProgram(1); + sp1.setShaderAttrNames(shaderAttrNames1); + sas1 = createShaderAttributeSet(1); + sas1.setCapability(ShaderAttributeSet.ALLOW_ATTRIBUTES_READ); + sas1.setCapability(ShaderAttributeSet.ALLOW_ATTRIBUTES_WRITE); + sApp1.setShaderProgram(sp1); + sApp1.setShaderAttributeSet(sas1); + + // Setup Brick shader + sp2 = createGLSLShaderProgram(2); + sp2.setShaderAttrNames(shaderAttrNames2); + sas2 = createShaderAttributeSet(2); + sApp2 = createShaderAppearance(); + sApp2.setShaderProgram(sp2); + sApp2.setShaderAttributeSet(sas2); + + // Setup Wood shader + sp3 = createGLSLShaderProgram(3); + sApp3 = createShaderAppearance(); + sApp3.setShaderProgram(sp3); + + // Setup Polkadot3d shader + sp4 = createGLSLShaderProgram(4); + sApp4 = createShaderAppearance(); + sApp4.setShaderProgram(sp4); + + sphere = new Sphere(1.5f, Sphere.GENERATE_NORMALS, 200, null); + s3d = (Shape3D)sphere.getShape(); + s3d.setCapability(Shape3D.ALLOW_APPEARANCE_READ); + s3d.setCapability(Shape3D.ALLOW_APPEARANCE_WRITE); + s3d.setAppearance(sApp1); + + TransformGroup objTG; + Transform3D t = new Transform3D(); + t.set(new Vector3d(0.0, 0.0, 0.0)); + objTG = new TransformGroup(t); + objTG.addChild(sphere); + subRoot.addChild(objTG); + + return subRoot; + } + + private BranchGroup createSceneGraph(int selectedScene) { + // Create the root of the branch graph + BranchGroup objRoot = new BranchGroup(); + objRoot.setCapability(BranchGroup.ALLOW_DETACH); + + // Create a Transformgroup to scale all objects so they + // appear in the scene. + TransformGroup objScale = new TransformGroup(); + Transform3D t3d = new Transform3D(); + t3d.setScale(0.4); + objScale.setTransform(t3d); + objRoot.addChild(objScale); + + // Create a bounds for the background and lights + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + + // Set up the background + Background bg = new Background(bgColor); + bg.setApplicationBounds(bounds); + objScale.addChild(bg); + + objScale.addChild(createSubSceneGraph()); + + // Create a position interpolator and attach it to the view + // platform + TransformGroup vpTrans = + univ.getViewingPlatform().getViewPlatformTransform(); + Transform3D axisOfTranslation = new Transform3D(); + Alpha transAlpha = new Alpha(-1, + Alpha.INCREASING_ENABLE | + Alpha.DECREASING_ENABLE, + 0, 0, + 5000, 0, 0, + 5000, 0, 0); + axisOfTranslation.rotY(-Math.PI/2.0); + PositionInterpolator translator = + new PositionInterpolator(transAlpha, + vpTrans, + axisOfTranslation, + 2.0f, 3.5f); + translator.setSchedulingBounds(bounds); + objScale.addChild(translator); + + // Let Java 3D perform optimizations on this scene graph. + objRoot.compile(); + + return objRoot; + } + + private Canvas3D initScene() { + GraphicsConfiguration config = + SimpleUniverse.getPreferredConfiguration(); + + Canvas3D c = new Canvas3D(config); + + univ = new SimpleUniverse(c); + + // Add a ShaderErrorListener + univ.addShaderErrorListener(new ShaderErrorListener() { + public void errorOccurred(ShaderError error) { + error.printVerbose(); + JOptionPane.showMessageDialog(ShaderTestGLSL.this, + error.toString(), + "ShaderError", + JOptionPane.ERROR_MESSAGE); + } + }); + + ViewingPlatform viewingPlatform = univ.getViewingPlatform(); + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + viewingPlatform.setNominalViewingTransform(); + + view = univ.getViewer().getView(); + + return c; + } + + /** + * Creates new form ShaderTestGLSL + */ + public ShaderTestGLSL() { + // Initialize the GUI components + initComponents(); + + // Create the scene and add the Canvas3D to the drawing panel + Canvas3D c = initScene(); + drawingPanel.add(c, java.awt.BorderLayout.CENTER); + } + + + // ---------------------------------------------------------------- + + /** This method is called from within the constructor to + * initialize the form. + * WARNING: Do NOT modify this code. The content of this method is + * always regenerated by the Form Editor. + */ + // <editor-fold defaultstate="collapsed" desc=" Generated Code ">//GEN-BEGIN:initComponents + private void initComponents() { + java.awt.GridBagConstraints gridBagConstraints; + + densityButtonGroup = new javax.swing.ButtonGroup(); + colorButtonGroup = new javax.swing.ButtonGroup(); + sceneGraphButtonGroup = new javax.swing.ButtonGroup(); + mainPanel = new javax.swing.JPanel(); + guiPanel = new javax.swing.JPanel(); + densityPanel = new javax.swing.JPanel(); + zeroButton = new javax.swing.JRadioButton(); + halfButton = new javax.swing.JRadioButton(); + fullButton = new javax.swing.JRadioButton(); + colorPanel = new javax.swing.JPanel(); + goldButton = new javax.swing.JRadioButton(); + silverButton = new javax.swing.JRadioButton(); + sceneGraphPanel = new javax.swing.JPanel(); + DetachButton = new javax.swing.JToggleButton(); + AttachButton = new javax.swing.JToggleButton(); + replaceSPButton = new javax.swing.JButton(); + drawingPanel = new javax.swing.JPanel(); + jMenuBar1 = new javax.swing.JMenuBar(); + fileMenu = new javax.swing.JMenu(); + exitMenuItem = new javax.swing.JMenuItem(); + + setTitle("Window Title"); + addWindowListener(new java.awt.event.WindowAdapter() { + public void windowClosing(java.awt.event.WindowEvent evt) { + exitForm(evt); + } + }); + + mainPanel.setLayout(new java.awt.BorderLayout()); + + guiPanel.setLayout(new javax.swing.BoxLayout(guiPanel, javax.swing.BoxLayout.X_AXIS)); + + guiPanel.setBorder(new javax.swing.border.LineBorder(new java.awt.Color(0, 0, 0))); + densityPanel.setLayout(new java.awt.GridBagLayout()); + + densityPanel.setBorder(new javax.swing.border.TitledBorder("Density")); + densityButtonGroup.add(zeroButton); + zeroButton.setText("Zero"); + zeroButton.addActionListener(new java.awt.event.ActionListener() { + public void actionPerformed(java.awt.event.ActionEvent evt) { + zeroButtonActionPerformed(evt); + } + }); + + gridBagConstraints = new java.awt.GridBagConstraints(); + gridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL; + densityPanel.add(zeroButton, gridBagConstraints); + + densityButtonGroup.add(halfButton); + halfButton.setText("Half"); + halfButton.addActionListener(new java.awt.event.ActionListener() { + public void actionPerformed(java.awt.event.ActionEvent evt) { + halfButtonActionPerformed(evt); + } + }); + + gridBagConstraints = new java.awt.GridBagConstraints(); + gridBagConstraints.gridx = 0; + gridBagConstraints.gridy = 1; + gridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL; + densityPanel.add(halfButton, gridBagConstraints); + + densityButtonGroup.add(fullButton); + fullButton.setSelected(true); + fullButton.setText("Full"); + fullButton.addActionListener(new java.awt.event.ActionListener() { + public void actionPerformed(java.awt.event.ActionEvent evt) { + fullButtonActionPerformed(evt); + } + }); + + gridBagConstraints = new java.awt.GridBagConstraints(); + gridBagConstraints.gridx = 0; + gridBagConstraints.gridy = 2; + gridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL; + densityPanel.add(fullButton, gridBagConstraints); + + guiPanel.add(densityPanel); + densityPanel.getAccessibleContext().setAccessibleName("ShaderAttributeValue \n"); + + colorPanel.setLayout(new java.awt.GridBagLayout()); + + colorPanel.setBorder(new javax.swing.border.TitledBorder("Color")); + colorButtonGroup.add(goldButton); + goldButton.setSelected(true); + goldButton.setText("Gold"); + goldButton.addActionListener(new java.awt.event.ActionListener() { + public void actionPerformed(java.awt.event.ActionEvent evt) { + goldButtonActionPerformed(evt); + } + }); + + gridBagConstraints = new java.awt.GridBagConstraints(); + gridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL; + colorPanel.add(goldButton, gridBagConstraints); + + colorButtonGroup.add(silverButton); + silverButton.setText("Silver"); + silverButton.addActionListener(new java.awt.event.ActionListener() { + public void actionPerformed(java.awt.event.ActionEvent evt) { + silverButtonActionPerformed(evt); + } + }); + + gridBagConstraints = new java.awt.GridBagConstraints(); + gridBagConstraints.gridx = 0; + gridBagConstraints.gridy = 1; + gridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL; + colorPanel.add(silverButton, gridBagConstraints); + + guiPanel.add(colorPanel); + + sceneGraphPanel.setLayout(new java.awt.GridBagLayout()); + + sceneGraphPanel.setBorder(new javax.swing.border.TitledBorder("Scene Graph")); + sceneGraphButtonGroup.add(DetachButton); + DetachButton.setSelected(true); + DetachButton.setText("Detach"); + DetachButton.addActionListener(new java.awt.event.ActionListener() { + public void actionPerformed(java.awt.event.ActionEvent evt) { + DetachButtonActionPerformed(evt); + } + }); + + gridBagConstraints = new java.awt.GridBagConstraints(); + gridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL; + sceneGraphPanel.add(DetachButton, gridBagConstraints); + + sceneGraphButtonGroup.add(AttachButton); + AttachButton.setText("Create"); + AttachButton.addActionListener(new java.awt.event.ActionListener() { + public void actionPerformed(java.awt.event.ActionEvent evt) { + AttachButtonActionPerformed(evt); + } + }); + + gridBagConstraints = new java.awt.GridBagConstraints(); + gridBagConstraints.gridx = 0; + gridBagConstraints.gridy = 1; + gridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL; + sceneGraphPanel.add(AttachButton, gridBagConstraints); + + replaceSPButton.setText("Replace Shader"); + replaceSPButton.setEnabled(false); + replaceSPButton.addActionListener(new java.awt.event.ActionListener() { + public void actionPerformed(java.awt.event.ActionEvent evt) { + replaceSPButtonActionPerformed(evt); + } + }); + + gridBagConstraints = new java.awt.GridBagConstraints(); + gridBagConstraints.gridx = 0; + gridBagConstraints.gridy = 2; + gridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL; + sceneGraphPanel.add(replaceSPButton, gridBagConstraints); + + guiPanel.add(sceneGraphPanel); + + mainPanel.add(guiPanel, java.awt.BorderLayout.NORTH); + + drawingPanel.setLayout(new java.awt.BorderLayout()); + + drawingPanel.setPreferredSize(new java.awt.Dimension(500, 500)); + mainPanel.add(drawingPanel, java.awt.BorderLayout.CENTER); + + getContentPane().add(mainPanel, java.awt.BorderLayout.CENTER); + + fileMenu.setText("File"); + exitMenuItem.setText("Exit"); + exitMenuItem.addActionListener(new java.awt.event.ActionListener() { + public void actionPerformed(java.awt.event.ActionEvent evt) { + exitMenuItemActionPerformed(evt); + } + }); + + fileMenu.add(exitMenuItem); + + jMenuBar1.add(fileMenu); + + setJMenuBar(jMenuBar1); + + pack(); + } + // </editor-fold>//GEN-END:initComponents + + private void silverButtonActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_silverButtonActionPerformed + color = SILVER; + if(scene != null) { + sao2.setValue(silver); + } + }//GEN-LAST:event_silverButtonActionPerformed + + private void goldButtonActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_goldButtonActionPerformed + color = GOLD; + if(scene != null) { + sao2.setValue(gold); + } + }//GEN-LAST:event_goldButtonActionPerformed + + private void replaceSPButtonActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_replaceSPButtonActionPerformed + if (shaderSelected != DIMPLE_SHADER) { + goldButton.setEnabled(false); + silverButton.setEnabled(false); + zeroButton.setEnabled(false); + halfButton.setEnabled(false); + fullButton.setEnabled(false); + } + + switch(shaderSelected) { + case DIMPLE_SHADER: + s3d.setAppearance(sApp1); + goldButton.setEnabled(true); + silverButton.setEnabled(true); + zeroButton.setEnabled(true); + halfButton.setEnabled(true); + fullButton.setEnabled(true); + shaderSelected = BRICK_SHADER; + break; + case BRICK_SHADER: + s3d.setAppearance(sApp2); + shaderSelected = WOOD_SHADER; + break; + case WOOD_SHADER: + s3d.setAppearance(sApp3); + shaderSelected = POLKADOT3D_SHADER; + break; + case POLKADOT3D_SHADER: + s3d.setAppearance(sApp4); + shaderSelected = DIMPLE_SHADER; + break; + default: + assert false; + } + + }//GEN-LAST:event_replaceSPButtonActionPerformed + + private void fullButtonActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_fullButtonActionPerformed + density = 16.0f; + if (scene != null) { + sao1.setValue(new Float(density)); + } + }//GEN-LAST:event_fullButtonActionPerformed + + private void DetachButtonActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_DetachButtonActionPerformed + if (scene != null) { + scene.detach(); + scene = null; + replaceSPButton.setEnabled(false); + goldButton.setEnabled(true); + silverButton.setEnabled(true); + zeroButton.setEnabled(true); + halfButton.setEnabled(true); + fullButton.setEnabled(true); + shaderSelected = DIMPLE_SHADER; + } + }//GEN-LAST:event_DetachButtonActionPerformed + + private void AttachButtonActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_AttachButtonActionPerformed + if (scene == null) { + scene = createSceneGraph(1); + univ.addBranchGraph(scene); + replaceSPButton.setEnabled(true); + shaderSelected = BRICK_SHADER; + } + }//GEN-LAST:event_AttachButtonActionPerformed + + private void halfButtonActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_halfButtonActionPerformed + density = 8.0f; + if(scene != null) { + sao1.setValue(new Float(density)); + } + }//GEN-LAST:event_halfButtonActionPerformed + + private void zeroButtonActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_zeroButtonActionPerformed + density = 0.0f; + if(scene != null) { + sao1.setValue(new Float(density)); + } + + }//GEN-LAST:event_zeroButtonActionPerformed + + private void exitMenuItemActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_exitMenuItemActionPerformed + System.exit(0); + }//GEN-LAST:event_exitMenuItemActionPerformed + + /** Exit the Application */ + private void exitForm(java.awt.event.WindowEvent evt) {//GEN-FIRST:event_exitForm + System.exit(0); + }//GEN-LAST:event_exitForm + + /** + * @param args the command line arguments + */ + public static void main(String args[]) { + new ShaderTestGLSL().setVisible(true); + } + + // Variables declaration - do not modify//GEN-BEGIN:variables + private javax.swing.JToggleButton AttachButton; + private javax.swing.JToggleButton DetachButton; + private javax.swing.ButtonGroup colorButtonGroup; + private javax.swing.JPanel colorPanel; + private javax.swing.ButtonGroup densityButtonGroup; + private javax.swing.JPanel densityPanel; + private javax.swing.JPanel drawingPanel; + private javax.swing.JMenuItem exitMenuItem; + private javax.swing.JMenu fileMenu; + private javax.swing.JRadioButton fullButton; + private javax.swing.JRadioButton goldButton; + private javax.swing.JPanel guiPanel; + private javax.swing.JRadioButton halfButton; + private javax.swing.JMenuBar jMenuBar1; + private javax.swing.JPanel mainPanel; + private javax.swing.JButton replaceSPButton; + private javax.swing.ButtonGroup sceneGraphButtonGroup; + private javax.swing.JPanel sceneGraphPanel; + private javax.swing.JRadioButton silverButton; + private javax.swing.JRadioButton zeroButton; + // End of variables declaration//GEN-END:variables + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/glsl_shader/SphereGLSL.form b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/SphereGLSL.form new file mode 100644 index 0000000..26e9b32 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/SphereGLSL.form @@ -0,0 +1,36 @@ +<?xml version="1.0" encoding="UTF-8" ?> + +<Form version="1.0" type="org.netbeans.modules.form.forminfo.JFrameFormInfo"> + <Properties> + <Property name="defaultCloseOperation" type="int" value="3"/> + <Property name="title" type="java.lang.String" value="SphereGLSL"/> + </Properties> + <SyntheticProperties> + <SyntheticProperty name="formSizePolicy" type="int" value="1"/> + </SyntheticProperties> + <AuxValues> + <AuxValue name="FormSettings_generateMnemonicsCode" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_listenerGenerationStyle" type="java.lang.Integer" value="0"/> + <AuxValue name="FormSettings_variablesLocal" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_variablesModifier" type="java.lang.Integer" value="2"/> + <AuxValue name="designerSize" type="java.awt.Dimension" value="-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,1,44,0,0,1,-112"/> + </AuxValues> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + <SubComponents> + <Container class="javax.swing.JPanel" name="drawingPanel"> + <Properties> + <Property name="preferredSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor"> + <Dimension value="[700, 700]"/> + </Property> + </Properties> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout" value="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription"> + <BorderConstraints direction="Center"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + </Container> + </SubComponents> +</Form> diff --git a/src/main/java/org/jdesktop/j3d/examples/glsl_shader/SphereGLSL.java b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/SphereGLSL.java new file mode 100644 index 0000000..03a514e --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/SphereGLSL.java @@ -0,0 +1,384 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.glsl_shader; + +import java.awt.GraphicsConfiguration; +import java.io.IOException; + +import javax.swing.JOptionPane; + +import org.jdesktop.j3d.examples.Resources; +import org.jogamp.java3d.Alpha; +import org.jogamp.java3d.AmbientLight; +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.Background; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.ColoringAttributes; +import org.jogamp.java3d.DirectionalLight; +import org.jogamp.java3d.GLSLShaderProgram; +import org.jogamp.java3d.Light; +import org.jogamp.java3d.Material; +import org.jogamp.java3d.PointLight; +import org.jogamp.java3d.PositionInterpolator; +import org.jogamp.java3d.RotationInterpolator; +import org.jogamp.java3d.Shader; +import org.jogamp.java3d.ShaderAppearance; +import org.jogamp.java3d.ShaderError; +import org.jogamp.java3d.ShaderErrorListener; +import org.jogamp.java3d.ShaderProgram; +import org.jogamp.java3d.SourceCodeShader; +import org.jogamp.java3d.SpotLight; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.utils.geometry.Sphere; +import org.jogamp.java3d.utils.shader.StringIO; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Point3f; +import org.jogamp.vecmath.Vector3d; +import org.jogamp.vecmath.Vector3f; + +/** + * Simple Java 3D example program with programmable shader. + */ +public class SphereGLSL extends javax.swing.JFrame { + + // Constants for type of light to use + private static final int DIRECTIONAL_LIGHT = 0; + private static final int POINT_LIGHT = 1; + private static final int SPOT_LIGHT = 2; + + // Flag indicates type of lights: directional, point, or spot + // lights. This flag is set based on command line argument + private static int lightType = POINT_LIGHT;//DIRECTIONAL_LIGHT; + private SimpleUniverse univ = null; + private BranchGroup scene = null; + + public BranchGroup createSceneGraph() { + Color3f eColor = new Color3f(0.0f, 0.0f, 0.0f); + Color3f sColor = new Color3f(1.0f, 1.0f, 1.0f); + Color3f objColor = new Color3f(0.6f, 0.6f, 0.6f); + Color3f lColor1 = new Color3f(1.0f, 0.0f, 0.0f); + Color3f lColor2 = new Color3f(0.0f, 1.0f, 0.0f); + Color3f alColor = new Color3f(0.2f, 0.2f, 0.2f); + Color3f bgColor = new Color3f(0.05f, 0.05f, 0.2f); + + Transform3D t; + + // Create the root of the branch graph + BranchGroup objRoot = new BranchGroup(); + + // Create a Transformgroup to scale all objects so they + // appear in the scene. + TransformGroup objScale = new TransformGroup(); + Transform3D t3d = new Transform3D(); + t3d.setScale(0.4); + objScale.setTransform(t3d); + objRoot.addChild(objScale); + + // Create a bounds for the background and lights + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + + // Set up the background + Background bg = new Background(bgColor); + bg.setApplicationBounds(bounds); + objScale.addChild(bg); + + // Create a Sphere object, generate one copy of the sphere, + // and add it into the scene graph. + ShaderAppearance a = new ShaderAppearance(); + Material m = new Material(objColor, eColor, objColor, sColor, 100.0f); + m.setLightingEnable(true); + String vertexProgram = null; + String fragmentProgram = null; + try { + vertexProgram = StringIO.readFully(Resources.getResource("glsl_shader/simple.vert")); + fragmentProgram = StringIO.readFully(Resources.getResource("glsl_shader/simple.frag")); + } + catch (IOException e) { + throw new RuntimeException(e); + } + Shader[] shaders = new Shader[2]; + shaders[0] = new SourceCodeShader(Shader.SHADING_LANGUAGE_GLSL, + Shader.SHADER_TYPE_VERTEX, + vertexProgram); + shaders[1] = new SourceCodeShader(Shader.SHADING_LANGUAGE_GLSL, + Shader.SHADER_TYPE_FRAGMENT, + fragmentProgram); + ShaderProgram shaderProgram = new GLSLShaderProgram(); + shaderProgram.setShaders(shaders); + + a.setShaderProgram(shaderProgram); + a.setMaterial(m); + Sphere sph = new Sphere(1.0f, Sphere.GENERATE_NORMALS, 200, a); + objScale.addChild(sph); + + // Create the transform group node for the each light and initialize + // it to the identity. Enable the TRANSFORM_WRITE capability so that + // our behavior code can modify it at runtime. Add them to the root + // of the subgraph. + TransformGroup l1RotTrans = new TransformGroup(); + l1RotTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + objScale.addChild(l1RotTrans); + + TransformGroup l2RotTrans = new TransformGroup(); + l2RotTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + objScale.addChild(l2RotTrans); + + // Create transformations for the positional lights + t = new Transform3D(); + Vector3d lPos1 = new Vector3d(0.0, 0.5, 2.0); + t.set(lPos1); + TransformGroup l1Trans = new TransformGroup(t); + l1RotTrans.addChild(l1Trans); + + t = new Transform3D(); + Vector3d lPos2 = new Vector3d(0.5, 0.8, 2.0); + t.set(lPos2); + TransformGroup l2Trans = new TransformGroup(t); + l2RotTrans.addChild(l2Trans); + + // Create Geometry for point lights + ColoringAttributes caL1 = new ColoringAttributes(); + ColoringAttributes caL2 = new ColoringAttributes(); + caL1.setColor(lColor1); + caL2.setColor(lColor2); + Appearance appL1 = new Appearance(); + Appearance appL2 = new Appearance(); + appL1.setColoringAttributes(caL1); + appL2.setColoringAttributes(caL2); + l1Trans.addChild(new Sphere(0.05f, appL1)); + l2Trans.addChild(new Sphere(0.05f, appL2)); + + // Create lights + AmbientLight aLgt = new AmbientLight(alColor); + + Light lgt1 = null; + Light lgt2 = null; + + Point3f lPoint = new Point3f(0.0f, 0.0f, 0.0f); + Point3f atten = new Point3f(1.0f, 0.0f, 0.0f); + Vector3f lDirect1 = new Vector3f(lPos1); + Vector3f lDirect2 = new Vector3f(lPos2); + lDirect1.negate(); + lDirect2.negate(); + + switch (lightType) { + case DIRECTIONAL_LIGHT: + lgt1 = new DirectionalLight(lColor1, lDirect1); + lgt2 = new DirectionalLight(lColor2, lDirect2); + break; + case POINT_LIGHT: + lgt1 = new PointLight(lColor1, lPoint, atten); + lgt2 = new PointLight(lColor2, lPoint, atten); + break; + case SPOT_LIGHT: + lgt1 = new SpotLight(lColor1, lPoint, atten, lDirect1, + 25.0f * (float)Math.PI / 180.0f, 10.0f); + lgt2 = new SpotLight(lColor2, lPoint, atten, lDirect2, + 25.0f * (float)Math.PI / 180.0f, 10.0f); + break; + } + + // Set the influencing bounds + aLgt.setInfluencingBounds(bounds); + lgt1.setInfluencingBounds(bounds); + lgt2.setInfluencingBounds(bounds); + + // Add the lights into the scene graph + objScale.addChild(aLgt); + l1Trans.addChild(lgt1); + l2Trans.addChild(lgt2); + + // Create a new Behavior object that will perform the desired + // operation on the specified transform object and add it into the + // scene graph. + Transform3D yAxis = new Transform3D(); + Alpha rotor1Alpha = new Alpha(-1, Alpha.INCREASING_ENABLE, + 0, 0, + 4000, 0, 0, + 0, 0, 0); + RotationInterpolator rotator1 = + new RotationInterpolator(rotor1Alpha, + l1RotTrans, + yAxis, + 0.0f, (float) Math.PI*2.0f); + rotator1.setSchedulingBounds(bounds); + l1RotTrans.addChild(rotator1); + + // Create a new Behavior object that will perform the desired + // operation on the specified transform object and add it into the + // scene graph. + Alpha rotor2Alpha = new Alpha(-1, Alpha.INCREASING_ENABLE, + 0, 0, + 1000, 0, 0, + 0, 0, 0); + RotationInterpolator rotator2 = + new RotationInterpolator(rotor2Alpha, + l2RotTrans, + yAxis, + 0.0f, 0.0f); + bounds = new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + rotator2.setSchedulingBounds(bounds); + l2RotTrans.addChild(rotator2); + + // Create a position interpolator and attach it to the view + // platform + TransformGroup vpTrans = + univ.getViewingPlatform().getViewPlatformTransform(); + Transform3D axisOfTranslation = new Transform3D(); + Alpha transAlpha = new Alpha(-1, + Alpha.INCREASING_ENABLE | + Alpha.DECREASING_ENABLE, + 0, 0, + 5000, 0, 0, + 5000, 0, 0); + axisOfTranslation.rotY(-Math.PI/2.0); + PositionInterpolator translator = + new PositionInterpolator(transAlpha, + vpTrans, + axisOfTranslation, + 2.0f, 3.5f); + translator.setSchedulingBounds(bounds); + objScale.addChild(translator); + + // Let Java 3D perform optimizations on this scene graph. + objRoot.compile(); + + return objRoot; + } + + private Canvas3D createUniverse() { + // Get the preferred graphics configuration for the default screen + GraphicsConfiguration config = + SimpleUniverse.getPreferredConfiguration(); + + // Create a Canvas3D using the preferred configuration + Canvas3D canvas3d = new Canvas3D(config); + + // Create simple universe with view branch + univ = new SimpleUniverse(canvas3d); + BoundingSphere bounds = new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + + // Add a ShaderErrorListener + univ.addShaderErrorListener(new ShaderErrorListener() { + public void errorOccurred(ShaderError error) { + error.printVerbose(); + JOptionPane.showMessageDialog(SphereGLSL.this, + error.toString(), + "ShaderError", + JOptionPane.ERROR_MESSAGE); + } + }); + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + univ.getViewingPlatform().setNominalViewingTransform(); + + // Ensure at least 5 msec per frame (i.e., < 200Hz) + univ.getViewer().getView().setMinimumFrameCycleTime(5); + + return canvas3d; + } + + + /** + * Creates new form SphereGLSL + */ + public SphereGLSL() { + + // Initialize the GUI components + initComponents(); + + // Create Canvas3D and SimpleUniverse; add canvas to drawing panel + Canvas3D c = createUniverse(); + drawingPanel.add(c, java.awt.BorderLayout.CENTER); + + // Create the content branch and add it to the universe + scene = createSceneGraph(); + univ.addBranchGraph(scene); } + + // ---------------------------------------------------------------- + + /** This method is called from within the constructor to + * initialize the form. + * WARNING: Do NOT modify this code. The content of this method is + * always regenerated by the Form Editor. + */ + // <editor-fold defaultstate="collapsed" desc=" Generated Code ">//GEN-BEGIN:initComponents + private void initComponents() { + drawingPanel = new javax.swing.JPanel(); + + setDefaultCloseOperation(javax.swing.WindowConstants.EXIT_ON_CLOSE); + setTitle("SphereGLSL"); + drawingPanel.setLayout(new java.awt.BorderLayout()); + + drawingPanel.setPreferredSize(new java.awt.Dimension(700, 700)); + getContentPane().add(drawingPanel, java.awt.BorderLayout.CENTER); + + pack(); + }// </editor-fold>//GEN-END:initComponents + + /** + * @param args the command line arguments + */ + public static void main(final String args[]) { + java.awt.EventQueue.invokeLater(new Runnable() { + public void run() { + SphereGLSL sphereGLSL = new SphereGLSL(); + sphereGLSL.setVisible(true); + } + }); + } + + // Variables declaration - do not modify//GEN-BEGIN:variables + private javax.swing.JPanel drawingPanel; + // End of variables declaration//GEN-END:variables + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/glsl_shader/VertexAttrTestGLSL.form b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/VertexAttrTestGLSL.form new file mode 100644 index 0000000..6e31a8f --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/VertexAttrTestGLSL.form @@ -0,0 +1,203 @@ +<?xml version="1.0" encoding="UTF-8" ?> + +<Form version="1.0" type="org.netbeans.modules.form.forminfo.JFrameFormInfo"> + <NonVisualComponents> + <Menu class="javax.swing.JMenuBar" name="jMenuBar1"> + <SubComponents> + <Menu class="javax.swing.JMenu" name="fileMenu"> + <Properties> + <Property name="text" type="java.lang.String" value="File"/> + </Properties> + <SubComponents> + <MenuItem class="javax.swing.JMenuItem" name="exitMenuItem"> + <Properties> + <Property name="text" type="java.lang.String" value="Exit"/> + </Properties> + <Events> + <EventHandler event="actionPerformed" listener="java.awt.event.ActionListener" parameters="java.awt.event.ActionEvent" handler="exitMenuItemActionPerformed"/> + </Events> + </MenuItem> + </SubComponents> + </Menu> + </SubComponents> + </Menu> + </NonVisualComponents> + <Properties> + <Property name="title" type="java.lang.String" value="VertexAttrTestGLSL"/> + </Properties> + <SyntheticProperties> + <SyntheticProperty name="menuBar" type="java.lang.String" value="jMenuBar1"/> + <SyntheticProperty name="formSizePolicy" type="int" value="1"/> + </SyntheticProperties> + <Events> + <EventHandler event="windowClosing" listener="java.awt.event.WindowListener" parameters="java.awt.event.WindowEvent" handler="exitForm"/> + </Events> + <AuxValues> + <AuxValue name="FormSettings_generateMnemonicsCode" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_listenerGenerationStyle" type="java.lang.Integer" value="0"/> + <AuxValue name="FormSettings_variablesLocal" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_variablesModifier" type="java.lang.Integer" value="2"/> + <AuxValue name="designerSize" type="java.awt.Dimension" value="-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,1,44,0,0,1,-112"/> + </AuxValues> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + <SubComponents> + <Container class="javax.swing.JPanel" name="mainPanel"> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout" value="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription"> + <BorderConstraints direction="Center"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + <SubComponents> + <Container class="javax.swing.JPanel" name="guiPanel"> + <Properties> + <Property name="border" type="javax.swing.border.Border" editor="org.netbeans.modules.form.editors2.BorderEditor"> + <Border info="org.netbeans.modules.form.compat2.border.LineBorderInfo"> + <LineBorder/> + </Border> + </Property> + </Properties> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout" value="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription"> + <BorderConstraints direction="North"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout"/> + <SubComponents> + <Container class="javax.swing.JPanel" name="vertexCheckBoxPanel"> + <Properties> + <Property name="border" type="javax.swing.border.Border" editor="org.netbeans.modules.form.editors2.BorderEditor"> + <Border info="org.netbeans.modules.form.compat2.border.TitledBorderInfo"> + <TitledBorder title="vertexFormat"> + <Font PropertyName="font" name="Lucida Sans" size="10" style="0"/> + </TitledBorder> + </Border> + </Property> + </Properties> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout" value="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription"> + <GridBagConstraints gridX="-1" gridY="0" gridWidth="1" gridHeight="1" fill="0" ipadX="0" ipadY="0" insetsTop="2" insetsLeft="2" insetsBottom="2" insetsRight="2" anchor="10" weightX="0.0" weightY="0.0"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout"/> + <SubComponents> + <Container class="javax.swing.JPanel" name="jPanel1"> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout" value="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription"> + <GridBagConstraints gridX="-1" gridY="-1" gridWidth="1" gridHeight="1" fill="0" ipadX="0" ipadY="0" insetsTop="0" insetsLeft="0" insetsBottom="0" insetsRight="0" anchor="11" weightX="0.0" weightY="0.0"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout"/> + <SubComponents> + <Component class="javax.swing.JSeparator" name="jSeparator1"> + <Properties> + <Property name="preferredSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor"> + <Dimension value="[0, 4]"/> + </Property> + </Properties> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout" value="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription"> + <GridBagConstraints gridX="0" gridY="1" gridWidth="1" gridHeight="1" fill="0" ipadX="0" ipadY="0" insetsTop="0" insetsLeft="0" insetsBottom="0" insetsRight="0" anchor="10" weightX="0.0" weightY="0.0"/> + </Constraint> + </Constraints> + </Component> + <Component class="javax.swing.JSeparator" name="jSeparator2"> + <Properties> + <Property name="preferredSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor"> + <Dimension value="[0, 4]"/> + </Property> + </Properties> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout" value="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription"> + <GridBagConstraints gridX="0" gridY="3" gridWidth="1" gridHeight="1" fill="0" ipadX="0" ipadY="0" insetsTop="0" insetsLeft="0" insetsBottom="0" insetsRight="0" anchor="10" weightX="0.0" weightY="0.0"/> + </Constraint> + </Constraints> + </Component> + </SubComponents> + </Container> + <Container class="javax.swing.JPanel" name="jPanel2"> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout" value="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription"> + <GridBagConstraints gridX="-1" gridY="-1" gridWidth="1" gridHeight="1" fill="0" ipadX="0" ipadY="0" insetsTop="0" insetsLeft="0" insetsBottom="0" insetsRight="0" anchor="11" weightX="0.0" weightY="0.0"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout"/> + <SubComponents> + <Component class="javax.swing.JCheckBox" name="vertexAttrsBox"> + <Properties> + <Property name="selected" type="boolean" value="true"/> + <Property name="text" type="java.lang.String" value="VertexAttrs"/> + </Properties> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout" value="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription"> + <GridBagConstraints gridX="0" gridY="4" gridWidth="1" gridHeight="1" fill="2" ipadX="0" ipadY="0" insetsTop="0" insetsLeft="0" insetsBottom="0" insetsRight="0" anchor="10" weightX="0.0" weightY="0.0"/> + </Constraint> + </Constraints> + </Component> + </SubComponents> + </Container> + </SubComponents> + </Container> + <Container class="javax.swing.JPanel" name="geometryPanel"> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout" value="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription"> + <GridBagConstraints gridX="-1" gridY="0" gridWidth="1" gridHeight="1" fill="0" ipadX="0" ipadY="0" insetsTop="2" insetsLeft="2" insetsBottom="2" insetsRight="2" anchor="10" weightX="0.0" weightY="0.0"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout"/> + <SubComponents> + <Component class="javax.swing.JButton" name="createButton"> + <Properties> + <Property name="text" type="java.lang.String" value="Create Geometry"/> + </Properties> + <Events> + <EventHandler event="actionPerformed" listener="java.awt.event.ActionListener" parameters="java.awt.event.ActionEvent" handler="createButtonActionPerformed"/> + </Events> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout" value="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription"> + <GridBagConstraints gridX="-1" gridY="-1" gridWidth="1" gridHeight="1" fill="2" ipadX="0" ipadY="0" insetsTop="0" insetsLeft="0" insetsBottom="0" insetsRight="0" anchor="10" weightX="0.0" weightY="0.0"/> + </Constraint> + </Constraints> + </Component> + <Component class="javax.swing.JButton" name="destroyButton"> + <Properties> + <Property name="text" type="java.lang.String" value="Destroy Geometry"/> + </Properties> + <Events> + <EventHandler event="actionPerformed" listener="java.awt.event.ActionListener" parameters="java.awt.event.ActionEvent" handler="destroyButtonActionPerformed"/> + </Events> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout" value="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription"> + <GridBagConstraints gridX="0" gridY="-1" gridWidth="1" gridHeight="1" fill="2" ipadX="0" ipadY="0" insetsTop="0" insetsLeft="0" insetsBottom="2" insetsRight="0" anchor="10" weightX="0.0" weightY="0.0"/> + </Constraint> + </Constraints> + </Component> + </SubComponents> + </Container> + </SubComponents> + </Container> + <Container class="javax.swing.JPanel" name="drawingPanel"> + <Properties> + <Property name="preferredSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor"> + <Dimension value="[500, 500]"/> + </Property> + </Properties> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout" value="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription"> + <BorderConstraints direction="Center"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + </Container> + </SubComponents> + </Container> + </SubComponents> +</Form> diff --git a/src/main/java/org/jdesktop/j3d/examples/glsl_shader/VertexAttrTestGLSL.java b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/VertexAttrTestGLSL.java new file mode 100644 index 0000000..014c0e9 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/VertexAttrTestGLSL.java @@ -0,0 +1,428 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.glsl_shader; + +import java.awt.GraphicsConfiguration; +import java.io.IOException; +import java.nio.ByteBuffer; +import java.nio.ByteOrder; +import java.nio.FloatBuffer; + +import javax.swing.JFrame; +import javax.swing.JOptionPane; + +import org.jdesktop.j3d.examples.Resources; +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.Background; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.GLSLShaderProgram; +import org.jogamp.java3d.GeometryArray; +import org.jogamp.java3d.J3DBuffer; +import org.jogamp.java3d.Shader; +import org.jogamp.java3d.ShaderAppearance; +import org.jogamp.java3d.ShaderError; +import org.jogamp.java3d.ShaderErrorListener; +import org.jogamp.java3d.ShaderProgram; +import org.jogamp.java3d.Shape3D; +import org.jogamp.java3d.SourceCodeShader; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.TriangleArray; +import org.jogamp.java3d.utils.shader.StringIO; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.java3d.utils.universe.ViewingPlatform; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3d; + +public class VertexAttrTestGLSL extends javax.swing.JFrame { + + SimpleUniverse univ = null; + BranchGroup scene = null; + + public BranchGroup createSceneGraph( boolean hasVertexAttrs ) { + + // Bounds for BG and behavior + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + + // Create the root of the branch graph + BranchGroup objRoot = new BranchGroup(); + objRoot.setCapability(BranchGroup.ALLOW_DETACH); + + // Set up the background + Color3f bgColor = new Color3f(0.1f, 0.1f, 0.1f); + Background bg = new Background(bgColor); + bg.setApplicationBounds(bounds); + objRoot.addChild(bg); + + // Create the TransformGroup node and initialize it to the + // identity. Enable the TRANSFORM_WRITE capability so that + // our behavior code can modify it at run time. Add it to + // the root of the subgraph. + TransformGroup objTrans = new TransformGroup(); + objTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + objRoot.addChild(objTrans); + + // Create a simple Shape3D node; add it to the scene graph. + objTrans.addChild(new MyShape(this, hasVertexAttrs)); + + return objRoot; + } + + private Canvas3D initScene() { + GraphicsConfiguration config = + SimpleUniverse.getPreferredConfiguration(); + + Canvas3D c = new Canvas3D(config); + univ = new SimpleUniverse(c); + + // Add a ShaderErrorListener + univ.addShaderErrorListener(new ShaderErrorListener() { + public void errorOccurred(ShaderError error) { + error.printVerbose(); + JOptionPane.showMessageDialog(VertexAttrTestGLSL.this, + error.toString(), + "ShaderError", + JOptionPane.ERROR_MESSAGE); + } + }); + + ViewingPlatform viewingPlatform = univ.getViewingPlatform(); + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + viewingPlatform.setNominalViewingTransform(); + + return c; + } + + /** + * Creates new form VertexAttrTestGLSL + */ + public VertexAttrTestGLSL() { + // Initialize the GUI components + initComponents(); + + // Create the scene and add the Canvas3D to the drawing panel + Canvas3D c = initScene(); + drawingPanel.add(c, java.awt.BorderLayout.CENTER); + } + + static class MyShape extends Shape3D { + private static String vertexProgName = "glsl_shader/vertexshader.vert"; + + // Coordinate data + private static final float[] coords = { + 0.0f, 0.0f, 0.0f, + 0.5f, 0.0f, 0.0f, + 0.0f, 0.5f, 0.0f, + }; + + private static final int[] sizes = { 1, 3 }; + private static final float[] weights = { + 0.45f, + 0.15f, + 0.95f, + }; + private static final float[] temps = { + 1.0f, 0.5f, 0.5f, + 0.5f, 1.0f, 0.5f, + 0.5f, 0.5f, 1.0f, + }; + + private static final String[] vaNames = { "weight", "temperature" }; + + J3DBuffer createDirectFloatBuffer(float[] arr) { + ByteOrder order = ByteOrder.nativeOrder(); + + FloatBuffer nioBuf = ByteBuffer.allocateDirect(arr.length * 4).order(order).asFloatBuffer(); + nioBuf.put(arr); + return new J3DBuffer(nioBuf); + } + + + MyShape(JFrame frame, boolean hasVertexAttrs) { + + int vertexFormat = GeometryArray.COORDINATES; + int vertexAttrCount = 0; + int[] vertexAttrSizes = null; + String[] vertexAttrNames = null; + String[] shaderAttrNames = null; + + if (hasVertexAttrs) { + vertexFormat |= GeometryArray.VERTEX_ATTRIBUTES; + vertexAttrCount = vaNames.length; + vertexAttrSizes = sizes; + vertexAttrNames = vaNames; + } + + TriangleArray tri = new TriangleArray(6, vertexFormat, 0, null, vertexAttrCount, vertexAttrSizes); + tri.setValidVertexCount(3); + tri.setCoordinates(0, coords); + + if (hasVertexAttrs) { + tri.setVertexAttrs(0, 0, weights); + tri.setVertexAttrs(1, 0, temps); + + String vertexProgram = null; + try { + vertexProgram = StringIO.readFully(Resources.getResource(vertexProgName)); + } catch (IOException e) { + throw new RuntimeException(e); + } + + Shader[] shaders = new Shader[1]; + shaders[0] = new SourceCodeShader(Shader.SHADING_LANGUAGE_GLSL, + Shader.SHADER_TYPE_VERTEX, + vertexProgram); + + ShaderProgram shaderProgram = new GLSLShaderProgram(); + shaderProgram.setShaders(shaders); + shaderProgram.setVertexAttrNames(vertexAttrNames); + shaderProgram.setShaderAttrNames(shaderAttrNames); + + ShaderAppearance app = new ShaderAppearance(); + app.setShaderProgram(shaderProgram); + + this.setGeometry(tri); + + this.setAppearance(app); + } else { + this.setGeometry(tri); + this.setAppearance(new Appearance()); + } + } + } + + // ---------------------------------------------------------------- + + /** This method is called from within the constructor to + * initialize the form. + * WARNING: Do NOT modify this code. The content of this method is + * always regenerated by the Form Editor. + */ + // <editor-fold defaultstate="collapsed" desc=" Generated Code ">//GEN-BEGIN:initComponents + private void initComponents() { + java.awt.GridBagConstraints gridBagConstraints; + + mainPanel = new javax.swing.JPanel(); + guiPanel = new javax.swing.JPanel(); + vertexCheckBoxPanel = new javax.swing.JPanel(); + jPanel1 = new javax.swing.JPanel(); + jSeparator1 = new javax.swing.JSeparator(); + jSeparator2 = new javax.swing.JSeparator(); + jPanel2 = new javax.swing.JPanel(); + vertexAttrsBox = new javax.swing.JCheckBox(); + geometryPanel = new javax.swing.JPanel(); + createButton = new javax.swing.JButton(); + destroyButton = new javax.swing.JButton(); + drawingPanel = new javax.swing.JPanel(); + jMenuBar1 = new javax.swing.JMenuBar(); + fileMenu = new javax.swing.JMenu(); + exitMenuItem = new javax.swing.JMenuItem(); + + setTitle("VertexAttrTestGLSL"); + addWindowListener(new java.awt.event.WindowAdapter() { + public void windowClosing(java.awt.event.WindowEvent evt) { + exitForm(evt); + } + }); + + mainPanel.setLayout(new java.awt.BorderLayout()); + + guiPanel.setLayout(new java.awt.GridBagLayout()); + + guiPanel.setBorder(javax.swing.BorderFactory.createLineBorder(new java.awt.Color(0, 0, 0))); + vertexCheckBoxPanel.setLayout(new java.awt.GridBagLayout()); + + vertexCheckBoxPanel.setBorder(javax.swing.BorderFactory.createTitledBorder(null, "vertexFormat", javax.swing.border.TitledBorder.DEFAULT_JUSTIFICATION, javax.swing.border.TitledBorder.DEFAULT_POSITION, new java.awt.Font("Lucida Sans", 0, 10))); + jPanel1.setLayout(new java.awt.GridBagLayout()); + + jSeparator1.setPreferredSize(new java.awt.Dimension(0, 4)); + gridBagConstraints = new java.awt.GridBagConstraints(); + gridBagConstraints.gridx = 0; + gridBagConstraints.gridy = 1; + jPanel1.add(jSeparator1, gridBagConstraints); + + jSeparator2.setPreferredSize(new java.awt.Dimension(0, 4)); + gridBagConstraints = new java.awt.GridBagConstraints(); + gridBagConstraints.gridx = 0; + gridBagConstraints.gridy = 3; + jPanel1.add(jSeparator2, gridBagConstraints); + + gridBagConstraints = new java.awt.GridBagConstraints(); + gridBagConstraints.anchor = java.awt.GridBagConstraints.NORTH; + vertexCheckBoxPanel.add(jPanel1, gridBagConstraints); + + jPanel2.setLayout(new java.awt.GridBagLayout()); + + vertexAttrsBox.setSelected(true); + vertexAttrsBox.setText("VertexAttrs"); + gridBagConstraints = new java.awt.GridBagConstraints(); + gridBagConstraints.gridx = 0; + gridBagConstraints.gridy = 4; + gridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL; + jPanel2.add(vertexAttrsBox, gridBagConstraints); + + gridBagConstraints = new java.awt.GridBagConstraints(); + gridBagConstraints.anchor = java.awt.GridBagConstraints.NORTH; + vertexCheckBoxPanel.add(jPanel2, gridBagConstraints); + + gridBagConstraints = new java.awt.GridBagConstraints(); + gridBagConstraints.gridy = 0; + gridBagConstraints.insets = new java.awt.Insets(2, 2, 2, 2); + guiPanel.add(vertexCheckBoxPanel, gridBagConstraints); + + geometryPanel.setLayout(new java.awt.GridBagLayout()); + + createButton.setText("Create Geometry"); + createButton.addActionListener(new java.awt.event.ActionListener() { + public void actionPerformed(java.awt.event.ActionEvent evt) { + createButtonActionPerformed(evt); + } + }); + + gridBagConstraints = new java.awt.GridBagConstraints(); + gridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL; + geometryPanel.add(createButton, gridBagConstraints); + + destroyButton.setText("Destroy Geometry"); + destroyButton.addActionListener(new java.awt.event.ActionListener() { + public void actionPerformed(java.awt.event.ActionEvent evt) { + destroyButtonActionPerformed(evt); + } + }); + + gridBagConstraints = new java.awt.GridBagConstraints(); + gridBagConstraints.gridx = 0; + gridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL; + gridBagConstraints.insets = new java.awt.Insets(0, 0, 2, 0); + geometryPanel.add(destroyButton, gridBagConstraints); + + gridBagConstraints = new java.awt.GridBagConstraints(); + gridBagConstraints.gridy = 0; + gridBagConstraints.insets = new java.awt.Insets(2, 2, 2, 2); + guiPanel.add(geometryPanel, gridBagConstraints); + + mainPanel.add(guiPanel, java.awt.BorderLayout.NORTH); + + drawingPanel.setLayout(new java.awt.BorderLayout()); + + drawingPanel.setPreferredSize(new java.awt.Dimension(500, 500)); + mainPanel.add(drawingPanel, java.awt.BorderLayout.CENTER); + + getContentPane().add(mainPanel, java.awt.BorderLayout.CENTER); + + fileMenu.setText("File"); + exitMenuItem.setText("Exit"); + exitMenuItem.addActionListener(new java.awt.event.ActionListener() { + public void actionPerformed(java.awt.event.ActionEvent evt) { + exitMenuItemActionPerformed(evt); + } + }); + + fileMenu.add(exitMenuItem); + + jMenuBar1.add(fileMenu); + + setJMenuBar(jMenuBar1); + + pack(); + }// </editor-fold>//GEN-END:initComponents + + private void destroyButtonActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_destroyButtonActionPerformed + if (scene != null) { + univ.getLocale().removeBranchGraph(scene); + scene = null; + } + }//GEN-LAST:event_destroyButtonActionPerformed + + private void createButtonActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_createButtonActionPerformed + if (scene == null) { + boolean hasVertexAttrs = vertexAttrsBox.isSelected(); + scene = createSceneGraph(hasVertexAttrs); + univ.addBranchGraph(scene); + } + }//GEN-LAST:event_createButtonActionPerformed + + private void exitMenuItemActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_exitMenuItemActionPerformed + System.exit(0); + }//GEN-LAST:event_exitMenuItemActionPerformed + + /** Exit the Application */ + private void exitForm(java.awt.event.WindowEvent evt) {//GEN-FIRST:event_exitForm + System.exit(0); + }//GEN-LAST:event_exitForm + + /** + * @param args the command line arguments + */ + public static void main(String args[]) { + java.awt.EventQueue.invokeLater(new Runnable() { + public void run() { + new VertexAttrTestGLSL().setVisible(true); + } + }); + } + + // Variables declaration - do not modify//GEN-BEGIN:variables + private javax.swing.JButton createButton; + private javax.swing.JButton destroyButton; + private javax.swing.JPanel drawingPanel; + private javax.swing.JMenuItem exitMenuItem; + private javax.swing.JMenu fileMenu; + private javax.swing.JPanel geometryPanel; + private javax.swing.JPanel guiPanel; + private javax.swing.JMenuBar jMenuBar1; + private javax.swing.JPanel jPanel1; + private javax.swing.JPanel jPanel2; + private javax.swing.JSeparator jSeparator1; + private javax.swing.JSeparator jSeparator2; + private javax.swing.JPanel mainPanel; + private javax.swing.JCheckBox vertexAttrsBox; + private javax.swing.JPanel vertexCheckBoxPanel; + // End of variables declaration//GEN-END:variables + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/glsl_shader/aabrick.frag b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/aabrick.frag new file mode 100644 index 0000000..7c9aab8 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/aabrick.frag @@ -0,0 +1,55 @@ +// +// Fragment shader for antialiased procedural bricks +// +// Authors: Dave Baldwin, Randi Rost +// based on a shader by Darwyn Peachey +// +// Copyright (c) 2002-2004 3Dlabs Inc. Ltd. +// +// See 3Dlabs-License.txt for license information +// + +uniform vec3 BrickColor; +//uniform vec3 MortarColor; +//uniform vec2 BrickSize; +//uniform vec2 BrickPct; +//uniform vec2 MortarPct; + +//const vec3 BrickColor = vec3 (1, 0.3, 0.2); +const vec3 MortarColor = vec3 (0.85, 0.86, 0.84); +const vec2 BrickSize = vec2 (0.3, 0.15); +const vec2 BrickPct = vec2 (0.9, 0.85); +const vec2 MortarPct = vec2 (0.1, 0.15); + +varying vec2 MCposition; +varying float LightIntensity; + +#define Integral(x, p, notp) ((floor(x)*(p)) + max(fract(x)-(notp), 0.0)) + +void main(void) +{ + vec2 position, fw, useBrick; + vec3 color; + + // Determine position within the brick pattern + position = MCposition / BrickSize; + + // Adjust every other row by an offset of half a brick + if (fract(position.y * 0.5) > 0.5) + position.x += 0.5; + + // Calculate filter size + //fw = fwidth(position); //fwidth not implemented on WildcatVP + fw = (abs(dFdx(MCposition)) + abs(dFdy(MCposition))) / BrickSize; + + // Perform filtering by integrating the 2D pulse made by the + // brick pattern over the filter width and height + useBrick = (Integral(position + fw, BrickPct, MortarPct) - + Integral(position, BrickPct, MortarPct)) / fw; + + // Determine final color + color = mix(MortarColor, BrickColor, useBrick.x * useBrick.y); + color *= LightIntensity; + + gl_FragColor = vec4 (color, 1.0); +} diff --git a/src/main/java/org/jdesktop/j3d/examples/glsl_shader/aabrick.vert b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/aabrick.vert new file mode 100644 index 0000000..226dbe4 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/aabrick.vert @@ -0,0 +1,42 @@ +// +// Vertex shader for antialiased procedural bricks +// +// Authors: Dave Baldwin, Steve Koren, Randi Rost +// based on a shader by Darwyn Peachey +// +// Copyright (c) 2002-2004 3Dlabs Inc. Ltd. +// +// See 3Dlabs-License.txt for license information +// + +uniform vec3 LightPosition; +//const vec3 LightPosition = vec3 (0, 4, 4); + +const float SpecularContribution = 0.3; +const float DiffuseContribution = 1.0 - SpecularContribution; + +varying float LightIntensity; +varying vec2 MCposition; + +void main(void) +{ + vec3 ecPosition = vec3 (gl_ModelViewMatrix * gl_Vertex); + vec3 tnorm = normalize(gl_NormalMatrix * gl_Normal); + vec3 lightVec = normalize(LightPosition - ecPosition); + vec3 reflectVec = reflect(-lightVec, tnorm); + vec3 viewVec = normalize(-ecPosition); + float diffuse = max(dot(lightVec, tnorm), 0.0); + float spec = 0.0; + + if (diffuse > 0.0) + { + spec = max(dot(reflectVec, viewVec), 0.0); + spec = pow(spec, 16.0); + } + + LightIntensity = DiffuseContribution * diffuse + + SpecularContribution * spec; + + MCposition = gl_Vertex.xy; + gl_Position = ftransform(); +} diff --git a/src/main/java/org/jdesktop/j3d/examples/glsl_shader/dimple.frag b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/dimple.frag new file mode 100644 index 0000000..282add7 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/dimple.frag @@ -0,0 +1,61 @@ + +// +// dimple.frag: Fragment shader for bump mapping dimples (bumps) +// +// author: John Kessenich +// +// Copyright (c) 2002: 3Dlabs, Inc. +// +// +varying vec3 LightDir; +varying vec3 EyeDir; +varying vec3 Normal; + +//const vec3 Color = vec3(0.7, 0.6, 0.18); + +//const float Density = 16.0; +//const float Size = 0.25; + +uniform vec3 Color; +uniform float Density; +uniform float Size; +// uniform float SpecularFactor; + +//float Density = 27.6; +//float Size = 0.13025; + + +//uniform float Scale; + +const float SpecularFactor = 0.4; + +void main (void) +{ + vec3 litColor; + + vec2 c = Density * (gl_TexCoord[0].xy); + vec2 p = fract(c) - vec2(0.5); + float d = (p.x * p.x) + (p.y * p.y); + if (d >= Size) + p = vec2(0.0); + + vec3 normDelta = vec3(-p.x, -p.y, 1.0); + + litColor = Color * max(0.0, dot(normDelta, LightDir)); + + float t = 2.0 * dot(LightDir, normDelta); + vec3 reflectDir = t * normDelta; + reflectDir = LightDir - reflectDir; + +// vec3 reflectDir = LightDir - 2.0 * dot(LightDir, normDelta) * normDelta; + + float spec = max(dot(EyeDir, reflectDir), 0.0); + spec = spec * spec; + spec = spec * spec; + spec *= SpecularFactor; + + litColor = min(litColor + spec, vec3(1.0)); + gl_FragColor = vec4(litColor, gl_Color.a); +// gl_FragColor = vec4(litColor, 1.0); +// gl_FragColor = vec4(Scale); +} diff --git a/src/main/java/org/jdesktop/j3d/examples/glsl_shader/dimple.vert b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/dimple.vert new file mode 100644 index 0000000..e45796b --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/dimple.vert @@ -0,0 +1,42 @@ + +// +// dimple.vert: Vertex shader for bump mapping dimples (bumps) +// +// author: John Kessenich +// +// Copyright (c) 2002: 3Dlabs, Inc. +// + +varying vec3 LightDir; +varying vec3 EyeDir; +varying vec3 Normal; + +uniform vec3 LightPosition; +// uniform float Scale; +// vec3 LightPosition = vec3(0.0, 0.0, 5.0); +float Scale = 1.0; + +void main(void) +{ + vec4 pos = gl_ModelViewMatrix * gl_Vertex; + gl_Position = gl_ModelViewProjectionMatrix * gl_Vertex; + vec3 eyeDir = vec3(pos); +// gl_TexCoord[0] = gl_MultiTexCoord0; + gl_TexCoord[0] = gl_Vertex; + gl_FrontColor = gl_Color; + + vec3 n = normalize(gl_NormalMatrix * gl_Normal); + vec3 t = normalize(cross(vec3(1.141, 2.78, 3.14), n)); + vec3 b = cross(n, t); + + vec3 v; + v.x = dot(LightPosition, t); + v.y = dot(LightPosition, b); + v.z = dot(LightPosition, n); + LightDir = normalize(v); + + v.x = dot(eyeDir, t); + v.y = dot(eyeDir, b); + v.z = dot(eyeDir, n); + EyeDir = normalize(v); +} diff --git a/src/main/java/org/jdesktop/j3d/examples/glsl_shader/envmap.frag b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/envmap.frag new file mode 100644 index 0000000..3e298f8 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/envmap.frag @@ -0,0 +1,61 @@ +// +// Fragment shader for environment mapping with an +// equirectangular 2D texture +// +// Authors: John Kessenich, Randi Rost +// +// Copyright (c) 2002-2004 3Dlabs Inc. Ltd. +// +// See 3Dlabs-License.txt for license information +// + +const vec3 Xunitvec = vec3 (1.0, 0.0, 0.0); +const vec3 Yunitvec = vec3 (0.0, 1.0, 0.0); + +uniform vec3 BaseColor; +uniform float MixRatio; + +uniform sampler2D EnvMap; + +varying vec3 Normal; +varying vec3 EyeDir; +varying float LightIntensity; + +void main (void) +{ + // Compute reflection vector + vec3 reflectDir = reflect(EyeDir, Normal); + + // Compute altitude and azimuth angles + + vec2 index; + + index.y = dot(normalize(reflectDir), Yunitvec); + reflectDir.y = 0.0; + index.x = dot(normalize(reflectDir), Xunitvec) * 0.5; + + // Translate index values into proper range + + if (reflectDir.z >= 0.0) + index = (index + 1.0) * 0.5; + else + { + index.t = (index.t + 1.0) * 0.5; + index.s = (-index.s) * 0.5 + 1.0; + } + + // if reflectDir.z >= 0.0, s will go from 0.25 to 0.75 + // if reflectDir.z < 0.0, s will go from 0.75 to 1.25, and + // that's OK, because we've set the texture to wrap. + + // Do a lookup into the environment map. + + vec3 envColor = vec3 (texture2D(EnvMap, index)); + + // Add lighting to base color and mix + + vec3 base = LightIntensity * BaseColor; + envColor = mix(envColor, base, MixRatio); + + gl_FragColor = vec4 (envColor, 1.0); +} diff --git a/src/main/java/org/jdesktop/j3d/examples/glsl_shader/envmap.vert b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/envmap.vert new file mode 100644 index 0000000..d4e8b44 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/envmap.vert @@ -0,0 +1,25 @@ +// +// Vertex shader for environment mapping with an +// equirectangular 2D texture +// +// Authors: John Kessenich, Randi Rost +// +// Copyright (c) 2002-2004 3Dlabs Inc. Ltd. +// +// See 3Dlabs-License.txt for license information +// + +varying vec3 Normal; +varying vec3 EyeDir; +varying float LightIntensity; + +uniform vec3 LightPos; + +void main(void) +{ + gl_Position = ftransform(); + Normal = normalize(gl_NormalMatrix * gl_Normal); + vec4 pos = gl_ModelViewMatrix * gl_Vertex; + EyeDir = pos.xyz; + LightIntensity = max(dot(normalize(LightPos - EyeDir), Normal), 0.0); +} diff --git a/src/main/java/org/jdesktop/j3d/examples/glsl_shader/gouraud.frag b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/gouraud.frag new file mode 100644 index 0000000..9169661 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/gouraud.frag @@ -0,0 +1,50 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +// Simple GLSL fragment program to add the primary and secondary (specular) colors + +void main() +{ + gl_FragColor = gl_Color + gl_SecondaryColor; +} diff --git a/src/main/java/org/jdesktop/j3d/examples/glsl_shader/gouraud.vert b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/gouraud.vert new file mode 100644 index 0000000..8503e6f --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/gouraud.vert @@ -0,0 +1,100 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +// A GLSL vertex program for handling 1 directional light with specular. +// This implements per-vertex lighting (Gouraud shading). + +void directionalLight0( + in vec3 normal, + inout vec4 ambient, + inout vec4 diffuse, + inout vec4 specular) +{ + // Normalized light direction and half vector + vec3 lightDirection = normalize(vec3(gl_LightSource[0].position)); + vec3 halfVector = normalize(vec3(gl_LightSource[0].halfVector)); + + float nDotVP; // normal . light_direction + float nDotHV; // normal . light_half_vector + float pf; // power factor + + nDotVP = max(0.0, dot(normal, lightDirection)); + nDotHV = max(0.0, dot(normal, halfVector)); + + if (nDotVP == 0.0) { + pf = 0.0; + } + else { + pf = pow(nDotHV, gl_FrontMaterial.shininess); + } + + ambient += gl_LightSource[0].ambient; + diffuse += gl_LightSource[0].diffuse * nDotVP; + specular += gl_LightSource[0].specular * pf; +} + + +void main() +{ + vec3 tnorm = normalize(vec3(gl_NormalMatrix * gl_Normal)); + vec4 amb = vec4(0.0); + vec4 diff = vec4(0.0); + vec4 spec = vec4(0.0); + int i; + + // Transform the vertex + vec4 outPosition = gl_ModelViewProjectionMatrix * gl_Vertex; + + directionalLight0(tnorm, amb, diff, spec); + + // Apply the result of the lighting equation + vec4 outSecondaryColor = vec4(vec3(spec * gl_FrontMaterial.specular), 1.0); + vec4 outColor = vec4(vec3(gl_FrontLightModelProduct.sceneColor + + amb * gl_FrontMaterial.ambient + + diff * gl_FrontMaterial.diffuse), 1.0); + + gl_FrontColor = outColor; + gl_FrontSecondaryColor = outSecondaryColor; + gl_Position = outPosition; +} diff --git a/src/main/java/org/jdesktop/j3d/examples/glsl_shader/multitex.frag b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/multitex.frag new file mode 100644 index 0000000..b79f85a --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/multitex.frag @@ -0,0 +1,61 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +uniform float cloudFactor; +uniform sampler2D earthTex; +uniform sampler2D cloudTex; + +uniform sampler2D EnvMap; + +void main (void) +{ + vec2 tc0 = gl_TexCoord[0].xy; + vec2 tc1 = gl_TexCoord[1].xy; + + vec3 color0 = vec3(texture2D(cloudTex, tc0)); + vec3 color1 = vec3(texture2D(earthTex, tc1)); + vec3 finalColor = color0*cloudFactor + color1; + + gl_FragColor = vec4(finalColor, 1.0); +} diff --git a/src/main/java/org/jdesktop/j3d/examples/glsl_shader/phong.frag b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/phong.frag new file mode 100644 index 0000000..90bab19 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/phong.frag @@ -0,0 +1,98 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +// A GLSL fragment program for handling 1 directional light with specular. +// This implements per-pixel lighting (Phong shading) + +void directionalLight0( + in vec3 normal, + inout vec4 ambient, + inout vec4 diffuse, + inout vec4 specular) +{ + // Normalized light direction and half vector + vec3 lightDirection = normalize(vec3(gl_LightSource[0].position)); + vec3 halfVector = normalize(vec3(gl_LightSource[0].halfVector)); + + float nDotVP; // normal . light_direction + float nDotHV; // normal . light_half_vector + float pf; // power factor + + nDotVP = max(0.0, dot(normal, lightDirection)); + nDotHV = max(0.0, dot(normal, halfVector)); + + if (nDotVP == 0.0) { + pf = 0.0; + } + else { + pf = pow(nDotHV, gl_FrontMaterial.shininess); + } + + ambient += gl_LightSource[0].ambient; + diffuse += gl_LightSource[0].diffuse * nDotVP; + specular += gl_LightSource[0].specular * pf; +} + + +// Per-pixel normal (input from vertex shader) +varying vec3 Normal; + +void main() +{ + vec3 unitNorm = normalize(Normal); + vec4 amb = vec4(0.0); + vec4 diff = vec4(0.0); + vec4 spec = vec4(0.0); + int i; + + directionalLight0(unitNorm, amb, diff, spec); + + // Apply the result of the lighting equation + vec4 secondaryColor = vec4(vec3(spec * gl_FrontMaterial.specular), 1.0); + vec4 color = vec4(vec3(gl_FrontLightModelProduct.sceneColor + + amb * gl_FrontMaterial.ambient + + diff * gl_FrontMaterial.diffuse), 1.0); + + gl_FragColor = color + secondaryColor; +} diff --git a/src/main/java/org/jdesktop/j3d/examples/glsl_shader/phong.vert b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/phong.vert new file mode 100644 index 0000000..ab27603 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/phong.vert @@ -0,0 +1,56 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +// A GLSL vertex program for doing Phone shading (per-fragment lighting) + +// Per-pixel normal (output to fragment shader) +varying vec3 Normal; + +void main() +{ + Normal = normalize(vec3(gl_NormalMatrix * gl_Normal)); + + // Transform the vertex + gl_Position = gl_ModelViewProjectionMatrix * gl_Vertex; +} diff --git a/src/main/java/org/jdesktop/j3d/examples/glsl_shader/polkadot3d.frag b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/polkadot3d.frag new file mode 100644 index 0000000..b341454 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/polkadot3d.frag @@ -0,0 +1,48 @@ +// +// Fragment shader for 3 dimensional polka dot shader. +// +// Author: Joshua Doss +// +// Copyright (C) 2002-2004 3Dlabs Inc. Ltd. +// +// See 3Dlabs-License.txt for license information +// +varying float LightIntensity; +varying vec3 MCPosition; + +//Create uniform variables so dots can be spaced and scaled by user +//uniform vec3 Spacing; +//uniform float DotSize; +const vec3 Spacing = vec3 (0.314, 0.36, 0.261); +const float DotSize = 0.123; + +//Create colors as uniform variables so they can be easily changed +//uniform vec3 ModelColor, PolkaDotColor; +const vec3 ModelColor = vec3 (0.75, 0.2, 0.1); +const vec3 PolkaDotColor = vec3 (1, 1, 1); + +void main(void) +{ + float insidesphere, sphereradius, scaledpointlength; + vec3 scaledpoint, finalcolor; + + // Scale the coordinate system + // The following line of code is not yet implemented in current drivers: + // mcpos = mod(Spacing, MCposition); + // We will use a workaround found below for now + scaledpoint = MCPosition - (Spacing * floor(MCPosition/Spacing)); + + // Bring the scaledpoint vector into the center of the scaled coordinate system + scaledpoint = scaledpoint - Spacing/2.0; + + // Find the length of the scaledpoint vector and compare it to the dotsize + scaledpointlength = length(scaledpoint); + insidesphere = step(scaledpointlength,DotSize); + + // Determine final output color before lighting + finalcolor = vec3(mix(ModelColor, PolkaDotColor, insidesphere)); + + // Output final color and factor in lighting + gl_FragColor = clamp((vec4( finalcolor, 1.0 ) * LightIntensity), vec4(0.0), vec4(1.0)); +} + diff --git a/src/main/java/org/jdesktop/j3d/examples/glsl_shader/polkadot3d.vert b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/polkadot3d.vert new file mode 100644 index 0000000..86f432f --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/polkadot3d.vert @@ -0,0 +1,58 @@ +// This is the Vertex Shader for three dimensional polka dots. +// +// author(s): Joshua Doss +// +// Copyright (C) 2002-2004 3Dlabs Inc. Ltd. + +//Create uniform variables for lighting to allow user interaction +//uniform float SpecularContribution; +//uniform vec3 LightPosition; + +const float SpecularContribution = 0.36; +const vec3 LightPosition = vec3 (0, 4, 5); + +varying vec3 MCPosition; +varying float LightIntensity; + +void main(void) +{ + float diffusecontribution = 1.0 - SpecularContribution; + + // compute the vertex position in eye coordinates + vec3 ecPosition = vec3(gl_ModelViewMatrix * gl_Vertex); + + // compute the transformed normal + vec3 tnorm = normalize(gl_NormalMatrix * gl_Normal); + + // compute a vector from the model to the light position + vec3 lightVec = normalize(LightPosition - ecPosition); + + // compute the reflection vector + vec3 reflectVec = reflect(-lightVec, tnorm); + + // compute a unit vector in direction of viewing position + vec3 viewVec = normalize(-ecPosition); + + // calculate amount of diffuse light based on normal and light angle + float diffuse = max(dot(lightVec, tnorm), 0.0); + float spec = 0.0; + + // if there is diffuse lighting, calculate specular + if(diffuse > 0.0) + { + spec = max(dot(reflectVec, viewVec), 0.0); + spec = pow(spec, 16.0); + } + + // add up the light sources, since this is a varying (global) it will pass to frag shader + LightIntensity = diffusecontribution * diffuse * 1.5 + + SpecularContribution * spec; + + // the varying variable MCPosition will be used by the fragment shader to determine where + // in model space the current pixel is + MCPosition = vec3 (gl_Vertex); + + // send vertex information + gl_Position = gl_ModelViewProjectionMatrix * gl_Vertex; +} + diff --git a/src/main/java/org/jdesktop/j3d/examples/glsl_shader/simple.frag b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/simple.frag new file mode 100644 index 0000000..51eaaf6 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/simple.frag @@ -0,0 +1,65 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + + +varying vec4 glFrontColor; + +// Simple GLSL fragment program to attenuate the input fragment color as a +// function of the distance of the fragment position from the center +// of the window + +const float windowSize = 700.0; // TODO: this should be a built-in parameter! + +void main() +{ + // Compute distance from center in range [0.0, 1.0] + vec2 dist = min(abs((gl_FragCoord.xy - (windowSize)/2.0) / windowSize), 1.0); + vec2 invDist = 1.0 - dist; + + // Compute attenuation + float atten = invDist.x * invDist.y; + vec4 outcolor = (gl_Color + gl_SecondaryColor) * atten; + + gl_FragColor = outcolor; +} diff --git a/src/main/java/org/jdesktop/j3d/examples/glsl_shader/simple.vert b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/simple.vert new file mode 100644 index 0000000..f90ef79 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/simple.vert @@ -0,0 +1,131 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +// A simple GLSL vertex program for handling 2 directional lights with +// separate specular + +varying vec4 glFrontColor; + +void directionalLight( + in int i, + in vec3 normal, + inout vec4 ambient, + inout vec4 diffuse, + inout vec4 specular) +{ + // Normalized light direction and half vector + // (shouldn't they be pre-normalized?!) + vec3 lightDirection = normalize(vec3(gl_LightSource[i].position)); + vec3 halfVector = normalize(vec3(gl_LightSource[i].halfVector)); + + float nDotVP; // normal . light_direction + float nDotHV; // normal . light_half_vector + float pf; // power factor + + nDotVP = max(0.0, dot(normal, lightDirection)); + nDotHV = max(0.0, dot(normal, halfVector)); + + if (nDotVP == 0.0) { + pf = 0.0; + } + else { + pf = pow(nDotHV, gl_FrontMaterial.shininess); + } + + ambient += gl_LightSource[i].ambient; + diffuse += gl_LightSource[i].diffuse * nDotVP; + specular += gl_LightSource[i].specular * pf; +} + + +const int numEnabledLights = 2; // TODO: this should be a built-in parameter! + +void main() +{ + //vec4 ecPosition = gl_ModelViewMatrix * gl_Vertex; + //vec3 ecPosition3 = ecPosition.xyz / ecPosition.w; + vec3 tnorm = normalize(vec3(gl_NormalMatrix * gl_Normal)); + vec4 amb = vec4(0.0); + vec4 diff = vec4(0.0); + vec4 spec = vec4(0.0); + int i; + + // Transform the vertex + vec4 outPosition = gl_ModelViewProjectionMatrix * gl_Vertex; + + for (i = 0; i < numEnabledLights; i++) { + directionalLight(i, tnorm, amb, diff, spec); + } + + // Apply the result of the lighting equation + vec4 outSecondaryColor = vec4(vec3(spec * gl_FrontMaterial.specular), 1.0); + vec3 color0 = vec3(gl_FrontLightModelProduct.sceneColor + + amb * gl_FrontMaterial.ambient + + diff * gl_FrontMaterial.diffuse); + + // Generate a pseudo-random noise pattern + vec3 xyz = clamp((outPosition.xyz + 1.0) * 0.5, 0.0, 1.0); + + xyz = fract(xyz * 262144.0); + float randSeed = fract(3.0 * xyz.x + 5.0 * xyz.y + 7.0 * xyz.z); + + vec3 altColor; + + randSeed = fract(37.0 * randSeed); + altColor.x = randSeed * 0.5 + 0.5; + randSeed = fract(37.0 * randSeed); + altColor.y = randSeed * 0.5 + 0.5; + randSeed = fract(37.0 * randSeed); + altColor.z = randSeed * 0.5 + 0.5; + randSeed = fract(37.0 * randSeed); + float altAlpha = randSeed * 0.5; + + // Apply noise and output final vertex color + vec4 outColor; + outColor = vec4(mix(color0, altColor, altAlpha), 1.0); + + gl_FrontColor = outColor; + gl_FrontSecondaryColor = outSecondaryColor; + gl_Position = outPosition; +} diff --git a/src/main/java/org/jdesktop/j3d/examples/glsl_shader/toon.frag b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/toon.frag new file mode 100644 index 0000000..fa50453 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/toon.frag @@ -0,0 +1,34 @@ +// +// Fragment shader for cartoon-style shading +// +// Author: Philip Rideout +// +// Copyright (c) 2004 3Dlabs Inc. Ltd. +// +// See 3Dlabs-License.txt for license information +// + +//uniform vec3 DiffuseColor; +//uniform vec3 PhongColor; +//uniform float Edge; +//uniform float Phong; + +vec3 DiffuseColor = vec3(0.5,0.5,1.0); +vec3 PhongColor = vec3(0.75,0.75,1.0); +float Edge = 0.64; +float Phong = 0.90; + +varying vec3 Normal; +varying vec3 LightDir; + +void main (void) +{ + vec3 color = DiffuseColor; + float f = max( 0.0, dot(LightDir,Normal)); + if (abs(f) < Edge) + color = DiffuseColor * 0.2; + if (f > Phong) + color = PhongColor; + + gl_FragColor = vec4(color, 1); +} diff --git a/src/main/java/org/jdesktop/j3d/examples/glsl_shader/toon.vert b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/toon.vert new file mode 100644 index 0000000..d044af7 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/toon.vert @@ -0,0 +1,19 @@ +// +// Vertex shader for cartoon-style shading +// +// Author: Philip Rideout +// +// Copyright (c) 2004 3Dlabs Inc. Ltd. +// +// See 3Dlabs-License.txt for license information +// + +varying vec3 Normal; +varying vec3 LightDir; + +void main(void) +{ + Normal = normalize(gl_NormalMatrix * gl_Normal); + gl_Position = gl_ModelViewProjectionMatrix * gl_Vertex; + LightDir = vec3(normalize(gl_LightSource[0].position)); +} diff --git a/src/main/java/org/jdesktop/j3d/examples/glsl_shader/vertexshader.vert b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/vertexshader.vert new file mode 100644 index 0000000..43b4a05 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/vertexshader.vert @@ -0,0 +1,61 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +// A simple GLSL vertex program for demo. vertex attributes + +attribute float weight; +attribute vec3 temperature; + +void main() +{ + // Transform the vertex + vec4 outPosition = gl_ModelViewProjectionMatrix * gl_Vertex; + + // Compute color from temperature + vec4 outColor; + outColor = vec4(temperature * weight, 1); + // Assign output parameters + gl_FrontColor = outColor; + gl_Position = outPosition; +} diff --git a/src/main/java/org/jdesktop/j3d/examples/glsl_shader/wood.frag b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/wood.frag new file mode 100644 index 0000000..eecf91f --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/wood.frag @@ -0,0 +1,66 @@ +// +// Simple fragment shader for wood +// +// Author: John Kessenich +// +// Copyright (c) 2002-2004 3Dlabs Inc. Ltd. +// +// See 3Dlabs-License.txt for license information +// + +//uniform float GrainSizeRecip; +//uniform vec3 DarkColor; +//uniform vec3 spread; +const float GrainSizeRecip = 1.0; +const vec3 DarkColor = vec3 (0.6, 0.3, 0.1); +const vec3 spread = vec3 (0.15, 0.075, 0.0); + +varying float lightIntensity; +varying vec3 Position; + +void main (void) +{ + // + // cheap noise + // + vec3 location = Position; + vec3 floorvec = vec3(floor(10.0 * Position.x), 0.0, floor(10.0 * Position.z)); + vec3 noise = Position * 10.0 - floorvec - 0.5; + noise *= noise; + location += noise * 0.12; + + // + // distance from axis + // + float dist = location.x * location.x + location.z * location.z; + float grain = dist * GrainSizeRecip; + + // + // grain effects as function of distance + // + float brightness = fract(grain); + if (brightness > 0.5) + brightness = (1.0 - brightness); + vec3 color = DarkColor + brightness * spread; + + brightness = fract(grain * 7.0); + if (brightness > 0.5) + brightness = 1.0 - brightness; + color -= brightness * spread; + + // + // also as a function of lines parallel to the axis + // + brightness = fract(grain * 47.0) * 0.60; + float line = fract(Position.z + Position.x); + float snap = floor(line * 20.0) * (1.0/20.0); + if (line < snap + 0.006) + color -= brightness * spread; + + // + // apply lighting effects from vertex processor + // + color = clamp(color * lightIntensity, 0.0, 1.0); + + gl_FragColor = vec4(color, 1.0); +} diff --git a/src/main/java/org/jdesktop/j3d/examples/glsl_shader/wood.vert b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/wood.vert new file mode 100644 index 0000000..84651aa --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/glsl_shader/wood.vert @@ -0,0 +1,25 @@ +// +// Simple vertex shader for wood +// +// Author: John Kessenich +// +// Copyright (c) 2002-2004 3Dlabs Inc. Ltd. +// +// See 3Dlabs-License.txt for license information +// + +varying float lightIntensity; +varying vec3 Position; +//uniform vec3 LightPosition; +//uniform float Scale; +const vec3 LightPosition = vec3 (0.0,0.0,0.4); +const float Scale = 1.0; + +void main(void) +{ + vec4 pos = gl_ModelViewMatrix * gl_Vertex; + Position = vec3(gl_Vertex) * Scale; + vec3 tnorm = normalize(gl_NormalMatrix * gl_Normal); + lightIntensity = max(dot(normalize(LightPosition - vec3(pos)), tnorm), 0.0) * 1.5; + gl_Position = gl_ModelViewProjectionMatrix * gl_Vertex; +} diff --git a/src/main/java/org/jdesktop/j3d/examples/hello_universe/HelloUniverse.form b/src/main/java/org/jdesktop/j3d/examples/hello_universe/HelloUniverse.form new file mode 100644 index 0000000..48fadea --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/hello_universe/HelloUniverse.form @@ -0,0 +1,36 @@ +<?xml version="1.0" encoding="UTF-8" ?> + +<Form version="1.0" type="org.netbeans.modules.form.forminfo.JFrameFormInfo"> + <Properties> + <Property name="defaultCloseOperation" type="int" value="3"/> + <Property name="title" type="java.lang.String" value="HelloUniverse"/> + </Properties> + <SyntheticProperties> + <SyntheticProperty name="formSizePolicy" type="int" value="1"/> + </SyntheticProperties> + <AuxValues> + <AuxValue name="FormSettings_generateMnemonicsCode" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_listenerGenerationStyle" type="java.lang.Integer" value="0"/> + <AuxValue name="FormSettings_variablesLocal" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_variablesModifier" type="java.lang.Integer" value="2"/> + <AuxValue name="designerSize" type="java.awt.Dimension" value="-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,1,44,0,0,1,-112"/> + </AuxValues> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + <SubComponents> + <Container class="javax.swing.JPanel" name="drawingPanel"> + <Properties> + <Property name="preferredSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor"> + <Dimension value="[250, 250]"/> + </Property> + </Properties> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout" value="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription"> + <BorderConstraints direction="Center"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + </Container> + </SubComponents> +</Form> diff --git a/src/main/java/org/jdesktop/j3d/examples/hello_universe/HelloUniverse.java b/src/main/java/org/jdesktop/j3d/examples/hello_universe/HelloUniverse.java new file mode 100644 index 0000000..a085405 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/hello_universe/HelloUniverse.java @@ -0,0 +1,176 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.hello_universe; + +import java.awt.GraphicsConfiguration; + +import org.jogamp.java3d.Alpha; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.RotationInterpolator; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.utils.geometry.ColorCube; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.vecmath.Point3d; + +/** + * Simple Java 3D example program to display a spinning cube. + */ +public class HelloUniverse extends javax.swing.JFrame { + + private SimpleUniverse univ = null; + private BranchGroup scene = null; + + public BranchGroup createSceneGraph() { + // Create the root of the branch graph + BranchGroup objRoot = new BranchGroup(); + + // Create the TransformGroup node and initialize it to the + // identity. Enable the TRANSFORM_WRITE capability so that + // our behavior code can modify it at run time. Add it to + // the root of the subgraph. + TransformGroup objTrans = new TransformGroup(); + objTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + objRoot.addChild(objTrans); + + // Create a simple Shape3D node; add it to the scene graph. + objTrans.addChild(new ColorCube(0.4)); + + // Create a new Behavior object that will perform the + // desired operation on the specified transform and add + // it into the scene graph. + Transform3D yAxis = new Transform3D(); + Alpha rotationAlpha = new Alpha(-1, 4000); + + RotationInterpolator rotator = + new RotationInterpolator(rotationAlpha, objTrans, yAxis, + 0.0f, (float) Math.PI*2.0f); + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + rotator.setSchedulingBounds(bounds); + objRoot.addChild(rotator); + + // Have Java 3D perform optimizations on this scene graph. + objRoot.compile(); + + return objRoot; + } + + private Canvas3D createUniverse() { + // Get the preferred graphics configuration for the default screen + GraphicsConfiguration config = + SimpleUniverse.getPreferredConfiguration(); + + // Create a Canvas3D using the preferred configuration + Canvas3D c = new Canvas3D(config); + + // Create simple universe with view branch + univ = new SimpleUniverse(c); + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + univ.getViewingPlatform().setNominalViewingTransform(); + + // Ensure at least 5 msec per frame (i.e., < 200Hz) + univ.getViewer().getView().setMinimumFrameCycleTime(5); + + return c; + } + + /** + * Creates new form HelloUniverse + */ + public HelloUniverse() { + // Initialize the GUI components + initComponents(); + + // Create Canvas3D and SimpleUniverse; add canvas to drawing panel + Canvas3D c = createUniverse(); + drawingPanel.add(c, java.awt.BorderLayout.CENTER); + + // Create the content branch and add it to the universe + scene = createSceneGraph(); + univ.addBranchGraph(scene); + } + + // ---------------------------------------------------------------- + + /** This method is called from within the constructor to + * initialize the form. + * WARNING: Do NOT modify this code. The content of this method is + * always regenerated by the Form Editor. + */ + // <editor-fold defaultstate="collapsed" desc=" Generated Code ">//GEN-BEGIN:initComponents + private void initComponents() { + drawingPanel = new javax.swing.JPanel(); + + setDefaultCloseOperation(javax.swing.WindowConstants.EXIT_ON_CLOSE); + setTitle("HelloUniverse"); + drawingPanel.setLayout(new java.awt.BorderLayout()); + + drawingPanel.setPreferredSize(new java.awt.Dimension(250, 250)); + getContentPane().add(drawingPanel, java.awt.BorderLayout.CENTER); + + pack(); + }// </editor-fold>//GEN-END:initComponents + + /** + * @param args the command line arguments + */ + public static void main(String args[]) {System.setProperty("sun.awt.noerasebackground", "true"); + java.awt.EventQueue.invokeLater(new Runnable() { + public void run() { + new HelloUniverse().setVisible(true); + } + }); + } + + // Variables declaration - do not modify//GEN-BEGIN:variables + private javax.swing.JPanel drawingPanel; + // End of variables declaration//GEN-END:variables + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/hello_universe/HelloUniverseGL2ES2.java b/src/main/java/org/jdesktop/j3d/examples/hello_universe/HelloUniverseGL2ES2.java new file mode 100644 index 0000000..b62906b --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/hello_universe/HelloUniverseGL2ES2.java @@ -0,0 +1,161 @@ +/* + * Copyright (c) 2016 JogAmp Community. All rights reserved. + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * This code is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 only, as + * published by the Free Software Foundation. Sun designates this + * particular file as subject to the "Classpath" exception as provided + * by Sun in the LICENSE file that accompanied this code. + * + * This code is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + * version 2 for more details (a copy is included in the LICENSE file that + * accompanied this code). + * + * You should have received a copy of the GNU General Public License version + * 2 along with this work; if not, write to the Free Software Foundation, + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. + * + */ + +package org.jdesktop.j3d.examples.hello_universe; + +import java.awt.GraphicsConfiguration; + +import org.jdesktop.j3d.examples.gl2es2pipeline.Cube; +import org.jogamp.java3d.Alpha; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.RotationInterpolator; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.vecmath.Point3d; + +/** + * Simple Java 3D example program to display a spinning cube. + */ +public class HelloUniverseGL2ES2 extends javax.swing.JFrame +{ + + private SimpleUniverse univ = null; + private BranchGroup scene = null; + + public BranchGroup createSceneGraph() + { + // Create the root of the branch graph + BranchGroup objRoot = new BranchGroup(); + + // Create the TransformGroup node and initialize it to the + // identity. Enable the TRANSFORM_WRITE capability so that + // our behavior code can modify it at run time. Add it to + // the root of the subgraph. + TransformGroup objTrans = new TransformGroup(); + objTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + objRoot.addChild(objTrans); + + // Create a simple Shape3D node; add it to the scene graph. + objTrans.addChild(new Cube(0.4)); + + // Create a new Behavior object that will perform the + // desired operation on the specified transform and add + // it into the scene graph. + Transform3D yAxis = new Transform3D(); + Alpha rotationAlpha = new Alpha(-1, 4000); + + RotationInterpolator rotator = new RotationInterpolator(rotationAlpha, objTrans, yAxis, 0.0f, (float) Math.PI * 2.0f); + BoundingSphere bounds = new BoundingSphere(new Point3d(0.0, 0.0, 0.0), 100.0); + rotator.setSchedulingBounds(bounds); + objRoot.addChild(rotator); + + // Have Java 3D perform optimizations on this scene graph. + objRoot.compile(); + + return objRoot; + } + + private Canvas3D createUniverse() + { + // Get the preferred graphics configuration for the default screen + GraphicsConfiguration config = SimpleUniverse.getPreferredConfiguration(); + + // Create a Canvas3D using the preferred configuration + Canvas3D c = new Canvas3D(config); + + // Create simple universe with view branch + univ = new SimpleUniverse(c); + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + univ.getViewingPlatform().setNominalViewingTransform(); + + // Ensure at least 5 msec per frame (i.e., < 200Hz) + univ.getViewer().getView().setMinimumFrameCycleTime(5); + + return c; + } + + /** + * Creates new form HelloUniverse + */ + public HelloUniverseGL2ES2() + { + // Initialize the GUI components + initComponents(); + + // Create Canvas3D and SimpleUniverse; add canvas to drawing panel + Canvas3D c = createUniverse(); + drawingPanel.add(c, java.awt.BorderLayout.CENTER); + + // Create the content branch and add it to the universe + scene = createSceneGraph(); + univ.addBranchGraph(scene); + } + + // ---------------------------------------------------------------- + + /** This method is called from within the constructor to + * initialize the form. + * WARNING: Do NOT modify this code. The content of this method is + * always regenerated by the Form Editor. + */ + // <editor-fold defaultstate="collapsed" desc=" Generated Code ">//GEN-BEGIN:initComponents + private void initComponents() + { + drawingPanel = new javax.swing.JPanel(); + + setDefaultCloseOperation(javax.swing.WindowConstants.EXIT_ON_CLOSE); + setTitle("HelloUniverse GL2ES2"); + drawingPanel.setLayout(new java.awt.BorderLayout()); + + drawingPanel.setPreferredSize(new java.awt.Dimension(250, 250)); + getContentPane().add(drawingPanel, java.awt.BorderLayout.CENTER); + + pack(); + }// </editor-fold>//GEN-END:initComponents + + /** + * @param args the command line arguments + */ + public static void main(String args[]) + { + System.setProperty("sun.awt.noerasebackground", "true"); + System.setProperty("j3d.rend", "jogl2es2"); + System.setProperty("j3d.displaylist", "false"); + java.awt.EventQueue.invokeLater(new Runnable() { + @Override + public void run() + { + new HelloUniverseGL2ES2().setVisible(true); + } + }); + } + + // Variables declaration - do not modify//GEN-BEGIN:variables + private javax.swing.JPanel drawingPanel; + // End of variables declaration//GEN-END:variables + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/jcanvas3d/JCanvas3DExample.form b/src/main/java/org/jdesktop/j3d/examples/jcanvas3d/JCanvas3DExample.form new file mode 100644 index 0000000..5efa763 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/jcanvas3d/JCanvas3DExample.form @@ -0,0 +1,142 @@ +<?xml version="1.0" encoding="UTF-8" ?> + +<Form version="1.0" type="org.netbeans.modules.form.forminfo.JFrameFormInfo"> + <Properties> + <Property name="defaultCloseOperation" type="int" value="3"/> + </Properties> + <SyntheticProperties> + <SyntheticProperty name="formSize" type="java.awt.Dimension" value="-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,2,-35,0,0,3,-13"/> + <SyntheticProperty name="formSizePolicy" type="int" value="0"/> + <SyntheticProperty name="generateSize" type="boolean" value="true"/> + <SyntheticProperty name="generateCenter" type="boolean" value="true"/> + </SyntheticProperties> + <AuxValues> + <AuxValue name="FormSettings_generateMnemonicsCode" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_i18nAutoMode" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_listenerGenerationStyle" type="java.lang.Integer" value="2"/> + <AuxValue name="FormSettings_variablesLocal" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_variablesModifier" type="java.lang.Integer" value="2"/> + </AuxValues> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + <SubComponents> + <Container class="javax.swing.JSplitPane" name="splitPane"> + <Properties> + <Property name="dividerLocation" type="int" value="300"/> + <Property name="dividerSize" type="int" value="8"/> + <Property name="continuousLayout" type="boolean" value="true"/> + <Property name="oneTouchExpandable" type="boolean" value="true"/> + </Properties> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout" value="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription"> + <BorderConstraints direction="Center"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.support.JSplitPaneSupportLayout"/> + <SubComponents> + <Container class="javax.swing.JScrollPane" name="scrollPane"> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.support.JSplitPaneSupportLayout" value="org.netbeans.modules.form.compat2.layouts.support.JSplitPaneSupportLayout$JSplitPaneConstraintsDescription"> + <JSplitPaneConstraints position="left"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.support.JScrollPaneSupportLayout"/> + <SubComponents> + <Container class="javax.swing.JPanel" name="panel"> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout"/> + <SubComponents> + <Component class="javax.swing.JButton" name="addButton"> + <Properties> + <Property name="text" type="java.lang.String" value="Create New Frame"/> + <Property name="toolTipText" type="java.lang.String" value="Adds a new frame containing an universe into the desktop pane"/> + </Properties> + <Events> + <EventHandler event="actionPerformed" listener="java.awt.event.ActionListener" parameters="java.awt.event.ActionEvent" handler="addButtonActionPerformed"/> + </Events> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout" value="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription"> + <GridBagConstraints gridX="-1" gridY="-1" gridWidth="1" gridHeight="1" fill="0" ipadX="0" ipadY="0" insetsTop="0" insetsLeft="0" insetsBottom="0" insetsRight="0" anchor="10" weightX="0.0" weightY="0.0"/> + </Constraint> + </Constraints> + </Component> + <Component class="javax.swing.JCheckBox" name="delayCheckBox"> + <Properties> + <Property name="text" type="java.lang.String" value="Resize Delayed"/> + <Property name="toolTipText" type="java.lang.String" value="Shows the effect of using a delayed resizing to the internal frames."/> + </Properties> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout" value="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription"> + <GridBagConstraints gridX="0" gridY="1" gridWidth="1" gridHeight="1" fill="2" ipadX="0" ipadY="0" insetsTop="0" insetsLeft="0" insetsBottom="0" insetsRight="0" anchor="10" weightX="0.0" weightY="0.0"/> + </Constraint> + </Constraints> + </Component> + <Component class="javax.swing.JCheckBox" name="interactiveCheckBox"> + <Properties> + <Property name="selected" type="boolean" value="true"/> + <Property name="text" type="java.lang.String" value="Interactive Cube"/> + <Property name="toolTipText" type="java.lang.String" value="Tests the use of AWT behaviors on the displayed component."/> + <Property name="border" type="javax.swing.border.Border" editor="org.netbeans.modules.form.editors2.BorderEditor"> + <Border info="org.netbeans.modules.form.compat2.border.EmptyBorderInfo"> + <EmptyBorder bottom="0" left="0" right="0" top="0"/> + </Border> + </Property> + <Property name="margin" type="java.awt.Insets" editor="org.netbeans.beaninfo.editors.InsetsEditor"> + <Insets value="[0, 0, 0, 0]"/> + </Property> + </Properties> + <Events> + <EventHandler event="actionPerformed" listener="java.awt.event.ActionListener" parameters="java.awt.event.ActionEvent" handler="interactiveCheckBoxActionPerformed"/> + </Events> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout" value="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription"> + <GridBagConstraints gridX="0" gridY="2" gridWidth="1" gridHeight="1" fill="2" ipadX="0" ipadY="0" insetsTop="0" insetsLeft="0" insetsBottom="0" insetsRight="0" anchor="10" weightX="0.0" weightY="0.0"/> + </Constraint> + </Constraints> + </Component> + <Component class="javax.swing.JCheckBox" name="randomCheckBox"> + <Properties> + <Property name="text" type="java.lang.String" value="Random start angle"/> + <Property name="border" type="javax.swing.border.Border" editor="org.netbeans.modules.form.editors2.BorderEditor"> + <Border info="org.netbeans.modules.form.compat2.border.EmptyBorderInfo"> + <EmptyBorder bottom="0" left="0" right="0" top="0"/> + </Border> + </Property> + <Property name="enabled" type="boolean" value="false"/> + <Property name="margin" type="java.awt.Insets" editor="org.netbeans.beaninfo.editors.InsetsEditor"> + <Insets value="[0, 0, 0, 0]"/> + </Property> + </Properties> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout" value="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription"> + <GridBagConstraints gridX="0" gridY="3" gridWidth="1" gridHeight="1" fill="2" ipadX="0" ipadY="0" insetsTop="0" insetsLeft="0" insetsBottom="0" insetsRight="0" anchor="10" weightX="0.0" weightY="0.0"/> + </Constraint> + </Constraints> + </Component> + </SubComponents> + </Container> + </SubComponents> + </Container> + <Container class="javax.swing.JDesktopPane" name="desktopPane"> + <Properties> + <Property name="background" type="java.awt.Color" editor="org.netbeans.beaninfo.editors.ColorEditor"> + <Color blue="c9" green="99" red="99" type="rgb"/> + </Property> + <Property name="preferredSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor"> + <Dimension value="[300, 300]"/> + </Property> + </Properties> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.support.JSplitPaneSupportLayout" value="org.netbeans.modules.form.compat2.layouts.support.JSplitPaneSupportLayout$JSplitPaneConstraintsDescription"> + <JSplitPaneConstraints position="right"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.support.JLayeredPaneSupportLayout"/> + </Container> + </SubComponents> + </Container> + </SubComponents> +</Form> diff --git a/src/main/java/org/jdesktop/j3d/examples/jcanvas3d/JCanvas3DExample.java b/src/main/java/org/jdesktop/j3d/examples/jcanvas3d/JCanvas3DExample.java new file mode 100644 index 0000000..1a83fdd --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/jcanvas3d/JCanvas3DExample.java @@ -0,0 +1,195 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.jcanvas3d; + + +/** + * Simple Java 3D example program that displays universes within lightweight swing components, layed in JInternalFrame objects. + */ +import java.awt.Toolkit; + +public class JCanvas3DExample extends javax.swing.JFrame implements java.awt.event.ActionListener +{ + + /** + * Creates new form JCanvas3DExample + */ + public JCanvas3DExample() + { + initComponents(); + Toolkit.getDefaultToolkit().setDynamicLayout( true ); + setDefaultCloseOperation( EXIT_ON_CLOSE ); + } + + /** This method is called from within the constructor to + * initialize the form. + * WARNING: Do NOT modify this code. The content of this method is + * always regenerated by the Form Editor. + */ + // <editor-fold defaultstate="collapsed" desc=" Generated Code ">//GEN-BEGIN:initComponents + private void initComponents() { + java.awt.GridBagConstraints gridBagConstraints; + + splitPane = new javax.swing.JSplitPane(); + scrollPane = new javax.swing.JScrollPane(); + panel = new javax.swing.JPanel(); + addButton = new javax.swing.JButton(); + delayCheckBox = new javax.swing.JCheckBox(); + interactiveCheckBox = new javax.swing.JCheckBox(); + randomCheckBox = new javax.swing.JCheckBox(); + desktopPane = new javax.swing.JDesktopPane(); + + setDefaultCloseOperation(javax.swing.WindowConstants.EXIT_ON_CLOSE); + splitPane.setDividerLocation(300); + splitPane.setDividerSize(8); + splitPane.setContinuousLayout(true); + splitPane.setOneTouchExpandable(true); + panel.setLayout(new java.awt.GridBagLayout()); + + addButton.setText("Create New Frame"); + addButton.setToolTipText("Adds a new frame containing an universe into the desktop pane"); + addButton.addActionListener(this); + + panel.add(addButton, new java.awt.GridBagConstraints()); + + delayCheckBox.setText("Resize Delayed"); + delayCheckBox.setToolTipText("Shows the effect of using a delayed resizing to the internal frames."); + gridBagConstraints = new java.awt.GridBagConstraints(); + gridBagConstraints.gridx = 0; + gridBagConstraints.gridy = 1; + gridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL; + panel.add(delayCheckBox, gridBagConstraints); + + interactiveCheckBox.setSelected(true); + interactiveCheckBox.setText("Interactive Cube"); + interactiveCheckBox.setToolTipText("Tests the use of AWT behaviors on the displayed component."); + interactiveCheckBox.setBorder(javax.swing.BorderFactory.createEmptyBorder(0, 0, 0, 0)); + interactiveCheckBox.setMargin(new java.awt.Insets(0, 0, 0, 0)); + interactiveCheckBox.addActionListener(this); + + gridBagConstraints = new java.awt.GridBagConstraints(); + gridBagConstraints.gridx = 0; + gridBagConstraints.gridy = 2; + gridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL; + panel.add(interactiveCheckBox, gridBagConstraints); + + randomCheckBox.setText("Random start angle"); + randomCheckBox.setBorder(javax.swing.BorderFactory.createEmptyBorder(0, 0, 0, 0)); + randomCheckBox.setEnabled(false); + randomCheckBox.setMargin(new java.awt.Insets(0, 0, 0, 0)); + gridBagConstraints = new java.awt.GridBagConstraints(); + gridBagConstraints.gridx = 0; + gridBagConstraints.gridy = 3; + gridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL; + panel.add(randomCheckBox, gridBagConstraints); + + scrollPane.setViewportView(panel); + + splitPane.setLeftComponent(scrollPane); + + desktopPane.setBackground(new java.awt.Color(153, 153, 201)); + desktopPane.setPreferredSize(new java.awt.Dimension(300, 300)); + splitPane.setRightComponent(desktopPane); + + getContentPane().add(splitPane, java.awt.BorderLayout.CENTER); + + java.awt.Dimension screenSize = java.awt.Toolkit.getDefaultToolkit().getScreenSize(); + setBounds((screenSize.width-1011)/2, (screenSize.height-733)/2, 1011, 733); + } + + // Code for dispatching events from components to event handlers. + + public void actionPerformed(java.awt.event.ActionEvent evt) { + if (evt.getSource() == addButton) { + JCanvas3DExample.this.addButtonActionPerformed(evt); + } + else if (evt.getSource() == interactiveCheckBox) { + JCanvas3DExample.this.interactiveCheckBoxActionPerformed(evt); + } + }// </editor-fold>//GEN-END:initComponents + + private void interactiveCheckBoxActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_interactiveCheckBoxActionPerformed + randomCheckBox.setEnabled( interactiveCheckBox.isSelected() ? false:true ); + }//GEN-LAST:event_interactiveCheckBoxActionPerformed + + private void addButtonActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_addButtonActionPerformed + JInternalWorld iWorld; + // we create an internal world to be added within the JDesktop. + iWorld = new JInternalWorld( interactiveCheckBox.isSelected(), + delayCheckBox.isSelected(), + randomCheckBox.isSelected() ); + iWorld.setSize( 256, 256 ); + iWorld.setLocation( 50, 50 ); + iWorld.setResizable( true ); + desktopPane.add( iWorld ); + iWorld.setVisible(true); + }//GEN-LAST:event_addButtonActionPerformed + + /** + * @param args the command line arguments + */ + public static void main(String args[]) + { + java.awt.EventQueue.invokeLater(new Runnable() + { + public void run() + { + new JCanvas3DExample().setVisible(true); + } + }); + } + + // Variables declaration - do not modify//GEN-BEGIN:variables + private javax.swing.JButton addButton; + private javax.swing.JCheckBox delayCheckBox; + private javax.swing.JDesktopPane desktopPane; + private javax.swing.JCheckBox interactiveCheckBox; + private javax.swing.JPanel panel; + private javax.swing.JCheckBox randomCheckBox; + private javax.swing.JScrollPane scrollPane; + private javax.swing.JSplitPane splitPane; + // End of variables declaration//GEN-END:variables + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/jcanvas3d/JCanvas3DExampleGL2ES2.java b/src/main/java/org/jdesktop/j3d/examples/jcanvas3d/JCanvas3DExampleGL2ES2.java new file mode 100644 index 0000000..45dccc0 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/jcanvas3d/JCanvas3DExampleGL2ES2.java @@ -0,0 +1,175 @@ +/* + * Copyright (c) 2016 JogAmp Community. All rights reserved. + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * This code is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 only, as + * published by the Free Software Foundation. Sun designates this + * particular file as subject to the "Classpath" exception as provided + * by Sun in the LICENSE file that accompanied this code. + * + * This code is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + * version 2 for more details (a copy is included in the LICENSE file that + * accompanied this code). + * + * You should have received a copy of the GNU General Public License version + * 2 along with this work; if not, write to the Free Software Foundation, + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. + * + */ + +package org.jdesktop.j3d.examples.jcanvas3d; + + +/** + * Simple Java 3D example program that displays universes within lightweight swing components, layed in JInternalFrame objects. + */ +import java.awt.Toolkit; + +public class JCanvas3DExampleGL2ES2 extends javax.swing.JFrame implements java.awt.event.ActionListener +{ + + /** + * Creates new form JCanvas3DExample + */ + public JCanvas3DExampleGL2ES2() + { + initComponents(); + Toolkit.getDefaultToolkit().setDynamicLayout( true ); + setDefaultCloseOperation( EXIT_ON_CLOSE ); + } + + /** This method is called from within the constructor to + * initialize the form. + * WARNING: Do NOT modify this code. The content of this method is + * always regenerated by the Form Editor. + */ + // <editor-fold defaultstate="collapsed" desc=" Generated Code ">//GEN-BEGIN:initComponents + private void initComponents() { + java.awt.GridBagConstraints gridBagConstraints; + + splitPane = new javax.swing.JSplitPane(); + scrollPane = new javax.swing.JScrollPane(); + panel = new javax.swing.JPanel(); + addButton = new javax.swing.JButton(); + delayCheckBox = new javax.swing.JCheckBox(); + interactiveCheckBox = new javax.swing.JCheckBox(); + randomCheckBox = new javax.swing.JCheckBox(); + desktopPane = new javax.swing.JDesktopPane(); + + setDefaultCloseOperation(javax.swing.WindowConstants.EXIT_ON_CLOSE); + splitPane.setDividerLocation(300); + splitPane.setDividerSize(8); + splitPane.setContinuousLayout(true); + splitPane.setOneTouchExpandable(true); + panel.setLayout(new java.awt.GridBagLayout()); + + addButton.setText("Create New Frame"); + addButton.setToolTipText("Adds a new frame containing an universe into the desktop pane"); + addButton.addActionListener(this); + + panel.add(addButton, new java.awt.GridBagConstraints()); + + delayCheckBox.setText("Resize Delayed"); + delayCheckBox.setToolTipText("Shows the effect of using a delayed resizing to the internal frames."); + gridBagConstraints = new java.awt.GridBagConstraints(); + gridBagConstraints.gridx = 0; + gridBagConstraints.gridy = 1; + gridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL; + panel.add(delayCheckBox, gridBagConstraints); + + interactiveCheckBox.setSelected(true); + interactiveCheckBox.setText("Interactive Cube"); + interactiveCheckBox.setToolTipText("Tests the use of AWT behaviors on the displayed component."); + interactiveCheckBox.setBorder(javax.swing.BorderFactory.createEmptyBorder(0, 0, 0, 0)); + interactiveCheckBox.setMargin(new java.awt.Insets(0, 0, 0, 0)); + interactiveCheckBox.addActionListener(this); + + gridBagConstraints = new java.awt.GridBagConstraints(); + gridBagConstraints.gridx = 0; + gridBagConstraints.gridy = 2; + gridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL; + panel.add(interactiveCheckBox, gridBagConstraints); + + randomCheckBox.setText("Random start angle"); + randomCheckBox.setBorder(javax.swing.BorderFactory.createEmptyBorder(0, 0, 0, 0)); + randomCheckBox.setEnabled(false); + randomCheckBox.setMargin(new java.awt.Insets(0, 0, 0, 0)); + gridBagConstraints = new java.awt.GridBagConstraints(); + gridBagConstraints.gridx = 0; + gridBagConstraints.gridy = 3; + gridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL; + panel.add(randomCheckBox, gridBagConstraints); + + scrollPane.setViewportView(panel); + + splitPane.setLeftComponent(scrollPane); + + desktopPane.setBackground(new java.awt.Color(153, 153, 201)); + desktopPane.setPreferredSize(new java.awt.Dimension(300, 300)); + splitPane.setRightComponent(desktopPane); + + getContentPane().add(splitPane, java.awt.BorderLayout.CENTER); + + java.awt.Dimension screenSize = java.awt.Toolkit.getDefaultToolkit().getScreenSize(); + setBounds((screenSize.width-1011)/2, (screenSize.height-733)/2, 1011, 733); + } + + // Code for dispatching events from components to event handlers. + + public void actionPerformed(java.awt.event.ActionEvent evt) { + if (evt.getSource() == addButton) { + JCanvas3DExampleGL2ES2.this.addButtonActionPerformed(evt); + } + else if (evt.getSource() == interactiveCheckBox) { + JCanvas3DExampleGL2ES2.this.interactiveCheckBoxActionPerformed(evt); + } + }// </editor-fold>//GEN-END:initComponents + + private void interactiveCheckBoxActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_interactiveCheckBoxActionPerformed + randomCheckBox.setEnabled( interactiveCheckBox.isSelected() ? false:true ); + }//GEN-LAST:event_interactiveCheckBoxActionPerformed + + private void addButtonActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_addButtonActionPerformed + JInternalWorldGL2ES2 iWorld; + // we create an internal world to be added within the JDesktop. + iWorld = new JInternalWorldGL2ES2( interactiveCheckBox.isSelected(), + delayCheckBox.isSelected(), + randomCheckBox.isSelected() ); + iWorld.setSize( 256, 256 ); + iWorld.setLocation( 50, 50 ); + iWorld.setResizable( true ); + desktopPane.add( iWorld ); + iWorld.setVisible(true); + }//GEN-LAST:event_addButtonActionPerformed + + /** + * @param args the command line arguments + */ + public static void main(String args[]) + {System.setProperty("sun.awt.noerasebackground", "true"); + System.setProperty("j3d.rend", "jogl2es2"); + System.setProperty("j3d.displaylist", "false"); + java.awt.EventQueue.invokeLater(new Runnable() + { + public void run() + { + new JCanvas3DExampleGL2ES2().setVisible(true); + } + }); + } + + // Variables declaration - do not modify//GEN-BEGIN:variables + private javax.swing.JButton addButton; + private javax.swing.JCheckBox delayCheckBox; + private javax.swing.JDesktopPane desktopPane; + private javax.swing.JCheckBox interactiveCheckBox; + private javax.swing.JPanel panel; + private javax.swing.JCheckBox randomCheckBox; + private javax.swing.JScrollPane scrollPane; + private javax.swing.JSplitPane splitPane; + // End of variables declaration//GEN-END:variables + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/jcanvas3d/JInternalWorld.java b/src/main/java/org/jdesktop/j3d/examples/jcanvas3d/JInternalWorld.java new file mode 100644 index 0000000..e702bc2 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/jcanvas3d/JInternalWorld.java @@ -0,0 +1,232 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.jcanvas3d; + +import java.awt.BorderLayout; +import java.awt.Component; +import java.awt.Dimension; +import java.awt.Font; + +import javax.swing.JInternalFrame; + +import org.jogamp.java3d.Alpha; +import org.jogamp.java3d.AmbientLight; +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.DirectionalLight; +import org.jogamp.java3d.Font3D; +import org.jogamp.java3d.FontExtrusion; +import org.jogamp.java3d.GraphicsConfigTemplate3D; +import org.jogamp.java3d.Material; +import org.jogamp.java3d.RotationInterpolator; +import org.jogamp.java3d.Shape3D; +import org.jogamp.java3d.Text3D; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.exp.swing.JCanvas3D; +import org.jogamp.java3d.utils.behaviors.mouse.MouseRotate; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Point3f; +import org.jogamp.vecmath.Vector3d; +import org.jogamp.vecmath.Vector3f; + + +/** + * This is a JInternalFrame holding an universe, which can be configured to + * be interactive -that is, where user can interact with object- or automatic + * -where the object spins only-. When in automatic mode, spinning speed is + * changed so that they look less the same. Changing the spinning start angle + * helps unsynchronizing the rotations too. + * + * @author pepe + */ +public class JInternalWorld extends JInternalFrame { + /** DOCUMENT ME! */ + private Component comp; + + /** + * Creates a new JInternalWorld object. + * + * @param isInteractive tells the world to be constructed as interactive + * @param isDelayed tells the rotator to start at a random alpha. + */ + public JInternalWorld(boolean isInteractive, boolean isDelayed, boolean isRandom) { + super(); + setSize(256, 256); + setClosable(true); + + JCanvas3D canvas = new JCanvas3D(new GraphicsConfigTemplate3D()); + + if (true == isDelayed) { + canvas.setResizeMode(canvas.RESIZE_DELAYED); + } + + comp = canvas; + + Dimension dim = new Dimension(256, 256); + comp.setPreferredSize(dim); + comp.setSize(dim); + getContentPane().setLayout(new BorderLayout()); + getContentPane().add(comp, BorderLayout.CENTER); + pack(); + + // Create a simple scene and attach it to the virtual universe + BranchGroup scene = createSceneGraph(isInteractive, isRandom); + SimpleUniverse universe = new SimpleUniverse(canvas.getOffscreenCanvas3D()); //TODO: this is awful and must not be done like that in final version + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + universe.getViewingPlatform().setNominalViewingTransform(); + universe.getViewer().getView().setMinimumFrameCycleTime(30); + universe.addBranchGraph(scene); + } + + /** + * Creates the world. Only exists to cleanup the source a bit + * + * @param isInteractive tells the world to be constructed as interactive + * @param isDelayed tells the rotator to start at a random alpha. + * + * @return a global branchgroup containing the world, as desired. + */ + private BranchGroup createSceneGraph(boolean isInteractive, boolean isRandom) { + // Create the root of the branch graph + BranchGroup objRoot = new BranchGroup(); + + // Create the TransformGroup node and initialize it to the + // identity. Enable the TRANSFORM_WRITE capability so that + // our behavior code can modify it at run time. Add it to + // the root of the subgraph. + TransformGroup objTrans = new TransformGroup(); + Transform3D t3dTrans = new Transform3D(); + t3dTrans.setTranslation(new Vector3d(0, 0, -1)); + objTrans.setTransform(t3dTrans); + + TransformGroup objRot = new TransformGroup(); + objRot.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + objRoot.addChild(objTrans); + objTrans.addChild(objRot); + + // Create a simple Shape3D node; add it to the scene graph. + // issue 383: changed the cube to a text, so that any graphical problem related to Yup can be seen. + Font3D f3d = new Font3D(new Font("dialog", Font.PLAIN, 1), + new FontExtrusion()); + Text3D text = new Text3D(f3d, "JCanvas3D", + new Point3f( -2.3f, -0.5f, 0.f)); + + Shape3D sh = new Shape3D(); + Appearance app = new Appearance(); + Material mm = new Material(); + mm.setLightingEnable(true); + app.setMaterial(mm); + sh.setGeometry(text); + sh.setAppearance(app); + + objRot.addChild( sh ); + + BoundingSphere bounds = new BoundingSphere(new Point3d(0.0, 0.0, 0.0), + 100.0); + + // Set up the ambient light + Color3f ambientColor = new Color3f(0.3f, 0.3f, 0.3f); + AmbientLight ambientLightNode = new AmbientLight(ambientColor); + ambientLightNode.setInfluencingBounds(bounds); + objRoot.addChild(ambientLightNode); + + // Set up the directional lights + Color3f light1Color = new Color3f(1.0f, 1.0f, 0.9f); + Vector3f light1Direction = new Vector3f(1.0f, 1.0f, 1.0f); + Color3f light2Color = new Color3f(1.0f, 1.0f, 0.9f); + Vector3f light2Direction = new Vector3f(-1.0f, -1.0f, -1.0f); + + DirectionalLight light1 + = new DirectionalLight(light1Color, light1Direction); + light1.setInfluencingBounds(bounds); + objRoot.addChild(light1); + + DirectionalLight light2 + = new DirectionalLight(light2Color, light2Direction); + light2.setInfluencingBounds(bounds); + objRoot.addChild(light2); + + + if (true == isInteractive) { + MouseRotate mr = new MouseRotate(comp, objRot); + mr.setSchedulingBounds(bounds); + mr.setSchedulingInterval(1); + objRoot.addChild(mr); + } else { + // Create a new Behavior object that will perform the + // desired operation on the specified transform and add + // it into the scene graph. + Transform3D yAxis = new Transform3D(); + + // rotation speed is randomized a bit so that it does not go at the same speed on every canvases, + // which will make it more natural and express the differences between every present universes + Alpha rotationAlpha = null; + + if (true == isRandom) { + int duration = Math.max(2000, (int) (Math.random() * 8000.)); + rotationAlpha = new Alpha(-1, + (int) ((double) duration * Math.random()), 0, duration, + 0, 0); + } else { + rotationAlpha = new Alpha(-1, 4000); + } + + RotationInterpolator rotator = new RotationInterpolator(rotationAlpha, + objRot, yAxis, 0.0f, (float) Math.PI * 2.0f); + + rotator.setSchedulingBounds(bounds); + objRoot.addChild(rotator); + } + + return objRoot; + } + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/jcanvas3d/JInternalWorldGL2ES2.java b/src/main/java/org/jdesktop/j3d/examples/jcanvas3d/JInternalWorldGL2ES2.java new file mode 100644 index 0000000..d38dc6e --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/jcanvas3d/JInternalWorldGL2ES2.java @@ -0,0 +1,211 @@ +/* + * Copyright (c) 2016 JogAmp Community. All rights reserved. + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * This code is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 only, as + * published by the Free Software Foundation. Sun designates this + * particular file as subject to the "Classpath" exception as provided + * by Sun in the LICENSE file that accompanied this code. + * + * This code is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + * version 2 for more details (a copy is included in the LICENSE file that + * accompanied this code). + * + * You should have received a copy of the GNU General Public License version + * 2 along with this work; if not, write to the Free Software Foundation, + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. + * + */ + +package org.jdesktop.j3d.examples.jcanvas3d; + +import java.awt.BorderLayout; +import java.awt.Component; +import java.awt.Dimension; +import java.awt.Font; + +import javax.swing.JInternalFrame; + +import org.jdesktop.j3d.examples.gl2es2pipeline.SimpleShaderAppearance; +import org.jogamp.java3d.Alpha; +import org.jogamp.java3d.AmbientLight; +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.DirectionalLight; +import org.jogamp.java3d.Font3D; +import org.jogamp.java3d.FontExtrusion; +import org.jogamp.java3d.GraphicsConfigTemplate3D; +import org.jogamp.java3d.Material; +import org.jogamp.java3d.RotationInterpolator; +import org.jogamp.java3d.Shape3D; +import org.jogamp.java3d.Text3D; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.exp.swing.JCanvas3D; +import org.jogamp.java3d.utils.behaviors.mouse.MouseRotate; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Point3f; +import org.jogamp.vecmath.Vector3d; +import org.jogamp.vecmath.Vector3f; + + +/** + * This is a JInternalFrame holding an universe, which can be configured to + * be interactive -that is, where user can interact with object- or automatic + * -where the object spins only-. When in automatic mode, spinning speed is + * changed so that they look less the same. Changing the spinning start angle + * helps unsynchronizing the rotations too. + * + * @author pepe + */ +public class JInternalWorldGL2ES2 extends JInternalFrame { + /** DOCUMENT ME! */ + private Component comp; + + /** + * Creates a new JInternalWorld object. + * + * @param isInteractive tells the world to be constructed as interactive + * @param isDelayed tells the rotator to start at a random alpha. + */ + public JInternalWorldGL2ES2(boolean isInteractive, boolean isDelayed, boolean isRandom) { + super(); + setSize(256, 256); + setClosable(true); + + JCanvas3D canvas = new JCanvas3D(new GraphicsConfigTemplate3D()); + + if (true == isDelayed) { + canvas.setResizeMode(canvas.RESIZE_DELAYED); + } + + comp = canvas; + + Dimension dim = new Dimension(256, 256); + comp.setPreferredSize(dim); + comp.setSize(dim); + getContentPane().setLayout(new BorderLayout()); + getContentPane().add(comp, BorderLayout.CENTER); + pack(); + + // Create a simple scene and attach it to the virtual universe + BranchGroup scene = createSceneGraph(isInteractive, isRandom); + SimpleUniverse universe = new SimpleUniverse(canvas.getOffscreenCanvas3D()); //TODO: this is awful and must not be done like that in final version + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + universe.getViewingPlatform().setNominalViewingTransform(); + universe.getViewer().getView().setMinimumFrameCycleTime(30); + universe.addBranchGraph(scene); + } + + /** + * Creates the world. Only exists to cleanup the source a bit + * + * @param isInteractive tells the world to be constructed as interactive + * @param isDelayed tells the rotator to start at a random alpha. + * + * @return a global branchgroup containing the world, as desired. + */ + private BranchGroup createSceneGraph(boolean isInteractive, boolean isRandom) { + // Create the root of the branch graph + BranchGroup objRoot = new BranchGroup(); + + // Create the TransformGroup node and initialize it to the + // identity. Enable the TRANSFORM_WRITE capability so that + // our behavior code can modify it at run time. Add it to + // the root of the subgraph. + TransformGroup objTrans = new TransformGroup(); + Transform3D t3dTrans = new Transform3D(); + t3dTrans.setTranslation(new Vector3d(0, 0, -1)); + objTrans.setTransform(t3dTrans); + + TransformGroup objRot = new TransformGroup(); + objRot.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + objRoot.addChild(objTrans); + objTrans.addChild(objRot); + + // Create a simple Shape3D node; add it to the scene graph. + // issue 383: changed the cube to a text, so that any graphical problem related to Yup can be seen. + Font3D f3d = new Font3D(new Font("dialog", Font.PLAIN, 1), + new FontExtrusion()); + Text3D text = new Text3D(f3d, "JCanvas3D", + new Point3f( -2.3f, -0.5f, 0.f)); + + Shape3D sh = new Shape3D(); + Appearance app = new SimpleShaderAppearance(false,false); + Material mm = new Material(); + mm.setLightingEnable(true); + app.setMaterial(mm); + sh.setGeometry(text); + sh.setAppearance(app); + + objRot.addChild( sh ); + + BoundingSphere bounds = new BoundingSphere(new Point3d(0.0, 0.0, 0.0), + 100.0); + + // Set up the ambient light + Color3f ambientColor = new Color3f(0.3f, 0.3f, 0.3f); + AmbientLight ambientLightNode = new AmbientLight(ambientColor); + ambientLightNode.setInfluencingBounds(bounds); + objRoot.addChild(ambientLightNode); + + // Set up the directional lights + Color3f light1Color = new Color3f(1.0f, 1.0f, 0.9f); + Vector3f light1Direction = new Vector3f(1.0f, 1.0f, 1.0f); + Color3f light2Color = new Color3f(1.0f, 1.0f, 0.9f); + Vector3f light2Direction = new Vector3f(-1.0f, -1.0f, -1.0f); + + DirectionalLight light1 + = new DirectionalLight(light1Color, light1Direction); + light1.setInfluencingBounds(bounds); + objRoot.addChild(light1); + + DirectionalLight light2 + = new DirectionalLight(light2Color, light2Direction); + light2.setInfluencingBounds(bounds); + objRoot.addChild(light2); + + + if (true == isInteractive) { + MouseRotate mr = new MouseRotate(comp, objRot); + mr.setSchedulingBounds(bounds); + mr.setSchedulingInterval(1); + objRoot.addChild(mr); + } else { + // Create a new Behavior object that will perform the + // desired operation on the specified transform and add + // it into the scene graph. + Transform3D yAxis = new Transform3D(); + + // rotation speed is randomized a bit so that it does not go at the same speed on every canvases, + // which will make it more natural and express the differences between every present universes + Alpha rotationAlpha = null; + + if (true == isRandom) { + int duration = Math.max(2000, (int) (Math.random() * 8000.)); + rotationAlpha = new Alpha(-1, + (int) ((double) duration * Math.random()), 0, duration, + 0, 0); + } else { + rotationAlpha = new Alpha(-1, 4000); + } + + RotationInterpolator rotator = new RotationInterpolator(rotationAlpha, + objRot, yAxis, 0.0f, (float) Math.PI * 2.0f); + + rotator.setSchedulingBounds(bounds); + objRoot.addChild(rotator); + } + + return objRoot; + } + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/lightwave/README.txt b/src/main/java/org/jdesktop/j3d/examples/lightwave/README.txt new file mode 100644 index 0000000..6ae5ce6 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/lightwave/README.txt @@ -0,0 +1,321 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + + Release Notes for the Lightwave 3D Java3D Loader + ------------------------------------------------ + Updated May 13, 1998 + + + +These release notes are intended to document the known working and +non-working features of the loader. This is important because the loader +implements an important subset of Lightwave functionality, but it definitely +skips many major features of Lightwave files. Please read these notes +to make sure that the features you need are actually implemented. Or +if you see differences between Lightwave display of your file and +the Java3D version of that file, take a look at these notes to see +what might not be working properly. + + +Testing the Loader +------------------ +The application in this directory (Viewer) is intended to be a very +basic test application for loading/viewing Lightwave 3D models. To +use the program, type: + java Viewer <filename> +where <filename> is the name of a valid Lightwave 3D scene file that is +reachable from the current directory. There is a very basic test file +included in this directory called ballcone.lws. To load/view that file, +type: + java Viewer ballcone.lws +Note that Lightwave scene files (*.lws) embed the pathnames to object +files (*.lwo) within them, and that object files have pathnames +to image files (for textures) embedded in them. Whatever those +pathnames are in those files must be valid for the directory in which +you are running the application that loads the scene file. For example, +if I was loading in a scene file that referred to an object file +called "data/object.lwo", then the file "object.lwo" should be located in +a subdirectory of this current directory called "data". + + +Summary of Loader +----------------- +The Lw3d loader was intended to implement a major subset of the features in +Lightwave 3D that would be used for realtime 3D animations. That is, any +features (such as Bones and other high-end rendering +options) which would require significant rendering time were simply +not doable. These more advanced features are intended to be rendered +off-line, saving each frame separately and later compositing them +together into an animation. But Java3D is a realtime 3D rendering +system, so these type of animations just do not map into a Java3D viewer +very well. + +Another category of non-implemented items are those that we simply have not +yet gotten to. There are a few known features of Lightwave files that +would work well through Java3D but just haven't been implemented in the +loader yet. + +Although there are a lot of features that are not yet implemented, +the basics of Lightwave 3D functionality (scene creation, animating +objects/lights/cameras, different surface properties) all work pretty +much as expected. So try it out and let us know non-documented items +that didn't work properly. + + +Details of Non-Implemented Features +----------------------------------- +This list is probably not comprehensive, but hopefully points out most of +the features or areas where the implementation is incomplete (or not +there at all). + + +Limitations of Scene Files (*.lws) +---------------------------------- +1) Bones/Skeleton +Bones functionality is not implemented at all. Unfortunately, this +great feature of Lightwave 3D is not currently implementable in the +loader because the processing time that it would take to compute +frames based on Bones data would be far more than a real-time rendering +system can afford. + +The loader may, at some future point, provide a mechanism to read +in frames of geometry that were saved from Lightwave Bones descriptions. +That is, there are plug-ins available for Lightwave 3D that allow you +to save out files with Bones information as a series of files with +pre-calculated geometry for each frame; eventually we would like the +Lightwave 3D loader to support those files. + +Workaround: None; the best and only workaround is to find a different +method of animating your objects. + + +2) Spline paths +Spline paths will be interpreted as linear piecewise paths instead, +traveling between each control point specified for the spline. + +Workaround: Specify linear paths. If your path looks too hard-jointed +through the loader, specify more keyframes for the path to smooth it out. + + +3) Object Scaling +Scaling objects in the scene (versus the object files) is currently +ignored. + +Workaround: scale the objects in their individual object files. + + +4) Shadows +Shadows options are ignored in the loader. + +Workaround: None. + + +5) Envelopes +Most envelopes are ignored. There are a couple of exceptions to this, +such as light intensity envelopes, but even those features have not been +completely implemented and tested. + +Workaround: None. + + +6) Camera effects +All advanced-rendering camera effects are ignored in the loader. This +includes the following items in Lightwave 3D files: + - Lens Flare + - F-stop + - Focal Distance + - Blur Length + - Dissolves + - Glow + - Zoom + - Intensity Falloff + - Antialiasing + +Workaround: None. + + +7) Inverse Kinematics +IK options such as Goal Objects and Anchors are ignored. + +Workaround: Animate objects directly instead of indirectly via IK. + + +8) Morphs +All morph options are ignored. + +Workaround: None. + + +9) Display properties +Lightwave allows you to specify surface properties for different rendering +modes (e.g., wireframe color). All of these parameters are ignored and +the full properties of any item are used at all times. + +Workaround: None. + + +10) Various Surface Properties +Various minor surface properties are currently ignored, including: + - Polygon size + - Dissolves + - Clip map + - Unaffected by fog + - Edge parameters + +Workaround: None. + + +11) Lights +The following items are currently ignored for Light objects: + - Target objects + - Flare parameters + - Shadow options + +Workaround: None for flares or shadows. For targeting problems, animate the +light directly (versus indirectly through using Target). + + +12) Camera Targeting +The Target option for Camera objects is currently ignored by the loader. + +Workaround: Animate the camera directly (versus indirectly through using +Target). + + +13) Effects +Most effects (from the Effects dialog box in the layout program) are +ignored, save for fog (which should accept all parameters) and +backdrop colors (solid backdrops only - gradient backdrops are +ignored). + +Workaround: None. + + +14) Render Options +Most options from the Render dialog box are ignored - most of these pertain +to saving the animation in any case (something that doesn't happen through +the Loader). + +Workaround: None. + + + +Limitations of Object Files (*.lwo) +----------------------------------- +1) MetaNURBS +Geometry stored in MetaNURBS format will be ignored by the loader. + +Workaround: pre-tessellate your MetaNURBS surfaces and save your +geometry (object) files in that format. + + +2) Layered Object Files +There is currently no support for the "Layered Object File Format" +of Lightwave 3D. + +Workaround: None. + + +3) Reflectivity +There is no way to reproduce the reflective properties of surfaces +through Java3D, so any reflectivity settings in Lightwave object files +will be ignored. + +Workaround: None. + + +4) Refraction +Refractive properties of surfaces are ignored. + +Workaround: None. + + +5) Edge Transparency +Edge transparency properties are ignored. + +Workaround. None. + + +6) Texture types +Texture mapping is currently somewhat limited in the loader. The following +types of texture mapping effects should work: + - Diffuse (the texture modifies the Diffuse aspects of the surface) + - Color (the texture modifies the Color properties of the surface). +Textures that attempt to modify other parameters of the surface will +be ignored. + +Also, the following texture types should work: + - Planar Image Map + - Spherical Image Map + - Cylindrical Image Map +Other kinds of mappings will not work (including Marble, Grid, Dots, etc.) + +Some Texture parameters will not work. The following should work correctly: + - size + - center +Advanced texture parameters such as falloff and velocity will be ignored. + +Summary: There are so many texture mapping parameters in Lightwave 3D that +it's difficult to produce a list of all of the items that won't work +properly. In a nutshell, basic decal-type (color modifying) or brightness +(diffuse modifying) textures that are mapped as planes, spheres, or +cylinders should work correctly. Anything else will probably not work. + +Workaround: Use the basics. + + +7) Plug-ins +There is currently no support for any plug-in capabilities. For example, +if there are plug-in shaders specified for your file, those shaders will be +ignored. + +Workaround: None. + + +8) Image Sequences +There is no support for image sequences - textures must be static files. + +Workaround: None. + + diff --git a/src/main/java/org/jdesktop/j3d/examples/lightwave/Viewer.java b/src/main/java/org/jdesktop/j3d/examples/lightwave/Viewer.java new file mode 100644 index 0000000..063c7cc --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/lightwave/Viewer.java @@ -0,0 +1,206 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.lightwave; + +import java.applet.Applet; +import java.awt.BorderLayout; +import java.awt.GraphicsConfiguration; + +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.View; +import org.jogamp.java3d.loaders.Loader; +import org.jogamp.java3d.loaders.Scene; +import org.jogamp.java3d.loaders.lw3d.Lw3dLoader; +import org.jogamp.java3d.utils.applet.MainFrame; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.vecmath.Matrix4d; + + +/** + * This class loads in a Lightwave3D file and displays it in an applet + * window. The application is fairly basic; a more complete version + * of a Lightwave 3D loader might incorporate features such as + * settable clip plane distances and animated views (these are both + * possible with the current Lightwave 3D loader, they just need to + * be implemented in the application). + */ +public class Viewer extends Applet { + + private java.net.URL filename; + private SimpleUniverse u; + + public Viewer(java.net.URL url) { + filename = url; + } + + public Viewer() {} + + public void init() {System.setProperty("sun.awt.noerasebackground", "true"); + if (filename == null) { + // the path to the file for an applet + try { + java.net.URL path = getCodeBase(); + filename = new java.net.URL(path.toString() + + "./ballcone.lws"); + } + catch (java.net.MalformedURLException ex) { + System.err.println(ex.getMessage()); + ex.printStackTrace(); + System.exit(1); + } + } + + // Construct the Lw3d loader and load the file + Loader lw3dLoader = new Lw3dLoader(Loader.LOAD_ALL); + Scene loaderScene = null; + try { + loaderScene = lw3dLoader.load(filename); + } + catch (Exception e) { + e.printStackTrace(); + System.exit(1); + } + + // Construct the applet canvas + setLayout(new BorderLayout()); + GraphicsConfiguration config = + SimpleUniverse.getPreferredConfiguration(); + + Canvas3D c = new Canvas3D(config); + add("Center", c); + + // Create a basic universe setup and the root of our scene + u = new SimpleUniverse(c); + BranchGroup sceneRoot = new BranchGroup(); + + // Change the back clip distance; the default is small for + // some lw3d worlds + View theView = u.getViewer().getView(); + theView.setBackClipDistance(50000f); + + // Now add the scene graph defined in the lw3d file + if (loaderScene.getSceneGroup() != null) { + // Instead of using the default view location (which may be + // completely bogus for the particular file you're loading), + // let's use the initial view from the file. We can get + // this by getting the view groups from the scene (there's + // only one for Lightwave 3D), then using the inverse of the + // transform on that view as the transform for the entire scene. + + // First, get the view groups (shouldn't be null unless there + // was something wrong in the load + TransformGroup viewGroups[] = loaderScene.getViewGroups(); + + // Get the Transform3D from the view and invert it + Transform3D t = new Transform3D(); + viewGroups[0].getTransform(t); + Matrix4d m = new Matrix4d(); + t.get(m); + m.invert(); + t.set(m); + + // Now we've got the transform we want. Create an + // appropriate TransformGroup and parent the scene to it. + // Then insert the new group into the main BranchGroup. + TransformGroup sceneTransform = new TransformGroup(t); + sceneTransform.addChild(loaderScene.getSceneGroup()); + sceneRoot.addChild(sceneTransform); + } + + // Make the scene graph live by inserting the root into the universe + u.addBranchGraph(sceneRoot); + } + + + public void destroy() { + u.cleanup(); + } + + private static void usage() { + System.out.println("Usage: java Viewer <.lws>") ; + System.exit(0) ; + } + + /** + * The main method of the application takes one argument in the + * args array; the filname that you want to load. Note that the + * file must be reachable from the directory in which you're running + * this application. + */ + public static void main(String args[]) {System.setProperty("sun.awt.noerasebackground", "true"); + java.net.URL url = null; + java.net.URL pathUrl = null; + if (args.length > 0) { + try { + if ((args[0].indexOf("file:") == 0) || + (args[0].indexOf("http") == 0)) { + url = new java.net.URL(args[0]); + } + else if (args[0].charAt(0) != '/') { + url = new java.net.URL("file:./" + args[0]); + } + else { + url = new java.net.URL("file:" + args[0]); + } + } + catch (java.net.MalformedURLException ex) { + System.err.println(ex.getMessage()); + ex.printStackTrace(); + System.exit(1); + } + } + else { + usage(); + } + new MainFrame(new Viewer(url), 500, 500); + } +} + + + + diff --git a/src/main/java/org/jdesktop/j3d/examples/lod/LOD.form b/src/main/java/org/jdesktop/j3d/examples/lod/LOD.form new file mode 100644 index 0000000..7bba785 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/lod/LOD.form @@ -0,0 +1,36 @@ +<?xml version="1.0" encoding="UTF-8" ?> + +<Form version="1.0" type="org.netbeans.modules.form.forminfo.JFrameFormInfo"> + <Properties> + <Property name="defaultCloseOperation" type="int" value="3"/> + <Property name="title" type="java.lang.String" value="LOD"/> + </Properties> + <SyntheticProperties> + <SyntheticProperty name="formSizePolicy" type="int" value="1"/> + </SyntheticProperties> + <AuxValues> + <AuxValue name="FormSettings_generateMnemonicsCode" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_listenerGenerationStyle" type="java.lang.Integer" value="0"/> + <AuxValue name="FormSettings_variablesLocal" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_variablesModifier" type="java.lang.Integer" value="2"/> + <AuxValue name="designerSize" type="java.awt.Dimension" value="-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,1,44,0,0,1,-112"/> + </AuxValues> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + <SubComponents> + <Container class="javax.swing.JPanel" name="drawingPanel"> + <Properties> + <Property name="preferredSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor"> + <Dimension value="[700, 700]"/> + </Property> + </Properties> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout" value="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription"> + <BorderConstraints direction="Center"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + </Container> + </SubComponents> +</Form> diff --git a/src/main/java/org/jdesktop/j3d/examples/lod/LOD.java b/src/main/java/org/jdesktop/j3d/examples/lod/LOD.java new file mode 100644 index 0000000..67aac84 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/lod/LOD.java @@ -0,0 +1,235 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.lod; + +import java.awt.GraphicsConfiguration; + +import org.jogamp.java3d.AmbientLight; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.DirectionalLight; +import org.jogamp.java3d.DistanceLOD; +import org.jogamp.java3d.Switch; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.utils.behaviors.vp.OrbitBehavior; +import org.jogamp.java3d.utils.geometry.Sphere; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.java3d.utils.universe.ViewingPlatform; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Vector3f; + +/** + * Simple Java 3D example program to display a spinning cube. + */ +public class LOD extends javax.swing.JFrame { + + private SimpleUniverse univ = null; + private BranchGroup scene = null; + + public BranchGroup createSceneGraph() { + // Create the root of the branch graph + BranchGroup objRoot = new BranchGroup(); + + createLights(objRoot); + + // Create the transform group node and initialize it to the + // identity. Enable the TRANSFORM_WRITE capability so that + // our behavior code can modify it at runtime. Add it to the + // root of the subgraph. + TransformGroup objTrans = new TransformGroup(); + objTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + objTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_READ); + objRoot.addChild(objTrans); + + // Create a switch to hold the different levels of detail + Switch sw = new Switch(0); + sw.setCapability(Switch.ALLOW_SWITCH_READ); + sw.setCapability(Switch.ALLOW_SWITCH_WRITE); + + + // Create several levels for the switch, with less detailed + // spheres for the ones which will be used when the sphere is + // further away + sw.addChild(new Sphere(0.4f, Sphere.GENERATE_NORMALS, 40)); + sw.addChild(new Sphere(0.4f, Sphere.GENERATE_NORMALS, 20)); + sw.addChild(new Sphere(0.4f, Sphere.GENERATE_NORMALS, 10)); + sw.addChild(new Sphere(0.4f, Sphere.GENERATE_NORMALS, 3)); + + // Add the switch to the main group + objTrans.addChild(sw); + + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + + // set up the DistanceLOD behavior + float[] distances = new float[3]; + distances[0] = 5.0f; + distances[1] = 10.0f; + distances[2] = 25.0f; + DistanceLOD lod = new DistanceLOD(distances); + lod.addSwitch(sw); + lod.setSchedulingBounds(bounds); + objTrans.addChild(lod); + + // Have Java 3D perform optimizations on this scene graph. + objRoot.compile(); + + return objRoot; + } + + private void createLights(BranchGroup graphRoot) { + + // Create a bounds for the light source influence + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + + // Set up the global, ambient light + Color3f alColor = new Color3f(0.2f, 0.2f, 0.2f); + AmbientLight aLgt = new AmbientLight(alColor); + aLgt.setInfluencingBounds(bounds); + graphRoot.addChild(aLgt); + + // Set up the directional (infinite) light source + Color3f lColor1 = new Color3f(0.9f, 0.9f, 0.9f); + Vector3f lDir1 = new Vector3f(1.0f, 1.0f, -1.0f); + DirectionalLight lgt1 = new DirectionalLight(lColor1, lDir1); + lgt1.setInfluencingBounds(bounds); + graphRoot.addChild(lgt1); + } + + private Canvas3D createUniverse() { + // Get the preferred graphics configuration for the default screen + GraphicsConfiguration config = + SimpleUniverse.getPreferredConfiguration(); + + // Create a Canvas3D using the preferred configuration + Canvas3D c = new Canvas3D(config); + + // Create simple universe with view branch + univ = new SimpleUniverse(c); + + // only add zoom mouse behavior to viewingPlatform + ViewingPlatform viewingPlatform = univ.getViewingPlatform(); + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + viewingPlatform.setNominalViewingTransform(); + + // add orbit behavior to the ViewingPlatform, but disable rotate + // and translate + OrbitBehavior orbit = new OrbitBehavior(c, + OrbitBehavior.REVERSE_ZOOM | + OrbitBehavior.DISABLE_ROTATE | + OrbitBehavior.DISABLE_TRANSLATE); + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0, 0.0, 0.0), 100.0); + orbit.setSchedulingBounds(bounds); + viewingPlatform.setViewPlatformBehavior(orbit); + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + univ.getViewingPlatform().setNominalViewingTransform(); + + // Ensure at least 5 msec per frame (i.e., < 200Hz) + univ.getViewer().getView().setMinimumFrameCycleTime(5); + + return c; + } + + /** + * Creates new form LOD + */ + public LOD() { + // Initialize the GUI components + initComponents(); + + // Create Canvas3D and SimpleUniverse; add canvas to drawing panel + Canvas3D c = createUniverse(); + drawingPanel.add(c, java.awt.BorderLayout.CENTER); + + // Create the content branch and add it to the universe + scene = createSceneGraph(); + univ.addBranchGraph(scene); + } + + // ---------------------------------------------------------------- + + /** This method is called from within the constructor to + * initialize the form. + * WARNING: Do NOT modify this code. The content of this method is + * always regenerated by the Form Editor. + */ + // <editor-fold defaultstate="collapsed" desc=" Generated Code ">//GEN-BEGIN:initComponents + private void initComponents() { + drawingPanel = new javax.swing.JPanel(); + + setDefaultCloseOperation(javax.swing.WindowConstants.EXIT_ON_CLOSE); + setTitle("LOD"); + drawingPanel.setLayout(new java.awt.BorderLayout()); + + drawingPanel.setPreferredSize(new java.awt.Dimension(700, 700)); + getContentPane().add(drawingPanel, java.awt.BorderLayout.CENTER); + + pack(); + }// </editor-fold>//GEN-END:initComponents + + /** + * @param args the command line arguments + */ + public static void main(String args[]) {System.setProperty("sun.awt.noerasebackground", "true"); + java.awt.EventQueue.invokeLater(new Runnable() { + public void run() { + new LOD().setVisible(true); + } + }); + } + + // Variables declaration - do not modify//GEN-BEGIN:variables + private javax.swing.JPanel drawingPanel; + // End of variables declaration//GEN-END:variables + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/model_clip/ModelClipTest.java b/src/main/java/org/jdesktop/j3d/examples/model_clip/ModelClipTest.java new file mode 100644 index 0000000..618b7f2 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/model_clip/ModelClipTest.java @@ -0,0 +1,190 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.model_clip; + +import java.applet.Applet; +import java.awt.BorderLayout; +import java.awt.GraphicsConfiguration; + +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.DirectionalLight; +import org.jogamp.java3d.Material; +import org.jogamp.java3d.ModelClip; +import org.jogamp.java3d.PolygonAttributes; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.utils.applet.MainFrame; +import org.jogamp.java3d.utils.behaviors.mouse.MouseRotate; +import org.jogamp.java3d.utils.behaviors.mouse.MouseZoom; +import org.jogamp.java3d.utils.geometry.Cylinder; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Vector3f; +import org.jogamp.vecmath.Vector4d; + +/** + * ModelClipTest draws a cylinder and creates two clip planes + * to see the interior of the cylinder. + */ +public class ModelClipTest extends Applet { + + private SimpleUniverse u = null; + + public BranchGroup createSceneGraph() + { + // Create the root of the branch graph + BranchGroup objRoot = new BranchGroup(); + + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + + // Create a Transformgroup to scale all objects so they + // appear in the scene. + TransformGroup objScale = new TransformGroup(); + Transform3D t3d = new Transform3D(); + t3d.setScale(0.4); + objScale.setTransform(t3d); + objRoot.addChild(objScale); + + // This Transformgroup is used by the mouse manipulators to + // move the CYlinder. + TransformGroup objTrans = new TransformGroup(); + objTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + objTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_READ); + objScale.addChild(objTrans); + + //Create Model Clip + ModelClip mc = new ModelClip(); + boolean enables[] = {false, false, false, false, false, false}; + Vector4d eqn1 = new Vector4d(0.0, 1.0, 0.0, 0.0); + Vector4d eqn2 = new Vector4d(1.0, 1.0, 0.0, 0.0); + mc.setEnables(enables); + mc.setPlane(1, eqn1); + mc.setPlane(2, eqn2); + mc.setEnable(1, true); + mc.setEnable(2, true); + mc.setInfluencingBounds(bounds); + objTrans.addChild(mc); + + //Create a cylinder + PolygonAttributes attr = new PolygonAttributes(); + attr.setCullFace(PolygonAttributes.CULL_NONE); + Appearance ap = new Appearance(); + Material mat = new Material(); + mat.setLightingEnable(true); + ap.setMaterial(mat); + ap.setPolygonAttributes(attr); + + Cylinder CylinderObj = new Cylinder(1.0f, 2.0f, ap); + objTrans.addChild(CylinderObj); + + // Create the rotate behavior node + MouseRotate behavior = new MouseRotate(objTrans); + objTrans.addChild(behavior); + behavior.setSchedulingBounds(bounds); + + // Create the zoom behavior node + MouseZoom behavior2 = new MouseZoom(objTrans); + objTrans.addChild(behavior2); + behavior2.setSchedulingBounds(bounds); + + //Shine it with two colored lights. + Color3f lColor1 = new Color3f(0.5f, 0.0f, 0.5f); + Color3f lColor2 = new Color3f(0.7f, 0.7f, 0.0f); + Vector3f lDir1 = new Vector3f(-1.0f, -1.0f, 1.0f); + Vector3f lDir2 = new Vector3f(0.0f, 0.0f, -1.0f); + DirectionalLight lgt1 = new DirectionalLight(lColor1, lDir1); + DirectionalLight lgt2 = new DirectionalLight(lColor2, lDir2); + lgt1.setInfluencingBounds(bounds); + lgt2.setInfluencingBounds(bounds); + objScale.addChild(lgt1); + objScale.addChild(lgt2); + + // Let Java 3D perform optimizations on this scene graph. + objRoot.compile(); + + return objRoot; + } + + public ModelClipTest (){ + } + + public void init() {System.setProperty("sun.awt.noerasebackground", "true"); + setLayout(new BorderLayout()); + GraphicsConfiguration config = + SimpleUniverse.getPreferredConfiguration(); + + Canvas3D c = new Canvas3D(config); + add("Center", c); + + // Create a simple scene and attach it to the virtual universe + BranchGroup scene = createSceneGraph(); + u = new SimpleUniverse(c); + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + u.getViewingPlatform().setNominalViewingTransform(); + + u.addBranchGraph(scene); + } + + public void destroy() { + u.cleanup(); + } + + + public static void main(String argv[]) + { + + BranchGroup group; + + new MainFrame(new ModelClipTest(), 500, 500); + } +} + diff --git a/src/main/java/org/jdesktop/j3d/examples/model_clip/ModelClipTest2.java b/src/main/java/org/jdesktop/j3d/examples/model_clip/ModelClipTest2.java new file mode 100644 index 0000000..ef5a407 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/model_clip/ModelClipTest2.java @@ -0,0 +1,213 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.model_clip; + +import java.applet.Applet; +import java.awt.BorderLayout; +import java.awt.GraphicsConfiguration; + +import org.jogamp.java3d.AmbientLight; +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.DirectionalLight; +import org.jogamp.java3d.Material; +import org.jogamp.java3d.ModelClip; +import org.jogamp.java3d.PolygonAttributes; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.utils.applet.MainFrame; +import org.jogamp.java3d.utils.behaviors.mouse.MouseRotate; +import org.jogamp.java3d.utils.behaviors.mouse.MouseZoom; +import org.jogamp.java3d.utils.geometry.Box; +import org.jogamp.java3d.utils.geometry.Cylinder; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.vecmath.AxisAngle4f; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Vector3f; +import org.jogamp.vecmath.Vector4d; + +/** + * ModelClipTest2 draws a cylinder and creates two clip planes + * to see the interior of the cylinder. It also has a behavior to + * move the clip planes. + */ +public class ModelClipTest2 extends Applet { + + private SimpleUniverse u; + + public BranchGroup createSceneGraph() + { + // Create the root of the branch graph + BranchGroup objRoot = new BranchGroup(); + + // Create a Transformgroup to scale all objects so they + // appear in the scene. + TransformGroup objScale = new TransformGroup(); + Transform3D t3d = new Transform3D(); + t3d.setScale(0.4); + objScale.setTransform(t3d); + objRoot.addChild(objScale); + + // Create lights + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + + //Shine it with two colored lights. + Color3f lColor0 = new Color3f(1.0f, 1.0f, 1.0f); + Color3f lColor1 = new Color3f(0.5f, 0.0f, 0.5f); + Color3f lColor2 = new Color3f(0.7f, 0.7f, 0.0f); + Vector3f lDir1 = new Vector3f(-1.0f, -1.0f, 1.0f); + Vector3f lDir2 = new Vector3f(0.0f, 0.0f, -1.0f); + + AmbientLight lgt0 = new AmbientLight(true, lColor2); + DirectionalLight lgt1 = new DirectionalLight(lColor1, lDir1); + DirectionalLight lgt2 = new DirectionalLight(lColor2, lDir2); + lgt0.setInfluencingBounds(bounds); + lgt1.setInfluencingBounds(bounds); + lgt2.setInfluencingBounds(bounds); + objScale.addChild(lgt0); + objScale.addChild(lgt1); + objScale.addChild(lgt2); + + // Create a Transformgroup for the geometry + TransformGroup objRot = new TransformGroup(); + Transform3D t3d1 = new Transform3D(); + AxisAngle4f rot1 = new AxisAngle4f(0.0f, 1.0f, 0.0f, 45.0f); + t3d1.setRotation(rot1); + objRot.setTransform(t3d1); + objScale.addChild(objRot); + + + //Create a cylinder + PolygonAttributes attr = new PolygonAttributes(); + attr.setCullFace(PolygonAttributes.CULL_NONE); + Appearance ap = new Appearance(); + Material mat = new Material(); + mat.setLightingEnable(true); + ap.setMaterial(mat); + ap.setPolygonAttributes(attr); + + Cylinder CylinderObj = new Cylinder(0.5f, 2.2f, ap); + objRot.addChild(CylinderObj); + + //Create a box + Box BoxObj = new Box(0.8f, 0.8f, 0.8f, ap); + objRot.addChild(BoxObj); + + + // This Transformgroup is used by the mouse manipulators to + // move the model clip planes. + TransformGroup objTrans = new TransformGroup(); + objTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + objTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_READ); + objRot.addChild(objTrans); + + // Create the rotate behavior node + MouseRotate behavior = new MouseRotate(objTrans); + objTrans.addChild(behavior); + behavior.setSchedulingBounds(bounds); + + // Create the zoom behavior node + MouseZoom behavior2 = new MouseZoom(objTrans); + objTrans.addChild(behavior2); + behavior2.setSchedulingBounds(bounds); + + //Create Model Clip + ModelClip mc = new ModelClip(); + boolean enables[] = {false, false, false, false, false, false}; + Vector4d eqn = new Vector4d(0.0, 1.0, 1.0, 0.0); + mc.setEnables(enables); + mc.setPlane(1, eqn); + mc.setEnable(1, true); + mc.setInfluencingBounds(bounds); + objTrans.addChild(mc); + + + // Let Java 3D perform optimizations on this scene graph. + objRoot.compile(); + + return objRoot; + } + + public ModelClipTest2 (){ + } + + public void init() {System.setProperty("sun.awt.noerasebackground", "true"); + setLayout(new BorderLayout()); + GraphicsConfiguration config = + SimpleUniverse.getPreferredConfiguration(); + + Canvas3D c = new Canvas3D(config); + add("Center", c); + + // Create a simple scene and attach it to the virtual universe + BranchGroup scene = createSceneGraph(); + u = new SimpleUniverse(c); + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + u.getViewingPlatform().setNominalViewingTransform(); + + u.addBranchGraph(scene); + } + + public void destroy() { + u.cleanup(); + } + + + + public static void main(String argv[]) + { + + BranchGroup group; + + new MainFrame(new ModelClipTest2(), 500, 500); + } +} + diff --git a/src/main/java/org/jdesktop/j3d/examples/morphing/ColorCube.java b/src/main/java/org/jdesktop/j3d/examples/morphing/ColorCube.java new file mode 100644 index 0000000..df36e9d --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/morphing/ColorCube.java @@ -0,0 +1,122 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.morphing; + +import org.jogamp.java3d.QuadArray; + +class ColorCube extends QuadArray { + private static final float[] verts = { + // front face + 1.0f, -1.0f, 1.0f, + 1.0f, 1.0f, 1.0f, + -1.0f, 1.0f, 1.0f, + -1.0f, -1.0f, 1.0f, + // back face + -1.0f, -1.0f, -1.0f, + -1.0f, 1.0f, -1.0f, + 1.0f, 1.0f, -1.0f, + 1.0f, -1.0f, -1.0f, + // right face + 1.0f, -1.0f, -1.0f, + 1.0f, 1.0f, -1.0f, + 1.0f, 1.0f, 1.0f, + 1.0f, -1.0f, 1.0f, + // left face + -1.0f, -1.0f, 1.0f, + -1.0f, 1.0f, 1.0f, + -1.0f, 1.0f, -1.0f, + -1.0f, -1.0f, -1.0f, + // top face + 1.0f, 1.0f, 1.0f, + 1.0f, 1.0f, -1.0f, + -1.0f, 1.0f, -1.0f, + -1.0f, 1.0f, 1.0f, + // bottom face + -1.0f, -1.0f, 1.0f, + -1.0f, -1.0f, -1.0f, + 1.0f, -1.0f, -1.0f, + 1.0f, -1.0f, 1.0f, + }; + + private static final float[] colors = { + // front face (red) + 1.0f, 0.0f, 0.0f, + 1.0f, 0.0f, 0.0f, + 1.0f, 0.0f, 0.0f, + 1.0f, 0.0f, 0.0f, + // back face (green) + 0.0f, 1.0f, 0.0f, + 0.0f, 1.0f, 0.0f, + 0.0f, 1.0f, 0.0f, + 0.0f, 1.0f, 0.0f, + // right face (blue) + 0.0f, 0.0f, 1.0f, + 0.0f, 0.0f, 1.0f, + 0.0f, 0.0f, 1.0f, + 0.0f, 0.0f, 1.0f, + // left face (yellow) + 1.0f, 1.0f, 0.0f, + 1.0f, 1.0f, 0.0f, + 1.0f, 1.0f, 0.0f, + 1.0f, 1.0f, 0.0f, + // top face (magenta) + 1.0f, 0.0f, 1.0f, + 1.0f, 0.0f, 1.0f, + 1.0f, 0.0f, 1.0f, + 1.0f, 0.0f, 1.0f, + // bottom face (cyan) + 0.0f, 1.0f, 1.0f, + 0.0f, 1.0f, 1.0f, + 0.0f, 1.0f, 1.0f, + 0.0f, 1.0f, 1.0f, + }; + + ColorCube() { + super(24, QuadArray.COORDINATES | QuadArray.COLOR_3); + + setCoordinates(0, verts); + setColors(0, colors); + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/morphing/ColorPyramidDown.java b/src/main/java/org/jdesktop/j3d/examples/morphing/ColorPyramidDown.java new file mode 100644 index 0000000..89d1a8b --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/morphing/ColorPyramidDown.java @@ -0,0 +1,122 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.morphing; + +import org.jogamp.java3d.QuadArray; + +class ColorPyramidDown extends QuadArray { + private static final float[] verts = { + // front face + 0.0f, -1.0f, 0.0f, + 1.0f, 1.0f, 1.0f, + -1.0f, 1.0f, 1.0f, + 0.0f, -1.0f, 0.0f, + // back face + 0.0f, -1.0f, 0.0f, + -1.0f, 1.0f, -1.0f, + 1.0f, 1.0f, -1.0f, + 0.0f, -1.0f, 0.0f, + // right face + 0.0f, -1.0f, 0.0f, + 1.0f, 1.0f, -1.0f, + 1.0f, 1.0f, 1.0f, + 0.0f, -1.0f, 0.0f, + // left face + 0.0f, -1.0f, 0.0f, + -1.0f, 1.0f, 1.0f, + -1.0f, 1.0f, -1.0f, + 0.0f, -1.0f, 0.0f, + // top face + 1.0f, 1.0f, 1.0f, + 1.0f, 1.0f, -1.0f, + -1.0f, 1.0f, -1.0f, + -1.0f, 1.0f, 1.0f, + // bottom face + 0.0f, -1.0f, 0.0f, + 0.0f, -1.0f, 0.0f, + 0.0f, -1.0f, 0.0f, + 0.0f, -1.0f, 0.0f, + }; + + private static final float[] colors = { + // front face (green) + 0.0f, 1.0f, 0.0f, + 0.0f, 1.0f, 0.0f, + 0.0f, 1.0f, 0.0f, + 0.0f, 1.0f, 0.0f, + // back face (red) + 1.0f, 0.0f, 0.0f, + 1.0f, 0.0f, 0.0f, + 1.0f, 0.0f, 0.0f, + 1.0f, 0.0f, 0.0f, + // right face (yellow) + 1.0f, 1.0f, 0.0f, + 1.0f, 1.0f, 0.0f, + 1.0f, 1.0f, 0.0f, + 1.0f, 1.0f, 0.0f, + // left face (magenta) + 1.0f, 0.0f, 1.0f, + 1.0f, 0.0f, 1.0f, + 1.0f, 0.0f, 1.0f, + 1.0f, 0.0f, 1.0f, + // top face (blue) + 0.0f, 0.0f, 1.0f, + 0.0f, 0.0f, 1.0f, + 0.0f, 0.0f, 1.0f, + 0.0f, 0.0f, 1.0f, + // bottom face (cyan) + 0.0f, 1.0f, 1.0f, + 0.0f, 1.0f, 1.0f, + 0.0f, 1.0f, 1.0f, + 0.0f, 1.0f, 1.0f, + }; + + ColorPyramidDown() { + super(24, QuadArray.COORDINATES | QuadArray.COLOR_3); + + setCoordinates(0, verts); + setColors(0, colors); + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/morphing/ColorPyramidUp.java b/src/main/java/org/jdesktop/j3d/examples/morphing/ColorPyramidUp.java new file mode 100644 index 0000000..b94e6f0 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/morphing/ColorPyramidUp.java @@ -0,0 +1,124 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.morphing; + +import org.jogamp.java3d.QuadArray; + +class ColorPyramidUp extends QuadArray { + private static final float[] verts = { + // front face + 1.0f, -1.0f, 1.0f, + 0.0f, 1.0f, 0.0f, + 0.0f, 1.0f, 0.0f, + -1.0f, -1.0f, 1.0f, + // back face + -1.0f, -1.0f, -1.0f, + 0.0f, 1.0f, 0.0f, + 0.0f, 1.0f, 0.0f, + 1.0f, -1.0f, -1.0f, + // right face + 1.0f, -1.0f, -1.0f, + 0.0f, 1.0f, 0.0f, + 0.0f, 1.0f, 0.0f, + 1.0f, -1.0f, 1.0f, + // left face + -1.0f, -1.0f, 1.0f, + 0.0f, 1.0f, 0.0f, + 0.0f, 1.0f, 0.0f, + -1.0f, -1.0f, -1.0f, + // top face + 0.0f, 1.0f, 0.0f, + 0.0f, 1.0f, 0.0f, + 0.0f, 1.0f, 0.0f, + 0.0f, 1.0f, 0.0f, + // bottom face + -1.0f, -1.0f, 1.0f, + -1.0f, -1.0f, -1.0f, + 1.0f, -1.0f, -1.0f, + 1.0f, -1.0f, 1.0f, + }; + + private static final float[] colors = { + + // front face (cyan) + 0.0f, 1.0f, 1.0f, + 0.0f, 1.0f, 1.0f, + 0.0f, 1.0f, 1.0f, + 0.0f, 1.0f, 1.0f, + // back face (magenta) + 1.0f, 0.0f, 1.0f, + 1.0f, 0.0f, 1.0f, + 1.0f, 0.0f, 1.0f, + 1.0f, 0.0f, 1.0f, + // right face (yellow) + 1.0f, 1.0f, 0.0f, + 1.0f, 1.0f, 0.0f, + 1.0f, 1.0f, 0.0f, + 1.0f, 1.0f, 0.0f, + // left face (blue) + 0.0f, 0.0f, 1.0f, + 0.0f, 0.0f, 1.0f, + 0.0f, 0.0f, 1.0f, + 0.0f, 0.0f, 1.0f, + // top face (green) + 0.0f, 1.0f, 0.0f, + 0.0f, 1.0f, 0.0f, + 0.0f, 1.0f, 0.0f, + 0.0f, 1.0f, 0.0f, + // bottom face (red) + 1.0f, 0.0f, 0.0f, + 1.0f, 0.0f, 0.0f, + 1.0f, 0.0f, 0.0f, + 1.0f, 0.0f, 0.0f, + + }; + + ColorPyramidUp() { + super(24, QuadArray.COORDINATES | QuadArray.COLOR_3); + + setCoordinates(0, verts); + setColors(0, colors); + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/morphing/Morphing.form b/src/main/java/org/jdesktop/j3d/examples/morphing/Morphing.form new file mode 100644 index 0000000..631f59a --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/morphing/Morphing.form @@ -0,0 +1,36 @@ +<?xml version="1.0" encoding="UTF-8" ?> + +<Form version="1.0" type="org.netbeans.modules.form.forminfo.JFrameFormInfo"> + <Properties> + <Property name="defaultCloseOperation" type="int" value="3"/> + <Property name="title" type="java.lang.String" value="Morphing"/> + </Properties> + <SyntheticProperties> + <SyntheticProperty name="formSizePolicy" type="int" value="1"/> + </SyntheticProperties> + <AuxValues> + <AuxValue name="FormSettings_generateMnemonicsCode" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_listenerGenerationStyle" type="java.lang.Integer" value="0"/> + <AuxValue name="FormSettings_variablesLocal" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_variablesModifier" type="java.lang.Integer" value="2"/> + <AuxValue name="designerSize" type="java.awt.Dimension" value="-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,1,44,0,0,1,-112"/> + </AuxValues> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + <SubComponents> + <Container class="javax.swing.JPanel" name="drawingPanel"> + <Properties> + <Property name="preferredSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor"> + <Dimension value="[700, 700]"/> + </Property> + </Properties> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout" value="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription"> + <BorderConstraints direction="Center"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + </Container> + </SubComponents> +</Form> diff --git a/src/main/java/org/jdesktop/j3d/examples/morphing/Morphing.java b/src/main/java/org/jdesktop/j3d/examples/morphing/Morphing.java new file mode 100644 index 0000000..4604f66 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/morphing/Morphing.java @@ -0,0 +1,304 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.morphing; + +import java.awt.GraphicsConfiguration; +import java.io.FileNotFoundException; + +import org.jdesktop.j3d.examples.Resources; +import org.jogamp.java3d.Alpha; +import org.jogamp.java3d.AmbientLight; +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.Background; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.DirectionalLight; +import org.jogamp.java3d.GeometryArray; +import org.jogamp.java3d.Material; +import org.jogamp.java3d.Morph; +import org.jogamp.java3d.Shape3D; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.loaders.IncorrectFormatException; +import org.jogamp.java3d.loaders.ParsingErrorException; +import org.jogamp.java3d.loaders.Scene; +import org.jogamp.java3d.loaders.objectfile.ObjectFile; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Vector3d; +import org.jogamp.vecmath.Vector3f; + +public class Morphing extends javax.swing.JFrame { + + private SimpleUniverse univ = null; + private BranchGroup scene = null; + private java.net.URL[] objFiles = null; + + private BranchGroup createSceneGraph() { + // Create the root of the branch graph + BranchGroup objRoot = new BranchGroup(); + + // Create a Transformgroup to scale all objects so they + // appear in the scene. + TransformGroup objScale = new TransformGroup(); + Transform3D t3d = new Transform3D(); + t3d.setScale(0.4); + objScale.setTransform(t3d); + objRoot.addChild(objScale); + + // Create a bounds for the background and lights + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + + // Set up the background + Color3f bgColor = new Color3f(0.05f, 0.05f, 0.2f); + Background bg = new Background(bgColor); + bg.setApplicationBounds(bounds); + objScale.addChild(bg); + + // Set up the global lights + Color3f lColor1 = new Color3f(0.7f, 0.7f, 0.7f); + Vector3f lDir1 = new Vector3f(-1.0f, -1.0f, -1.0f); + Color3f alColor = new Color3f(0.2f, 0.2f, 0.2f); + + AmbientLight aLgt = new AmbientLight(alColor); + aLgt.setInfluencingBounds(bounds); + DirectionalLight lgt1 = new DirectionalLight(lColor1, lDir1); + lgt1.setInfluencingBounds(bounds); + objScale.addChild(aLgt); + objScale.addChild(lgt1); + + // + // Create the transform group nodes for the 3 original objects + // and the morphed object. Add them to the root of the + // branch graph. + // + TransformGroup objTrans[] = new TransformGroup[4]; + + for(int i=0; i<4; i++) { + objTrans[i] = new TransformGroup(); + objScale.addChild(objTrans[i]); + } + + Transform3D tr = new Transform3D(); + Transform3D rotX90 = new Transform3D(); + rotX90.rotX(90.0 * Math.PI / 180.0); + + objTrans[0].getTransform(tr); + tr.setTranslation(new Vector3d(-2.0, 1.5, -2.0)); + tr.mul(rotX90); + objTrans[0].setTransform(tr); + + objTrans[1].getTransform(tr); + tr.setTranslation(new Vector3d(0.0, 1.5, -2.0)); + tr.mul(rotX90); + objTrans[1].setTransform(tr); + + objTrans[2].getTransform(tr); + tr.setTranslation(new Vector3d(2.0, 1.5, -2.0)); + tr.mul(rotX90); + objTrans[2].setTransform(tr); + + objTrans[3].getTransform(tr); + tr.setTranslation(new Vector3d(0.0, -2.0, -2.0)); + tr.mul(rotX90); + objTrans[3].setTransform(tr); + + + // Now load the object files + Scene s[] = new Scene[3]; + GeometryArray g[] = new GeometryArray[3]; + Shape3D shape[] = new Shape3D[3]; + ObjectFile loader = new ObjectFile(ObjectFile.RESIZE); + for(int i=0; i<3; i++) { + s[i] = null; + g[i] = null; + shape[i] = null; + } + + for(int i=0; i<3;i++) { + try { + s[i] = loader.load(objFiles[i]); + } + catch (FileNotFoundException e) { + System.err.println(e); + System.exit(1); + } + catch (ParsingErrorException e) { + System.err.println(e); + System.exit(1); + } + catch (IncorrectFormatException e) { + System.err.println(e); + System.exit(1); + } + + BranchGroup b = s[i].getSceneGroup(); + shape[i] = (Shape3D) b.getChild(0); + g[i] = (GeometryArray) shape[i].getGeometry(); + + shape[i].setGeometry(g[i]); + objTrans[i].addChild(b); + } + + // + // Create a Morph node, and set the appearance and input geometry + // arrays. Set the Morph node's capability bits to allow the weights + // to be modified at runtime. + // + Appearance app = new Appearance(); + Color3f objColor = new Color3f(1.0f, 0.7f, 0.8f); + Color3f black = new Color3f(0.0f, 0.0f, 0.0f); + app.setMaterial(new Material(objColor, black, objColor, black, 80.0f)); + Morph morph = new Morph(g, app); + morph.setCapability(Morph.ALLOW_WEIGHTS_READ); + morph.setCapability(Morph.ALLOW_WEIGHTS_WRITE); + + objTrans[3].addChild(morph); + + // Now create the Alpha object that controls the speed of the + // morphing operation. + Alpha morphAlpha = new Alpha(-1, Alpha.INCREASING_ENABLE | + Alpha.DECREASING_ENABLE, + 0, 0, + 2000, 1000, 200, + 2000, 1000, 200); + + // Finally, create the morphing behavior + MorphingBehavior mBeh = new MorphingBehavior(morphAlpha, morph); + mBeh.setSchedulingBounds(bounds); + objScale.addChild(mBeh); + + return objRoot; + } + + + private Canvas3D createUniverse() { + // Get the preferred graphics configuration for the default screen + GraphicsConfiguration config = + SimpleUniverse.getPreferredConfiguration(); + + // Create a Canvas3D using the preferred configuration + Canvas3D c = new Canvas3D(config); + + // Create simple universe with view branch + univ = new SimpleUniverse(c); + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + univ.getViewingPlatform().setNominalViewingTransform(); + + // Ensure at least 5 msec per frame (i.e., < 200Hz) + univ.getViewer().getView().setMinimumFrameCycleTime(5); + + return c; + } + + /** + * Creates new form LOD + */ + public Morphing(String args[]) { + + objFiles = new java.net.URL[3]; + for(int i=0; i<3; i++) { + objFiles[i] = Resources.getResource("resources/geometry/hand" + (i+1) + ".obj"); + if (objFiles[i] == null) { + System.err.println("resources/geometry/hand" + (i+1) + ".obj not found"); + System.exit(1); + } + } + + // Initialize the GUI components + initComponents(); + + // Create Canvas3D and SimpleUniverse; add canvas to drawing panel + Canvas3D c = createUniverse(); + drawingPanel.add(c, java.awt.BorderLayout.CENTER); + + // Create the content branch and add it to the universe + scene = createSceneGraph(); + univ.addBranchGraph(scene); + } + + // ---------------------------------------------------------------- + + /** This method is called from within the constructor to + * initialize the form. + * WARNING: Do NOT modify this code. The content of this method is + * always regenerated by the Form Editor. + */ + // <editor-fold defaultstate="collapsed" desc=" Generated Code ">//GEN-BEGIN:initComponents + private void initComponents() { + drawingPanel = new javax.swing.JPanel(); + + setDefaultCloseOperation(javax.swing.WindowConstants.EXIT_ON_CLOSE); + setTitle("Morphing"); + drawingPanel.setLayout(new java.awt.BorderLayout()); + + drawingPanel.setPreferredSize(new java.awt.Dimension(700, 700)); + getContentPane().add(drawingPanel, java.awt.BorderLayout.CENTER); + + pack(); + }// </editor-fold>//GEN-END:initComponents + + /** + * @param args the command line arguments + */ + public static void main(final String args[]) { + java.awt.EventQueue.invokeLater(new Runnable() { + public void run() { + Morphing morphing = new Morphing(args); + morphing.setVisible(true); + } + }); + } + + // Variables declaration - do not modify//GEN-BEGIN:variables + private javax.swing.JPanel drawingPanel; + // End of variables declaration//GEN-END:variables + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/morphing/MorphingBehavior.java b/src/main/java/org/jdesktop/j3d/examples/morphing/MorphingBehavior.java new file mode 100644 index 0000000..49520c2 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/morphing/MorphingBehavior.java @@ -0,0 +1,102 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.morphing; + +import java.util.Enumeration; + +import org.jogamp.java3d.Alpha; +import org.jogamp.java3d.Behavior; +import org.jogamp.java3d.Morph; +import org.jogamp.java3d.WakeupOnElapsedFrames; + +// User-defined morphing behavior class +public class MorphingBehavior extends Behavior { + + Alpha alpha; + Morph morph; + double weights[]; + + WakeupOnElapsedFrames w = new WakeupOnElapsedFrames(0); + + // Override Behavior's initialize method to setup wakeup criteria + public void initialize() { + alpha.setStartTime(System.currentTimeMillis()); + + // Establish initial wakeup criteria + wakeupOn(w); + } + + // Override Behavior's stimulus method to handle the event + public void processStimulus(Enumeration criteria) { + + // NOTE: This assumes 3 objects. It should be generalized to + // "n" objects. + + double val = alpha.value(); + if (val < 0.5) { + double a = val * 2.0; + weights[0] = 1.0 - a; + weights[1] = a; + weights[2] = 0.0; + } + else { + double a = (val - 0.5) * 2.0; + weights[0] = 0.0; + weights[1] = 1.0f - a; + weights[2] = a; + } + + morph.setWeights(weights); + + // Set wakeup criteria for next time + wakeupOn(w); + } + + public MorphingBehavior(Alpha a, Morph m) { + alpha = a; + morph = m; + weights = morph.getWeights(); + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/morphing/Pyramid2Cube.form b/src/main/java/org/jdesktop/j3d/examples/morphing/Pyramid2Cube.form new file mode 100644 index 0000000..0c0b7e2 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/morphing/Pyramid2Cube.form @@ -0,0 +1,36 @@ +<?xml version="1.0" encoding="UTF-8" ?> + +<Form version="1.0" type="org.netbeans.modules.form.forminfo.JFrameFormInfo"> + <Properties> + <Property name="defaultCloseOperation" type="int" value="3"/> + <Property name="title" type="java.lang.String" value="Pyramid2Cube"/> + </Properties> + <SyntheticProperties> + <SyntheticProperty name="formSizePolicy" type="int" value="1"/> + </SyntheticProperties> + <AuxValues> + <AuxValue name="FormSettings_generateMnemonicsCode" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_listenerGenerationStyle" type="java.lang.Integer" value="0"/> + <AuxValue name="FormSettings_variablesLocal" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_variablesModifier" type="java.lang.Integer" value="2"/> + <AuxValue name="designerSize" type="java.awt.Dimension" value="-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,1,44,0,0,1,-112"/> + </AuxValues> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + <SubComponents> + <Container class="javax.swing.JPanel" name="drawingPanel"> + <Properties> + <Property name="preferredSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor"> + <Dimension value="[700, 700]"/> + </Property> + </Properties> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout" value="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription"> + <BorderConstraints direction="Center"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + </Container> + </SubComponents> +</Form> diff --git a/src/main/java/org/jdesktop/j3d/examples/morphing/Pyramid2Cube.java b/src/main/java/org/jdesktop/j3d/examples/morphing/Pyramid2Cube.java new file mode 100644 index 0000000..7435588 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/morphing/Pyramid2Cube.java @@ -0,0 +1,250 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.morphing; + +import java.awt.GraphicsConfiguration; + +import org.jogamp.java3d.Alpha; +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.Background; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.GeometryArray; +import org.jogamp.java3d.Morph; +import org.jogamp.java3d.QuadArray; +import org.jogamp.java3d.Shape3D; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Vector3d; + +public class Pyramid2Cube extends javax.swing.JFrame { + + private SimpleUniverse univ = null; + private BranchGroup scene = null; + + private BranchGroup createSceneGraph() { + // Create the root of the branch graph + BranchGroup objRoot = new BranchGroup(); + + // Create a Transformgroup to scale all objects so they + // appear in the scene. + TransformGroup objScale = new TransformGroup(); + Transform3D t3d = new Transform3D(); + t3d.setScale(0.4); + objScale.setTransform(t3d); + objRoot.addChild(objScale); + + + // Create a bounds for the background and behavior + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + + // Set up the background + Color3f bgColor = new Color3f(0.05f, 0.05f, 0.2f); + Background bg = new Background(bgColor); + bg.setApplicationBounds(bounds); + objScale.addChild(bg); + + // + // Create the transform group nodes for the 3 original objects + // and the morphed object. Add them to the root of the + // branch graph. + // + TransformGroup objTrans[] = new TransformGroup[4]; + + for(int i=0; i<4; i++) { + objTrans[i] = new TransformGroup(); + objScale.addChild(objTrans[i]); + } + + Transform3D tr = new Transform3D(); + Transform3D rotY15 = new Transform3D(); + rotY15.rotY(15.0 * Math.PI / 180.0); + + objTrans[0].getTransform(tr); + tr.setTranslation(new Vector3d(-3.0, 1.5, -6.5)); + tr.mul(rotY15); + objTrans[0].setTransform(tr); + + objTrans[1].getTransform(tr); + tr.setTranslation(new Vector3d(0.0, 1.5, -6.5)); + tr.mul(rotY15); + objTrans[1].setTransform(tr); + + objTrans[2].getTransform(tr); + tr.setTranslation(new Vector3d(3.0, 1.5, -6.5)); + tr.mul(rotY15); + objTrans[2].setTransform(tr); + + objTrans[3].getTransform(tr); + tr.setTranslation(new Vector3d(0.0, -2.0, -5.0)); + tr.mul(rotY15); + objTrans[3].setTransform(tr); + + // Now create simple geometries. + + QuadArray g[] = new QuadArray[3]; + Shape3D shape[] = new Shape3D[3]; + for(int i=0; i<3; i++) { + g[i] = null; + shape[i] = null; + } + + g[0] = new ColorPyramidUp(); + g[1] = new ColorCube(); + g[2] = new ColorPyramidDown(); + + Appearance a = new Appearance(); + + for(int i=0; i<3;i++) { + shape[i] = new Shape3D(g[i],a); + objTrans[i].addChild(shape[i]); + } + + // + // Create a Morph node, and set the appearance and input geometry + // arrays. Set the Morph node's capability bits to allow the weights + // to be modified at runtime. + // + Morph morph = new Morph((GeometryArray[]) g, a); + morph.setCapability(Morph.ALLOW_WEIGHTS_READ); + morph.setCapability(Morph.ALLOW_WEIGHTS_WRITE); + + objTrans[3].addChild(morph); + + // Now create the Alpha object that controls the speed of the + // morphing operation. + Alpha morphAlpha = new Alpha(-1, Alpha.INCREASING_ENABLE | + Alpha.DECREASING_ENABLE, + 0, 0, + 4000, 1000, 500, + 4000, 1000, 500); + + // Finally, create the morphing behavior + MorphingBehavior mBeh = new MorphingBehavior(morphAlpha, morph); + mBeh.setSchedulingBounds(bounds); + objScale.addChild(mBeh); + + return objRoot; + } + + private Canvas3D createUniverse() { + // Get the preferred graphics configuration for the default screen + GraphicsConfiguration config = + SimpleUniverse.getPreferredConfiguration(); + + // Create a Canvas3D using the preferred configuration + Canvas3D c = new Canvas3D(config); + + // Create simple universe with view branch + univ = new SimpleUniverse(c); + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + univ.getViewingPlatform().setNominalViewingTransform(); + + // Ensure at least 5 msec per frame (i.e., < 200Hz) + univ.getViewer().getView().setMinimumFrameCycleTime(5); + + return c; + } + + /** + * Creates new form Pyramid2Cube + */ + public Pyramid2Cube() { + // Initialize the GUI components + initComponents(); + + // Create Canvas3D and SimpleUniverse; add canvas to drawing panel + Canvas3D c = createUniverse(); + drawingPanel.add(c, java.awt.BorderLayout.CENTER); + + // Create the content branch and add it to the universe + scene = createSceneGraph(); + univ.addBranchGraph(scene); + } + + // ---------------------------------------------------------------- + + /** This method is called from within the constructor to + * initialize the form. + * WARNING: Do NOT modify this code. The content of this method is + * always regenerated by the Form Editor. + */ + // <editor-fold defaultstate="collapsed" desc=" Generated Code ">//GEN-BEGIN:initComponents + private void initComponents() { + drawingPanel = new javax.swing.JPanel(); + + setDefaultCloseOperation(javax.swing.WindowConstants.EXIT_ON_CLOSE); + setTitle("Pyramid2Cube"); + drawingPanel.setLayout(new java.awt.BorderLayout()); + + drawingPanel.setPreferredSize(new java.awt.Dimension(700, 700)); + getContentPane().add(drawingPanel, java.awt.BorderLayout.CENTER); + + pack(); + }// </editor-fold>//GEN-END:initComponents + + /** + * @param args the command line arguments + */ + public static void main(String args[]) {System.setProperty("sun.awt.noerasebackground", "true"); + java.awt.EventQueue.invokeLater(new Runnable() { + public void run() { + new Pyramid2Cube().setVisible(true); + } + }); + } + + // Variables declaration - do not modify//GEN-BEGIN:variables + private javax.swing.JPanel drawingPanel; + // End of variables declaration//GEN-END:variables + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/objload/ObjLoad.form b/src/main/java/org/jdesktop/j3d/examples/objload/ObjLoad.form new file mode 100644 index 0000000..f8ced41 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/objload/ObjLoad.form @@ -0,0 +1,36 @@ +<?xml version="1.0" encoding="UTF-8" ?> + +<Form version="1.0" type="org.netbeans.modules.form.forminfo.JFrameFormInfo"> + <Properties> + <Property name="defaultCloseOperation" type="int" value="3"/> + <Property name="title" type="java.lang.String" value="ObjLoad"/> + </Properties> + <SyntheticProperties> + <SyntheticProperty name="formSizePolicy" type="int" value="1"/> + </SyntheticProperties> + <AuxValues> + <AuxValue name="FormSettings_generateMnemonicsCode" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_listenerGenerationStyle" type="java.lang.Integer" value="0"/> + <AuxValue name="FormSettings_variablesLocal" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_variablesModifier" type="java.lang.Integer" value="2"/> + <AuxValue name="designerSize" type="java.awt.Dimension" value="-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,1,44,0,0,1,-112"/> + </AuxValues> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + <SubComponents> + <Container class="javax.swing.JPanel" name="drawingPanel"> + <Properties> + <Property name="preferredSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor"> + <Dimension value="[700, 700]"/> + </Property> + </Properties> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout" value="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription"> + <BorderConstraints direction="Center"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + </Container> + </SubComponents> +</Form> diff --git a/src/main/java/org/jdesktop/j3d/examples/objload/ObjLoad.java b/src/main/java/org/jdesktop/j3d/examples/objload/ObjLoad.java new file mode 100644 index 0000000..9936e97 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/objload/ObjLoad.java @@ -0,0 +1,325 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.objload; + +import java.awt.GraphicsConfiguration; +import java.io.FileNotFoundException; +import java.net.MalformedURLException; +import java.net.URL; + +import org.jdesktop.j3d.examples.Resources; +import org.jogamp.java3d.Alpha; +import org.jogamp.java3d.AmbientLight; +import org.jogamp.java3d.Background; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.DirectionalLight; +import org.jogamp.java3d.RotationInterpolator; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.loaders.IncorrectFormatException; +import org.jogamp.java3d.loaders.ParsingErrorException; +import org.jogamp.java3d.loaders.Scene; +import org.jogamp.java3d.loaders.objectfile.ObjectFile; +import org.jogamp.java3d.utils.behaviors.vp.OrbitBehavior; +import org.jogamp.java3d.utils.universe.PlatformGeometry; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.java3d.utils.universe.ViewingPlatform; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Vector3f; + +/** + * Simple Java 3D example program to display an .obj object. + */ +public class ObjLoad extends javax.swing.JFrame { + + private boolean spin = false; + private boolean noTriangulate = false; + private boolean noStripify = false; + private double creaseAngle = 60.0; + private URL filename = null; + + private SimpleUniverse univ = null; + private BranchGroup scene = null; + + public BranchGroup createSceneGraph() { + // Create the root of the branch graph + BranchGroup objRoot = new BranchGroup(); + + // Create a Transformgroup to scale all objects so they + // appear in the scene. + TransformGroup objScale = new TransformGroup(); + Transform3D t3d = new Transform3D(); + t3d.setScale(0.7); + objScale.setTransform(t3d); + objRoot.addChild(objScale); + + // Create the transform group node and initialize it to the + // identity. Enable the TRANSFORM_WRITE capability so that + // our behavior code can modify it at runtime. Add it to the + // root of the subgraph. + TransformGroup objTrans = new TransformGroup(); + objTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + objTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_READ); + objScale.addChild(objTrans); + + int flags = ObjectFile.RESIZE; + if (!noTriangulate) flags |= ObjectFile.TRIANGULATE; + if (!noStripify) flags |= ObjectFile.STRIPIFY; + ObjectFile f = new ObjectFile(flags, + (float)(creaseAngle * Math.PI / 180.0)); + Scene s = null; + try { + s = f.load(filename); + } + catch (FileNotFoundException e) { + System.err.println(e); + System.exit(1); + } + catch (ParsingErrorException e) { + System.err.println(e); + System.exit(1); + } + catch (IncorrectFormatException e) { + System.err.println(e); + System.exit(1); + } + + objTrans.addChild(s.getSceneGroup()); + + BoundingSphere bounds = new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + + if (spin) { + Transform3D yAxis = new Transform3D(); + Alpha rotationAlpha = new Alpha(-1, Alpha.INCREASING_ENABLE, + 0, 0, + 4000, 0, 0, + 0, 0, 0); + + RotationInterpolator rotator = + new RotationInterpolator(rotationAlpha, objTrans, yAxis, + 0.0f, (float) Math.PI*2.0f); + rotator.setSchedulingBounds(bounds); + objTrans.addChild(rotator); + } + + // Set up the background + Color3f bgColor = new Color3f(0.05f, 0.05f, 0.5f); + Background bgNode = new Background(bgColor); + bgNode.setApplicationBounds(bounds); + objRoot.addChild(bgNode); + + return objRoot; + } + + private Canvas3D createUniverse() { + // Get the preferred graphics configuration for the default screen + GraphicsConfiguration config = + SimpleUniverse.getPreferredConfiguration(); + + // Create a Canvas3D using the preferred configuration + Canvas3D canvas3d = new Canvas3D(config); + + // Create simple universe with view branch + univ = new SimpleUniverse(canvas3d); + BoundingSphere bounds = new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + + // add mouse behaviors to the ViewingPlatform + ViewingPlatform viewingPlatform = univ.getViewingPlatform(); + + PlatformGeometry pg = new PlatformGeometry(); + + // Set up the ambient light + Color3f ambientColor = new Color3f(0.1f, 0.1f, 0.1f); + AmbientLight ambientLightNode = new AmbientLight(ambientColor); + ambientLightNode.setInfluencingBounds(bounds); + pg.addChild(ambientLightNode); + + // Set up the directional lights + Color3f light1Color = new Color3f(1.0f, 1.0f, 0.9f); + Vector3f light1Direction = new Vector3f(1.0f, 1.0f, 1.0f); + Color3f light2Color = new Color3f(1.0f, 1.0f, 1.0f); + Vector3f light2Direction = new Vector3f(-1.0f, -1.0f, -1.0f); + + DirectionalLight light1 + = new DirectionalLight(light1Color, light1Direction); + light1.setInfluencingBounds(bounds); + pg.addChild(light1); + + DirectionalLight light2 + = new DirectionalLight(light2Color, light2Direction); + light2.setInfluencingBounds(bounds); + pg.addChild(light2); + + viewingPlatform.setPlatformGeometry( pg ); + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + viewingPlatform.setNominalViewingTransform(); + + if (!spin) { + OrbitBehavior orbit = new OrbitBehavior(canvas3d, + OrbitBehavior.REVERSE_ALL); + orbit.setSchedulingBounds(bounds); + viewingPlatform.setViewPlatformBehavior(orbit); + } + + // Ensure at least 5 msec per frame (i.e., < 200Hz) + univ.getViewer().getView().setMinimumFrameCycleTime(5); + + return canvas3d; + } + + private void usage() { + System.out.println( + "Usage: java ObjLoad [-s] [-n] [-t] [-c degrees] <.obj file>"); + System.out.println(" -s Spin (no user interaction)"); + System.out.println(" -n No triangulation"); + System.out.println(" -t No stripification"); + System.out.println( + " -c Set crease angle for normal generation (default is 60 without"); + System.out.println( + " smoothing group info, otherwise 180 within smoothing groups)"); + System.exit(0); + } // End of usage + + /** + * Creates new form ObjLoad + */ + public ObjLoad(String args[]) { + if (args.length != 0) { + for (int i = 0 ; i < args.length ; i++) { + if (args[i].startsWith("-")) { + if (args[i].equals("-s")) { + spin = true; + } else if (args[i].equals("-n")) { + noTriangulate = true; + } else if (args[i].equals("-t")) { + noStripify = true; + } else if (args[i].equals("-c")) { + if (i < args.length - 1) { + creaseAngle = (new Double(args[++i])).doubleValue(); + } else usage(); + } else { + usage(); + } + } else { + try { + if ((args[i].indexOf("file:") == 0) || + (args[i].indexOf("http") == 0)) { + filename = new URL(args[i]); + } else if (args[i].charAt(0) != '/') { + filename = new URL("file:./" + args[i]); + } else { + filename = new URL("file:" + args[i]); + } + } catch (MalformedURLException e) { + System.err.println(e); + System.exit(1); + } + } + } + } + + if (filename == null) { + filename = Resources.getResource("resources/geometry/galleon.obj"); + if (filename == null) { + System.err.println("resources/geometry/galleon.obj not found"); + System.exit(1); + } + } + + // Initialize the GUI components + initComponents(); + + // Create Canvas3D and SimpleUniverse; add canvas to drawing panel + Canvas3D c = createUniverse(); + drawingPanel.add(c, java.awt.BorderLayout.CENTER); + + // Create the content branch and add it to the universe + scene = createSceneGraph(); + univ.addBranchGraph(scene); + } + + // ---------------------------------------------------------------- + + /** This method is called from within the constructor to + * initialize the form. + * WARNING: Do NOT modify this code. The content of this method is + * always regenerated by the Form Editor. + */ + // <editor-fold defaultstate="collapsed" desc=" Generated Code ">//GEN-BEGIN:initComponents + private void initComponents() { + drawingPanel = new javax.swing.JPanel(); + + setDefaultCloseOperation(javax.swing.WindowConstants.EXIT_ON_CLOSE); + setTitle("ObjLoad"); + drawingPanel.setLayout(new java.awt.BorderLayout()); + + drawingPanel.setPreferredSize(new java.awt.Dimension(700, 700)); + getContentPane().add(drawingPanel, java.awt.BorderLayout.CENTER); + + pack(); + }// </editor-fold>//GEN-END:initComponents + + /** + * @param args the command line arguments + */ + public static void main(final String args[]) { + java.awt.EventQueue.invokeLater(new Runnable() { + public void run() { + ObjLoad objLoad = new ObjLoad(args); + objLoad.setVisible(true); + } + }); + } + + // Variables declaration - do not modify//GEN-BEGIN:variables + private javax.swing.JPanel drawingPanel; + // End of variables declaration//GEN-END:variables + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/offscreen_canvas3d/OffScreenCanvas3D.java b/src/main/java/org/jdesktop/j3d/examples/offscreen_canvas3d/OffScreenCanvas3D.java new file mode 100644 index 0000000..913bc74 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/offscreen_canvas3d/OffScreenCanvas3D.java @@ -0,0 +1,107 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.offscreen_canvas3d; + +import java.awt.GraphicsConfiguration; +import java.awt.image.BufferedImage; + +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.ImageComponent; +import org.jogamp.java3d.ImageComponent2D; +import org.jogamp.java3d.Raster; + + +class OffScreenCanvas3D extends Canvas3D { + + Raster drawRaster; + boolean printing = false; + + public OffScreenCanvas3D(GraphicsConfiguration gconfig, boolean offscreenflag, + Raster drawRaster) { + + super(gconfig, offscreenflag); + this.drawRaster = drawRaster; + } + + public void print(boolean toWait) { + + if (!toWait) + printing = true; + + BufferedImage bImage = new BufferedImage( + 200, 200 , BufferedImage.TYPE_INT_ARGB); + + ImageComponent2D buffer = new ImageComponent2D( + ImageComponent.FORMAT_RGBA, bImage, true, true); + buffer.setCapability(ImageComponent2D.ALLOW_IMAGE_READ); + + this.setOffScreenBuffer(buffer); + this.renderOffScreenBuffer(); + + if (toWait) { + this.waitForOffScreenRendering(); + drawOffScreenBuffer(); + } + } + + public void postSwap() { + + if (printing) { + super.postSwap(); + drawOffScreenBuffer(); + printing = false; + } + } + + void drawOffScreenBuffer() { + + BufferedImage bImage = this.getOffScreenBuffer().getImage(); + ImageComponent2D newImageComponent = new ImageComponent2D( + ImageComponent.FORMAT_RGBA, bImage, true, true); + + drawRaster.setImage(newImageComponent); + } +} + diff --git a/src/main/java/org/jdesktop/j3d/examples/offscreen_canvas3d/OffScreenTest.form b/src/main/java/org/jdesktop/j3d/examples/offscreen_canvas3d/OffScreenTest.form new file mode 100644 index 0000000..39a0712 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/offscreen_canvas3d/OffScreenTest.form @@ -0,0 +1,36 @@ +<?xml version="1.0" encoding="UTF-8" ?> + +<Form version="1.0" type="org.netbeans.modules.form.forminfo.JFrameFormInfo"> + <Properties> + <Property name="defaultCloseOperation" type="int" value="3"/> + <Property name="title" type="java.lang.String" value="Window Title"/> + </Properties> + <SyntheticProperties> + <SyntheticProperty name="formSizePolicy" type="int" value="1"/> + </SyntheticProperties> + <AuxValues> + <AuxValue name="FormSettings_generateMnemonicsCode" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_listenerGenerationStyle" type="java.lang.Integer" value="0"/> + <AuxValue name="FormSettings_variablesLocal" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_variablesModifier" type="java.lang.Integer" value="2"/> + <AuxValue name="designerSize" type="java.awt.Dimension" value="-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,1,44,0,0,1,-112"/> + </AuxValues> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + <SubComponents> + <Container class="javax.swing.JPanel" name="drawingPanel"> + <Properties> + <Property name="preferredSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor"> + <Dimension value="[500, 500]"/> + </Property> + </Properties> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout" value="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription"> + <BorderConstraints direction="Center"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + </Container> + </SubComponents> +</Form> diff --git a/src/main/java/org/jdesktop/j3d/examples/offscreen_canvas3d/OffScreenTest.java b/src/main/java/org/jdesktop/j3d/examples/offscreen_canvas3d/OffScreenTest.java new file mode 100644 index 0000000..dbb841e --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/offscreen_canvas3d/OffScreenTest.java @@ -0,0 +1,231 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.offscreen_canvas3d; + +import java.awt.GraphicsConfiguration; +import java.awt.GraphicsEnvironment; +import java.awt.image.BufferedImage; + +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.GraphicsConfigTemplate3D; +import org.jogamp.java3d.ImageComponent; +import org.jogamp.java3d.ImageComponent2D; +import org.jogamp.java3d.Raster; +import org.jogamp.java3d.Screen3D; +import org.jogamp.java3d.Shape3D; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.View; +import org.jogamp.java3d.utils.geometry.ColorCube; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.vecmath.Point3f; +import org.jogamp.vecmath.Vector3d; + +/** + * OffScreenTest programs with no UI. + */ +public class OffScreenTest extends javax.swing.JFrame { + + private SimpleUniverse univ = null; + private BranchGroup scene = null; + private Raster drawRaster = null; + + private BranchGroup createSceneGraph() { + // Create the root of the branch graph + BranchGroup objRoot = new BranchGroup(); + + // trans object has composited transformation matrix + Transform3D trans = new Transform3D(); + Transform3D rot = new Transform3D(); + + trans.rotX(Math.PI/4.0d); + rot.rotY(Math.PI/5.0d); + trans.mul(rot); + trans.setScale(0.7); + trans.setTranslation(new Vector3d(-0.4, 0.3, 0.0)); + + TransformGroup objTrans = new TransformGroup(trans); + objRoot.addChild(objTrans); + + // Create a simple shape leaf node, add it to the scene graph. + // ColorCube is a Convenience Utility class + objTrans.addChild(new ColorCube(0.4)); + + //Create a raster + BufferedImage bImage = new BufferedImage(200, 200 , + BufferedImage.TYPE_INT_ARGB); + ImageComponent2D buffer = + new ImageComponent2D(ImageComponent.FORMAT_RGBA, bImage, true, true); + buffer.setCapability(ImageComponent2D.ALLOW_IMAGE_READ); + + drawRaster = new Raster(new Point3f(0.0f, 0.0f, 0.0f), + Raster.RASTER_COLOR, + 0, 0, 200, 200, buffer, null); + + drawRaster.setCapability(Raster.ALLOW_IMAGE_WRITE); + Shape3D shape = new Shape3D(drawRaster); + objRoot.addChild(shape); + + // Let Java 3D perform optimizations on this scene graph. + objRoot.compile(); + + return objRoot; + } + + + private OnScreenCanvas3D createOnScreenCanvasAndUniverse() { + // Get the preferred graphics configuration for the default screen + GraphicsConfiguration config = + SimpleUniverse.getPreferredConfiguration(); + + // Create a Canvas3D using the preferred configuration + OnScreenCanvas3D onScrCanvas = new OnScreenCanvas3D(config, false); + + // Create simple universe with view branch + univ = new SimpleUniverse(onScrCanvas); + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + univ.getViewingPlatform().setNominalViewingTransform(); + + // Ensure at least 5 msec per frame (i.e., < 200Hz) + univ.getViewer().getView().setMinimumFrameCycleTime(5); + + return onScrCanvas; + } + + private OffScreenCanvas3D createOffScreenCanvas() { + // request an offscreen Canvas3D with a single buffer configuration + GraphicsConfigTemplate3D template = new GraphicsConfigTemplate3D(); + template.setDoubleBuffer(GraphicsConfigTemplate3D.UNNECESSARY); + GraphicsConfiguration gc = + GraphicsEnvironment.getLocalGraphicsEnvironment(). + getDefaultScreenDevice().getBestConfiguration(template); + + // Create a offscreen Canvas3D using the single buffer configuration. + OffScreenCanvas3D offScrCanvas = + new OffScreenCanvas3D(gc, true, drawRaster); + + return offScrCanvas; + } + + /** + * Creates new form OffScreenTest + */ + public OffScreenTest() { + // Initialize the GUI components + initComponents(); + + // Create the content branch and add it to the universe + scene = createSceneGraph(); + + // Create an OnScreenCanvas3D and SimpleUniverse; add canvas to drawing panel + OnScreenCanvas3D onScreenCanvas = createOnScreenCanvasAndUniverse(); + drawingPanel.add(onScreenCanvas, java.awt.BorderLayout.CENTER); + + // Creante an OffScreenCanvas3D + OffScreenCanvas3D offScreenCanvas = createOffScreenCanvas(); + + // set the offscreen to match the onscreen + Screen3D sOn = onScreenCanvas.getScreen3D(); + Screen3D sOff = offScreenCanvas.getScreen3D(); + sOff.setSize(sOn.getSize()); + sOff.setPhysicalScreenWidth(sOn.getPhysicalScreenWidth()); + sOff.setPhysicalScreenHeight(sOn.getPhysicalScreenHeight()); + + // attach the same view to the offscreen canvas + View view = univ.getViewer().getView(); + view.addCanvas3D(offScreenCanvas); + + // tell onscreen about the offscreen so it knows to + // render to the offscreen at postswap + onScreenCanvas.setOffScreenCanvas(offScreenCanvas); + + univ.addBranchGraph(scene); + + view.stopView(); + // Make sure that image are render completely + // before grab it in postSwap(). + onScreenCanvas.setImageReady(); + view.startView(); + } + + // ---------------------------------------------------------------- + + /** This method is called from within the constructor to + * initialize the form. + * WARNING: Do NOT modify this code. The content of this method is + * always regenerated by the Form Editor. + */ + // <editor-fold defaultstate="collapsed" desc=" Generated Code ">//GEN-BEGIN:initComponents + private void initComponents() { + drawingPanel = new javax.swing.JPanel(); + + setDefaultCloseOperation(javax.swing.WindowConstants.EXIT_ON_CLOSE); + setTitle("Window Title"); + drawingPanel.setLayout(new java.awt.BorderLayout()); + + drawingPanel.setPreferredSize(new java.awt.Dimension(500, 500)); + getContentPane().add(drawingPanel, java.awt.BorderLayout.CENTER); + + pack(); + }// </editor-fold>//GEN-END:initComponents + + /** + * @param args the command line arguments + */ + public static void main(String args[]) {System.setProperty("sun.awt.noerasebackground", "true"); + java.awt.EventQueue.invokeLater(new Runnable() { + public void run() { + new OffScreenTest().setVisible(true); + } + }); + } + + // Variables declaration - do not modify//GEN-BEGIN:variables + private javax.swing.JPanel drawingPanel; + // End of variables declaration//GEN-END:variables + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/offscreen_canvas3d/OnScreenCanvas3D.java b/src/main/java/org/jdesktop/j3d/examples/offscreen_canvas3d/OnScreenCanvas3D.java new file mode 100644 index 0000000..ce671e2 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/offscreen_canvas3d/OnScreenCanvas3D.java @@ -0,0 +1,79 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.offscreen_canvas3d; + +import java.awt.GraphicsConfiguration; + +import org.jogamp.java3d.Canvas3D; + + +class OnScreenCanvas3D extends Canvas3D { + + OffScreenCanvas3D c; + boolean print = false; + boolean imageReady = false; + + public OnScreenCanvas3D(GraphicsConfiguration gconfig, boolean offscreenflag) + { + super(gconfig, offscreenflag); + } + + public void setOffScreenCanvas(OffScreenCanvas3D c) + { + this.c = c; + } + + public void setImageReady() { + imageReady = true; + } + + public void postSwap() + { + if (imageReady && !print) { + c.print(false); + print = true; + } + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/offscreen_canvas3d/PrintFromButton.form b/src/main/java/org/jdesktop/j3d/examples/offscreen_canvas3d/PrintFromButton.form new file mode 100644 index 0000000..54d6721 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/offscreen_canvas3d/PrintFromButton.form @@ -0,0 +1,82 @@ +<?xml version="1.0" encoding="UTF-8" ?> + +<Form version="1.0" type="org.netbeans.modules.form.forminfo.JFrameFormInfo"> + <NonVisualComponents> + <Menu class="javax.swing.JMenuBar" name="jMenuBar1"> + <SubComponents> + <Menu class="javax.swing.JMenu" name="fileMenu"> + <Properties> + <Property name="text" type="java.lang.String" value="File"/> + </Properties> + <SubComponents> + <MenuItem class="javax.swing.JMenuItem" name="exitMenuItem"> + <Properties> + <Property name="text" type="java.lang.String" value="Exit"/> + </Properties> + <Events> + <EventHandler event="actionPerformed" listener="java.awt.event.ActionListener" parameters="java.awt.event.ActionEvent" handler="exitMenuItemActionPerformed"/> + </Events> + </MenuItem> + </SubComponents> + </Menu> + </SubComponents> + </Menu> + </NonVisualComponents> + <Properties> + <Property name="defaultCloseOperation" type="int" value="3"/> + <Property name="title" type="java.lang.String" value="Window Title"/> + </Properties> + <SyntheticProperties> + <SyntheticProperty name="menuBar" type="java.lang.String" value="jMenuBar1"/> + <SyntheticProperty name="formSizePolicy" type="int" value="1"/> + </SyntheticProperties> + <AuxValues> + <AuxValue name="FormSettings_generateMnemonicsCode" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_listenerGenerationStyle" type="java.lang.Integer" value="0"/> + <AuxValue name="FormSettings_variablesLocal" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_variablesModifier" type="java.lang.Integer" value="2"/> + <AuxValue name="designerSize" type="java.awt.Dimension" value="-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,1,44,0,0,1,-112"/> + </AuxValues> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + <SubComponents> + <Container class="javax.swing.JPanel" name="guiPanel"> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout" value="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription"> + <BorderConstraints direction="North"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout"/> + <SubComponents> + <Component class="javax.swing.JButton" name="myButton"> + <Properties> + <Property name="text" type="java.lang.String" value="Print"/> + </Properties> + <Events> + <EventHandler event="actionPerformed" listener="java.awt.event.ActionListener" parameters="java.awt.event.ActionEvent" handler="myButtonActionPerformed"/> + </Events> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout" value="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription"> + <GridBagConstraints gridX="-1" gridY="-1" gridWidth="1" gridHeight="1" fill="2" ipadX="0" ipadY="0" insetsTop="4" insetsLeft="4" insetsBottom="4" insetsRight="4" anchor="10" weightX="0.0" weightY="0.0"/> + </Constraint> + </Constraints> + </Component> + </SubComponents> + </Container> + <Container class="javax.swing.JPanel" name="drawingPanel"> + <Properties> + <Property name="preferredSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor"> + <Dimension value="[500, 500]"/> + </Property> + </Properties> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout" value="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription"> + <BorderConstraints direction="Center"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + </Container> + </SubComponents> +</Form> diff --git a/src/main/java/org/jdesktop/j3d/examples/offscreen_canvas3d/PrintFromButton.java b/src/main/java/org/jdesktop/j3d/examples/offscreen_canvas3d/PrintFromButton.java new file mode 100644 index 0000000..e53a094 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/offscreen_canvas3d/PrintFromButton.java @@ -0,0 +1,274 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.offscreen_canvas3d; + +import java.awt.GraphicsConfiguration; +import java.awt.GraphicsEnvironment; +import java.awt.image.BufferedImage; + +import javax.swing.JPopupMenu; + +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.GraphicsConfigTemplate3D; +import org.jogamp.java3d.ImageComponent; +import org.jogamp.java3d.ImageComponent2D; +import org.jogamp.java3d.Raster; +import org.jogamp.java3d.Screen3D; +import org.jogamp.java3d.Shape3D; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.View; +import org.jogamp.java3d.utils.geometry.ColorCube; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.vecmath.Point3f; +import org.jogamp.vecmath.Vector3d; + +/** + * PrintFromButton programs with simple UI. + */ +public class PrintFromButton extends javax.swing.JFrame { + + private SimpleUniverse univ = null; + private BranchGroup scene = null; + private Raster drawRaster = null; + private OffScreenCanvas3D offScreenCanvas = null; + + public BranchGroup createSceneGraph() { + // Create the root of the branch graph + BranchGroup objRoot = new BranchGroup(); + + // trans object has composited transformation matrix + Transform3D trans = new Transform3D(); + Transform3D rot = new Transform3D(); + + trans.rotX(Math.PI/4.0d); + rot.rotY(Math.PI/5.0d); + trans.mul(rot); + trans.setScale(0.7); + trans.setTranslation(new Vector3d(-0.4, 0.3, 0.0)); + + TransformGroup objTrans = new TransformGroup(trans); + objRoot.addChild(objTrans); + + // Create a simple shape leaf node, add it to the scene graph. + // ColorCube is a Convenience Utility class + objTrans.addChild(new ColorCube(0.4)); + + //Create a raster + BufferedImage bImage = new BufferedImage(200, 200 , + BufferedImage.TYPE_INT_ARGB); + ImageComponent2D buffer = + new ImageComponent2D(ImageComponent.FORMAT_RGBA, bImage, true, true); + buffer.setCapability(ImageComponent2D.ALLOW_IMAGE_READ); + + drawRaster = new Raster(new Point3f(0.0f, 0.0f, 0.0f), + Raster.RASTER_COLOR, + 0, 0, 200, 200, buffer, null); + + drawRaster.setCapability(Raster.ALLOW_IMAGE_WRITE); + Shape3D shape = new Shape3D(drawRaster); + objRoot.addChild(shape); + + // Let Java 3D perform optimizations on this scene graph. + objRoot.compile(); + + return objRoot; + } + + private OnScreenCanvas3D createOnScreenCanvasAndUniverse() { + // Get the preferred graphics configuration for the default screen + GraphicsConfiguration config = + SimpleUniverse.getPreferredConfiguration(); + + // Create a Canvas3D using the preferred configuration + OnScreenCanvas3D onScrCanvas = new OnScreenCanvas3D(config, false); + + // Create simple universe with view branch + univ = new SimpleUniverse(onScrCanvas); + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + univ.getViewingPlatform().setNominalViewingTransform(); + + // Ensure at least 5 msec per frame (i.e., < 200Hz) + univ.getViewer().getView().setMinimumFrameCycleTime(5); + + return onScrCanvas; + } + + private OffScreenCanvas3D createOffScreenCanvas() { + // request an offscreen Canvas3D with a single buffer configuration + GraphicsConfigTemplate3D template = new GraphicsConfigTemplate3D(); + template.setDoubleBuffer(GraphicsConfigTemplate3D.UNNECESSARY); + GraphicsConfiguration gc = + GraphicsEnvironment.getLocalGraphicsEnvironment(). + getDefaultScreenDevice().getBestConfiguration(template); + + // Create a offscreen Canvas3D using the single buffer configuration. + OffScreenCanvas3D offScrCanvas = + new OffScreenCanvas3D(gc, true, drawRaster); + + return offScrCanvas; + } + + /** + * Creates new form PrintFromButton + */ + public PrintFromButton() { + // Initialize the GUI components + JPopupMenu.setDefaultLightWeightPopupEnabled(false); + initComponents(); + + // Create the content branch and add it to the universe + scene = createSceneGraph(); + + // Create an OnScreenCanvas3D and SimpleUniverse; add canvas to drawing panel + OnScreenCanvas3D onScreenCanvas = createOnScreenCanvasAndUniverse(); + drawingPanel.add(onScreenCanvas, java.awt.BorderLayout.CENTER); + + // Creante an OffScreenCanvas3D + offScreenCanvas = createOffScreenCanvas(); + + // set the offscreen to match the onscreen + Screen3D sOn = onScreenCanvas.getScreen3D(); + Screen3D sOff = offScreenCanvas.getScreen3D(); + sOff.setSize(sOn.getSize()); + sOff.setPhysicalScreenWidth(sOn.getPhysicalScreenWidth()); + sOff.setPhysicalScreenHeight(sOn.getPhysicalScreenHeight()); + + // attach the same view to the offscreen canvas + View view = univ.getViewer().getView(); + view.addCanvas3D(offScreenCanvas); + + univ.addBranchGraph(scene); + } + + // ---------------------------------------------------------------- + + /** This method is called from within the constructor to + * initialize the form. + * WARNING: Do NOT modify this code. The content of this method is + * always regenerated by the Form Editor. + */ + // <editor-fold defaultstate="collapsed" desc=" Generated Code ">//GEN-BEGIN:initComponents + private void initComponents() { + java.awt.GridBagConstraints gridBagConstraints; + + guiPanel = new javax.swing.JPanel(); + myButton = new javax.swing.JButton(); + drawingPanel = new javax.swing.JPanel(); + jMenuBar1 = new javax.swing.JMenuBar(); + fileMenu = new javax.swing.JMenu(); + exitMenuItem = new javax.swing.JMenuItem(); + + setDefaultCloseOperation(javax.swing.WindowConstants.EXIT_ON_CLOSE); + setTitle("Window Title"); + guiPanel.setLayout(new java.awt.GridBagLayout()); + + myButton.setText("Print"); + myButton.addActionListener(new java.awt.event.ActionListener() { + public void actionPerformed(java.awt.event.ActionEvent evt) { + myButtonActionPerformed(evt); + } + }); + + gridBagConstraints = new java.awt.GridBagConstraints(); + gridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL; + gridBagConstraints.insets = new java.awt.Insets(4, 4, 4, 4); + guiPanel.add(myButton, gridBagConstraints); + + getContentPane().add(guiPanel, java.awt.BorderLayout.NORTH); + + drawingPanel.setLayout(new java.awt.BorderLayout()); + + drawingPanel.setPreferredSize(new java.awt.Dimension(500, 500)); + getContentPane().add(drawingPanel, java.awt.BorderLayout.CENTER); + + fileMenu.setText("File"); + exitMenuItem.setText("Exit"); + exitMenuItem.addActionListener(new java.awt.event.ActionListener() { + public void actionPerformed(java.awt.event.ActionEvent evt) { + exitMenuItemActionPerformed(evt); + } + }); + + fileMenu.add(exitMenuItem); + + jMenuBar1.add(fileMenu); + + setJMenuBar(jMenuBar1); + + pack(); + }// </editor-fold>//GEN-END:initComponents + + private void myButtonActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_myButtonActionPerformed + offScreenCanvas.print(false); + }//GEN-LAST:event_myButtonActionPerformed + + private void exitMenuItemActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_exitMenuItemActionPerformed + System.exit(0); + }//GEN-LAST:event_exitMenuItemActionPerformed + + /** + * @param args the command line arguments + */ + public static void main(String args[]) {System.setProperty("sun.awt.noerasebackground", "true"); + java.awt.EventQueue.invokeLater(new Runnable() { + public void run() { + new PrintFromButton().setVisible(true); + } + }); + } + + // Variables declaration - do not modify//GEN-BEGIN:variables + private javax.swing.JPanel drawingPanel; + private javax.swing.JMenuItem exitMenuItem; + private javax.swing.JMenu fileMenu; + private javax.swing.JPanel guiPanel; + private javax.swing.JMenuBar jMenuBar1; + private javax.swing.JButton myButton; + // End of variables declaration//GEN-END:variables + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/oriented_shape3d/MouseRotateY.java b/src/main/java/org/jdesktop/j3d/examples/oriented_shape3d/MouseRotateY.java new file mode 100644 index 0000000..473eaf7 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/oriented_shape3d/MouseRotateY.java @@ -0,0 +1,200 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.oriented_shape3d; + +import java.awt.AWTEvent; +import java.awt.event.MouseEvent; +import java.util.Enumeration; + +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.WakeupCriterion; +import org.jogamp.java3d.WakeupOnAWTEvent; +import org.jogamp.java3d.utils.behaviors.mouse.MouseBehavior; +import org.jogamp.vecmath.Matrix4d; +import org.jogamp.vecmath.Vector3d; + +/** + * MouseRotateY is a Java3D behavior object that lets users control the + * rotation of an object via a mouse. + * <p> + * To use this utility, first create a transform group that this + * rotate behavior will operate on. Then, + *<blockquote><pre> + * + * MouseRotateY behavior = new MouseRotateY(); + * behavior.setTransformGroup(objTrans); + * objTrans.addChild(behavior); + * behavior.setSchedulingBounds(bounds); + * + *</pre></blockquote> + * The above code will add the rotate behavior to the transform + * group. The user can rotate any object attached to the objTrans. + */ + +public class MouseRotateY extends MouseBehavior { + double y_angle; + double y_factor; + + /** + * Creates a rotate behavior given the transform group. + * @param transformGroup The transformGroup to operate on. + */ + public MouseRotateY(TransformGroup transformGroup) { + super(transformGroup); + } + + /** + * Creates a default mouse rotate behavior. + **/ + public MouseRotateY() { + super(0); + } + + /** + * Creates a rotate behavior. + * Note that this behavior still needs a transform + * group to work on (use setTransformGroup(tg)) and + * the transform group must add this behavior. + * @param flags interesting flags (wakeup conditions). + */ + public MouseRotateY(int flags) { + super(flags); + } + + public void initialize() { + super.initialize(); + y_angle = 0; + y_factor = .03; + if ((flags & INVERT_INPUT) == INVERT_INPUT) { + invert = true; + y_factor *= -1; + } + } + + public double getYFactor() { + return y_factor; + } + + public void setFactor( double factor) { + y_factor = factor; + + } + + + public void processStimulus (Enumeration criteria) { + WakeupCriterion wakeup; + AWTEvent[] event; + int id; + int dx; + + while (criteria.hasMoreElements()) { + wakeup = (WakeupCriterion) criteria.nextElement(); + if (wakeup instanceof WakeupOnAWTEvent) { + event = ((WakeupOnAWTEvent)wakeup).getAWTEvent(); + for (int i=0; i<event.length; i++) { + processMouseEvent((MouseEvent) event[i]); + + if (((buttonPress)&&((flags & MANUAL_WAKEUP) == 0)) || + ((wakeUp)&&((flags & MANUAL_WAKEUP) != 0))){ + + id = event[i].getID(); + if ((id == MouseEvent.MOUSE_DRAGGED) && + !((MouseEvent)event[i]).isMetaDown() && + !((MouseEvent)event[i]).isAltDown()){ + + x = ((MouseEvent)event[i]).getX(); + + dx = x - x_last; + + if (!reset){ + y_angle = dx * y_factor; + + transformY.rotY(y_angle); + + transformGroup.getTransform(currXform); + + //Vector3d translation = new Vector3d(); + //Matrix3f rotation = new Matrix3f(); + Matrix4d mat = new Matrix4d(); + + // Remember old matrix + currXform.get(mat); + + // Translate to origin + currXform.setTranslation(new Vector3d(0.0,0.0,0.0)); + if (invert) { + currXform.mul(currXform, transformX); + currXform.mul(currXform, transformY); + } else { + currXform.mul(transformX, currXform); + currXform.mul(transformY, currXform); + } + + // Set old translation back + Vector3d translation = new + Vector3d(mat.m03, mat.m13, mat.m23); + currXform.setTranslation(translation); + + // Update xform + transformGroup.setTransform(currXform); + } + else { + reset = false; + } + + x_last = x; + } + else if (id == MouseEvent.MOUSE_PRESSED) { + x_last = ((MouseEvent)event[i]).getX(); + } + } + } + } + } + + wakeupOn (mouseCriterion); + + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/oriented_shape3d/OrientedPtTest.java b/src/main/java/org/jdesktop/j3d/examples/oriented_shape3d/OrientedPtTest.java new file mode 100644 index 0000000..2810378 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/oriented_shape3d/OrientedPtTest.java @@ -0,0 +1,309 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.oriented_shape3d; + +import java.applet.Applet; +import java.awt.BorderLayout; +import java.awt.Font; + +import org.jdesktop.j3d.examples.Resources; +import org.jogamp.java3d.AmbientLight; +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.Background; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.DirectionalLight; +import org.jogamp.java3d.Font3D; +import org.jogamp.java3d.FontExtrusion; +import org.jogamp.java3d.Material; +import org.jogamp.java3d.OrientedShape3D; +import org.jogamp.java3d.Text3D; +import org.jogamp.java3d.TextureAttributes; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.utils.applet.MainFrame; +import org.jogamp.java3d.utils.behaviors.vp.OrbitBehavior; +import org.jogamp.java3d.utils.geometry.ColorCube; +import org.jogamp.java3d.utils.geometry.Cone; +import org.jogamp.java3d.utils.geometry.Cylinder; +import org.jogamp.java3d.utils.geometry.Sphere; +import org.jogamp.java3d.utils.image.TextureLoader; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.java3d.utils.universe.ViewingPlatform; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Point3f; +import org.jogamp.vecmath.Vector3d; +import org.jogamp.vecmath.Vector3f; + +public class OrientedPtTest extends Applet { + + // setup font stuff + private String fontName = "TestFont"; + private String textString = "OrientedShape3D"; + float sl = textString.length(); + + // paths to texture image files + private java.net.URL earthImage = null; + private java.net.URL stoneImage = null; + + private SimpleUniverse u; + + public BranchGroup createSceneGraph() { + + // Create the root of the branch graph + BranchGroup objRoot = new BranchGroup(); + + TransformGroup objScale = new TransformGroup(); + Transform3D textMat = new Transform3D(); + // Assuming uniform size chars, set scale to fit string in view + textMat.setScale(1.2/sl); + objScale.setTransform(textMat); + + + + // Create the transform group node and initialize it to the + // identity. Enable the TRANSFORM_WRITE capability so that + // our behavior code can modify it at runtime. Add it to the + // root of the subgraph. + TransformGroup objTrans = new TransformGroup(); + objTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + objTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_READ); + objRoot.addChild(objTrans); + + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + + Appearance apText = new Appearance(); + Material m = new Material(); + m.setLightingEnable(true); + apText.setMaterial(m); + + + Appearance apEarth= new Appearance(); + Material mm = new Material(); + mm.setLightingEnable(true); + apEarth.setMaterial(mm); + + Appearance apStone = new Appearance(); + apStone.setMaterial(mm); + +// create 3D text + Font3D f3d = new Font3D(new Font(fontName, Font.PLAIN, 2), + new FontExtrusion()); + Point3f textPt = new Point3f( -sl/2.0f, 3.0f, 0.0f); + Text3D txt = new Text3D(f3d, textString, textPt); + OrientedShape3D textShape = new OrientedShape3D(); + textShape.setGeometry(txt); + textShape.setAppearance(apText); + + textShape.setAlignmentMode(OrientedShape3D.ROTATE_ABOUT_POINT); + // text is centered around 0, 3, 0. Make it rotate around 0,5,0 + Point3f rotationPt = new Point3f(0.0f, 5.0f, 0.0f); + textShape.setRotationPoint(rotationPt); + objScale.addChild( textShape ); + + // also add a small Sphere at the rotation point to + // show that we are rotating around the right point + Sphere sphere = new Sphere(0.2f); + TransformGroup sphereGroup = new TransformGroup(); + Transform3D sphereXform = new Transform3D(); + sphereXform.set(new Vector3f(rotationPt)); + sphereGroup.setTransform(sphereXform); + sphereGroup.addChild(sphere); + objScale.addChild(sphereGroup); + + + // Create a simple shape leaf node, add it to the scene graph. + + Transform3D cubeMat = new Transform3D(); + TransformGroup cubeTrans = new TransformGroup(cubeMat); + cubeMat.set(new Vector3d(0.9, 0.0, -1.0)); + cubeTrans.setTransform(cubeMat); + cubeTrans.addChild(new ColorCube(0.3)); + objTrans.addChild(cubeTrans); + + TextureLoader stoneTex = new TextureLoader(stoneImage, new String("RGB"), + TextureLoader.BY_REFERENCE | TextureLoader.Y_UP, this); + if (stoneTex != null) apStone.setTexture(stoneTex.getTexture()); + + TextureAttributes texAttr = new TextureAttributes(); + texAttr.setTextureMode(TextureAttributes.REPLACE); + apStone.setTextureAttributes(texAttr); + + Transform3D coneMat = new Transform3D(); + TransformGroup coneTrans = new TransformGroup(coneMat); + coneMat.set(new Vector3d(0.0, 0.0, 0.0)); + coneTrans.setTransform(coneMat); + coneTrans.addChild(new Cone(.2f, 0.8f,Cone.GENERATE_NORMALS | + Cone.GENERATE_TEXTURE_COORDS | Cone.GENERATE_TEXTURE_COORDS_Y_UP, apStone)); + objTrans.addChild(coneTrans); + + TextureLoader earthTex = new TextureLoader(earthImage, new String("RGB"), + TextureLoader.BY_REFERENCE | TextureLoader.Y_UP, this); + if (earthTex != null) apEarth.setTexture(earthTex.getTexture()); + apEarth.setTextureAttributes(texAttr); + + Transform3D cylinderMat = new Transform3D(); + TransformGroup cylinderTrans = new TransformGroup(cylinderMat); + cylinderMat.set(new Vector3d(-0.9, 0.5, -1.0)); + cylinderTrans.setTransform(cylinderMat); + cylinderTrans.addChild(new Cylinder(.35f, 2.0f,Cylinder.GENERATE_NORMALS | + Cylinder.GENERATE_TEXTURE_COORDS | + Cylinder.GENERATE_TEXTURE_COORDS_Y_UP, apEarth)); + objTrans.addChild(cylinderTrans); + + objTrans.addChild(objScale); + + // Set up the background + Color3f bgColor = new Color3f(0.05f, 0.05f, 0.5f); + Background bgNode = new Background(bgColor); + bgNode.setApplicationBounds(bounds); + objRoot.addChild(bgNode); + + // Set up the ambient light + Color3f ambientColor = new Color3f(0.1f, 0.1f, 0.1f); + AmbientLight ambientLightNode = new AmbientLight(ambientColor); + ambientLightNode.setInfluencingBounds(bounds); + objRoot.addChild(ambientLightNode); + + // Set up the directional lights + Color3f light1Color = new Color3f(1.0f, 1.0f, 0.9f); + Vector3f light1Direction = new Vector3f(1.0f, 1.0f, 1.0f); + Color3f light2Color = new Color3f(1.0f, 1.0f, 0.9f); + Vector3f light2Direction = new Vector3f(-1.0f, -1.0f, -1.0f); + + DirectionalLight light1 + = new DirectionalLight(light1Color, light1Direction); + light1.setInfluencingBounds(bounds); + objRoot.addChild(light1); + + DirectionalLight light2 + = new DirectionalLight(light2Color, light2Direction); + light2.setInfluencingBounds(bounds); + objRoot.addChild(light2); + + apText.setMaterial(mm); + + // Have Java 3D perform optimizations on this scene graph. + objRoot.compile(); + + return objRoot; + } + + public OrientedPtTest() { + } + + public OrientedPtTest(java.net.URL earthURL, java.net.URL stoneURL) { + earthImage = earthURL; + stoneImage = stoneURL; + } + + public void init() {System.setProperty("sun.awt.noerasebackground", "true"); + // the paths to the image files for an applet + earthImage = Resources.getResource("resources/images/earth.jpg"); + if (earthImage == null) { + System.err.println("resources/images/earth.jpg not found"); + System.exit(1); + } + + stoneImage = Resources.getResource("resources/images/stone.jpg"); + if (stoneImage == null) { + System.err.println("resources/images/stone.jpg not found"); + System.exit(1); + } + + setLayout(new BorderLayout()); + Canvas3D c = new Canvas3D(SimpleUniverse.getPreferredConfiguration()); + add("Center", c); + + // Create a simple scene and attach it to the virtual universe + BranchGroup scene = createSceneGraph(); + u = new SimpleUniverse(c); + + // add mouse behaviors to the ViewingPlatform + ViewingPlatform viewingPlatform = u.getViewingPlatform(); + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + u.getViewingPlatform().setNominalViewingTransform(); + + // add orbit behavior to the viewing platform + OrbitBehavior orbit = new OrbitBehavior(c, OrbitBehavior.REVERSE_ALL); + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0, 0.0, 0.0), 100.0); + orbit.setSchedulingBounds(bounds); + viewingPlatform.setViewPlatformBehavior(orbit); + + u.addBranchGraph(scene); + } + + public void destroy() { + u.cleanup(); + } + + // + // The following allows OrientedPtTest to be run as an application + // as well as an applet + // + public static void main(String[] args) {System.setProperty("sun.awt.noerasebackground", "true"); + java.net.URL earthURL = null; + java.net.URL stoneURL = null; + earthURL = Resources.getResource("resources/images/earth.jpg"); + if (earthURL == null) { + System.err.println("resources/images/earth.jpg not found"); + System.exit(1); + } + + stoneURL = Resources.getResource("resources/images/stone.jpg"); + if (stoneURL == null) { + System.err.println("resources/images/stone.jpg not found"); + System.exit(1); + } + + new MainFrame(new OrientedPtTest(earthURL, stoneURL), 400, 400); + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/oriented_shape3d/OrientedTest.java b/src/main/java/org/jdesktop/j3d/examples/oriented_shape3d/OrientedTest.java new file mode 100644 index 0000000..0f062e1 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/oriented_shape3d/OrientedTest.java @@ -0,0 +1,329 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.oriented_shape3d; + +import java.applet.Applet; +import java.awt.BorderLayout; +import java.awt.Font; +import java.awt.GraphicsConfiguration; + +import org.jdesktop.j3d.examples.Resources; +import org.jogamp.java3d.AmbientLight; +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.Background; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.DirectionalLight; +import org.jogamp.java3d.Font3D; +import org.jogamp.java3d.FontExtrusion; +import org.jogamp.java3d.Material; +import org.jogamp.java3d.OrientedShape3D; +import org.jogamp.java3d.Text3D; +import org.jogamp.java3d.TextureAttributes; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.utils.applet.MainFrame; +import org.jogamp.java3d.utils.behaviors.mouse.MouseTranslate; +import org.jogamp.java3d.utils.behaviors.mouse.MouseZoom; +import org.jogamp.java3d.utils.geometry.ColorCube; +import org.jogamp.java3d.utils.geometry.Cone; +import org.jogamp.java3d.utils.geometry.Cylinder; +import org.jogamp.java3d.utils.image.TextureLoader; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.java3d.utils.universe.ViewingPlatform; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Point3f; +import org.jogamp.vecmath.Vector3d; +import org.jogamp.vecmath.Vector3f; + +public class OrientedTest extends Applet { + + // setup font stuff + private String fontName = "TestFont"; + private String textString = "OrientedShape3D"; + float sl = textString.length(); + + // paths to texture image files + private java.net.URL earthImage = null; + private java.net.URL stoneImage = null; + + private SimpleUniverse u = null; + + public BranchGroup createSceneGraph() { + + // Create the root of the branch graph + BranchGroup objRoot = new BranchGroup(); + + TransformGroup objScale = new TransformGroup(); + Transform3D textMat = new Transform3D(); + // Assuming uniform size chars, set scale to fit string in view + textMat.setScale(1.2/sl); + objScale.setTransform(textMat); + + + + // Create the transform group node and initialize it to the + // identity. Enable the TRANSFORM_WRITE capability so that + // our behavior code can modify it at runtime. Add it to the + // root of the subgraph. + TransformGroup objTrans = new TransformGroup(); + objTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + objTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_READ); + objRoot.addChild(objTrans); + + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + + Appearance apText = new Appearance(); + Material m = new Material(); + m.setLightingEnable(true); + apText.setMaterial(m); + + + Appearance apEarth= new Appearance(); + Material mm = new Material(); + mm.setLightingEnable(true); + apEarth.setMaterial(mm); + + Appearance apStone = new Appearance(); + apStone.setMaterial(mm); + +// create 3D text + Font3D f3d = new Font3D(new Font(fontName, Font.PLAIN, 2), + new FontExtrusion()); + Text3D txt = new Text3D(f3d, textString, + new Point3f( -sl/2.0f, 3.0f, 0.0f)); + OrientedShape3D textShape = new OrientedShape3D(); + textShape.setGeometry(txt); + textShape.setAppearance(apText); + textShape.setAlignmentAxis( 0.0f, 1.0f, 0.0f); + objScale.addChild( textShape ); + + + // Create a simple shape leaf node, add it to the scene graph. + + Transform3D cubeMat = new Transform3D(); + TransformGroup cubeTrans = new TransformGroup(cubeMat); + cubeMat.set(new Vector3d(0.9, 0.0, -1.0)); + cubeTrans.setTransform(cubeMat); + cubeTrans.addChild(new ColorCube(0.3)); + objTrans.addChild(cubeTrans); + + TextureLoader stoneTex = new TextureLoader(stoneImage, new String("RGB"), + TextureLoader.BY_REFERENCE | TextureLoader.Y_UP, this); + if (stoneTex != null) apStone.setTexture(stoneTex.getTexture()); + + TextureAttributes texAttr = new TextureAttributes(); + texAttr.setTextureMode(TextureAttributes.MODULATE); + apStone.setTextureAttributes(texAttr); + + + Transform3D coneMat = new Transform3D(); + TransformGroup coneTrans = new TransformGroup(coneMat); + coneMat.set(new Vector3d(0.0, 0.0, 0.0)); + coneTrans.setTransform(coneMat); + coneTrans.addChild(new Cone(.2f, 0.8f, Cone.GENERATE_NORMALS | + Cone.GENERATE_TEXTURE_COORDS | + Cone.GENERATE_TEXTURE_COORDS_Y_UP, apStone)); + objTrans.addChild(coneTrans); + + TextureLoader earthTex = new TextureLoader(earthImage, new String("RGB"), + TextureLoader.BY_REFERENCE | TextureLoader.Y_UP, this); + if (earthTex != null) apEarth.setTexture(earthTex.getTexture()); + + apEarth.setTextureAttributes(texAttr); + + Transform3D cylinderMat = new Transform3D(); + TransformGroup cylinderTrans = new TransformGroup(cylinderMat); + cylinderMat.set(new Vector3d(-0.9, 0.5, -1.0)); + cylinderTrans.setTransform(cylinderMat); + cylinderTrans.addChild(new Cylinder(.35f, 2.0f, Cylinder.GENERATE_NORMALS | + Cylinder.GENERATE_TEXTURE_COORDS | + Cylinder.GENERATE_TEXTURE_COORDS_Y_UP, apEarth)); + objTrans.addChild(cylinderTrans); + + objTrans.addChild(objScale); + + + + + // Set up the background + Color3f bgColor = new Color3f(0.05f, 0.05f, 0.5f); + Background bgNode = new Background(bgColor); + bgNode.setApplicationBounds(bounds); + objRoot.addChild(bgNode); + + // Set up the ambient light + Color3f ambientColor = new Color3f(0.1f, 0.1f, 0.1f); + AmbientLight ambientLightNode = new AmbientLight(ambientColor); + ambientLightNode.setInfluencingBounds(bounds); + objRoot.addChild(ambientLightNode); + + // Set up the directional lights + Color3f light1Color = new Color3f(1.0f, 1.0f, 0.9f); + Vector3f light1Direction = new Vector3f(1.0f, 1.0f, 1.0f); + Color3f light2Color = new Color3f(1.0f, 1.0f, 0.9f); + Vector3f light2Direction = new Vector3f(-1.0f, -1.0f, -1.0f); + + DirectionalLight light1 + = new DirectionalLight(light1Color, light1Direction); + light1.setInfluencingBounds(bounds); + objRoot.addChild(light1); + + DirectionalLight light2 + = new DirectionalLight(light2Color, light2Direction); + light2.setInfluencingBounds(bounds); + objRoot.addChild(light2); + + apText.setMaterial(mm); + + // Have Java 3D perform optimizations on this scene graph. + objRoot.compile(); + + return objRoot; + } + + public OrientedTest() { + } + + public OrientedTest(java.net.URL earthURL, java.net.URL stoneURL) { + earthImage = earthURL; + stoneImage = stoneURL; + } + + public void init() {System.setProperty("sun.awt.noerasebackground", "true"); + // the paths to the image files for an applet + earthImage = Resources.getResource("resources/images/earth.jpg"); + if (earthImage == null) { + System.err.println("resources/images/earth.jpg not found"); + System.exit(1); + } + + stoneImage = Resources.getResource("resources/images/stone.jpg"); + if (stoneImage == null) { + System.err.println("resources/images/stone.jpg not found"); + System.exit(1); + } + + setLayout(new BorderLayout()); + GraphicsConfiguration config = + SimpleUniverse.getPreferredConfiguration(); + + Canvas3D c = new Canvas3D(config); + add("Center", c); + + // Create a simple scene and attach it to the virtual universe + BranchGroup scene = createSceneGraph(); + u = new SimpleUniverse(c, 4); + + // add mouse behaviors to ViewingPlatform + ViewingPlatform viewingPlatform = u.getViewingPlatform(); + + // there is a special rotate behavior, so can't use the utility + // method + MouseRotateY rotate = new MouseRotateY(MouseRotateY.INVERT_INPUT); + rotate.setTransformGroup(viewingPlatform.getMultiTransformGroup(). + getTransformGroup(0)); + BranchGroup rotateBG = new BranchGroup(); + rotateBG.addChild(rotate); + viewingPlatform.addChild(rotateBG); + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + rotate.setSchedulingBounds(bounds); + + MouseZoom zoom = + new MouseZoom(c, MouseZoom.INVERT_INPUT); + zoom.setTransformGroup(viewingPlatform.getMultiTransformGroup(). + getTransformGroup(1)); + zoom.setSchedulingBounds(bounds); + BranchGroup zoomBG = new BranchGroup(); + zoomBG.addChild(zoom); + viewingPlatform.addChild(zoomBG); + + MouseTranslate translate = + new MouseTranslate(c, MouseTranslate.INVERT_INPUT); + translate.setTransformGroup(viewingPlatform.getMultiTransformGroup(). + getTransformGroup(2)); + translate.setSchedulingBounds(bounds); + BranchGroup translateBG = new BranchGroup(); + translateBG.addChild(translate); + viewingPlatform.addChild(translateBG); + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + u.getViewingPlatform().setNominalViewingTransform(); + + u.addBranchGraph(scene); + } + + public void destroy() { + u.cleanup(); + } + + // + // The following allows OrientedTest to be run as an application + // as well as an applet + // + public static void main(String[] args) {System.setProperty("sun.awt.noerasebackground", "true"); + java.net.URL earthURL = null; + java.net.URL stoneURL = null; + + earthURL = Resources.getResource("resources/images/earth.jpg"); + if (earthURL == null) { + System.err.println("resources/images/earth.jpg not found"); + System.exit(1); + } + + stoneURL = Resources.getResource("resources/images/stone.jpg"); + if (stoneURL == null) { + System.err.println("resources/images/stone.jpg not found"); + System.exit(1); + } + + new MainFrame(new OrientedTest(earthURL, stoneURL), 400, 400); + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/overlay2d/Canvas3D2D.java b/src/main/java/org/jdesktop/j3d/examples/overlay2d/Canvas3D2D.java new file mode 100644 index 0000000..f0e20cb --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/overlay2d/Canvas3D2D.java @@ -0,0 +1,60 @@ +/*
+ * Copyright (c) 2016 JogAmp Community. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation. Sun designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Sun in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ */
+
+package org.jdesktop.j3d.examples.overlay2d;
+
+import java.awt.GraphicsConfiguration;
+
+import org.jogamp.java3d.Canvas3D;
+import org.jogamp.java3d.J3DGraphics2D;
+
+/**
+ * This is an extension to the Canvas3D with the postRender method overridden to draw some things on the
+ * 2DGraphics of the Canvas3D
+ */
+public class Canvas3D2D extends Canvas3D
+{
+
+ public Canvas3D2D(GraphicsConfiguration gc)
+ {
+ super(gc);
+ }
+
+ @Override
+ public void postRender()
+ {
+ J3DGraphics2D g = getGraphics2D();
+
+ // draw a cross hair
+ g.drawLine((this.getWidth() / 2) - 5, (this.getHeight() / 2), (this.getWidth() / 2) + 5, (this.getHeight() / 2));
+ g.drawLine((this.getWidth() / 2), (this.getHeight() / 2) - 5, (this.getWidth() / 2), (this.getHeight() / 2) + 5);
+
+ g.drawString("This is an example String", 50, 20);
+
+ // etc e.g.
+ //g.drawImage(getBufferedImage(), 10, 50, null);
+
+ g.flush(false);
+
+ }
+
+}
\ No newline at end of file diff --git a/src/main/java/org/jdesktop/j3d/examples/overlay2d/Overlay2D.java b/src/main/java/org/jdesktop/j3d/examples/overlay2d/Overlay2D.java new file mode 100644 index 0000000..adf4d8f --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/overlay2d/Overlay2D.java @@ -0,0 +1,201 @@ +/* + * Copyright (c) 2016 JogAmp Community. All rights reserved. + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * This code is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 only, as + * published by the Free Software Foundation. Sun designates this + * particular file as subject to the "Classpath" exception as provided + * by Sun in the LICENSE file that accompanied this code. + * + * This code is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + * version 2 for more details (a copy is included in the LICENSE file that + * accompanied this code). + * + * You should have received a copy of the GNU General Public License version + * 2 along with this work; if not, write to the Free Software Foundation, + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. + * + */ + +package org.jdesktop.j3d.examples.overlay2d; + +import java.awt.GraphicsConfiguration; +import java.net.URL; + +import org.jdesktop.j3d.examples.Resources; +import org.jogamp.java3d.Alpha; +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.GeometryArray; +import org.jogamp.java3d.PolygonAttributes; +import org.jogamp.java3d.RotationInterpolator; +import org.jogamp.java3d.Shape3D; +import org.jogamp.java3d.Texture; +import org.jogamp.java3d.TextureAttributes; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.TriangleArray; +import org.jogamp.java3d.utils.image.TextureLoader; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Point3f; +import org.jogamp.vecmath.TexCoord2f; +import org.jogamp.vecmath.Vector3f; + +/** + * Simple Java 3D example program to show use of the 2DGraphics overlay. + */ +public class Overlay2D extends javax.swing.JFrame +{ + + private SimpleUniverse univ = null; + private BranchGroup scene = null; + + public BranchGroup createSceneGraph() + { + final BranchGroup objRoot = new BranchGroup(); + + // Create a triangle with each point a different color. Remember to + // draw the points in counter-clockwise order. That is the default + // way of determining which is the front of a polygon. + // o (1) + // / \ + // / \ + // (2) o-----o (0) + Shape3D shape = new Shape3D(); + TriangleArray tri = new TriangleArray(3, GeometryArray.COORDINATES | GeometryArray.COLOR_3 | GeometryArray.TEXTURE_COORDINATE_2); + tri.setCoordinate(0, new Point3f(0.5f, 0.0f, 0.0f)); + tri.setCoordinate(1, new Point3f(0.0f, 0.5f, 0.0f)); + tri.setCoordinate(2, new Point3f(-0.5f, 0.0f, 0.0f)); + tri.setColor(0, new Color3f(1.0f, 0.0f, 0.0f)); + tri.setColor(1, new Color3f(0.0f, 1.0f, 0.0f)); + tri.setColor(2, new Color3f(0.0f, 0.0f, 1.0f)); + tri.setTextureCoordinate(0, 0, new TexCoord2f(1.0f, 0.0f)); + tri.setTextureCoordinate(0, 1, new TexCoord2f(0.0f, 1.0f)); + tri.setTextureCoordinate(0, 2, new TexCoord2f(0.0f, 0.0f)); + + // Because we're about to spin this triangle, be sure to draw + // backfaces. If we don't, the back side of the triangle is invisible. + Appearance ap = new Appearance(); + PolygonAttributes pa = new PolygonAttributes(); + pa.setCullFace(PolygonAttributes.CULL_NONE); + ap.setPolygonAttributes(pa); + + // Add a transformed texture to the cube, for interest sake + URL earthURL = Resources.getResource("resources/images/earth.jpg"); + Texture earthTex = new TextureLoader(earthURL, this).getTexture(); + ap.setTexture(earthTex); + + TextureAttributes textureAttributes = new TextureAttributes(); + Transform3D textureTransform = new Transform3D(); + textureTransform.rotZ(Math.PI / 3f); + textureTransform.setTranslation(new Vector3f(10, 1, 0)); + textureAttributes.setTextureTransform(textureTransform); + + ap.setTextureAttributes(textureAttributes); + + shape.setAppearance(ap); + + // Set up a simple RotationInterpolator + BoundingSphere bounds = new BoundingSphere(new Point3d(0.0, 0.0, 0.0), 5.0); + TransformGroup tg = new TransformGroup(); + Transform3D yAxis = new Transform3D(); + Alpha rotationAlpha = new Alpha(-1, 4000); + tg.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + RotationInterpolator rotator = new RotationInterpolator(rotationAlpha, tg, yAxis, 0.0f, (float) Math.PI * 2.0f); + rotator.setSchedulingBounds(bounds); + + shape.setGeometry(tri); + tg.addChild(rotator); + tg.addChild(shape); + objRoot.addChild(tg); + objRoot.compile(); + return objRoot; + + } + + private Canvas3D2D createUniverse() + { + // Get the preferred graphics configuration for the default screen + GraphicsConfiguration config = SimpleUniverse.getPreferredConfiguration(); + + // Create a Canvas3D using the preferred configuration + Canvas3D2D c = new Canvas3D2D(config); + + // Create simple universe with view branch + univ = new SimpleUniverse(c); + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + univ.getViewingPlatform().setNominalViewingTransform(); + + // Ensure at least 5 msec per frame (i.e., < 200Hz) + univ.getViewer().getView().setMinimumFrameCycleTime(5); + + return c; + } + + public Overlay2D() + { + // Initialize the GUI components + initComponents(); + + // Create Canvas3D and SimpleUniverse; add canvas to drawing panel + Canvas3D2D c = createUniverse(); + drawingPanel.add(c, java.awt.BorderLayout.CENTER); + + // Create the content branch and add it to the universe + scene = createSceneGraph(); + univ.addBranchGraph(scene); + } + + // ---------------------------------------------------------------- + + /** This method is called from within the constructor to + * initialize the form. + * WARNING: Do NOT modify this code. The content of this method is + * always regenerated by the Form Editor. + */ + // <editor-fold defaultstate="collapsed" desc=" Generated Code ">//GEN-BEGIN:initComponents + private void initComponents() + { + drawingPanel = new javax.swing.JPanel(); + + setDefaultCloseOperation(javax.swing.WindowConstants.EXIT_ON_CLOSE); + setTitle("Overlay2D"); + drawingPanel.setLayout(new java.awt.BorderLayout()); + + drawingPanel.setPreferredSize(new java.awt.Dimension(250, 250)); + getContentPane().add(drawingPanel, java.awt.BorderLayout.CENTER); + + pack(); + }// </editor-fold>//GEN-END:initComponents + + /** + * @param args the command line arguments + */ + public static void main(String args[]) + { + + System.setProperty("sun.awt.noerasebackground", "true"); + //System.setProperty("j3d.rend", "jogl2es2"); + + java.awt.EventQueue.invokeLater(new Runnable() { + @Override + public void run() + { + new Overlay2D().setVisible(true); + } + }); + } + + // Variables declaration - do not modify//GEN-BEGIN:variables + private javax.swing.JPanel drawingPanel; + // End of variables declaration//GEN-END:variables + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/package_info/PackageInfo.form b/src/main/java/org/jdesktop/j3d/examples/package_info/PackageInfo.form new file mode 100644 index 0000000..a82c39c --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/package_info/PackageInfo.form @@ -0,0 +1,45 @@ +<?xml version="1.0" encoding="UTF-8" ?> + +<Form version="1.0" type="org.netbeans.modules.form.forminfo.JFrameFormInfo"> + <Properties> + <Property name="defaultCloseOperation" type="int" value="3"/> + <Property name="title" type="java.lang.String" value="Package Info"/> + </Properties> + <SyntheticProperties> + <SyntheticProperty name="formSizePolicy" type="int" value="1"/> + </SyntheticProperties> + <AuxValues> + <AuxValue name="FormSettings_generateMnemonicsCode" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_listenerGenerationStyle" type="java.lang.Integer" value="0"/> + <AuxValue name="FormSettings_variablesLocal" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_variablesModifier" type="java.lang.Integer" value="2"/> + <AuxValue name="designerSize" type="java.awt.Dimension" value="-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,1,44,0,0,1,-112"/> + </AuxValues> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + <SubComponents> + <Container class="javax.swing.JScrollPane" name="jScrollPane1"> + <Properties> + <Property name="preferredSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor"> + <Dimension value="[400, 400]"/> + </Property> + </Properties> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout" value="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription"> + <BorderConstraints direction="Center"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.support.JScrollPaneSupportLayout"/> + <SubComponents> + <Component class="javax.swing.JTextArea" name="myTextArea"> + <Properties> + <Property name="columns" type="int" value="20"/> + <Property name="editable" type="boolean" value="false"/> + <Property name="rows" type="int" value="5"/> + </Properties> + </Component> + </SubComponents> + </Container> + </SubComponents> +</Form> diff --git a/src/main/java/org/jdesktop/j3d/examples/package_info/PackageInfo.java b/src/main/java/org/jdesktop/j3d/examples/package_info/PackageInfo.java new file mode 100644 index 0000000..d44e2a9 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/package_info/PackageInfo.java @@ -0,0 +1,139 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.package_info; + +import javax.swing.JTextArea; + +public class PackageInfo extends javax.swing.JFrame { + + private void pkgInfo(JTextArea textArea, + ClassLoader classLoader, + String pkgName, + String className) { + + try { + classLoader.loadClass(pkgName + "." + className); + + Package p = Package.getPackage(pkgName); + if (p == null) { + textArea.append("WARNING: Package.getPackage(" + + pkgName + + ") is null\n"); + } else { + textArea.append(p.toString() + "\n"); + textArea.append("Specification Title = " + + p.getSpecificationTitle() + "\n"); + textArea.append("Specification Vendor = " + + p.getSpecificationVendor() + "\n"); + textArea.append("Specification Version = " + + p.getSpecificationVersion() + "\n"); + + textArea.append("Implementation Vendor = " + + p.getImplementationVendor() + "\n"); + textArea.append("Implementation Version = " + + p.getImplementationVersion() + "\n"); + } + } catch (ClassNotFoundException e) { + textArea.append("Unable to load " + pkgName + "\n"); + } + + textArea.append("\n"); + } + + /** + * Creates new form PackageInfo + */ + public PackageInfo() { + initComponents(); + + ClassLoader classLoader = getClass().getClassLoader(); + + pkgInfo(myTextArea, classLoader, "org.jogamp.vecmath", "Point3d"); + pkgInfo(myTextArea, classLoader, "org.jogamp.java3d", "SceneGraphObject"); + pkgInfo(myTextArea, classLoader, "com.sun.j3d.utils.universe", "SimpleUniverse"); + } + + // ---------------------------------------------------------------- + + /** This method is called from within the constructor to + * initialize the form. + * WARNING: Do NOT modify this code. The content of this method is + * always regenerated by the Form Editor. + */ + // <editor-fold defaultstate="collapsed" desc=" Generated Code ">//GEN-BEGIN:initComponents + private void initComponents() { + jScrollPane1 = new javax.swing.JScrollPane(); + myTextArea = new javax.swing.JTextArea(); + + setDefaultCloseOperation(javax.swing.WindowConstants.EXIT_ON_CLOSE); + setTitle("Package Info"); + jScrollPane1.setPreferredSize(new java.awt.Dimension(400, 400)); + myTextArea.setColumns(20); + myTextArea.setEditable(false); + myTextArea.setRows(5); + jScrollPane1.setViewportView(myTextArea); + + getContentPane().add(jScrollPane1, java.awt.BorderLayout.CENTER); + + pack(); + }// </editor-fold>//GEN-END:initComponents + + /** + * @param args the command line arguments + */ + public static void main(String args[]) {System.setProperty("sun.awt.noerasebackground", "true"); + java.awt.EventQueue.invokeLater(new Runnable() { + public void run() { + new PackageInfo().setVisible(true); + } + }); + } + + // Variables declaration - do not modify//GEN-BEGIN:variables + private javax.swing.JScrollPane jScrollPane1; + private javax.swing.JTextArea myTextArea; + // End of variables declaration//GEN-END:variables + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/package_info/QueryProperties.form b/src/main/java/org/jdesktop/j3d/examples/package_info/QueryProperties.form new file mode 100644 index 0000000..daef961 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/package_info/QueryProperties.form @@ -0,0 +1,44 @@ +<?xml version="1.0" encoding="UTF-8" ?> + +<Form version="1.0" type="org.netbeans.modules.form.forminfo.JFrameFormInfo"> + <Properties> + <Property name="defaultCloseOperation" type="int" value="3"/> + <Property name="title" type="java.lang.String" value="QueryProperties"/> + </Properties> + <SyntheticProperties> + <SyntheticProperty name="formSizePolicy" type="int" value="1"/> + </SyntheticProperties> + <AuxValues> + <AuxValue name="FormSettings_generateMnemonicsCode" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_listenerGenerationStyle" type="java.lang.Integer" value="0"/> + <AuxValue name="FormSettings_variablesLocal" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_variablesModifier" type="java.lang.Integer" value="2"/> + </AuxValues> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + <SubComponents> + <Container class="javax.swing.JScrollPane" name="jScrollPane1"> + <Properties> + <Property name="preferredSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor"> + <Dimension value="[400, 500]"/> + </Property> + </Properties> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout" value="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription"> + <BorderConstraints direction="Center"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.support.JScrollPaneSupportLayout"/> + <SubComponents> + <Component class="javax.swing.JTextArea" name="myTextArea"> + <Properties> + <Property name="columns" type="int" value="20"/> + <Property name="editable" type="boolean" value="false"/> + <Property name="rows" type="int" value="5"/> + </Properties> + </Component> + </SubComponents> + </Container> + </SubComponents> +</Form> diff --git a/src/main/java/org/jdesktop/j3d/examples/package_info/QueryProperties.java b/src/main/java/org/jdesktop/j3d/examples/package_info/QueryProperties.java new file mode 100644 index 0000000..16a3116 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/package_info/QueryProperties.java @@ -0,0 +1,203 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.package_info; + +import java.awt.GraphicsConfiguration; +import java.awt.GraphicsEnvironment; +import java.util.ArrayList; +import java.util.Collections; +import java.util.HashSet; +import java.util.Iterator; +import java.util.List; +import java.util.Map; + +import javax.swing.JTextArea; + +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.GraphicsConfigTemplate3D; +import org.jogamp.java3d.VirtualUniverse; + +public class QueryProperties extends javax.swing.JFrame { + + public static void printProps(JTextArea textArea, Map map, String[] propList) { + // Create an alphabetical list of keys + List keyList = new ArrayList(map.keySet()); + Collections.sort(keyList); + Iterator it; + + // Collection used to remember the properties we've already + // printed, so we don't print them twice + HashSet hs = new HashSet(); + + // Print out the values for the caller-specified properties + String key; + for (int i = 0; i < propList.length; i++) { + int len = propList[i].length(); + int idxWild = propList[i].indexOf('*'); + if (idxWild < 0) { + key = propList[i]; + if (!hs.contains(key)) { + textArea.append(key + " = " + map.get(key) + "\n"); + hs.add(key); + } + } + else if (idxWild == len-1) { + String pattern = propList[i].substring(0, len-1); + it = keyList.iterator(); + while (it.hasNext()) { + key = (String)it.next(); + if (key.startsWith(pattern) && !hs.contains(key)) { + textArea.append(key + " = " + map.get(key) + "\n"); + hs.add(key); + } + } + } + else { + textArea.append(propList[i] + + " = ERROR: KEY WITH EMBEDDED WILD CARD IGNORED\n"); + } + } + + // Print out the values for those properties not already printed + it = keyList.iterator(); + while (it.hasNext()) { + key = (String)it.next(); + if (!hs.contains(key)) { + textArea.append(key + " = " + map.get(key) + "\n"); + } + } + + } + + /** Creates new form QueryProperties */ + public QueryProperties() { + initComponents(); + + VirtualUniverse vu = new VirtualUniverse(); + Map vuMap = vu.getProperties(); + final String[] vuPropList = { + "j3d.version", + "j3d.vendor", + "j3d.specification.version", + "j3d.specification.vendor", + "j3d.*" + // Just print all other properties in alphabetical order + }; + + printProps(myTextArea, vuMap, vuPropList); + myTextArea.append("\n"); + + GraphicsConfigTemplate3D template = new GraphicsConfigTemplate3D(); + + /* We need to set this to force choosing a pixel format + that support the canvas. + */ + template.setStereo(template.PREFERRED); + template.setSceneAntialiasing(template.PREFERRED); + + GraphicsConfiguration config = + GraphicsEnvironment.getLocalGraphicsEnvironment(). + getDefaultScreenDevice().getBestConfiguration(template); + + Map c3dMap = new Canvas3D(config).queryProperties(); + final String[] c3dPropList = { + "native.*", + "doubleBufferAvailable", + "stereoAvailable", + "sceneAntialiasing*", + "compressedGeometry.majorVersionNumber", + "compressedGeometry.minorVersionNumber", + "compressedGeometry.*", + "textureUnitStateMax", + "textureWidthMax", + "textureHeightMax", + // Just print all other properties in alphabetical order + }; + + printProps(myTextArea, c3dMap, c3dPropList); + } + + // ---------------------------------------------------------------- + + /** This method is called from within the constructor to + * initialize the form. + * WARNING: Do NOT modify this code. The content of this method is + * always regenerated by the Form Editor. + */ + // <editor-fold defaultstate="collapsed" desc=" Generated Code ">//GEN-BEGIN:initComponents + private void initComponents() { + jScrollPane1 = new javax.swing.JScrollPane(); + myTextArea = new javax.swing.JTextArea(); + + setDefaultCloseOperation(javax.swing.WindowConstants.EXIT_ON_CLOSE); + setTitle("QueryProperties"); + jScrollPane1.setPreferredSize(new java.awt.Dimension(400, 500)); + myTextArea.setColumns(20); + myTextArea.setEditable(false); + myTextArea.setRows(5); + jScrollPane1.setViewportView(myTextArea); + + getContentPane().add(jScrollPane1, java.awt.BorderLayout.CENTER); + + pack(); + }// </editor-fold>//GEN-END:initComponents + + /** + * @param args the command line arguments + */ + public static void main(String args[]) {System.setProperty("sun.awt.noerasebackground", "true"); + java.awt.EventQueue.invokeLater(new Runnable() { + public void run() { + new QueryProperties().setVisible(true); + } + }); + } + + // Variables declaration - do not modify//GEN-BEGIN:variables + private javax.swing.JScrollPane jScrollPane1; + private javax.swing.JTextArea myTextArea; + // End of variables declaration//GEN-END:variables + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/picking/BoltCG.java b/src/main/java/org/jdesktop/j3d/examples/picking/BoltCG.java new file mode 100644 index 0000000..44db05f --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/picking/BoltCG.java @@ -0,0 +1,359 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.picking; + +import org.jogamp.java3d.CompressedGeometry; +import org.jogamp.java3d.CompressedGeometryHeader; + +class BoltCG extends CompressedGeometry { + + BoltCG() { + super(cgHeader, cgData) ; + } + + private static final byte cgData[] = { + 25, 0, -120, 16, -124, 64, 33, -35, + 0, 67, 60, 48, -121, 90, 1, 3, + 116, -62, 25, 105, -60, 60, -32, 8, + 5, -58, 16, -9, -114, 32, -1, -104, + 67, 16, 0, -117, -128, 97, 40, 62, + -62, -128, -122, 5, 67, 48, 10, -76, + -32, 21, 1, 6, 40, 10, -128, 86, + -123, 24, -96, 76, 65, 74, 88, 2, + -117, -80, -59, 21, 113, -118, -40, -28, + 21, 110, 6, 40, 27, 64, 81, 23, + -124, -7, 47, 54, 13, -3, -4, 69, + 40, 25, -69, -99, -123, 64, 8, 48, + 3, 64, 16, 23, 16, 97, -39, 8, + -20, -125, 0, 36, 2, 1, -123, 2, + 8, -120, 48, 27, 122, 91, 65, -67, + 108, 18, 26, 13, -12, -35, 95, -48, + 107, 63, -5, 91, -46, 12, 84, -44, + -53, -120, 54, -45, -98, 115, 64, -69, + 92, 126, -55, 1, 6, -80, 34, -49, + -24, 53, -30, 61, -19, 9, 6, -76, + 10, -115, -24, 53, 87, -54, -2, -127, + 113, 68, -15, -33, 16, 97, -9, 113, + -54, -30, 12, 75, 34, -48, -48, 107, + 86, -32, -10, -125, 97, -42, 19, -78, + 12, 0, -48, 4, 4, 68, 8, 12, + -67, -69, 32, -64, 9, 0, 0, 92, + 65, -121, 116, 42, 10, 13, 98, -52, + -97, 16, 34, 104, 114, 75, 66, 12, + -45, 11, -82, 32, -34, -74, -127, -15, + 6, 74, 51, 70, -81, 32, -42, 27, + 105, 13, 6, -97, 13, 111, -24, 22, + -12, 22, -19, -95, 6, -49, -85, -48, + 16, 107, 2, 44, -8, -125, 6, 73, + -123, -97, 16, 37, 40, 68, -22, -30, + 12, 58, 97, 80, -112, 104, -16, -104, + -72, -125, 122, -38, 22, -12, 25, -114, + -39, 124, 64, -111, -115, -112, -49, -24, + 53, -34, 85, -23, 5, 6, -82, -26, + 15, 104, 54, 1, -31, 62, 32, 68, + -17, 100, -58, 84, 27, 33, -54, -66, + -125, 55, -2, -89, 32, -119, 122, -73, + -25, -36, 105, -128, 8, 53, -128, 2, + 76, -71, 9, -56, -128, 30, 112, -59, + -48, 96, -37, 0, 0, 0, 9, -112, + 28, -117, 100, 64, 127, 58, 113, -58, + 13, 96, 0, -109, 46, 70, 50, 80, + 103, -88, 56, -86, 13, 96, 0, -109, + 46, 67, 114, -112, 95, -74, 49, 84, + 49, -74, -72, 15, 96, 2, 80, 6, + 55, 80, 0, -36, 82, 0, 40, 3, + 108, 1, -58, -95, -63, -84, 0, 18, + 101, -56, -74, 87, 10, 56, 39, 31, + -32, -43, -32, 9, 50, -28, 87, 46, + -125, 28, -61, -117, -48, 107, 0, 4, + -103, 114, 19, -105, -65, -98, 117, -60, + 32, -63, -84, 0, 18, 101, -116, -74, + 45, 1, -15, 1, -57, 0, -29, -116, + 26, -64, 1, 38, 92, -116, 101, 111, + 79, 124, 113, 83, -6, -68, 8, 37, + -36, -83, -4, -93, -4, 109, 46, 55, + 6, -81, 0, 73, -105, 33, -71, 63, + -57, -40, -36, 82, 28, 26, -64, 1, + 38, 92, -117, 100, -113, 71, 71, 113, + -2, 13, 96, 0, -109, 46, 69, 114, + 47, -41, -99, -72, -67, 6, -80, 0, + 73, -107, -63, 72, -64, -113, -83, 99, + 72, 53, 97, -6, 65, 57, -67, 60, + -38, -26, -63, -78, 105, 11, 112, 85, + 110, 101, -95, 58, -128, 16, 107, -125, + 90, -60, 3, 0, 0, 1, 0, 32, + 64, 67, -32, -54, -41, -103, 113, 6, + -55, -92, 45, -63, 85, -71, -106, -34, + -22, 0, 55, -79, -36, -28, 62, -95, + -68, 97, -73, -41, -70, -122, -13, 117, + -50, 94, -22, 32, 80, 21, 77, -39, + 6, 0, 48, 6, 2, 10, 13, 61, + 106, -104, 80, 32, -68, -125, 64, -75, + 100, 17, 91, -78, 90, -67, -42, 24, + 55, 27, -39, 61, 0, -56, 63, -40, + -71, -95, -124, 49, 74, 37, 3, 7, + -83, 118, -18, 13, -79, 30, -96, -126, + 80, 77, 53, 19, -32, -47, -121, -103, + 104, -122, 82, 89, -19, 56, 92, 45, + -96, -73, 42, -128, 16, 109, -120, -11, + 4, 18, -126, 105, -88, 126, 70, -127, + -56, -24, 48, -43, -36, 20, -25, -48, + -60, -115, -4, -98, -42, -31, -84, 8, + -35, -13, 59, -96, -36, 11, 1, 64, + 69, 65, -126, 80, -85, 10, 4, 22, + -48, 97, 109, -42, -114, 71, 112, -106, + -58, -51, 6, 104, 48, 82, 8, -19, + -74, -36, -81, -100, -56, -122, 85, 34, + -111, -37, 125, -83, 103, 65, -89, 125, + -30, -15, 36, -20, -5, 81, -63, 68, + 27, -17, -89, -83, 3, -63, -89, 33, + -24, 66, 0, 7, 50, 45, 2, -56, + 17, 6, -99, -9, -117, -60, -109, -77, + -19, 122, 5, 14, 96, 110, 114, 71, + -92, 117, 39, 107, 93, -50, 105, 49, + 110, -75, 80, 46, -125, -68, -18, -125, + 80, 60, 10, 1, -111, 6, -76, 10, + 48, -96, 65, 105, 6, -120, 27, 8, + 68, -77, -109, -59, 90, -64, 16, 106, + -61, -12, -26, 17, 26, 10, 54, -53, + 40, -88, 1, 6, -14, 124, 52, 32, + -39, 13, -117, 66, 13, 63, -111, -80, + -96, 65, 117, 6, 103, -11, -120, 104, + 54, -49, 116, 92, 65, -102, -84, -125, + 50, 12, 87, -109, 67, 64, -124, 106, + -22, -22, 12, 28, -24, -48, -48, 109, + 94, -22, -48, -125, 10, -96, 75, -120, + 17, 39, -119, 104, 65, -92, -110, 68, + 36, 27, 99, -87, -73, -96, -56, -42, + -85, 18, 12, 8, 3, -22, 0, 28, + 1, 120, 34, -112, -6, -81, 52, -64, + 4, 24, -88, 0, 0, 14, 0, -104, + 39, 32, 44, 23, -98, -125, 6, 44, + 0, 0, 3, -128, 38, 22, -56, 95, + 13, -25, 24, 49, 80, 0, 0, 28, + 1, 48, -58, -28, -38, -113, 42, -125, + 21, 0, 0, 1, -80, 19, 70, -24, + 73, -46, -13, 80, -32, -59, 64, 0, + 0, 108, 7, -94, -37, -127, -1, 30, + 127, -125, 21, 0, 0, 1, -64, 30, + -118, -18, -124, -124, 121, 122, 12, 84, + 0, 0, 7, 0, 78, 19, -81, -32, + 99, -56, 65, -125, 22, 0, 0, 1, + -64, 30, 11, 110, 64, 117, 0, 0, + 2, -106, 48, 106, 2, 56, -102, 99, + 126, 15, 53, 37, 65, -81, -8, -30, + 104, -36, -75, -8, -98, 82, 28, 24, + -88, 0, 0, 13, -128, -104, 91, 93, + -20, -41, -97, -32, -59, 64, 0, 0, + 112, 7, -94, -69, 31, 56, -98, 94, + -125, 21, 0, 0, 1, -64, 24, 77, + -96, -39, -12, 65, -125, 41, 86, -79, + 58, 14, -56, 87, 102, -112, 105, -50, + 18, -42, 11, 91, 10, -54, -9, 6, + 61, -1, -87, 3, 51, 55, -14, 86, + 108, 80, 111, -5, -18, -110, 55, 34, + 112, -43, 114, -123, 6, 1, 63, 9, + 32, -11, 21, 28, 87, 36, 4, 32, + -56, 83, -3, 36, -82, -1, -60, -86, + -31, -63, -88, -40, 98, 73, -99, -72, + 71, 27, 59, 6, 3, 38, -110, 12, + 111, -92, 4, -39, -8, 49, -111, 74, + -112, 51, 28, -18, -90, -64, 37, 6, + 80, -54, -38, -51, 106, -93, 73, -80, + 5, 8, 50, 119, 84, -116, 47, 110, + 123, -10, -60, 45, 6, 45, 104, 81, + -116, 106, 15, 126, -40, -40, 48, 101, + 42, -30, 109, 90, -16, 69, 123, -81, + -47, 6, 112, 0, 0, 9, 1, 4, + 78, 1, 17, -114, -67, 6, 12, -32, + 0, 0, 18, 2, 9, 108, -111, -28, + 29, 113, -125, 56, 0, 0, 4, -128, + -124, 99, 119, 92, 87, 85, 65, -100, + 0, 0, 2, 64, 106, 53, -112, 31, + 101, -80, 30, 13, -35, -80, 85, -86, + -95, -63, -109, -1, 117, -46, -38, 46, + -94, -70, 127, 6, -112, 0, 0, 119, + 1, 124, -82, 39, 15, 46, -113, 65, + -92, 0, 0, 29, -128, 127, 19, -67, + -4, -112, -82, -127, 6, 13, 40, 0, + 0, -18, 2, -15, 108, -81, -40, 29, + 49, -125, 72, 0, 0, 59, 0, -70, + 99, 9, -61, -106, -91, 65, -112, 31, + 102, -44, 27, 62, -118, 116, 65, -92, + 0, 0, 29, -64, 117, 65, -100, 0, + 0, 2, 64, 122, 27, -111, -127, -35, + -75, 33, -63, -80, 8, -92, 34, -40, + -52, 86, -70, -1, 6, 108, 0, 0, + 10, 1, 4, -82, 122, 114, -114, -81, + 65, -100, 0, 0, 2, 64, 115, 26, + -113, -107, -98, -115, -46, -95, -63, -71, + 0, 0, 28, -128, 87, 65, -123, -57, + -69, -22, 12, 4, 9, -32, 118, 65, + -128, 24, 7, -128, -96, -127, 27, -128, + 101, -12, 27, 36, 13, -93, -96, -50, + -29, 89, -31, 6, -114, 0, 0, 29, + -96, 48, -96, 65, -7, 6, -4, 72, + 30, -79, 32, -56, 32, 59, -32, 60, + 96, 23, -48, 110, -124, 50, -80, -127, + 116, -126, -89, 100, 25, -128, 0, 120, + 15, 72, 51, 119, -74, 52, 32, -38, + -8, -94, -70, 5, 65, -123, 30, 16, + 104, -96, 0, 1, -36, 3, 42, 13, + -1, 127, 124, 26, -122, -64, 5, -22, + -4, 74, 12, 0, 68, -102, -48, 99, + 117, 1, 73, 6, -72, -55, -17, -120, + 54, 115, -83, -3, 73, 6, -46, 15, + -85, -88, 50, 112, -91, 104, 65, -110, + 43, 22, -12, 27, 27, 83, 104, 65, + -114, -126, -105, -64, -119, -33, 105, -120, + -71, 76, 0, 65, -81, -99, -54, 82, + 13, 3, 78, 81, 80, 107, -25, 76, + -122, -125, 0, -60, 23, -28, 10, -17, + -97, 42, -24, -125, 112, 0, 0, 56, + -128, -76, -125, 32, -43, -89, -92, 27, + -65, 50, -99, -112, 96, 1, 0, -32, + 40, -96, 72, 49, -107, 57, 6, -34, + -109, 104, 40, 51, 12, 68, 67, 64, + -128, 98, 11, -78, 12, -64, 16, 24, + 7, -108, 25, -64, 0, 0, 9, -128, + -16, 109, 72, 0, 0, 14, -48, 30, + -20, 56, 55, -23, 7, 43, -96, -54, + -29, -35, 97, 6, -88, 69, 13, 8, + 49, 69, -46, -6, -127, 14, 68, -125, + -34, 80, 103, 0, 0, 0, 36, 2, + 58, 12, 110, 53, -44, 80, 110, -112, + 112, -54, -125, 127, -33, -40, 80, 32, + -68, -125, 59, -18, -74, 36, 25, 0, + 0, 0, 7, -66, 3, -14, 13, -1, + -12, 31, 104, 64, -118, 46, -105, 100, + 24, 1, 32, 104, 14, -120, 55, 32, + 0, 3, -112, 15, -29, 85, 84, -127, + 5, -120, 9, 65, -112, 0, 0, 0, + 123, -32, 63, 32, -38, -57, 127, 55, + -44, 24, -97, 40, 18, -4, -125, 105, + 56, -15, 95, 80, 96, -68, 16, -93, + 122, 5, 110, -88, 40, 32, -64, 20, + 113, -11, 6, 11, -59, 8, -69, 32, + -64, 12, 0, -64, 111, 64, -83, -43, + 7, 100, 24, -128, -96, 88, 12, 104, + 53, -4, 0, 0, 0, -124, 7, -64, + -118, -33, -106, -102, -13, -84, 0, 65, + -100, 0, 0, 0, -104, 9, 72, 50, + 13, 56, 126, 65, -70, -4, -6, -49, + -88, 50, 112, -39, -59, -115, 6, -83, + 1, -13, 1, -53, 0, -8, -125, 37, + 13, 34, -41, 16, 107, -25, 116, -122, + -125, 0, -60, 7, -16, -118, 102, 102, + -36, -66, -118, 0, 65, -67, -1, -30, + 10, 12, -99, 74, 94, -48, 110, -31, + 108, 104, 65, -102, -87, 103, -60, 8, + 34, -100, 36, -2, -125, 124, -84, -5, + -97, 16, 98, 43, -46, 27, 34, 12, + 127, -101, 127, 64, -80, -47, -16, -19, + 8, 53, -33, 88, -8, -125, 20, 109, + 19, 95, -48, 111, -111, -1, -117, 66, + 13, -57, 92, 63, -96, 93, -104, -99, + 119, -60, 24, 84, -16, 82, -8, -125, + 3, 80, 2, -38, 16, 103, -116, 101, + -19, 2, -18, 110, -26, 68, 24, -117, + -98, -56, -125, 5, -64, -35, -112, 96, + 4, 0, 32, 63, -102, 89, 15, 119, + -122, 112, 12, 32, -38, -68, 70, -110, + 91, -114, -68, 111, 2, 16, 96, -65, + -23, -123, 2, 13, 7, 118, -36, 104, + -127, 46, -26, -117, -92, -19, 36, 102, + 0, -128, -64, 61, -61, 84, 87, -73, + 74, 32, -24, 50, 11, 10, 111, 57, + -79, -36, -28, 10, 93, 24, 4, 22, + 106, -32, -42, 17, -42, -29, -104, -37, + 74, 105, -73, -9, -48, 112, -35, -82, + 107, 119, 73, 10, -33, 78, -4, -79, + -97, 96, -54, -14, 54, -128, 58, 97, + 8, 111, 4, 3, -50, -37, -53, 64, + -124, 0, 14, -103, 65, -41, -127, 8, + 53, 6, -14, 65, 65, -97, -48, 115, + 113, -51, -74, 42, 50, 82, 57, 40, + -86, -53, -100, -41, -66, -74, 106, -125, + 82, 116, -39, -48, 38, 51, 107, 121, + 44, 88, -28, 34, 96, 4, -78, 4, + 75, 118, -64, 16, 96, 4, -127, -96, + 45, -110, 88, 14, -31, 3, 0, 65, + -65, -128, 10, 25, 44, -61, 81, -40, + -16, 3, -85, -100, 0, 20, 6, -12, + 3, 49, -63, -107, 14, 15, 71, -16, + 99, 19, -81, -37, -102, -15, -37, 32, + -21, -7, 6, -91, -81, 91, -119, -4, + 88, -77, -20, 26, -49, -96, -54, 23, + 112, -72, -41, -35, 64, 8, 53, 11, + 14, 102, 65, -123, -35, -52, -94, 55, + 24, -7, -45, -72, -75, -123, 0, 0, + 22, -64, 111, -16, 2, 13, 97, -46, + 48, -96, 65, 0, 86, 40, 32, -120, + 21, -124, -115, 46, 54, 29, -69, 11, + 88, 0, -96, 96, 11, -32, 60, 20, + -94, 25, 99, 53, 97, -125, 8, 91, + -48, 2, 101, 113, -54, -128, -20, 0, + 10, -85, -70, -117, 50, 32, 1, 6, + 75, 84, 46, -99, -38, -53, -51, 9, + -59, -59, 52, 25, 121, 16, 0, 119, + 27, -114, -108, 39, 21, 4, -111, -26, + 116, 64, 2, 13, 121, -104, 105, 63, + -115, 58, -42, 122, -125, 106, -15, 25, + -112, 99, 35, -32, 8, 5, -96, 0 + } ; + + private static final CompressedGeometryHeader cgHeader ; + + static { + cgHeader = new CompressedGeometryHeader() ; + cgHeader.majorVersionNumber = 1 ; + cgHeader.minorVersionNumber = 0 ; + cgHeader.minorMinorVersionNumber = 1 ; + cgHeader.bufferType = CompressedGeometryHeader.TRIANGLE_BUFFER ; + cgHeader.bufferDataPresent = CompressedGeometryHeader.NORMAL_IN_BUFFER ; + cgHeader.start = 0 ; + cgHeader.size = cgData.length ; + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/picking/ColorCube.java b/src/main/java/org/jdesktop/j3d/examples/picking/ColorCube.java new file mode 100644 index 0000000..a92f641 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/picking/ColorCube.java @@ -0,0 +1,122 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.picking; + +import org.jogamp.java3d.QuadArray; + +class ColorCube extends QuadArray { + private static final float[] verts = { + // front face + 1.0f, -1.0f, 1.0f, + 1.0f, 1.0f, 1.0f, + -1.0f, 1.0f, 1.0f, + -1.0f, -1.0f, 1.0f, + // back face + -1.0f, -1.0f, -1.0f, + -1.0f, 1.0f, -1.0f, + 1.0f, 1.0f, -1.0f, + 1.0f, -1.0f, -1.0f, + // right face + 1.0f, -1.0f, -1.0f, + 1.0f, 1.0f, -1.0f, + 1.0f, 1.0f, 1.0f, + 1.0f, -1.0f, 1.0f, + // left face + -1.0f, -1.0f, 1.0f, + -1.0f, 1.0f, 1.0f, + -1.0f, 1.0f, -1.0f, + -1.0f, -1.0f, -1.0f, + // top face + 1.0f, 1.0f, 1.0f, + 1.0f, 1.0f, -1.0f, + -1.0f, 1.0f, -1.0f, + -1.0f, 1.0f, 1.0f, + // bottom face + -1.0f, -1.0f, 1.0f, + -1.0f, -1.0f, -1.0f, + 1.0f, -1.0f, -1.0f, + 1.0f, -1.0f, 1.0f, + }; + + private static final float[] colors = { + // front face (red) + 1.0f, 0.0f, 0.0f, + 1.0f, 0.0f, 0.0f, + 1.0f, 0.0f, 0.0f, + 1.0f, 0.0f, 0.0f, + // back face (green) + 0.0f, 1.0f, 0.0f, + 0.0f, 1.0f, 0.0f, + 0.0f, 1.0f, 0.0f, + 0.0f, 1.0f, 0.0f, + // right face (blue) + 0.0f, 0.0f, 1.0f, + 0.0f, 0.0f, 1.0f, + 0.0f, 0.0f, 1.0f, + 0.0f, 0.0f, 1.0f, + // left face (yellow) + 1.0f, 1.0f, 0.0f, + 1.0f, 1.0f, 0.0f, + 1.0f, 1.0f, 0.0f, + 1.0f, 1.0f, 0.0f, + // top face (magenta) + 1.0f, 0.0f, 1.0f, + 1.0f, 0.0f, 1.0f, + 1.0f, 0.0f, 1.0f, + 1.0f, 0.0f, 1.0f, + // bottom face (cyan) + 0.0f, 1.0f, 1.0f, + 0.0f, 1.0f, 1.0f, + 0.0f, 1.0f, 1.0f, + 0.0f, 1.0f, 1.0f, + }; + + ColorCube() { + super(24, QuadArray.COORDINATES | QuadArray.COLOR_3); + + setCoordinates(0, verts); + setColors(0, colors); + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/picking/ColorPyramidDown.java b/src/main/java/org/jdesktop/j3d/examples/picking/ColorPyramidDown.java new file mode 100644 index 0000000..3cf18cb --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/picking/ColorPyramidDown.java @@ -0,0 +1,122 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.picking; + +import org.jogamp.java3d.QuadArray; + +class ColorPyramidDown extends QuadArray { + private static final float[] verts = { + // front face + 0.0f, -1.0f, 0.0f, + 1.0f, 1.0f, 1.0f, + -1.0f, 1.0f, 1.0f, + 0.0f, -1.0f, 0.0f, + // back face + 0.0f, -1.0f, 0.0f, + -1.0f, 1.0f, -1.0f, + 1.0f, 1.0f, -1.0f, + 0.0f, -1.0f, 0.0f, + // right face + 0.0f, -1.0f, 0.0f, + 1.0f, 1.0f, -1.0f, + 1.0f, 1.0f, 1.0f, + 0.0f, -1.0f, 0.0f, + // left face + 0.0f, -1.0f, 0.0f, + -1.0f, 1.0f, 1.0f, + -1.0f, 1.0f, -1.0f, + 0.0f, -1.0f, 0.0f, + // top face + 1.0f, 1.0f, 1.0f, + 1.0f, 1.0f, -1.0f, + -1.0f, 1.0f, -1.0f, + -1.0f, 1.0f, 1.0f, + // bottom face + 0.0f, -1.0f, 0.0f, + 0.0f, -1.0f, 0.0f, + 0.0f, -1.0f, 0.0f, + 0.0f, -1.0f, 0.0f, + }; + + private static final float[] colors = { + // front face (green) + 0.0f, 1.0f, 0.0f, + 0.0f, 1.0f, 0.0f, + 0.0f, 1.0f, 0.0f, + 0.0f, 1.0f, 0.0f, + // back face (red) + 1.0f, 0.0f, 0.0f, + 1.0f, 0.0f, 0.0f, + 1.0f, 0.0f, 0.0f, + 1.0f, 0.0f, 0.0f, + // right face (yellow) + 1.0f, 1.0f, 0.0f, + 1.0f, 1.0f, 0.0f, + 1.0f, 1.0f, 0.0f, + 1.0f, 1.0f, 0.0f, + // left face (magenta) + 1.0f, 0.0f, 1.0f, + 1.0f, 0.0f, 1.0f, + 1.0f, 0.0f, 1.0f, + 1.0f, 0.0f, 1.0f, + // top face (blue) + 0.0f, 0.0f, 1.0f, + 0.0f, 0.0f, 1.0f, + 0.0f, 0.0f, 1.0f, + 0.0f, 0.0f, 1.0f, + // bottom face (cyan) + 0.0f, 1.0f, 1.0f, + 0.0f, 1.0f, 1.0f, + 0.0f, 1.0f, 1.0f, + 0.0f, 1.0f, 1.0f, + }; + + ColorPyramidDown() { + super(24, QuadArray.COORDINATES | QuadArray.COLOR_3); + + setCoordinates(0, verts); + setColors(0, colors); + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/picking/ColorPyramidUp.java b/src/main/java/org/jdesktop/j3d/examples/picking/ColorPyramidUp.java new file mode 100644 index 0000000..c59211d --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/picking/ColorPyramidUp.java @@ -0,0 +1,124 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.picking; + +import org.jogamp.java3d.QuadArray; + +class ColorPyramidUp extends QuadArray { + private static final float[] verts = { + // front face + 1.0f, -1.0f, 1.0f, + 0.0f, 1.0f, 0.0f, + 0.0f, 1.0f, 0.0f, + -1.0f, -1.0f, 1.0f, + // back face + -1.0f, -1.0f, -1.0f, + 0.0f, 1.0f, 0.0f, + 0.0f, 1.0f, 0.0f, + 1.0f, -1.0f, -1.0f, + // right face + 1.0f, -1.0f, -1.0f, + 0.0f, 1.0f, 0.0f, + 0.0f, 1.0f, 0.0f, + 1.0f, -1.0f, 1.0f, + // left face + -1.0f, -1.0f, 1.0f, + 0.0f, 1.0f, 0.0f, + 0.0f, 1.0f, 0.0f, + -1.0f, -1.0f, -1.0f, + // top face + 0.0f, 1.0f, 0.0f, + 0.0f, 1.0f, 0.0f, + 0.0f, 1.0f, 0.0f, + 0.0f, 1.0f, 0.0f, + // bottom face + -1.0f, -1.0f, 1.0f, + -1.0f, -1.0f, -1.0f, + 1.0f, -1.0f, -1.0f, + 1.0f, -1.0f, 1.0f, + }; + + private static final float[] colors = { + + // front face (cyan) + 0.0f, 1.0f, 1.0f, + 0.0f, 1.0f, 1.0f, + 0.0f, 1.0f, 1.0f, + 0.0f, 1.0f, 1.0f, + // back face (magenta) + 1.0f, 0.0f, 1.0f, + 1.0f, 0.0f, 1.0f, + 1.0f, 0.0f, 1.0f, + 1.0f, 0.0f, 1.0f, + // right face (yellow) + 1.0f, 1.0f, 0.0f, + 1.0f, 1.0f, 0.0f, + 1.0f, 1.0f, 0.0f, + 1.0f, 1.0f, 0.0f, + // left face (blue) + 0.0f, 0.0f, 1.0f, + 0.0f, 0.0f, 1.0f, + 0.0f, 0.0f, 1.0f, + 0.0f, 0.0f, 1.0f, + // top face (green) + 0.0f, 1.0f, 0.0f, + 0.0f, 1.0f, 0.0f, + 0.0f, 1.0f, 0.0f, + 0.0f, 1.0f, 0.0f, + // bottom face (red) + 1.0f, 0.0f, 0.0f, + 1.0f, 0.0f, 0.0f, + 1.0f, 0.0f, 0.0f, + 1.0f, 0.0f, 0.0f, + + }; + + ColorPyramidUp() { + super(24, QuadArray.COORDINATES | QuadArray.COLOR_3); + + setCoordinates(0, verts); + setColors(0, colors); + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/picking/Cube.java b/src/main/java/org/jdesktop/j3d/examples/picking/Cube.java new file mode 100644 index 0000000..4c5faf4 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/picking/Cube.java @@ -0,0 +1,113 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.picking; + +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.Geometry; +import org.jogamp.java3d.QuadArray; +import org.jogamp.java3d.Shape3D; +import org.jogamp.vecmath.Vector3f; + +public class Cube extends Shape3D { + private static final float[] verts = { + // front face + 1.0f, -1.0f, 1.0f, + 1.0f, 1.0f, 1.0f, + -1.0f, 1.0f, 1.0f, + -1.0f, -1.0f, 1.0f, + // back face + -1.0f, -1.0f, -1.0f, + -1.0f, 1.0f, -1.0f, + 1.0f, 1.0f, -1.0f, + 1.0f, -1.0f, -1.0f, + // right face + 1.0f, -1.0f, -1.0f, + 1.0f, 1.0f, -1.0f, + 1.0f, 1.0f, 1.0f, + 1.0f, -1.0f, 1.0f, + // left face + -1.0f, -1.0f, 1.0f, + -1.0f, 1.0f, 1.0f, + -1.0f, 1.0f, -1.0f, + -1.0f, -1.0f, -1.0f, + // top face + 1.0f, 1.0f, 1.0f, + 1.0f, 1.0f, -1.0f, + -1.0f, 1.0f, -1.0f, + -1.0f, 1.0f, 1.0f, + // bottom face + -1.0f, -1.0f, 1.0f, + -1.0f, -1.0f, -1.0f, + 1.0f, -1.0f, -1.0f, + 1.0f, -1.0f, 1.0f, + }; + + private static final Vector3f[] normals = { + new Vector3f( 0.0f, 0.0f, 1.0f), // front face + new Vector3f( 0.0f, 0.0f, -1.0f), // back face + new Vector3f( 1.0f, 0.0f, 0.0f), // right face + new Vector3f(-1.0f, 0.0f, 0.0f), // left face + new Vector3f( 0.0f, 1.0f, 0.0f), // top face + new Vector3f( 0.0f, -1.0f, 0.0f), // bottom face + }; + + public Cube() { + super(); + + int i; + + QuadArray cube = new QuadArray(24, QuadArray.COORDINATES | + QuadArray.NORMALS); + + cube.setCoordinates(0, verts); + for (i = 0; i < 24; i++) { + cube.setNormal(i, normals[i/4]); + } + + cube.setCapability(Geometry.ALLOW_INTERSECT); + setGeometry(cube); + setAppearance(new Appearance()); + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/picking/CubeIQA.java b/src/main/java/org/jdesktop/j3d/examples/picking/CubeIQA.java new file mode 100644 index 0000000..e9dcd12 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/picking/CubeIQA.java @@ -0,0 +1,140 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.picking; + +import org.jogamp.java3d.GeometryArray; +import org.jogamp.java3d.IndexedQuadArray; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3f; + +class CubeIQA extends IndexedQuadArray { + CubeIQA() { + super(8, GeometryArray.COORDINATES | GeometryArray.COLOR_3, 24); + + + Point3f verts[] = new Point3f[8]; + Color3f colors[] = new Color3f[8]; + + verts[0] = new Point3f(1.0f, 1.0f, 1.0f); + verts[1] = new Point3f(-1.0f, 1.0f, 1.0f); + verts[2] = new Point3f(-1.0f,-1.0f, 1.0f); + verts[3] = new Point3f( 1.0f,-1.0f, 1.0f); + verts[4] = new Point3f( 1.0f, 1.0f,-1.0f); + verts[5] = new Point3f( -1.0f, 1.0f,-1.0f); + verts[6] = new Point3f( -1.0f,-1.0f,-1.0f); + verts[7] = new Point3f( 1.0f,-1.0f,-1.0f); + + colors[0] = new Color3f(1.0f, 0.0f, 0.0f); + colors[1] = new Color3f(0.0f, 1.0f, 0.0f); + colors[2] = new Color3f(0.0f, 0.0f, 1.0f); + colors[3] = new Color3f(1.0f, 1.0f, 0.0f); + colors[4] = new Color3f(1.0f, 0.0f, 1.0f); + colors[5] = new Color3f(0.0f, 1.0f, 1.0f); + colors[6] = new Color3f(0.0f, 1.0f, 1.0f); + colors[7] = new Color3f(0.0f, 1.0f, 1.0f); + + int pntsIndex[] = new int[24]; + int clrsIndex[] = new int[24]; + + pntsIndex[0] = 0; + clrsIndex[0] = 0; + pntsIndex[1] = 3; + clrsIndex[1] = 0; + pntsIndex[2] = 7; + clrsIndex[2] = 0; + pntsIndex[3] = 4; + clrsIndex[3] = 0; + + pntsIndex[4] = 1; + clrsIndex[4] = 1; + pntsIndex[5] = 5; + clrsIndex[5] = 1; + pntsIndex[6] = 6; + clrsIndex[6] = 1; + pntsIndex[7] = 2; + clrsIndex[7] = 1; + + pntsIndex[8] = 0; + clrsIndex[8] = 2; + pntsIndex[9] = 4; + clrsIndex[9] = 2; + pntsIndex[10] = 5; + clrsIndex[10] = 2; + pntsIndex[11] = 1; + clrsIndex[11] = 2; + + pntsIndex[12] = 3; + clrsIndex[12] = 3; + pntsIndex[13] = 2; + clrsIndex[13] = 3; + pntsIndex[14] = 6; + clrsIndex[14] = 3; + pntsIndex[15] = 7; + clrsIndex[15] = 3; + + pntsIndex[16] = 0; + clrsIndex[16] = 4; + pntsIndex[17] = 1; + clrsIndex[17] = 4; + pntsIndex[18] = 2; + clrsIndex[18] = 4; + pntsIndex[19] = 3; + clrsIndex[19] = 4; + + pntsIndex[20] = 7; + clrsIndex[20] = 5; + pntsIndex[21] = 6; + clrsIndex[21] = 5; + pntsIndex[22] = 5; + clrsIndex[22] = 5; + pntsIndex[23] = 4; + clrsIndex[23] = 5; + + setCoordinates(0, verts); + setCoordinateIndices(0, pntsIndex); + setColors(0, colors); + setColorIndices(0, clrsIndex); + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/picking/CubeQA.java b/src/main/java/org/jdesktop/j3d/examples/picking/CubeQA.java new file mode 100644 index 0000000..246e506 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/picking/CubeQA.java @@ -0,0 +1,137 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.picking; + +import org.jogamp.java3d.GeometryArray; +import org.jogamp.java3d.QuadArray; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3f; + +class CubeQA extends QuadArray { + CubeQA() { + super(24, GeometryArray.COORDINATES | GeometryArray.COLOR_3); + + + Point3f verts[] = new Point3f[8]; + Color3f colors[] = new Color3f[6]; + + verts[0] = new Point3f(1.0f, 1.0f, 1.0f); + verts[1] = new Point3f(-1.0f, 1.0f, 1.0f); + verts[2] = new Point3f(-1.0f,-1.0f, 1.0f); + verts[3] = new Point3f( 1.0f,-1.0f, 1.0f); + verts[4] = new Point3f( 1.0f, 1.0f,-1.0f); + verts[5] = new Point3f( -1.0f, 1.0f,-1.0f); + verts[6] = new Point3f( -1.0f,-1.0f,-1.0f); + verts[7] = new Point3f( 1.0f,-1.0f,-1.0f); + + colors[0] = new Color3f(1.0f, 0.0f, 0.0f); + colors[1] = new Color3f(0.0f, 1.0f, 0.0f); + colors[2] = new Color3f(0.0f, 0.0f, 1.0f); + colors[3] = new Color3f(1.0f, 1.0f, 0.0f); + colors[4] = new Color3f(1.0f, 0.0f, 1.0f); + colors[5] = new Color3f(0.0f, 1.0f, 1.0f); + + Point3f pnts[] = new Point3f[24]; + Color3f clrs[] = new Color3f[24]; + + pnts[0] = verts[0]; + clrs[0] = colors[0]; + pnts[1] = verts[3]; + clrs[1] = colors[0]; + pnts[2] = verts[7]; + clrs[2] = colors[0]; + pnts[3] = verts[4]; + clrs[3] = colors[0]; + + pnts[4] = verts[1]; + clrs[4] = colors[1]; + pnts[5] = verts[5]; + clrs[5] = colors[1]; + pnts[6] = verts[6]; + clrs[6] = colors[1]; + pnts[7] = verts[2]; + clrs[7] = colors[1]; + + pnts[8] = verts[0]; + clrs[8] = colors[2]; + pnts[9] = verts[4]; + clrs[9] = colors[2]; + pnts[10] = verts[5]; + clrs[10] = colors[2]; + pnts[11] = verts[1]; + clrs[11] = colors[2]; + + pnts[12] = verts[3]; + clrs[12] = colors[3]; + pnts[13] = verts[2]; + clrs[13] = colors[3]; + pnts[14] = verts[6]; + clrs[14] = colors[3]; + pnts[15] = verts[7]; + clrs[15] = colors[3]; + + pnts[16] = verts[0]; + clrs[16] = colors[4]; + pnts[17] = verts[1]; + clrs[17] = colors[4]; + pnts[18] = verts[2]; + clrs[18] = colors[4]; + pnts[19] = verts[3]; + clrs[19] = colors[4]; + + pnts[20] = verts[7]; + clrs[20] = colors[5]; + pnts[21] = verts[6]; + clrs[21] = colors[5]; + pnts[22] = verts[5]; + clrs[22] = colors[5]; + pnts[23] = verts[4]; + clrs[23] = colors[5]; + + + setCoordinates(0, pnts); + setColors(0, clrs); + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/picking/GullCG.java b/src/main/java/org/jdesktop/j3d/examples/picking/GullCG.java new file mode 100644 index 0000000..dee9e2a --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/picking/GullCG.java @@ -0,0 +1,578 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.picking; + +import org.jogamp.java3d.CompressedGeometry; +import org.jogamp.java3d.CompressedGeometryHeader; + +class GullCG extends CompressedGeometry { + + GullCG() { + super(cgHeader, cgData) ; + } + + private static final byte cgData[] = { + 25, 0, -120, 16, -58, -52, 33, -35, + -128, 67, -36, 0, -127, -72, 97, 14, + 64, 2, 29, 104, 4, 2, -45, 8, + 125, -89, 16, 51, -116, 33, -1, -104, + 71, -64, 48, -106, 31, 1, 32, -52, + 2, -127, 6, 5, 5, 32, 10, -78, + -128, 20, 14, 6, 40, 74, -128, 81, + -43, 24, -94, 44, 1, 86, -104, 98, + -96, 49, 5, 34, 112, 10, -68, -29, + 21, -115, -56, 40, 8, -64, 81, -74, + -128, -90, 13, 49, 71, 30, 2, -81, + -68, -30, -62, 122, 56, 37, -107, 60, + -109, 120, 0, 0, 26, -32, 18, 85, + -128, 14, -16, 71, -13, 66, -33, 103, + 127, -81, 78, -61, -106, -112, 0, 1, + -32, 13, -86, -96, 4, -103, -36, 59, + -23, 25, 39, 18, 11, 122, -80, 1, + -34, -22, -112, -109, -80, -71, -7, -39, + -40, 0, -127, 0, 0, 0, 0, 43, + 97, -102, 118, 16, 83, -32, -121, -87, + -32, -86, -4, 32, 121, 8, 33, -48, + -100, -39, 64, 0, 0, 50, 0, -47, + -9, -97, -118, 53, 75, -122, 89, -54, + -10, 8, 0, 69, -98, 0, 0, 54, + 3, -67, 0, 29, -17, 2, 64, 0, + 5, 126, -93, -56, -31, 15, 74, -95, + -128, 5, -64, 0, 3, -46, 8, 0, + 36, 0, 0, 58, 93, -92, 0, 0, + 30, 0, 87, 4, 0, 23, 4, 68, + 36, 64, 30, -17, -25, -121, -40, 22, + 13, 48, 78, -43, 73, -64, -10, 48, + 51, -25, -1, -82, -65, 3, 55, -71, + 41, 124, -50, -118, -64, 4, -102, 112, + 0, 1, -20, 5, 98, 59, -58, -95, + -87, 42, -9, -112, -99, -107, -91, -11, + 127, 5, 36, -46, -112, 121, 9, -39, + -17, -1, -41, 0, 0, 0, 112, 4, + -121, -19, -124, -16, -44, 66, -40, 36, + 116, -83, -96, -128, 7, -37, 100, -37, + 121, 11, 123, -81, -106, 43, 82, 14, + -85, -8, 41, -95, 67, 81, 18, 125, + 15, 39, -114, -88, 63, -10, 0, -11, + 5, 4, 73, -38, 13, 80, -64, 7, + 64, 56, 14, -56, 108, 3, -64, 96, + 5, -33, 81, 24, 11, -115, 26, -95, + -104, 95, -69, -95, -112, 15, 0, -128, + 40, 30, 67, -27, 1, 107, -55, 102, + -39, 97, 67, 103, 66, 79, 67, 37, + -60, 62, -95, -88, -32, 105, 72, 106, + -113, -59, -108, 54, -64, 43, 50, 9, + 86, 30, 45, 72, 101, 31, -51, -120, + 106, -8, 75, -24, 98, 111, -106, -12, + 54, 104, 54, 47, 87, -115, -61, -106, + 64, -47, 13, -80, 10, -116, -122, 39, + -3, 118, -7, 0, 0, 0, 0, 42, + -13, -118, 27, 96, 9, 27, -20, 71, + -8, -96, -50, 61, 111, 87, 102, -83, + -93, -54, 47, -37, 51, -113, 27, 122, + 98, -52, -91, -75, 1, 53, -96, 8, + 97, -120, 54, -44, 55, -1, -10, 105, + -108, -84, -4, -101, -64, 67, 41, -4, + 105, 67, 117, -60, 92, 67, 115, -4, + -65, 124, -125, 90, 64, 118, -85, 97, + 67, 39, 126, 96, 67, 78, 80, 65, + -15, 12, -57, 61, 94, 67, 50, 3, + -93, 33, -107, -2, -44, 16, 91, -34, + -115, -88, 109, 24, 75, -120, 109, -113, + -108, 20, 49, 52, 59, 122, 25, 51, + -29, 23, -85, -39, 33, -50, -28, 104, + -122, -16, 2, 0, -128, 90, 67, 20, + 1, -93, 124, -122, 31, 91, 113, -59, + 13, -55, -7, 121, 12, -57, 10, -10, + -122, 120, 0, 1, -8, 8, -56, 33, + -49, -59, 94, -78, -45, -85, 6, -33, + 105, -55, -121, -77, 99, -113, 91, 105, + -2, 77, -37, 70, -118, -2, 52, 102, + -122, -45, -120, -66, -122, 25, -7, 65, + 65, 19, 67, -69, 33, -92, 1, 0, + 0, 23, 16, -37, 31, 40, 113, -90, + 120, 118, -84, -48, -55, -17, -37, 16, + -59, 62, -88, 28, -126, 21, 70, 1, + -108, 3, 80, 1, -96, 45, 107, -115, + 124, 58, -60, 102, -128, 0, 7, 64, + 27, -60, 125, -107, 127, 42, -40, -83, + 57, -15, -71, 1, -32, -50, -60, 42, + 123, 106, 60, -16, -32, -66, 85, 26, + -14, -31, 82, -20, -49, -128, -120, 94, + -64, 0, -25, 50, 85, 26, -52, -80, + 23, -21, 7, -120, 1, 118, 53, -55, + 75, -83, -96, 2, 24, -16, 0, 0, + 0, 4, 18, -77, 92, -101, -64, 8, + 84, 72, -22, -33, 85, -126, -42, -69, + -41, -79, -49, -69, 126, -128, 5, 0, + -1, -128, 125, 54, 0, -53, 47, 110, + 91, -59, 64, 13, 119, 115, -59, 63, + 93, -28, -6, -23, -61, -128, 1, 40, + 0, 0, 80, 75, 64, -18, -33, -123, + -2, -117, -74, -116, 26, -106, -80, 6, + 91, -70, 21, -23, -44, 0, -121, 12, + 7, 64, 0, 5, 38, -73, 118, -79, + -114, 104, 118, 0, -5, 87, 2, 85, + -46, 94, 115, -112, -117, 72, 124, 100, + -32, 106, 106, 81, -98, -121, -100, 116, + 76, -121, -23, -112, 40, 43, 40, -92, + 57, -96, 4, 121, 47, -29, -65, 81, + -26, 2, -128, 16, 6, 62, -85, 86, + -67, -8, 74, -35, -77, -62, -5, -81, + -106, 56, 0, 0, 31, 1, -91, -48, + 0, 67, 27, -62, 100, 43, 80, 68, + 61, -48, 1, 24, 0, 45, 1, -16, + 7, 18, 1, -23, -88, -84, 127, -6, + 11, 37, -98, 14, 57, 107, -61, -52, + -114, -128, 1, 91, -92, -95, -82, -128, + 16, -64, 1, 108, 0, -128, 55, 111, + -101, 96, -80, 61, -90, -94, 122, 49, + -21, 14, -2, -73, 99, 115, 81, 11, + 90, -118, 74, -99, 30, -9, -9, 67, + -57, 80, 42, 79, -14, 3, -86, -91, + -94, 51, -1, 83, 64, -118, 50, 53, + -59, 74, -89, 126, -23, 32, 13, 57, + 40, -123, 76, 97, -41, 91, -115, -23, + 107, -83, -37, 81, 67, 27, -73, -113, + 58, 22, -80, 4, 88, 64, 109, -10, + -64, 14, -80, -19, -43, 15, 62, -80, + -116, -14, -121, -11, 110, -25, 38, -109, + 3, 55, -103, 85, -65, -79, -117, -37, + 66, -102, 97, -70, -123, 43, 104, -128, + 21, 100, 40, 71, -55, -125, 104, 33, + -43, 82, 84, -102, 7, -3, -32, -114, + 20, -37, -27, -4, -107, 116, 67, 3, + -7, -91, -9, -99, -25, -44, -71, -57, + 4, 5, -75, 74, 0, 1, 107, -120, + -19, -92, 21, -66, 100, 8, -124, -6, + -79, 18, -44, -27, 12, 12, -112, -32, + -108, -68, 99, 123, -89, -39, 98, -53, + 51, -10, -128, 10, 42, -48, -9, -108, + -34, -100, -7, -52, -123, -39, 100, -46, + 85, 45, 16, 0, 12, 97, -58, -25, + 32, 111, -32, 0, -48, 0, -48, 10, + -73, 86, -18, 104, 114, -102, -80, 32, + 0, 88, 0, 64, 7, -25, -127, 66, + -6, -75, 74, 73, 78, -51, -125, 4, + -103, -88, 1, 78, -62, 54, 84, 90, + -14, 32, 35, -18, -40, -67, -44, 106, + -102, -128, 2, 107, -24, -124, -64, 66, + -51, 15, 100, -87, 44, 0, 70, 125, + -120, 95, 33, 50, 123, 70, 83, 0, + -115, 122, 22, -102, 35, 92, -112, 94, + -87, -121, -66, -64, -105, -65, -15, 17, + -22, 122, -80, 33, 94, -5, 5, 75, + -35, 114, 65, 99, 99, 94, 28, -52, + -3, -77, 42, -16, -24, -87, 84, 12, + -76, 76, 90, 110, -120, 0, 86, -36, + -95, 85, 0, -122, -62, -125, 97, 67, + 13, 0, -127, -78, -19, 63, -3, -46, + 80, 0, -84, 0, 10, -128, 46, 3, + 40, 4, 55, 114, -8, -38, 16, -59, + -12, 84, -90, -35, -83, 111, 64, 21, + -128, 3, 96, 30, 3, -112, 12, -111, + -120, 13, -24, 14, -32, 5, 29, 16, + 1, 12, 123, -6, -60, 86, 82, 25, + 59, -56, 11, -74, -16, 4, 0, -104, + -91, 0, 16, -53, 59, 29, 101, 43, + 119, -41, -23, -100, 6, 74, 81, 56, + 10, -6, 32, 1, 91, -27, -31, -124, + 5, -40, -22, -90, 46, -78, -128, 5, + 99, -64, 0, 0, 0, 19, -128, 33, + -106, 5, -44, -26, -57, -97, -113, -64, + 20, -93, 72, 2, 55, 48, 8, 111, + 80, 31, -32, 31, -16, 12, -30, -26, + -88, 9, -69, -128, 8, 98, 3, 64, + 120, 5, -67, 118, -12, 59, -118, -122, + -115, 122, -6, -122, -125, -95, -77, -95, + -105, 73, -28, -6, -122, -86, -127, 51, + -95, -105, 125, -22, -6, -122, -38, -31, + -65, 84, -86, -14, 95, 71, -97, 67, + 111, -66, -81, -47, -124, 92, 22, 1, + -43, 16, 1, 13, 97, -18, -63, -82, + -46, -120, 106, -110, -122, -17, 120, 97, + -87, 82, 67, -99, 75, -48, -33, 95, + 79, 2, -32, -32, -104, 13, 41, 0, + 8, 103, 79, -105, -115, 112, 112, 70, + 3, 21, 84, 51, -101, -53, 18, 8, + 14, -62, -83, 72, 100, 72, 72, -24, + 102, 71, -73, -117, 17, 30, -65, -32, + -40, 36, 4, 46, -51, 76, 44, 96, + -44, 0, -57, 102, 54, -31, -2, 80, + 0, -71, 98, -72, 80, 46, 82, -64, + 8, 96, -80, 0, 32, 0, 16, 8, + 55, 106, -98, -121, -19, 64, 11, -108, + 36, 103, 8, -88, 8, 0, 46, -116, + -101, 104, -128, 50, -54, 112, 93, 73, + 64, 0, 115, -128, 0, 3, -32, 14, + -100, 25, 96, 0, -66, 0, 0, 22, + 49, -64, 12, -76, -124, 35, -95, 56, + 1, -10, 0, 11, -32, 122, 1, 98, + 20, 114, -38, 16, -18, -124, -32, 7, + -40, 0, 47, -128, 0, 5, 104, 97, + -53, 8, 127, -70, 35, -128, 29, -32, + 0, -66, 0, 0, 20, 7, -17, 104, + 124, -70, 47, -34, 0, 11, -32, 0, + 1, 93, 124, -78, -121, -29, -93, 56, + 0, 22, 0, 11, -32, 0, 1, 82, + -58, 122, -38, 31, 110, -101, 125, -128, + 2, -8, 0, 0, 86, -26, 28, -74, + -121, -29, -92, 56, 1, -106, 0, 11, + -32, 0, 1, -2, -104, 0, 35, 53, + -127, 65, -82, 34, 38, -51, -74, -34, + 0, -71, 123, 66, 111, -63, -24, 16, + 1, 12, 0, 17, 0, 0, 21, 5, + -48, -125, 109, 48, 7, -118, -125, 83, + -68, 10, 115, -112, 1, 0, -128, 18, + -47, -89, 61, 121, -86, 77, 58, 16, + 109, 92, 65, 86, 127, -82, -100, 31, + 96, 0, 64, 0, 0, 30, -7, 68, + -116, 32, 0, 3, -32, 28, 72, 13, + -110, -125, 43, 0, 17, 107, -64, 23, + -92, 0, 46, -64, 1, -96, 13, 1, + 91, -112, 1, 12, 5, -2, -66, -122, + -110, -104, 81, 19, 30, -2, 60, 2, + 18, 96, 48, -112, 20, 51, 16, 38, + -51, 126, 67, 56, 33, -82, -78, -87, + -117, -10, 10, -52, -86, -18, -97, 120, + 62, -47, 67, -9, -86, 81, -17, 0, + 8, 0, 24, 5, -127, -5, -38, 0, + 47, 67, -9, -128, 4, 0, 0, 2, + -80, -1, 97, 7, -9, -82, 81, -53, + 0, 8, 0, 0, 5, 4, 112, 3, + -19, -96, -14, -11, -56, 57, 96, 1, + 0, 0, 0, -82, -116, 0, 125, -108, + 31, 30, -71, 71, -68, 0, 32, 0, + 0, 21, 7, -53, 104, 61, -67, 35, + 0, 5, 96, 1, 0, 0, 0, -84, + 3, 45, -96, -8, -11, 12, 0, 21, + -128, 4, 0, 0, 3, -8, 15, -77, + -64, -108, 16, -30, 14, 61, 105, -40, + -81, 27, 124, -75, 64, 40, 6, -11, + -54, 32, -32, 1, 0, 0, 0, -111, + -63, -106, -116, -125, 115, 5, 0, 33, + 76, 0, 1, -64, 61, -96, 25, 26, + -116, 24, 37, 66, -113, -55, 42, 77, + 19, -35, -4, -73, -111, -110, -14, 12, + -23, 12, 0, 101, -91, 0, 0, 1, + 0, 104, 70, 0, 43, -39, -99, -46, + 78, 45, -5, 58, -30, 2, -127, 27, + 44, -22, 80, -118, 53, -24, 58, -3, + -17, -76, -90, 95, 18, 55, -16, -39, + -4, -121, -55, -25, -11, -38, 85, 68, + 60, -76, 15, -5, 124, 40, 0, 86, + -14, 12, -2, 3, 124, -16, 63, 0, + -69, -91, 102, 2, -128, 16, 6, 48, + 31, 43, 94, -4, 50, 42, 14, 90, + -126, -95, 107, -18, -96, 0, -102, 71, + -11, -68, 16, -37, 11, -59, 122, -2, + 64, 1, -64, 59, 1, -38, 24, 80, + -48, 5, 64, 0, 15, -46, 104, -82, + -57, -19, -4, -115, 115, 112, 92, 20, + -28, -3, -127, 64, 125, -64, 127, -64, + 56, -125, -113, 74, 118, 43, 78, -35, + 107, 47, -18, 91, -121, -111, 0, 0, + 0, 126, -128, 63, -23, 31, 102, -65, + 32, 53, -30, -104, 102, 86, -16, -16, + 8, 86, 2, -20, 31, 24, -11, -56, + 1, 78, 0, 16, -127, -104, 10, 18, + 102, -51, 8, 122, 0, 86, 0, 19, + 1, -120, 10, -32, 34, -55, 65, 111, + 64, 16, 119, -128, 5, -128, 98, 3, + -82, -103, 100, -64, 0, 7, -80, 31, + -111, -128, 11, -108, 89, 16, 106, -107, + -56, 1, 118, -75, -10, 121, -92, 0, + -69, 121, 5, 32, -79, 43, -104, 2, + -20, 123, -2, -51, 72, 1, 118, -6, + 40, -5, -105, 48, 2, 24, 56, 0, + 4, 0, 4, 2, -15, 90, 90, 93, + -4, 1, -117, 86, -87, -89, 67, 0, + 86, -98, -94, 121, 1, -66, -34, 0, + -64, 18, 10, 86, -40, 21, 115, 0, + 70, -28, 1, -22, 1, -14, 0, -126, + 33, 12, -87, 38, -3, -30, -104, -28, + 124, 89, -63, -58, 77, -76, -79, -89, + 98, 8, -64, 7, 0, 56, 11, -62, + 59, -45, 18, 46, -62, -51, -128, 14, + 0, 96, 25, -128, -33, 93, 64, 45, + -35, -101, 120, 31, 0, -96, 58, -128, + -122, -120, 7, 0, 0, 1, -39, 12, + 0, 124, 2, 0, -80, 70, -36, -127, + 119, 16, -122, -16, 62, 0, -128, 126, + -19, 54, 70, 121, 108, 26, 17, -117, + 107, -52, -30, 35, -36, 19, 93, -128, + 28, 102, -39, -122, -61, 118, 1, 12, + 0, 28, 10, -128, -13, 114, -33, 14, + 66, -109, 7, 48, 2, 24, -24, 3, + -52, -92, 110, 123, 124, -96, 8, 67, + 40, 8, -87, -111, -117, -71, -98, -124, + 73, -128, 3, 96, 30, 2, 105, 8, + 32, 64, -74, 41, 48, -6, -67, -105, + -56, 43, 106, -53, -75, 0, 67, 113, + 2, 121, -89, 114, 4, -128, 57, -60, + 80, -50, 56, -107, 16, -46, -64, 45, + 72, 96, 88, 107, 8, 105, -64, 55, + -31, -112, 108, -89, -76, -59, 0, 107, + -124, 42, 26, -53, -21, -116, 92, 14, + -100, -107, -109, -62, 94, 64, 33, -75, + -128, -121, -12, -102, -122, 17, -119, 101, + 67, 88, 27, -27, 41, 13, -76, 22, + -20, -126, 0, 0, 0, 0, 71, 67, + 113, -66, 51, -95, -92, -122, 12, -94, + -126, 33, -13, 103, 35, 46, -1, -47, + 40, 68, -101, 48, 41, -100, -119, -79, + 47, 60, 83, 64, 67, 101, -122, 51, + -103, -119, 107, -62, -102, 1, 12, 8, + 22, -2, 42, -73, 77, 6, 91, 32, + 2, 49, -73, -89, -63, 8, 98, -45, + -21, -16, 10, 50, 41, -87, 74, -76, + 53, 91, 75, -43, -40, 0, 42, 1, + -96, 36, -46, 0, 111, -85, 57, 94, + 93, 119, -104, 116, 17, -104, -65, 84, + 97, 100, -102, 37, 15, -68, 126, 73, + 47, -111, 115, -53, -46, -72, 0, 102, + -60, -123, 119, 1, -54, 64, 4, 2, + 0, 118, 71, 92, 0, 12, 12, -128, + -34, -55, -65, 74, -85, -111, 78, -125, + -3, 127, -100, -111, -80, -128, 10, -108, + -56, 16, 1, -109, -24, 21, -44, -115, + -9, -32, -16, 35, 37, 14, -22, -69, + -106, -15, 64, 3, 45, -22, 33, 86, + -64, 32, -41, 32, 117, 52, 62, -27, + -101, -118, -74, -125, -66, 56, -13, 93, + 113, -56, 21, 79, -76, -128, 0, -103, + 122, 126, -48, 20, 93, -90, 47, 42, + -40, 8, 17, -83, -94, -33, 8, 93, + -113, 10, 79, 62, -128, 23, 109, -25, + -8, 1, 33, 90, 0, 33, -118, 5, + -44, -54, -64, 127, -113, 64, 16, -64, + 2, 80, 15, 1, -5, -27, -38, -16, + -83, 41, -118, 15, -37, -57, -79, -94, + -51, 50, -59, -47, 20, -59, 64, 15, + -75, 107, -53, -91, -96, -9, -128, 1, + 48, 0, 0, 80, 94, -19, 92, -10, + -127, -20, 0, 14, 82, 125, 83, -24, + -121, 56, -124, 61, -67, -88, -73, 64, + 120, 0, 0, 84, 0, -61, -19, 99, + 32, -33, -26, -76, -26, -17, -51, -122, + 38, -111, -84, -36, 12, 93, -77, -66, + -85, -86, 0, 107, -68, 6, -36, 92, + -74, 30, 102, 71, 64, 3, 93, 78, + -80, -75, -7, 5, 93, -6, -57, -74, + -79, 79, -109, 78, 22, 117, 108, -111, + 122, 52, 96, -49, 38, -117, -125, 123, + 10, 114, 121, 85, 96, -48, 0, -96, + 31, 16, 13, 39, -42, 113, 50, -109, + -9, 90, 59, 93, 15, -8, -79, 116, + -14, 77, -128, 29, 104, -19, -42, -97, + -94, -62, 6, -33, 44, 0, -5, 108, + -3, 91, -19, 7, -83, -27, 81, 49, + 24, -12, -109, 123, -51, 60, 39, 111, + -50, 23, -78, 53, -10, 14, -80, -93, + 122, -87, 33, -78, -30, 59, -95, -96, + 10, -128, 0, 30, 61, 92, -112, -53, + -25, 104, -76, 24, -79, 9, 37, 32, + 22, 4, -57, 1, 109, 65, 7, 26, + -98, 59, 106, -101, 103, -64, -116, -52, + 11, 29, 23, 106, 107, 106, -51, -15, + 120, -5, -20, 1, 54, -16, -47, -77, + 0, 38, -81, -54, 18, -8, 32, -122, + 69, 70, 117, 23, 44, 0, 0, 30, + 0, -68, 0, 109, -128, -45, -37, 80, + 48, 5, 118, -25, -85, 50, 110, 108, + -111, 51, -47, 23, 16, -96, 45, 99, + -51, -110, -12, 96, -63, -42, 20, 120, + 89, 86, 41, 120, 32, 5, 41, -5, + 0, 13, -99, 104, -100, -128, 10, -80, + 16, 0, 104, 15, -104, 5, 106, -85, + 125, 9, 57, -1, 91, -16, 0, 44, + 7, -32, 3, -10, 55, 40, -1, 80, + 65, -126, -64, 66, -20, -37, 66, -59, + 95, 64, 4, 55, -20, 26, 13, -37, + -126, 125, -106, -48, 1, 13, -48, -65, + -90, -126, -79, -123, 21, 32, 8, 108, + 95, -91, -111, 115, 44, -101, -112, 1, + 82, 16, 0, 103, 1, -51, 0, -112, + -14, 103, -112, -122, 98, 46, -43, -71, + 41, 126, -76, 0, -71, 79, 2, 127, + 108, -2, -128, 23, 109, 93, -111, -74, + 90, 0, 33, -96, 63, -94, -107, -86, + 70, 92, -64, 21, -67, 64, 0, -128, + 127, -64, 51, 0, 23, 126, -40, 69, + 68, 0, -101, 71, -5, -84, -127, -82, + 104, -123, 85, 80, -55, -81, 47, -88, + 109, -46, 27, -11, 74, -83, 49, -35, + 116, 113, 112, 0, 86, 0, -72, 15, + 32, 4, -37, 124, 11, 126, -116, -32, + 11, -113, 126, 40, -92, 0, 33, -110, + -2, 87, 53, -51, 64, -81, -51, 74, + -36, 121, -4, 102, -15, 117, -19, 4, + 93, -32, 4, 49, 0, 96, 60, 3, + -23, 26, 19, -124, -92, 33, 13, -94, + -16, -6, -122, -83, -127, 54, 33, -118, + -99, -79, 32, -107, 112, 30, -8, -122, + -125, -66, -77, -95, -91, 122, 16, -114, + -122, 92, 123, 113, 65, 69, 125, 125, + 67, 66, 48, -43, 80, -53, 78, -49, + 29, 37, 10, 121, -59, 36, -61, -114, + -109, -28, 103, -92, 0, 46, -57, -115, + 72, 127, -12, 0, -55, 101, -48, -119, + -117, 22, -64, 1, 25, -110, 21, -60, + 66, 26, 43, -21, -59, -55, -62, -58, + -21, 46, -96, -128, 25, 101, 0, 0, + 1, -64, 31, 9, 64, 1, -75, -73, + -55, 82, 0, -89, 94, 13, -76, -56, + 74, -1, 83, 115, 72, -21, -104, 43, + 56, -75, -32, -10, 74, -11, -66, 126, + 11, 72, 113, -40, 29, -51, -12, -127, + 6, -85, -116, -85, 78, 30, -65, -44, + -111, -1, -95, -111, 62, -33, 68, -55, + -29, -91, 112, -93, 37, 1, 72, -111, + -114, 0, 125, -96, -32, -38, 9, 70, + 76, -102, 5, -28, -116, -109, -53, -58, + -7, -37, -7, 0, 10, 114, 100, -105, + -47, -53, 59, 46, -37, -23, 64, 2, + -73, 112, 103, -16, 4, 102, -18, 104, + 21, -40, 70, -70, 0, 88, 0, 1, + -113, -123, 88, -89, -55, -112, -84, -45, + -107, -82, 28, -128, 40, 105, 24, 55, + 61, -73, -40, 15, -72, 0, 8, 4, + 47, -27, 88, -18, -3, 74, 50, 104, + -111, 31, -27, -4, -115, 115, 111, -92, + 22, -12, -10, -128, 3, -128, 10, 3, + 78, -56, 97, 127, 104, 8, 105, 24, + 53, -2, -43, 119, -21, -12, -13, 104, + -95, 71, -19, -4, 13, -13, -57, -20, + 16, -16, -36, -84, 95, 88, 52, -5, + 8, 1, 78, 97, -68, -67, 120, -40, + 0, 66, 1, -96, 40, 64, 2, -20, + -2, -57, -88, 2, -84, 0, 38, 0, + -16, 21, -2, 60, -102, -38, -12, -115, + 88, 0, 88, 1, -32, 43, 95, 57, + -9, -115, 32, -3, 113, -28, -45, 31, + -62, 57, 7, -5, -30, -105, 106, 102, + 59, -44, 32, 7, 56, 0, 52, 6, + 96, 61, 3, 54, -24, 0, 1, -56, + 11, 0, 92, -70, 40, 85, 113, 0, + 16, -42, -79, 73, -73, 106, 66, 21, + 104, 64, 11, -79, -20, 11, 14, 32, + 1, 88, 119, -60, 14, 96, 16, -34, + 64, 0, 32, 63, -32, 23, -48, -35, + 82, -20, -92, 110, -102, -15, 52, 8, + 67, 24, 17, 83, 35, 2, 58, -84, + -120, -41, 50, -55, -65, 123, 39, -42, + 6, -71, 71, 19, 1, 126, 60, 2, + 4, 98, 87, 124, 19, 60, -112, -41, + 111, 63, -96, 9, -119, -109, 47, 24, + 113, -108, -126, 55, 2, -66, 88, -60, + 120, -127, -24, 18, -64, 78, 40, 99, + 32, -21, 56, -5, -66, 100, -80, 19, + -116, -37, 77, -75, -18, -64, 33, -128, + 3, -128, -80, 25, -4, 71, -122, 61, + 103, 39, 20, 54, -81, -54, -99, -112, + -64, 7, 0, -56, 11, -63, 106, -71, + -25, 100, -103, 51, 0, 28, 3, 64, + 51, 0, -33, 90, -44, 89, -39, -101, + 8, 31, 3, 96, 44, 0, -122, 101, + 9, 114, 67, 0, 0, -1, -64, -1, + 0, 88, 35, 82, 67, -71, 8, 43, + 0, 64, -1, -64, -1, -128, 126, 1, + -110, 101, 95, -6, -37, 113, 0, 9, + -79, 19, -26, 112, 41, -51, -83, 18, + 113, -108, 52, -113, -25, -44, 54, 33, + 13, -59, 13, 5, -11, 97, 12, -58, + 8, -50, -122, 90, -17, -102, -46, 26, + -82, 9, -80, -116, 83, -23, -56, 69, + 73, 84, 0, -28, 7, -12, 3, 47, + 17, -68, 43, -26, -62, 32, 92, 25, + -15, -43, 24, 1, 13, -98, -18, -64, + -122, -51, 120, 98, -102, 24, 71, -35, + -127, 5, 90, 48, -42, -92, 49, -36, + 36, 116, 52, -29, -21, -11, 72, -59, + 21, -22, 106, -14, -73, -16, 36, 16, + 19, 105, 110, -105, -16, 41, 71, 54, + 80, -38, 109, 73, -110, -63, 21, 72, + 35, 38, 59, 49, 8, -109, 24, 88, + 29, 72, -125, 50, 91, -93, 16, 9, + -77, -53, 126, 20, -64, 33, 2, 58, + -90, 8, -109, 102, 61, 41, -112, 70, + 65, -9, 75, 17, 38, 22, -12, 83, + 35, 125, -4, -14, -62, -95, -106, -103, + -66, -82, 70, -60, -16, 115, 17, 30, + -4, 0, 11, 1, -8, 0, -126, -120, + 75, 65, -47, -42, -58, 126, -55, -128, + 0, 15, 96, 52, 115, 14, -37, 79, + -70, 71, 10, 60, -102, 74, 34, 124, + -25, 10, 5, 112, -24, -46, -68, 105, + 23, -34, -3, 4, 95, -20, 69, -37, + 50, -98, 8, 17, -113, 97, 20, 72, + 33, -107, 88, -45, -56, -49, -80, -85, + -30, 36, 85, -77, 9, 68, 33, -94, + -67, -97, 72, -52, 35, -108, -95, 23, + 96, 40, 22, 40, 64, 12, 87, -122, + -9, 27, -23, 2, 8, -73, -6, -26, + -112, 22, 4, -44, 116, 85, 2, -116, + -109, -24, -101, -34, 56, 1, -74, 16, + 0, 1, -16, 14, 61, 89, 56, 51, + -21, -107, -101, -72, -17, 64, 46, -64, + 2, -80, 13, 1, -37, 16, 1, 4, + 0, 0, 0, 0, -63, 118, 101, -103, + 91, -60, 32, 4, -40, 52, 58, 119, + 64, 32, 0, -52, 0, 0, 0, -120 + } ; + + private static final CompressedGeometryHeader cgHeader ; + + static { + cgHeader = new CompressedGeometryHeader() ; + cgHeader.majorVersionNumber = 1 ; + cgHeader.minorVersionNumber = 0 ; + cgHeader.minorMinorVersionNumber = 1 ; + cgHeader.bufferType = CompressedGeometryHeader.TRIANGLE_BUFFER ; + cgHeader.bufferDataPresent = CompressedGeometryHeader.NORMAL_IN_BUFFER ; + cgHeader.start = 0 ; + cgHeader.size = cgData.length ; + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/picking/IcosahedronITSA.java b/src/main/java/org/jdesktop/j3d/examples/picking/IcosahedronITSA.java new file mode 100644 index 0000000..5d87553 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/picking/IcosahedronITSA.java @@ -0,0 +1,182 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.picking; + +import org.jogamp.java3d.GeometryArray; +import org.jogamp.java3d.IndexedTriangleStripArray; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3f; + +class IcosahedronITSA extends IndexedTriangleStripArray { + + private static final int[] sVertCnt = { + 3, 11, 5, 4, 5, 4 + }; + + IcosahedronITSA() { + super(12, GeometryArray.COORDINATES | GeometryArray.COLOR_3, 32, sVertCnt); + + Point3f verts[] = new Point3f[12]; + Color3f colors[] = new Color3f[12]; + + verts[0] = new Point3f(0.0f, 1.4f, 0.8652f); + verts[1] = new Point3f(0.0f, 1.4f, -0.8652f); + verts[2] = new Point3f(1.4f, 0.8652f, 0.0f); + verts[3] = new Point3f(1.4f, -0.8652f, 0.0f); + verts[4] = new Point3f(0.0f, -1.4f, -0.8652f); + verts[5] = new Point3f(0.0f, -1.4f, 0.8652f); + verts[6] = new Point3f(0.8652f, 0.0f, 1.4f); + verts[7] = new Point3f(-0.8652f, 0.0f, 1.4f); + verts[8] = new Point3f(0.8652f, 0.0f, -1.4f); + verts[9] = new Point3f(-0.8652f, 0.0f, -1.4f); + verts[10] = new Point3f(-1.4f, 0.8652f, 0.0f); + verts[11] = new Point3f(-1.4f, -0.8652f, 0.0f); + + colors[0] = new Color3f(1.0f, 0.0f, 0.0f); + colors[1] = new Color3f(0.0f, 1.0f, 0.0f); + colors[2] = new Color3f(0.0f, 0.0f, 1.0f); + colors[3] = new Color3f(1.0f, 1.0f, 0.0f); + colors[4] = new Color3f(0.0f, 1.0f, 1.0f); + colors[5] = new Color3f(1.0f, 0.0f, 1.0f); + colors[6] = new Color3f(0.0f, 0.5f, 0.0f); + colors[7] = new Color3f(0.0f, 0.0f, 0.5f); + colors[8] = new Color3f(0.5f, 0.5f, 0.0f); + colors[9] = new Color3f(0.0f, 0.5f, 0.5f); + colors[10] = new Color3f(0.5f, 0.0f, 0.5f); + colors[11] = new Color3f(0.5f, 0.5f, 0.5f); + + int pntsIndex[] = new int[32]; + int clrsIndex[] = new int[32]; + + pntsIndex[0] = 4; + clrsIndex[0] = 4; + pntsIndex[1] = 5; + clrsIndex[1] = 5; + pntsIndex[2] = 11; + clrsIndex[2] = 11; + + pntsIndex[3] = 11; + clrsIndex[3] = 11; + pntsIndex[4] = 5; + clrsIndex[4] = 5; + pntsIndex[5] = 7; + clrsIndex[5] = 7; + + pntsIndex[6] = 6; + clrsIndex[6] = 6; + + pntsIndex[7] = 0; + clrsIndex[7] = 0; + + pntsIndex[8] = 2; + clrsIndex[8] = 2; + + pntsIndex[9] = 1; + clrsIndex[9] = 1; + + pntsIndex[10] = 8; + clrsIndex[10] = 8; + + pntsIndex[11] = 9; + clrsIndex[11] = 9; + + pntsIndex[12] = 4; + clrsIndex[12] = 4; + + pntsIndex[13] = 11; + clrsIndex[13] = 11; + + pntsIndex[14] = 2; + clrsIndex[14] = 2; + pntsIndex[15] = 6; + clrsIndex[15] = 6; + pntsIndex[16] = 3; + clrsIndex[16] = 3; + + pntsIndex[17] = 5; + clrsIndex[17] = 5; + + pntsIndex[18] = 4; + clrsIndex[18] = 4; + + pntsIndex[19] = 4; + clrsIndex[19] = 4; + pntsIndex[20] = 8; + clrsIndex[20] = 8; + pntsIndex[21] = 3; + clrsIndex[21] = 3; + + pntsIndex[22] = 2; + clrsIndex[22] = 2; + + pntsIndex[23] = 0; + clrsIndex[23] = 0; + pntsIndex[24] = 1; + clrsIndex[24] = 1; + pntsIndex[25] = 10; + clrsIndex[25] = 10; + + pntsIndex[26] = 9; + clrsIndex[26] = 9; + + pntsIndex[27] = 11; + clrsIndex[27] = 11; + + pntsIndex[28] = 0; + clrsIndex[28] = 0; + pntsIndex[29] = 10; + clrsIndex[29] = 10; + pntsIndex[30] = 7; + clrsIndex[30] = 7; + + pntsIndex[31] = 11; + clrsIndex[31] = 11; + + setCoordinates(0, verts); + setCoordinateIndices(0, pntsIndex); + setColors(0, colors); + setColorIndices(0, clrsIndex); + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/picking/IcosahedronTSA.java b/src/main/java/org/jdesktop/j3d/examples/picking/IcosahedronTSA.java new file mode 100644 index 0000000..065b410 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/picking/IcosahedronTSA.java @@ -0,0 +1,179 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.picking; + +import org.jogamp.java3d.GeometryArray; +import org.jogamp.java3d.TriangleStripArray; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3f; + +class IcosahedronTSA extends TriangleStripArray { + private static final int[] sVertCnt = { + 3, 11, 5, 4, 5, 4 + }; + + IcosahedronTSA() { + super(32, GeometryArray.COORDINATES | GeometryArray.COLOR_3, sVertCnt); + + Point3f verts[] = new Point3f[12]; + Color3f colors[] = new Color3f[12]; + + verts[0] = new Point3f(0.0f, 1.4f, 0.8652f); + verts[1] = new Point3f(0.0f, 1.4f, -0.8652f); + verts[2] = new Point3f(1.4f, 0.8652f, 0.0f); + verts[3] = new Point3f(1.4f, -0.8652f, 0.0f); + verts[4] = new Point3f(0.0f, -1.4f, -0.8652f); + verts[5] = new Point3f(0.0f, -1.4f, 0.8652f); + verts[6] = new Point3f(0.8652f, 0.0f, 1.4f); + verts[7] = new Point3f(-0.8652f, 0.0f, 1.4f); + verts[8] = new Point3f(0.8652f, 0.0f, -1.4f); + verts[9] = new Point3f(-0.8652f, 0.0f, -1.4f); + verts[10] = new Point3f(-1.4f, 0.8652f, 0.0f); + verts[11] = new Point3f(-1.4f, -0.8652f, 0.0f); + + colors[0] = new Color3f(1.0f, 0.0f, 0.0f); + colors[1] = new Color3f(0.0f, 1.0f, 0.0f); + colors[2] = new Color3f(0.0f, 0.0f, 1.0f); + colors[3] = new Color3f(1.0f, 1.0f, 0.0f); + colors[4] = new Color3f(0.0f, 1.0f, 1.0f); + colors[5] = new Color3f(1.0f, 0.0f, 1.0f); + colors[6] = new Color3f(0.0f, 0.5f, 0.0f); + colors[7] = new Color3f(0.0f, 0.0f, 0.5f); + colors[8] = new Color3f(0.5f, 0.5f, 0.0f); + colors[9] = new Color3f(0.0f, 0.5f, 0.5f); + colors[10] = new Color3f(0.5f, 0.0f, 0.5f); + colors[11] = new Color3f(0.5f, 0.5f, 0.5f); + + Point3f pnts[] = new Point3f[32]; + Color3f clrs[] = new Color3f[32]; + + pnts[0] = verts[4]; + clrs[0] = colors[4]; + pnts[1] = verts[5]; + clrs[1] = colors[5]; + pnts[2] = verts[11]; + clrs[2] = colors[11]; + + pnts[3] = verts[11]; + clrs[3] = colors[11]; + pnts[4] = verts[5]; + clrs[4] = colors[5]; + pnts[5] = verts[7]; + clrs[5] = colors[7]; + + pnts[6] = verts[6]; + clrs[6] = colors[6]; + + pnts[7] = verts[0]; + clrs[7] = colors[0]; + + pnts[8] = verts[2]; + clrs[8] = colors[2]; + + pnts[9] = verts[1]; + clrs[9] = colors[1]; + + pnts[10] = verts[8]; + clrs[10] = colors[8]; + + pnts[11] = verts[9]; + clrs[11] = colors[9]; + + pnts[12] = verts[4]; + clrs[12] = colors[4]; + + pnts[13] = verts[11]; + clrs[13] = colors[11]; + + pnts[14] = verts[2]; + clrs[14] = colors[2]; + pnts[15] = verts[6]; + clrs[15] = colors[6]; + pnts[16] = verts[3]; + clrs[16] = colors[3]; + + pnts[17] = verts[5]; + clrs[17] = colors[5]; + + pnts[18] = verts[4]; + clrs[18] = colors[4]; + + pnts[19] = verts[4]; + clrs[19] = colors[4]; + pnts[20] = verts[8]; + clrs[20] = colors[8]; + pnts[21] = verts[3]; + clrs[21] = colors[3]; + + pnts[22] = verts[2]; + clrs[22] = colors[2]; + + pnts[23] = verts[0]; + clrs[23] = colors[0]; + pnts[24] = verts[1]; + clrs[24] = colors[1]; + pnts[25] = verts[10]; + clrs[25] = colors[10]; + + pnts[26] = verts[9]; + clrs[26] = colors[9]; + + pnts[27] = verts[11]; + clrs[27] = colors[11]; + + pnts[28] = verts[0]; + clrs[28] = colors[0]; + pnts[29] = verts[10]; + clrs[29] = colors[10]; + pnts[30] = verts[7]; + clrs[30] = colors[7]; + + pnts[31] = verts[11]; + clrs[31] = colors[11]; + + setCoordinates(0, pnts); + setColors(0, clrs); + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/picking/IntersectInfoBehavior.java b/src/main/java/org/jdesktop/j3d/examples/picking/IntersectInfoBehavior.java new file mode 100644 index 0000000..56c12da --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/picking/IntersectInfoBehavior.java @@ -0,0 +1,271 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.picking; + +import java.awt.AWTEvent; +import java.awt.event.MouseEvent; +import java.util.Enumeration; + +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.Behavior; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.GeometryArray; +import org.jogamp.java3d.Material; +import org.jogamp.java3d.Node; +import org.jogamp.java3d.PickInfo; +import org.jogamp.java3d.PolygonAttributes; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.WakeupCriterion; +import org.jogamp.java3d.WakeupOnAWTEvent; +import org.jogamp.java3d.utils.geometry.Sphere; +import org.jogamp.java3d.utils.pickfast.PickCanvas; +import org.jogamp.java3d.utils.pickfast.PickIntersection; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Color4f; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Vector3d; +import org.jogamp.vecmath.Vector3f; + +/** + * Class: IntersectInfoBehavior + * + * Description: Used to respond to mouse pick and drag events + * in the 3D window. Displays information about the pick. + * + * Version: 1.0 + * + */ +public class IntersectInfoBehavior extends Behavior { + + float size; + PickCanvas pickCanvas; + PickInfo[] pickInfoArr; + Appearance oldlook, redlookwf, redlook, greenlook, bluelook; + Node oldNode = null; + GeometryArray oldGeom = null; + Color3f redColor = new Color3f (1.0f, 0.0f, 0.0f); + TransformGroup[] sphTrans = new TransformGroup [6]; + Sphere[] sph = new Sphere [6]; + Transform3D spht3 = new Transform3D(); + + public IntersectInfoBehavior(Canvas3D canvas3D, BranchGroup branchGroup, + float size) { + pickCanvas = new PickCanvas(canvas3D, branchGroup); + pickCanvas.setTolerance(5.0f); + pickCanvas.setMode(PickInfo.PICK_GEOMETRY); + pickCanvas.setFlags(PickInfo.LOCAL_TO_VWORLD | PickInfo.CLOSEST_GEOM_INFO); + this.size = size; + // Create an Appearance. + redlook = new Appearance(); + Color3f objColor = new Color3f(0.5f, 0.0f, 0.0f); + Color3f black = new Color3f(0.0f, 0.0f, 0.0f); + Color3f white = new Color3f(1.0f, 1.0f, 1.0f); + redlook.setMaterial(new Material(objColor, black, objColor, white, 50.0f)); + redlook.setCapability (Appearance.ALLOW_MATERIAL_WRITE); + + redlookwf = new Appearance (); + redlookwf.setMaterial(new Material(objColor, black, objColor, white, 50.0f)); + PolygonAttributes pa = new PolygonAttributes(); + pa.setPolygonMode(pa.POLYGON_LINE); + pa.setCullFace(pa.CULL_NONE); + redlookwf.setPolygonAttributes(pa); + + oldlook = new Appearance(); + objColor = new Color3f(1.0f, 1.0f, 1.0f); + oldlook.setMaterial(new Material(objColor, black, objColor, white, 50.0f)); + + greenlook = new Appearance(); + objColor = new Color3f(0.0f, 0.8f, 0.0f); + greenlook.setMaterial(new Material(objColor, black, objColor, white, 50.0f)); + bluelook = new Appearance(); + objColor = new Color3f(0.0f, 0.0f, 0.8f); + bluelook.setMaterial(new Material(objColor, black, objColor, white, 50.0f)); + for (int i=0;i<6;i++) { + switch (i) { + case 0: + sph[i] = new Sphere(size*1.15f, redlook); + break; + case 1: + sph[i] = new Sphere(size*1.1f, greenlook); + break; + default: + sph[i] = new Sphere(size, bluelook); + break; + } + sph[i].setPickable (false); + sphTrans[i] = new TransformGroup (); + sphTrans[i].setCapability (TransformGroup.ALLOW_TRANSFORM_READ); + sphTrans[i].setCapability (TransformGroup.ALLOW_TRANSFORM_WRITE); + + // Add sphere, transform + branchGroup.addChild (sphTrans[i]); + sphTrans[i].addChild (sph[i]); + } + } + + public void initialize() { + wakeupOn (new WakeupOnAWTEvent(MouseEvent.MOUSE_PRESSED)); + } + + public void processStimulus (Enumeration criteria) { + WakeupCriterion wakeup; + AWTEvent[] event; + int eventId; + + while (criteria.hasMoreElements()) { + wakeup = (WakeupCriterion) criteria.nextElement(); + if (wakeup instanceof WakeupOnAWTEvent) { + event = ((WakeupOnAWTEvent)wakeup).getAWTEvent(); + for (int i=0; i<event.length; i++) { + eventId = event[i].getID(); + if (eventId == MouseEvent.MOUSE_PRESSED) { + int x = ((MouseEvent)event[i]).getX(); + int y = ((MouseEvent)event[i]).getY(); + pickCanvas.setShapeLocation(x, y); + + pickInfoArr = pickCanvas.pickAllSorted(); + // Use this to do picking benchmarks + /* + long start = System.currentTimeMillis(); + for (int l=0;l<2;l++) { + if (l == 0) System.out.print ("BOUNDS: "); + if (l == 1) System.out.print ("GEOMETRY: "); + + for (int k=0;k<1000;k++) { + if (l == 0) { + pickCanvas.setMode(PickTool.BOUNDS); + pickResult = pickCanvas.pickAllSorted(); + } + if (l == 1) { + pickCanvas.setMode(PickTool.GEOMETRY); + pickResult = pickCanvas.pickAllSorted(); + } + } + long delta = System.currentTimeMillis() - start; + System.out.println ("\t"+delta+" ms / 1000 picks"); + } + */ + if (pickInfoArr != null) { + + // Get closest intersection results + Transform3D l2vw = pickInfoArr[0].getLocalToVWorld(); + PickInfo.IntersectionInfo[] iInfoArr = pickInfoArr[0].getIntersectionInfos(); + PickIntersection pi = new PickIntersection(l2vw, iInfoArr[0]); + + // Safe to assume the return geometry is of GeometryArray type. + GeometryArray curGeomArray = (GeometryArray) iInfoArr[0].getGeometry(); + + // Position sphere at intersection point + Vector3d v = new Vector3d(); + Point3d intPt = pi.getPointCoordinatesVW(); + v.set(intPt); + spht3.setTranslation (v); + sphTrans[0].setTransform (spht3); + + // Position sphere at closest vertex + Point3d closestVert = pi.getClosestVertexCoordinatesVW(); + v.set(closestVert); + spht3.setTranslation (v); + sphTrans[1].setTransform (spht3); + + Point3d []ptw = pi.getPrimitiveCoordinatesVW(); + Point3d []pt = pi.getPrimitiveCoordinates(); + int []coordidx = pi.getPrimitiveCoordinateIndices(); + Point3d ptcoord = new Point3d(); + for (int k=0;k<pt.length;k++) { + v.set(ptw[k]); + spht3.setTranslation (v); + sphTrans[k+2].setTransform (spht3); + } + + // Get interpolated color (if available) + Color4f iColor4 = null; + Color3f iColor = null; + Vector3f iNormal = null; + + if (curGeomArray != null) { + int vf = curGeomArray.getVertexFormat(); + + if (((vf & + (GeometryArray.COLOR_3 | + GeometryArray.COLOR_4)) != 0) && + (null != (iColor4 = + pi.getPointColor()))) { + iColor = + new Color3f(iColor4.x, iColor4.y, iColor4.z); + + // Change the point's color + redlook.setMaterial(new Material(iColor, new Color3f (0.0f, 0.0f, 0.0f), iColor, new Color3f(1.0f, 1.0f, 1.0f), 50.0f)); + } + if (((vf & GeometryArray.NORMALS) != 0) && + (null != (iNormal = + pi.getPointNormal()))) { + System.out.println ("Interpolated normal: "+iNormal); + } + } + + System.out.println ("============="); + System.out.println ("Coordinates of intersection pt:"+intPt); + System.out.println ("Coordinates of vertices: "); + for (int k=0;k<pt.length;k++) { + System.out.println (k + ":" + ptw[k].x + " " + ptw[k].y + " " + ptw[k].z); + } + System.out.println ("Closest vertex: "+closestVert); + if (iColor != null) { + System.out.println ("Interpolated color: "+iColor); + } + if (iNormal != null) { + System.out.println ("Interpolated normal: "+iNormal); + } + } + } + } + } + } + wakeupOn (new WakeupOnAWTEvent(MouseEvent.MOUSE_PRESSED)); + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/picking/IntersectTest.java b/src/main/java/org/jdesktop/j3d/examples/picking/IntersectTest.java new file mode 100644 index 0000000..a95c377 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/picking/IntersectTest.java @@ -0,0 +1,251 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.picking; + +import java.applet.Applet; +import java.awt.BorderLayout; +import java.awt.GraphicsConfiguration; + +import org.jogamp.java3d.AmbientLight; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.DirectionalLight; +import org.jogamp.java3d.GeometryArray; +import org.jogamp.java3d.Group; +import org.jogamp.java3d.LineArray; +import org.jogamp.java3d.PointArray; +import org.jogamp.java3d.Shape3D; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.View; +import org.jogamp.java3d.utils.applet.MainFrame; +import org.jogamp.java3d.utils.behaviors.keyboard.KeyNavigatorBehavior; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Point3f; +import org.jogamp.vecmath.Vector3d; +import org.jogamp.vecmath.Vector3f; + +public class IntersectTest extends Applet { + + BoundingSphere bounds = new BoundingSphere(new Point3d(0.0,0.0,0.0), 1000.0); + + private SimpleUniverse u = null; + + public BranchGroup createSceneGraph () { + + // Create the root of the branch graph + BranchGroup objRoot = new BranchGroup(); + + // Set up the ambient light + Color3f ambientColor = new Color3f(0.1f, 0.1f, 0.1f); + AmbientLight ambientLightNode = new AmbientLight(ambientColor); + ambientLightNode.setInfluencingBounds(bounds); + objRoot.addChild(ambientLightNode); + + // Set up the directional lights + Color3f light1Color = new Color3f(1.0f, 1.0f, 0.9f); + Vector3f light1Direction = new Vector3f(4.0f, -7.0f, -12.0f); + Color3f light2Color = new Color3f(0.3f, 0.3f, 0.4f); + Vector3f light2Direction = new Vector3f(-6.0f, -2.0f, -1.0f); + + DirectionalLight light1 + = new DirectionalLight(light1Color, light1Direction); + light1.setInfluencingBounds(bounds); + objRoot.addChild(light1); + + DirectionalLight light2 + = new DirectionalLight(light2Color, light2Direction); + light2.setInfluencingBounds(bounds); + objRoot.addChild(light2); + + Transform3D t3 = new Transform3D (); + + // Shapes + for (int x=0;x<3;x++) { + for (int y=0;y<3;y++) { + for (int z=0;z<3;z++) { + t3.setTranslation (new Vector3d(-4+x*4.0, -4+y*4.0, -20-z*4.0)); + TransformGroup objTrans = new TransformGroup(t3); + + objRoot.addChild(objTrans); + + // Create a simple shape leaf node, add it to the scene graph. + GeometryArray geom = null; + + if (((x+y+z) % 2) == 0) { + geom = new RandomColorCube(); + } + else { + geom = new RandomColorTetrahedron(); + } + + Shape3D shape = new Shape3D(geom); + + objTrans.addChild(shape); + } + } + } + + // Lines + Point3f[] verts = { + new Point3f (-2.0f, 0.0f, 0.0f),new Point3f(2.0f, 0.0f, 0.0f) + }; + Color3f grey = new Color3f (0.7f, 0.7f, 0.7f); + Color3f[] colors = { + grey, grey + }; + + for (int y=0;y<5;y++) { + for (int z=0;z<5;z++) { + t3.setTranslation (new Vector3d(7.0, -4+y*2.0, -20.0-z*2.0)); + TransformGroup objTrans = new TransformGroup(t3); + + objRoot.addChild(objTrans); + + LineArray la = new LineArray (verts.length, + LineArray.COORDINATES | + LineArray.COLOR_3); + la.setCoordinates (0, verts); + la.setColors (0, colors); + + + Shape3D shape = new Shape3D(); + shape.setGeometry (la); + + + objTrans.addChild(shape); + } + } + + // Points + for (double x=-2.0;x<=2.0;x+=1.0) { + for (double y=-2.0;y<=2.0;y+=1.0) { + for (double z=-2.0;z<=2.0;z+=1.0) { + t3.setTranslation (new Vector3d(-10.0+2.0*x, 0.0+2.0*y,-20.0+2.0*z)); + TransformGroup objTrans = new TransformGroup(t3); + + objRoot.addChild(objTrans); + + PointArray pa = new PointArray (1, + PointArray.COORDINATES | + PointArray.COLOR_3); + + pa.setCoordinate (0, new Point3d (0.0, 0.0, 0.0)); + pa.setColor (0, grey); + + Shape3D shape = new Shape3D(); + shape.setGeometry (pa); + + + objTrans.addChild(shape); + } + } + } + + return objRoot; + } + + public IntersectTest () { + } + + public void init() {System.setProperty("sun.awt.noerasebackground", "true"); + setLayout(new BorderLayout()); + + GraphicsConfiguration config = + SimpleUniverse.getPreferredConfiguration(); + + Canvas3D c = new Canvas3D(config); + add("Center", c); + + // Create a simple scene and attach it to the virtual universe + BranchGroup scene = createSceneGraph(); + u = new SimpleUniverse(c); + + // Add picking behavior + IntersectInfoBehavior behavior = + new IntersectInfoBehavior (c, scene,0.05f); + behavior.setSchedulingBounds (bounds); + scene.addChild (behavior); + + TransformGroup vpTrans = + u.getViewingPlatform().getViewPlatformTransform(); + + KeyNavigatorBehavior keybehavior = new KeyNavigatorBehavior (vpTrans); + keybehavior.setSchedulingBounds (bounds); + scene.addChild (keybehavior); + scene.setCapability (Group.ALLOW_CHILDREN_EXTEND); + scene.compile(); + u.addBranchGraph(scene); + + View view = u.getViewer().getView(); + view.setBackClipDistance (100000); + + } + + public void destroy() { + u.cleanup(); + } + + // + // The following allows IntersectTest to be run as an application + // as well as an applet + // + public static void main(String[] args) {System.setProperty("sun.awt.noerasebackground", "true"); + String s = "\n\nIntersectTest:\n-----------\n"; + s += "Pick with the mouse over the primitives\n"; + s += "- A sphere will be placed to indicate the picked point.\n"; + s += "If color information is available, the sphere will change color to reflect\n"; + s += "the interpolated color.\n"; + s += "- Other spheres will be placed to show the vertices of the selected polygon\n"; + s += "- Information will be displayed about the picking operation\n\n\n"; + + System.out.println (s); + + new MainFrame(new IntersectTest(), 640, 640); + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/picking/MorphingBehavior.java b/src/main/java/org/jdesktop/j3d/examples/picking/MorphingBehavior.java new file mode 100644 index 0000000..0aaf1e1 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/picking/MorphingBehavior.java @@ -0,0 +1,102 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.picking; + +import java.util.Enumeration; + +import org.jogamp.java3d.Alpha; +import org.jogamp.java3d.Behavior; +import org.jogamp.java3d.Morph; +import org.jogamp.java3d.WakeupOnElapsedFrames; + +// User-defined morphing behavior class +public class MorphingBehavior extends Behavior { + + Alpha alpha; + Morph morph; + double weights[]; + + WakeupOnElapsedFrames w = new WakeupOnElapsedFrames(0); + + // Override Behavior's initialize method to setup wakeup criteria + public void initialize() { + alpha.setStartTime(System.currentTimeMillis()); + + // Establish initial wakeup criteria + wakeupOn(w); + } + + // Override Behavior's stimulus method to handle the event + public void processStimulus(Enumeration criteria) { + + // NOTE: This assumes 3 objects. It should be generalized to + // "n" objects. + + double val = alpha.value(); + if (val < 0.5) { + double a = val * 2.0; + weights[0] = 1.0 - a; + weights[1] = a; + weights[2] = 0.0; + } + else { + double a = (val - 0.5) * 2.0; + weights[0] = 0.0; + weights[1] = 1.0f - a; + weights[2] = a; + } + + morph.setWeights(weights); + + // Set wakeup criteria for next time + wakeupOn(w); + } + + public MorphingBehavior(Alpha a, Morph m) { + alpha = a; + morph = m; + weights = morph.getWeights(); + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/picking/OctahedronITFA.java b/src/main/java/org/jdesktop/j3d/examples/picking/OctahedronITFA.java new file mode 100644 index 0000000..b81a00b --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/picking/OctahedronITFA.java @@ -0,0 +1,117 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.picking; + +import org.jogamp.java3d.GeometryArray; +import org.jogamp.java3d.IndexedTriangleFanArray; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3f; + +class OctahedronITFA extends IndexedTriangleFanArray { + private static final int[] sVertCnt = { + 6, 6 + }; + + OctahedronITFA() { + super(6, GeometryArray.COORDINATES | GeometryArray.COLOR_3, 12, sVertCnt); + + Point3f verts[] = new Point3f[6]; + Color3f colors[] = new Color3f[6]; + + verts[0] = new Point3f(0.0f,0.0f,-1.5f); + verts[1] = new Point3f(0.0f,0.0f,1.5f); + verts[2] = new Point3f(0.0f,-1.5f,0.0f); + verts[3] = new Point3f(0.0f,1.5f,0.0f); + verts[4] = new Point3f(1.5f,0.0f,0.0f); + verts[5] = new Point3f(-1.5f,0.0f,0.0f); + + colors[0] = new Color3f(1.0f, 0.0f, 0.0f); + colors[1] = new Color3f(0.0f, 1.0f, 0.0f); + colors[2] = new Color3f(0.0f, 0.0f, 1.0f); + colors[3] = new Color3f(1.0f, 1.0f, 0.0f); + colors[4] = new Color3f(1.0f, 0.0f, 1.0f); + colors[5] = new Color3f(0.0f, 1.0f, 1.0f); + + int pntsIndex[] = new int[12]; + int clrsIndex[] = new int[12]; + + pntsIndex[0] = 4; + clrsIndex[0] = 4; + pntsIndex[1] = 2; + clrsIndex[1] = 2; + pntsIndex[2] = 0; + clrsIndex[2] = 0; + + pntsIndex[3] = 3; + clrsIndex[3] = 3; + + pntsIndex[4] = 1; + clrsIndex[4] = 1; + + pntsIndex[5] = 2; + clrsIndex[5] = 2; + + pntsIndex[6] = 5; + clrsIndex[6] = 5; + pntsIndex[7] = 1; + clrsIndex[7] = 1; + pntsIndex[8] = 3; + clrsIndex[8] = 3; + + pntsIndex[9] = 0; + clrsIndex[9] = 0; + + pntsIndex[10] = 2; + clrsIndex[10] = 2; + + pntsIndex[11] = 1; + clrsIndex[11] = 1; + + setCoordinates(0, verts); + setCoordinateIndices(0, pntsIndex); + setColors(0, colors); + setColorIndices(0, clrsIndex); + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/picking/OctahedronTFA.java b/src/main/java/org/jdesktop/j3d/examples/picking/OctahedronTFA.java new file mode 100644 index 0000000..18e1328 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/picking/OctahedronTFA.java @@ -0,0 +1,116 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.picking; + +import org.jogamp.java3d.GeometryArray; +import org.jogamp.java3d.TriangleFanArray; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3f; + +class OctahedronTFA extends TriangleFanArray { + private static final int[] sVertCnt = { + 6, 6 + }; + + OctahedronTFA() { + super(12, GeometryArray.COORDINATES | GeometryArray.COLOR_3, sVertCnt); + + Point3f verts[] = new Point3f[6]; + Color3f colors[] = new Color3f[6]; + + verts[0] = new Point3f(0.0f,0.0f,-1.5f); + verts[1] = new Point3f(0.0f,0.0f,1.5f); + verts[2] = new Point3f(0.0f,-1.5f,0.0f); + verts[3] = new Point3f(0.0f,1.5f,0.0f); + verts[4] = new Point3f(1.5f,0.0f,0.0f); + verts[5] = new Point3f(-1.5f,0.0f,0.0f); + + colors[0] = new Color3f(1.0f, 0.0f, 0.0f); + colors[1] = new Color3f(0.0f, 1.0f, 0.0f); + colors[2] = new Color3f(0.0f, 0.0f, 1.0f); + colors[3] = new Color3f(1.0f, 1.0f, 0.0f); + colors[4] = new Color3f(1.0f, 0.0f, 1.0f); + colors[5] = new Color3f(0.0f, 1.0f, 1.0f); + + + Point3f pnts[] = new Point3f[12]; + Color3f clrs[] = new Color3f[12]; + + pnts[0] = verts[4]; + clrs[0] = colors[4]; + pnts[1] = verts[2]; + clrs[1] = colors[2]; + pnts[2] = verts[0]; + clrs[2] = colors[0]; + + pnts[3] = verts[3]; + clrs[3] = colors[3]; + + pnts[4] = verts[1]; + clrs[4] = colors[1]; + + pnts[5] = verts[2]; + clrs[5] = colors[2]; + + pnts[6] = verts[5]; + clrs[6] = colors[5]; + pnts[7] = verts[1]; + clrs[7] = colors[1]; + pnts[8] = verts[3]; + clrs[8] = colors[3]; + + pnts[9] = verts[0]; + clrs[9] = colors[0]; + + pnts[10] = verts[2]; + clrs[10] = colors[2]; + + pnts[11] = verts[1]; + clrs[11] = colors[1]; + + setCoordinates(0, pnts); + setColors(0, clrs); + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/picking/PickHighlightBehavior.java b/src/main/java/org/jdesktop/j3d/examples/picking/PickHighlightBehavior.java new file mode 100644 index 0000000..afc5630 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/picking/PickHighlightBehavior.java @@ -0,0 +1,102 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.picking; + +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.Bounds; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.Material; +import org.jogamp.java3d.Shape3D; +import org.jogamp.java3d.utils.picking.PickResult; +import org.jogamp.java3d.utils.picking.PickTool; +import org.jogamp.java3d.utils.picking.behaviors.PickMouseBehavior; +import org.jogamp.vecmath.Color3f; + +public class PickHighlightBehavior extends PickMouseBehavior { + Appearance savedAppearance = null; + Shape3D oldShape = null; + Appearance highlightAppearance; + + public PickHighlightBehavior(Canvas3D canvas, BranchGroup root, + Bounds bounds) { + super(canvas, root, bounds); + this.setSchedulingBounds(bounds); + root.addChild(this); + Color3f white = new Color3f(1.0f, 1.0f, 1.0f); + Color3f black = new Color3f(0.0f, 0.0f, 0.0f); + Color3f highlightColor = new Color3f(0.0f, 1.0f, 0.0f); + Material highlightMaterial = new Material(highlightColor, black, + highlightColor, white, + 80.0f); + highlightAppearance = new Appearance(); + highlightAppearance.setMaterial(new Material(highlightColor, black, + highlightColor, white, + 80.0f)); + + pickCanvas.setMode(PickTool.BOUNDS); + } + + public void updateScene(int xpos, int ypos) { + PickResult pickResult = null; + Shape3D shape = null; + + pickCanvas.setShapeLocation(xpos, ypos); + + pickResult = pickCanvas.pickClosest(); + if (pickResult != null) { + shape = (Shape3D) pickResult.getNode(PickResult.SHAPE3D); + } + + if (oldShape != null){ + oldShape.setAppearance(savedAppearance); + } + if (shape != null) { + savedAppearance = shape.getAppearance(); + oldShape = shape; + shape.setAppearance(highlightAppearance); + } + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/picking/PickTest.java b/src/main/java/org/jdesktop/j3d/examples/picking/PickTest.java new file mode 100644 index 0000000..e36c28b --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/picking/PickTest.java @@ -0,0 +1,442 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.picking; + +import java.applet.Applet; +import java.awt.BorderLayout; +import java.awt.Component; +import java.awt.event.ActionEvent; +import java.awt.event.ActionListener; + +import javax.swing.BoxLayout; +import javax.swing.ButtonGroup; +import javax.swing.JLabel; +import javax.swing.JPanel; +import javax.swing.JRadioButton; +import javax.swing.border.BevelBorder; + +import org.jogamp.java3d.Alpha; +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.DirectionalLight; +import org.jogamp.java3d.Geometry; +import org.jogamp.java3d.GeometryArray; +import org.jogamp.java3d.Group; +import org.jogamp.java3d.Material; +import org.jogamp.java3d.Morph; +import org.jogamp.java3d.PickInfo; +import org.jogamp.java3d.PointAttributes; +import org.jogamp.java3d.QuadArray; +import org.jogamp.java3d.Shape3D; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.View; +import org.jogamp.java3d.utils.applet.MainFrame; +import org.jogamp.java3d.utils.pickfast.behaviors.PickRotateBehavior; +import org.jogamp.java3d.utils.pickfast.behaviors.PickTranslateBehavior; +import org.jogamp.java3d.utils.pickfast.behaviors.PickZoomBehavior; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Vector3d; +import org.jogamp.vecmath.Vector3f; + +/** + * PickTest shows how to use the Picking utilities on various GeometryArray + * subclasses and Morph object. + * Type of Geometry : CompressedGeometry ( GullCG.java ) + * IndexedQuadArray ( CubeIQA.java ) + * TriangleArray ( TetrahedronTA.java ) + * IndexedTriangleArray ( TetrahedronITA.java ) + * TriangleFanArray ( OctahedronTFA.java ) + * IndexedTriangleFanArray ( OctahedronITA.java ) + * TriangleStripArray ( IcosahedronTFA.java ) + * IndexedTriangleStripArray ( IcosahedronITA.java ) + * PointArray( TetrahedronPA.java ) + * LineArray( TetrahedronLA.java ) + * IndexLineArray( TetrahedronILA.java ) + * LineStripArray( TetrahedronLSA.java ) + * IndexLineStripArray( TetrahedronILSA.java ) + * + * Morph Object uses : QuadArray ( ColorCube.java, ColorPyramidDown.java, + * and ColorPyramidUp.java ). + */ + +public class PickTest extends Applet implements ActionListener { + + private View view = null; + private QuadArray geomMorph[] = new QuadArray[3]; + private Morph morph; + + private PickRotateBehavior behavior1; + private PickZoomBehavior behavior2; + private PickTranslateBehavior behavior3; + + private SimpleUniverse u = null; + + public BranchGroup createSceneGraph(Canvas3D canvas) + { + // Create the root of the branch graph + BranchGroup objRoot = new BranchGroup(); + + // Create a Transformgroup to scale all objects so they + // appear in the scene. + TransformGroup objScale = new TransformGroup(); + Transform3D t3d = new Transform3D(); + t3d.setScale(1.0); + objScale.setTransform(t3d); + objRoot.addChild(objScale); + + // Create a bunch of objects with a behavior and add them + // into the scene graph. + + int row, col; + int numRows = 4, numCols = 4; + + for (int i = 0; i < numRows; i++) { + double ypos = (double)(i - numRows/2) * 0.45 + 0.25; + for (int j = 0; j < numCols; j++) { + double xpos = (double)(j - numCols/2) * 0.45 + 0.25; + objScale.addChild(createObject(i * numCols + j, 0.1, xpos, ypos)); + } + } + + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + + // Add a light. + Color3f lColor = new Color3f(1.0f, 1.0f, 1.0f) ; + Vector3f lDir = new Vector3f(0.0f, 0.0f, -1.0f) ; + + DirectionalLight lgt = new DirectionalLight(lColor, lDir) ; + lgt.setInfluencingBounds(bounds) ; + objRoot.addChild(lgt) ; + + + // Now create the Alpha object that controls the speed of the + // morphing operation. + Alpha morphAlpha = new Alpha(-1, Alpha.INCREASING_ENABLE | + Alpha.DECREASING_ENABLE, + 0, 0, + 4000, 1000, 500, + 4000, 1000, 500); + + // Finally, create the morphing behavior + MorphingBehavior mBeh = new MorphingBehavior(morphAlpha, morph); + mBeh.setSchedulingBounds(bounds); + objRoot.addChild(mBeh); + + behavior1 = new PickRotateBehavior(objRoot, canvas, bounds); + objRoot.addChild(behavior1); + + behavior2 = new PickZoomBehavior(objRoot, canvas, bounds); + objRoot.addChild(behavior2); + + behavior3 = new PickTranslateBehavior(objRoot, canvas, bounds); + objRoot.addChild(behavior3); + + // Let Java 3D perform optimizations on this scene graph. + objRoot.compile(); + + return objRoot; + } + + + private Group createObject(int index, double scale, double xpos, double ypos){ + + Shape3D shape = null; + Geometry geom = null; + + // Create a transform group node to scale and position the object. + Transform3D t = new Transform3D(); + t.set(scale, new Vector3d(xpos, ypos, 0.0)); + TransformGroup objTrans = new TransformGroup(t); + objTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + objTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_READ); + objTrans.setCapability(TransformGroup.ENABLE_PICK_REPORTING); + + // Create a second transform group node and initialize it to the + // identity. Enable the TRANSFORM_WRITE capability so that + // our behavior code can modify it at runtime. + TransformGroup spinTg = new TransformGroup(); + spinTg.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + spinTg.setCapability(TransformGroup.ALLOW_TRANSFORM_READ); + spinTg.setCapability(TransformGroup.ENABLE_PICK_REPORTING); + + Appearance appearance = new Appearance(); + + switch(index) { + case 0: + geom = new GullCG(); + break; + case 1: + geom = new TetrahedronTA(); + break; + case 2: + geom = new OctahedronTFA(); + break; + case 3: + geom = new IcosahedronTSA(); + break; + case 4: + geom = new CubeIQA(); + break; + case 5: + geom = new TetrahedronITA(); + break; + case 6: + geom = new OctahedronITFA(); + break; + case 7: + geom = new IcosahedronITSA(); + break; + case 8: + geomMorph[0] = new ColorPyramidUp(); + geomMorph[1] = new ColorCube(); + geomMorph[2] = new ColorPyramidDown(); + break; + case 9: + geom = new TetrahedronLA(); + break; + case 10: + geom = new TetrahedronILA(); + break; + case 11: + geom = new TetrahedronLSA(); + break; + case 12: + geom = new TetrahedronILSA(); + break; + case 13: + geom = new TetrahedronPA(); + break; + case 14: + geom = new TetrahedronIPA(); + break; + // TODO: other geo types, Text3D? + case 15: + geom = new TetrahedronTA(); + break; + } + + Material m = new Material() ; + + if(index == 8) { + m.setLightingEnable(false) ; + appearance.setMaterial(m) ; + morph = new Morph((GeometryArray[]) geomMorph, appearance); + morph.setCapability(Morph.ALLOW_WEIGHTS_READ); + morph.setCapability(Morph.ALLOW_WEIGHTS_WRITE); + spinTg.addChild(morph); + } else { + // Geometry picking require this to be set. + if (index == 0) + m.setLightingEnable(true) ; + else + m.setLightingEnable(false) ; + appearance.setMaterial(m) ; + + if ((index == 13) || (index == 14)) { + PointAttributes pa = new PointAttributes(); + pa.setPointSize(4.0f); + appearance.setPointAttributes(pa); + } + + shape = new Shape3D(geom,appearance); + shape.setCapability(Shape3D.ALLOW_APPEARANCE_READ); + shape.setCapability(Shape3D.ALLOW_APPEARANCE_WRITE); + shape.setCapability(Shape3D.ENABLE_PICK_REPORTING); + spinTg.addChild(shape); + } + + // add it to the scene graph. + objTrans.addChild(spinTg); + + return objTrans; + } + + private void setPickMode(int mode) { + behavior1.setMode(mode); + behavior2.setMode(mode); + behavior3.setMode(mode); + } + + private void setPickTolerance(float tolerance) { + behavior1.setTolerance(tolerance); + behavior2.setTolerance(tolerance); + behavior3.setTolerance(tolerance); + } + + private void setViewMode(int mode) { + view.setProjectionPolicy(mode); + } + + // GUI stuff + + String pickModeString = new String("Pick Mode"); + String boundsString = new String("BOUNDS"); + String geometryString = new String("GEOMETRY"); + String toleranceString = new String("Pick Tolerance"); + String tolerance0String = new String("0"); + String tolerance2String = new String("2"); + String tolerance4String = new String("4"); + String tolerance8String = new String("8"); + String viewModeString = new String("View Mode"); + String perspectiveString = new String("Perspective"); + String parallelString = new String("Parallel"); + + private void addRadioButton(JPanel panel, ButtonGroup bg, String ownerName, + String buttonName, boolean selected) { + JRadioButton item; + item = new JRadioButton(buttonName); + item.setName(ownerName); + item.addActionListener(this); + if (selected) { + item.setSelected(true); + } + panel.add(item); + bg.add(item); + } + + private void setupGUI(JPanel panel) { + ButtonGroup bg; + + panel.setLayout(new BoxLayout(panel, BoxLayout.Y_AXIS)); + panel.setBorder(new BevelBorder(BevelBorder.RAISED)); + + panel.add(new JLabel(pickModeString)); + bg = new ButtonGroup(); + addRadioButton(panel, bg, pickModeString, boundsString, true); + addRadioButton(panel, bg, pickModeString, geometryString, false); + + panel.add(new JLabel(toleranceString)); + bg = new ButtonGroup(); + addRadioButton(panel, bg, toleranceString, tolerance0String,false); + addRadioButton(panel, bg, toleranceString, tolerance2String,true); + addRadioButton(panel, bg, toleranceString, tolerance4String,false); + addRadioButton(panel, bg, toleranceString, tolerance8String,false); + + panel.add(new JLabel(viewModeString)); + bg = new ButtonGroup(); + addRadioButton(panel, bg, viewModeString, perspectiveString, true); + addRadioButton(panel, bg, viewModeString, parallelString, false); + + } + + public void actionPerformed(ActionEvent e) { + String name = ((Component)e.getSource()).getName(); + String value = e.getActionCommand(); + //System.out.println("action: name = " + name + " value = " + value); + if (name == pickModeString) { + if (value == boundsString) { + setPickMode(PickInfo.PICK_BOUNDS); + } else if (value == geometryString) { + setPickMode(PickInfo.PICK_GEOMETRY); + } else { + System.out.println("Unknown pick mode: " + value); + } + } else if (name == toleranceString) { + if (value == tolerance0String) { + setPickTolerance(0.0f); + } else if (value == tolerance2String) { + setPickTolerance(2.0f); + } else if (value == tolerance4String) { + setPickTolerance(4.0f); + } else if (value == tolerance8String) { + setPickTolerance(8.0f); + } else { + System.out.println("Unknown tolerance: " + value); + } + } else if (name == viewModeString) { + if (value == perspectiveString) { + setViewMode(View.PERSPECTIVE_PROJECTION); + } else if (value == parallelString) { + setViewMode(View.PARALLEL_PROJECTION); + } + } else { + System.out.println("Unknown action name: " + name); + } + } + + public PickTest (){ + } + + public void init() {System.setProperty("sun.awt.noerasebackground", "true"); + setLayout(new BorderLayout()); + Canvas3D c = new Canvas3D(SimpleUniverse.getPreferredConfiguration()); + add("Center", c); + + JPanel guiPanel = new JPanel(); + setupGUI(guiPanel); + add(guiPanel, BorderLayout.EAST); + + // Create a scene and attach it to the virtual universe + BranchGroup scene = createSceneGraph(c); + u = new SimpleUniverse(c); + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + u.getViewingPlatform().setNominalViewingTransform(); + view = u.getViewer().getView(); + + u.addBranchGraph(scene); + } + + public void destroy() { + u.cleanup(); + } + + + public static void main(String argv[]) + { + + BranchGroup group; + + new MainFrame(new PickTest(), 750, 550); + } +} + diff --git a/src/main/java/org/jdesktop/j3d/examples/picking/PickText3DBounds.java b/src/main/java/org/jdesktop/j3d/examples/picking/PickText3DBounds.java new file mode 100644 index 0000000..35ef883 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/picking/PickText3DBounds.java @@ -0,0 +1,254 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.picking; + +import java.applet.Applet; +import java.awt.BorderLayout; +import java.awt.Font; +import java.awt.GraphicsConfiguration; + +import org.jogamp.java3d.AmbientLight; +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.Background; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.ColoringAttributes; +import org.jogamp.java3d.Font3D; +import org.jogamp.java3d.FontExtrusion; +import org.jogamp.java3d.Light; +import org.jogamp.java3d.Material; +import org.jogamp.java3d.PointLight; +import org.jogamp.java3d.Shape3D; +import org.jogamp.java3d.Text3D; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.utils.applet.MainFrame; +import org.jogamp.java3d.utils.geometry.Sphere; +import org.jogamp.java3d.utils.picking.PickTool; +import org.jogamp.java3d.utils.picking.behaviors.PickRotateBehavior; +import org.jogamp.java3d.utils.picking.behaviors.PickTranslateBehavior; +import org.jogamp.java3d.utils.picking.behaviors.PickZoomBehavior; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Point3f; +import org.jogamp.vecmath.Vector3d; + +public class PickText3DBounds extends Applet { + + private SimpleUniverse u = null; + + public BranchGroup createSceneGraph(Canvas3D canvas) { + Color3f eColor = new Color3f(0.0f, 0.0f, 0.0f); + Color3f sColor = new Color3f(1.0f, 1.0f, 1.0f); + Color3f objColor = new Color3f(0.6f, 0.6f, 0.6f); + Color3f lColor1 = new Color3f(1.0f, 0.0f, 0.0f); + Color3f lColor2 = new Color3f(0.0f, 1.0f, 0.0f); + Color3f alColor = new Color3f(0.2f, 0.2f, 0.2f); + Color3f bgColor = new Color3f(0.05f, 0.05f, 0.2f); + + Transform3D t; + + // Create the root of the branch graph + BranchGroup objRoot = new BranchGroup(); + + // Create a Transformgroup to scale all objects so they + // appear in the scene. + TransformGroup objScale = new TransformGroup(); + Transform3D t3d = new Transform3D(); + t3d.setScale(0.4); + objScale.setTransform(t3d); + objRoot.addChild(objScale); + + // Create a bounds for the background and lights + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + + // Set up the background + Background bg = new Background(bgColor); + bg.setApplicationBounds(bounds); + objScale.addChild(bg); + + Material m = new Material(objColor, eColor, objColor, sColor, 100.0f); + Appearance a = new Appearance(); + m.setLightingEnable(true); + a.setMaterial(m); + Font3D f3d = new Font3D(new Font("TestFont", Font.PLAIN, 1), + new FontExtrusion()); + Text3D txt = new Text3D(f3d, new String("TEXT3D"), + new Point3f(-2.0f, 0.0f, 0.0f)); + // txt.setCapability(Geometry.ALLOW_INTERSECT); + Shape3D s3D = new Shape3D(); + s3D.setGeometry(txt); + s3D.setAppearance(a); + + // Create a transform group node and initialize it to the + // identity. Enable the TRANSFORM_WRITE capability so that + // our behavior code can modify it at runtime. + TransformGroup spinTg = new TransformGroup(); + spinTg.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + spinTg.setCapability(TransformGroup.ALLOW_TRANSFORM_READ); + spinTg.setCapability(TransformGroup.ENABLE_PICK_REPORTING); + + spinTg.addChild(s3D); + objScale.addChild(spinTg); + + // Create the transform group node for the each light and initialize + // it to the identity. Enable the TRANSFORM_WRITE capability so that + // our behavior code can modify it at runtime. Add them to the root + // of the subgraph. + + // Create transformations for the positional lights + t = new Transform3D(); + Vector3d lPos1 = new Vector3d(0.0, 0.0, 2.0); + t.set(lPos1); + TransformGroup l1Trans = new TransformGroup(t); + l1Trans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + l1Trans.setCapability(TransformGroup.ALLOW_TRANSFORM_READ); + l1Trans.setCapability(TransformGroup.ENABLE_PICK_REPORTING); + objScale.addChild(l1Trans); + + t = new Transform3D(); + Vector3d lPos2 = new Vector3d(0.5, 0.8, 2.0); + t.set(lPos2); + TransformGroup l2Trans = new TransformGroup(t); + l2Trans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + l2Trans.setCapability(TransformGroup.ALLOW_TRANSFORM_READ); + l2Trans.setCapability(TransformGroup.ENABLE_PICK_REPORTING); + + objScale.addChild(l2Trans); + + // Create Geometry for point lights + ColoringAttributes caL1 = new ColoringAttributes(); + ColoringAttributes caL2 = new ColoringAttributes(); + caL1.setColor(lColor1); + caL2.setColor(lColor2); + Appearance appL1 = new Appearance(); + Appearance appL2 = new Appearance(); + appL1.setColoringAttributes(caL1); + appL2.setColoringAttributes(caL2); + l1Trans.addChild(new Sphere(0.05f, + Sphere.GENERATE_NORMALS, 15, appL1)); + l2Trans.addChild(new Sphere(0.05f, + Sphere.GENERATE_NORMALS, 15, appL2)); + + // Create lights + AmbientLight aLgt = new AmbientLight(alColor); + + Light lgt1; + Light lgt2; + + Point3f lPoint = new Point3f(0.0f, 0.0f, 0.0f); + Point3f atten = new Point3f(1.0f, 0.0f, 0.0f); + lgt1 = new PointLight(lColor1, lPoint, atten); + lgt2 = new PointLight(lColor2, lPoint, atten); + + // Set the influencing bounds + aLgt.setInfluencingBounds(bounds); + lgt1.setInfluencingBounds(bounds); + lgt2.setInfluencingBounds(bounds); + + // Add the lights into the scene graph + objScale.addChild(aLgt); + l1Trans.addChild(lgt1); + l2Trans.addChild(lgt2); + + + PickRotateBehavior behavior1 = + new PickRotateBehavior(objRoot, canvas, bounds); + behavior1.setMode(PickTool.BOUNDS); + objRoot.addChild(behavior1); + + PickZoomBehavior behavior2 = + new PickZoomBehavior(objRoot, canvas, bounds); + behavior2.setMode(PickTool.BOUNDS); + objRoot.addChild(behavior2); + + PickTranslateBehavior behavior3 = + new PickTranslateBehavior(objRoot, canvas, bounds); + behavior3.setMode(PickTool.BOUNDS); + objRoot.addChild(behavior3); + + + // Let Java 3D perform optimizations on this scene graph. + objRoot.compile(); + + return objRoot; + } + + public PickText3DBounds() { + } + + public void init() {System.setProperty("sun.awt.noerasebackground", "true"); + setLayout(new BorderLayout()); + GraphicsConfiguration config = + SimpleUniverse.getPreferredConfiguration(); + + Canvas3D c = new Canvas3D(config); + add("Center", c); + + u = new SimpleUniverse(c); + BranchGroup scene = createSceneGraph(c); + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + u.getViewingPlatform().setNominalViewingTransform(); + + u.addBranchGraph(scene); + } + + public void destroy() { + u.cleanup(); + } + + // + // The following allows Text3DMotion to be run as an application + // as well as an applet + // + public static void main(String[] args) {System.setProperty("sun.awt.noerasebackground", "true"); + new MainFrame(new PickText3DBounds(), 700, 700); + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/picking/PickText3DGeometry.java b/src/main/java/org/jdesktop/j3d/examples/picking/PickText3DGeometry.java new file mode 100644 index 0000000..577c217 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/picking/PickText3DGeometry.java @@ -0,0 +1,273 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.picking; + +import java.applet.Applet; +import java.awt.BorderLayout; +import java.awt.Font; +import java.awt.GraphicsConfiguration; + +import org.jogamp.java3d.AmbientLight; +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.Background; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.ColoringAttributes; +import org.jogamp.java3d.Font3D; +import org.jogamp.java3d.FontExtrusion; +import org.jogamp.java3d.Geometry; +import org.jogamp.java3d.Light; +import org.jogamp.java3d.Material; +import org.jogamp.java3d.PointLight; +import org.jogamp.java3d.Shape3D; +import org.jogamp.java3d.Text3D; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.utils.applet.MainFrame; +import org.jogamp.java3d.utils.geometry.Sphere; +import org.jogamp.java3d.utils.picking.PickTool; +import org.jogamp.java3d.utils.picking.behaviors.PickRotateBehavior; +import org.jogamp.java3d.utils.picking.behaviors.PickTranslateBehavior; +import org.jogamp.java3d.utils.picking.behaviors.PickZoomBehavior; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Point3f; +import org.jogamp.vecmath.Vector3d; + +public class PickText3DGeometry extends Applet { + + private SimpleUniverse u = null; + + public BranchGroup createSceneGraph(Canvas3D canvas) { + Color3f eColor = new Color3f(0.0f, 0.0f, 0.0f); + Color3f sColor = new Color3f(1.0f, 1.0f, 1.0f); + Color3f objColor = new Color3f(0.6f, 0.6f, 0.6f); + Color3f lColor1 = new Color3f(1.0f, 0.0f, 0.0f); + Color3f lColor2 = new Color3f(0.0f, 1.0f, 0.0f); + Color3f alColor = new Color3f(0.2f, 0.2f, 0.2f); + Color3f bgColor = new Color3f(0.05f, 0.05f, 0.2f); + + Transform3D t; + + // Create the root of the branch graph + BranchGroup objRoot = new BranchGroup(); + + // Create a Transformgroup to scale all objects so they + // appear in the scene. + TransformGroup objScale = new TransformGroup(); + Transform3D t3d = new Transform3D(); + t3d.setScale(0.4); + objScale.setTransform(t3d); + objRoot.addChild(objScale); + + // Create a bounds for the background and lights + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + + // Set up the background + Background bg = new Background(bgColor); + bg.setApplicationBounds(bounds); + objScale.addChild(bg); + + Material m = new Material(objColor, eColor, objColor, sColor, 100.0f); + Appearance a = new Appearance(); + m.setLightingEnable(true); + a.setMaterial(m); + Font3D f3d = new Font3D(new Font("TestFont", Font.PLAIN, 1), + new FontExtrusion()); + + Text3D text3D = new Text3D(f3d, new String("TEXT3D"), + new Point3f(-2.0f, 0.7f, 0.0f)); + text3D.setCapability(Geometry.ALLOW_INTERSECT); + Shape3D s3D1 = new Shape3D(); + s3D1.setGeometry(text3D); + s3D1.setAppearance(a); + + // Create a transform group node and initialize it to the + // identity. Enable the TRANSFORM_WRITE capability so that + // our behavior code can modify it at runtime. + TransformGroup spinTg1 = new TransformGroup(); + spinTg1.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + spinTg1.setCapability(TransformGroup.ALLOW_TRANSFORM_READ); + spinTg1.setCapability(TransformGroup.ENABLE_PICK_REPORTING); + + spinTg1.addChild(s3D1); + objScale.addChild(spinTg1); + + Text3D pick = new Text3D(f3d, new String("Pick me"), + new Point3f(-2.0f, -0.7f, 0.0f)); + pick.setCapability(Geometry.ALLOW_INTERSECT); + Shape3D s3D2 = new Shape3D(); + s3D2.setGeometry(pick); + s3D2.setAppearance(a); + + // Create a transform group node and initialize it to the + // identity. Enable the TRANSFORM_WRITE capability so that + // our behavior code can modify it at runtime. + TransformGroup spinTg2 = new TransformGroup(); + spinTg2.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + spinTg2.setCapability(TransformGroup.ALLOW_TRANSFORM_READ); + spinTg2.setCapability(TransformGroup.ENABLE_PICK_REPORTING); + + spinTg2.addChild(s3D2); + objScale.addChild(spinTg2); + + // Create the transform group node for the each light and initialize + // it to the identity. Enable the TRANSFORM_WRITE capability so that + // our behavior code can modify it at runtime. Add them to the root + // of the subgraph. + + // Create transformations for the positional lights + t = new Transform3D(); + Vector3d lPos1 = new Vector3d(0.0, 0.0, 2.0); + t.set(lPos1); + TransformGroup l1Trans = new TransformGroup(t); + l1Trans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + l1Trans.setCapability(TransformGroup.ALLOW_TRANSFORM_READ); + l1Trans.setCapability(TransformGroup.ENABLE_PICK_REPORTING); + objScale.addChild(l1Trans); + + t = new Transform3D(); + Vector3d lPos2 = new Vector3d(0.5, 1.2, 2.0); + t.set(lPos2); + TransformGroup l2Trans = new TransformGroup(t); + l2Trans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + l2Trans.setCapability(TransformGroup.ALLOW_TRANSFORM_READ); + l2Trans.setCapability(TransformGroup.ENABLE_PICK_REPORTING); + objScale.addChild(l2Trans); + + // Create Geometry for point lights + ColoringAttributes caL1 = new ColoringAttributes(); + ColoringAttributes caL2 = new ColoringAttributes(); + caL1.setColor(lColor1); + caL2.setColor(lColor2); + Appearance appL1 = new Appearance(); + Appearance appL2 = new Appearance(); + appL1.setColoringAttributes(caL1); + appL2.setColoringAttributes(caL2); + l1Trans.addChild(new Sphere(0.05f, + Sphere.GENERATE_NORMALS | Sphere.ENABLE_GEOMETRY_PICKING, 15, appL1)); + l2Trans.addChild(new Sphere(0.05f, + Sphere.GENERATE_NORMALS | Sphere.ENABLE_GEOMETRY_PICKING, 15, appL2)); + + // Create lights + AmbientLight aLgt = new AmbientLight(alColor); + + Light lgt1; + Light lgt2; + + Point3f lPoint = new Point3f(0.0f, 0.0f, 0.0f); + Point3f atten = new Point3f(1.0f, 0.0f, 0.0f); + lgt1 = new PointLight(lColor1, lPoint, atten); + lgt2 = new PointLight(lColor2, lPoint, atten); + + // Set the influencing bounds + aLgt.setInfluencingBounds(bounds); + lgt1.setInfluencingBounds(bounds); + lgt2.setInfluencingBounds(bounds); + + // Add the lights into the scene graph + objScale.addChild(aLgt); + l1Trans.addChild(lgt1); + l2Trans.addChild(lgt2); + + PickRotateBehavior behavior1 = + new PickRotateBehavior(objRoot, canvas, bounds); + behavior1.setMode(PickTool.GEOMETRY); + behavior1.setTolerance(0.0f); + objRoot.addChild(behavior1); + + PickZoomBehavior behavior2 = + new PickZoomBehavior(objRoot, canvas, bounds); + behavior2.setMode(PickTool.GEOMETRY); + behavior2.setTolerance(0.0f); + objRoot.addChild(behavior2); + + PickTranslateBehavior behavior3 = + new PickTranslateBehavior(objRoot, canvas, bounds); + behavior3.setMode(PickTool.GEOMETRY); + behavior3.setTolerance(0.0f); + objRoot.addChild(behavior3); + + // Let Java 3D perform optimizations on this scene graph. + objRoot.compile(); + + return objRoot; + } + + public PickText3DGeometry() { + } + + public void init() {System.setProperty("sun.awt.noerasebackground", "true"); + setLayout(new BorderLayout()); + GraphicsConfiguration config = + SimpleUniverse.getPreferredConfiguration(); + Canvas3D c = new Canvas3D(config); + add("Center", c); + + u = new SimpleUniverse(c); + BranchGroup scene = createSceneGraph(c); + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + u.getViewingPlatform().setNominalViewingTransform(); + + u.addBranchGraph(scene); + } + + public void destroy() { + u.cleanup(); + } + + // + // The following allows Text3DMotion to be run as an application + // as well as an applet + // + public static void main(String[] args) {System.setProperty("sun.awt.noerasebackground", "true"); + new MainFrame(new PickText3DGeometry(), 700, 700); + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/picking/RandomColorCube.java b/src/main/java/org/jdesktop/j3d/examples/picking/RandomColorCube.java new file mode 100644 index 0000000..e278580 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/picking/RandomColorCube.java @@ -0,0 +1,133 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.picking; + +import org.jogamp.java3d.GeometryArray; +import org.jogamp.java3d.QuadArray; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3f; + +class RandomColorCube extends QuadArray { + RandomColorCube() { + super(24, GeometryArray.COORDINATES | GeometryArray.COLOR_3); + + Point3f verts[] = new Point3f[8]; + Color3f colors[] = new Color3f[3]; + + verts[0] = new Point3f(0.5f, 0.5f, 0.5f); + verts[1] = new Point3f(-0.5f, 0.5f, 0.5f); + verts[2] = new Point3f(-0.5f,-0.5f, 0.5f); + verts[3] = new Point3f( 0.5f,-0.5f, 0.5f); + verts[4] = new Point3f( 0.5f, 0.5f,-0.5f); + verts[5] = new Point3f( -0.5f, 0.5f,-0.5f); + verts[6] = new Point3f( -0.5f,-0.5f,-0.5f); + verts[7] = new Point3f( 0.5f,-0.5f,-0.5f); + + colors[0] = new Color3f(1.0f, 0.0f, 0.0f); + colors[1] = new Color3f(0.0f, 1.0f, 0.0f); + colors[2] = new Color3f(0.0f, 0.0f, 1.0f); + + Point3f pnts[] = new Point3f[24]; + Color3f clrs[] = new Color3f[24]; + + pnts[0] = verts[0]; + clrs[0] = colors[(int)(Math.random()*3.0)]; + pnts[1] = verts[3]; + clrs[1] = colors[(int)(Math.random()*3.0)]; + pnts[2] = verts[7]; + clrs[2] = colors[(int)(Math.random()*3.0)]; + pnts[3] = verts[4]; + clrs[3] = colors[(int)(Math.random()*3.0)]; + + pnts[4] = verts[1]; + clrs[4] = colors[(int)(Math.random()*3.0)]; + pnts[5] = verts[5]; + clrs[5] = colors[(int)(Math.random()*3.0)]; + pnts[6] = verts[6]; + clrs[6] = colors[(int)(Math.random()*3.0)]; + pnts[7] = verts[2]; + clrs[7] = colors[(int)(Math.random()*3.0)]; + + pnts[8] = verts[0]; + clrs[8] = colors[(int)(Math.random()*3.0)]; + pnts[9] = verts[4]; + clrs[9] = colors[(int)(Math.random()*3.0)]; + pnts[10] = verts[5]; + clrs[10] = colors[(int)(Math.random()*3.0)]; + pnts[11] = verts[1]; + clrs[11] = colors[(int)(Math.random()*3.0)]; + + pnts[12] = verts[3]; + clrs[12] = colors[(int)(Math.random()*3.0)]; + pnts[13] = verts[2]; + clrs[13] = colors[(int)(Math.random()*3.0)]; + pnts[14] = verts[6]; + clrs[14] = colors[(int)(Math.random()*3.0)]; + pnts[15] = verts[7]; + clrs[15] = colors[(int)(Math.random()*3.0)]; + + pnts[16] = verts[0]; + clrs[16] = colors[(int)(Math.random()*3.0)]; + pnts[17] = verts[1]; + clrs[17] = colors[(int)(Math.random()*3.0)]; + pnts[18] = verts[2]; + clrs[18] = colors[(int)(Math.random()*3.0)]; + pnts[19] = verts[3]; + clrs[19] = colors[(int)(Math.random()*3.0)]; + + pnts[20] = verts[7]; + clrs[20] = colors[(int)(Math.random()*3.0)]; + pnts[21] = verts[6]; + clrs[21] = colors[(int)(Math.random()*3.0)]; + pnts[22] = verts[5]; + clrs[22] = colors[(int)(Math.random()*3.0)]; + pnts[23] = verts[4]; + clrs[23] = colors[(int)(Math.random()*3.0)]; + + + setCoordinates(0, pnts); + setColors(0, clrs); + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/picking/RandomColorTetrahedron.java b/src/main/java/org/jdesktop/j3d/examples/picking/RandomColorTetrahedron.java new file mode 100644 index 0000000..dd8c1b0 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/picking/RandomColorTetrahedron.java @@ -0,0 +1,103 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.picking; + +import org.jogamp.java3d.GeometryArray; +import org.jogamp.java3d.TriangleArray; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3f; + +class RandomColorTetrahedron extends TriangleArray { + + RandomColorTetrahedron() { + super(12, GeometryArray.COORDINATES | GeometryArray.COLOR_3); + + Point3f verts[] = new Point3f[4]; + Color3f colors[] = new Color3f[4]; + + verts[0] = new Point3f(0.5f,0.5f,0.5f); + verts[1] = new Point3f(0.5f,-0.5f,-0.5f); + verts[2] = new Point3f(-0.5f,-0.5f,0.5f); + verts[3] = new Point3f(-0.5f,0.5f,-0.5f); + + colors[0] = new Color3f(1.0f, 0.0f, 0.0f); + colors[1] = new Color3f(0.0f, 1.0f, 0.0f); + colors[2] = new Color3f(0.0f, 0.0f, 1.0f); + + Point3f pnts[] = new Point3f[12]; + Color3f clrs[] = new Color3f[12]; + + pnts[0] = verts[2]; + clrs[0] = colors[(int)(Math.random() * 3.0)]; + pnts[1] = verts[1]; + clrs[1] = colors[(int)(Math.random() * 3.0)]; + pnts[2] = verts[0]; + clrs[2] = colors[(int)(Math.random() * 3.0)]; + + pnts[3] = verts[3]; + clrs[3] = colors[(int)(Math.random() * 3.0)]; + pnts[4] = verts[2]; + clrs[4] = colors[(int)(Math.random() * 3.0)]; + pnts[5] = verts[0]; + clrs[5] = colors[(int)(Math.random() * 3.0)]; + + pnts[6] = verts[1]; + clrs[6] = colors[(int)(Math.random() * 3.0)]; + pnts[7] = verts[2]; + clrs[7] = colors[(int)(Math.random() * 3.0)]; + pnts[8] = verts[3]; + clrs[8] = colors[(int)(Math.random() * 3.0)]; + + pnts[9] = verts[1]; + clrs[9] = colors[(int)(Math.random() * 3.0)]; + pnts[10] = verts[3]; + clrs[10] = colors[(int)(Math.random() * 3.0)]; + pnts[11] = verts[0]; + clrs[11] = colors[(int)(Math.random() * 3.0)]; + + setCoordinates(0, pnts); + setColors(0, clrs); + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/picking/Tetrahedron.java b/src/main/java/org/jdesktop/j3d/examples/picking/Tetrahedron.java new file mode 100644 index 0000000..5f8859b --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/picking/Tetrahedron.java @@ -0,0 +1,117 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.picking; + +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.Geometry; +import org.jogamp.java3d.Shape3D; +import org.jogamp.java3d.TriangleArray; +import org.jogamp.vecmath.Point3f; +import org.jogamp.vecmath.TexCoord2f; +import org.jogamp.vecmath.Vector3f; + +public class Tetrahedron extends Shape3D { + private static final float sqrt3 = (float) Math.sqrt(3.0); + private static final float sqrt3_3 = sqrt3 / 3.0f; + private static final float sqrt24_3 = (float) Math.sqrt(24.0) / 3.0f; + + private static final float ycenter = 0.5f * sqrt24_3; + private static final float zcenter = -sqrt3_3; + + private static final Point3f p1 = new Point3f(-1.0f, -ycenter, -zcenter); + private static final Point3f p2 = new Point3f(1.0f, -ycenter, -zcenter); + private static final Point3f p3 = + new Point3f(0.0f, -ycenter, -sqrt3 - zcenter); + private static final Point3f p4 = + new Point3f(0.0f, sqrt24_3 - ycenter, 0.0f); + + private static final Point3f[] verts = { + p1, p2, p4, // front face + p1, p4, p3, // left, back face + p2, p3, p4, // right, back face + p1, p3, p2, // bottom face + }; + + private TexCoord2f texCoord[] = { + new TexCoord2f(0.0f, 0.0f), + new TexCoord2f(1.0f, 0.0f), + new TexCoord2f(0.5f, sqrt3 / 2.0f), + }; + + public Tetrahedron() { + int i; + + TriangleArray tetra = new TriangleArray(12, TriangleArray.COORDINATES | + TriangleArray.NORMALS | TriangleArray.TEXTURE_COORDINATE_2); + + tetra.setCoordinates(0, verts); + for (i = 0; i < 12; i++) { + tetra.setTextureCoordinate(0, i, texCoord[i%3]); + } + + int face; + Vector3f normal = new Vector3f(); + Vector3f v1 = new Vector3f(); + Vector3f v2 = new Vector3f(); + Point3f [] pts = new Point3f[3]; + for (i = 0; i < 3; i++) pts[i] = new Point3f(); + + for (face = 0; face < 4; face++) { + tetra.getCoordinates(face*3, pts); + v1.sub(pts[1], pts[0]); + v2.sub(pts[2], pts[0]); + normal.cross(v1, v2); + normal.normalize(); + for (i = 0; i < 3; i++) { + tetra.setNormal((face * 3 + i), normal); + } + } + + tetra.setCapability(Geometry.ALLOW_INTERSECT); + + this.setGeometry(tetra); + this.setAppearance(new Appearance()); + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/picking/TetrahedronILA.java b/src/main/java/org/jdesktop/j3d/examples/picking/TetrahedronILA.java new file mode 100644 index 0000000..507edf1 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/picking/TetrahedronILA.java @@ -0,0 +1,108 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.picking; + +import org.jogamp.java3d.GeometryArray; +import org.jogamp.java3d.IndexedLineArray; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3f; + +class TetrahedronILA extends IndexedLineArray { + + TetrahedronILA() { + super(4, GeometryArray.COORDINATES | GeometryArray.COLOR_3, 12); + + Point3f verts[] = new Point3f[4]; + Color3f colors[] = new Color3f[4]; + + verts[0] = new Point3f(1.0f,1.0f,1.0f); + verts[1] = new Point3f(1.0f,-1.0f,-1.0f); + verts[2] = new Point3f(-1.0f,-1.0f,1.0f); + verts[3] = new Point3f(-1.0f,1.0f,-1.0f); + + colors[0] = new Color3f(1.0f, 0.0f, 0.0f); + colors[1] = new Color3f(0.0f, 1.0f, 0.0f); + colors[2] = new Color3f(0.0f, 0.0f, 1.0f); + colors[3] = new Color3f(1.0f, 1.0f, 0.0f); + + int[] pntsIndex = new int[12]; + int[] clrsIndex = new int[12]; + + pntsIndex[0] = 0; + clrsIndex[0] = 0; + pntsIndex[1] = 1; + clrsIndex[1] = 1; + + pntsIndex[2] = 1; + clrsIndex[2] = 1; + pntsIndex[3] = 2; + clrsIndex[3] = 2; + + pntsIndex[4] = 2; + clrsIndex[4] = 2; + pntsIndex[5] = 0; + clrsIndex[5] = 0; + + pntsIndex[6] = 1; + clrsIndex[6] = 1; + pntsIndex[7] = 3; + clrsIndex[7] = 3; + + pntsIndex[8] = 2; + clrsIndex[8] = 2; + pntsIndex[9] = 3; + clrsIndex[9] = 3; + + pntsIndex[10] = 0; + clrsIndex[10] = 0; + pntsIndex[11] = 3; + clrsIndex[11] = 3; + + setCoordinates(0, verts); + setCoordinateIndices(0, pntsIndex); + setColors(0, colors); + setColorIndices(0, clrsIndex); + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/picking/TetrahedronILSA.java b/src/main/java/org/jdesktop/j3d/examples/picking/TetrahedronILSA.java new file mode 100644 index 0000000..27af0ae --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/picking/TetrahedronILSA.java @@ -0,0 +1,99 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.picking; + +import org.jogamp.java3d.GeometryArray; +import org.jogamp.java3d.IndexedLineStripArray; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3f; + +class TetrahedronILSA extends IndexedLineStripArray { + + private static final int[] lineLengths = { + 4, 4 + }; + TetrahedronILSA() { + super(4, GeometryArray.COORDINATES | GeometryArray.COLOR_3, 8, lineLengths); + + Point3f verts[] = new Point3f[4]; + Color3f colors[] = new Color3f[4]; + + verts[0] = new Point3f(1.0f,1.0f,1.0f); + verts[1] = new Point3f(1.0f,-1.0f,-1.0f); + verts[2] = new Point3f(-1.0f,-1.0f,1.0f); + verts[3] = new Point3f(-1.0f,1.0f,-1.0f); + + colors[0] = new Color3f(1.0f, 0.0f, 0.0f); + colors[1] = new Color3f(0.0f, 1.0f, 0.0f); + colors[2] = new Color3f(0.0f, 0.0f, 1.0f); + colors[3] = new Color3f(1.0f, 1.0f, 0.0f); + + int pntsIndex[] = new int[8]; + int clrsIndex[] = new int[8]; + + pntsIndex[0] = 0; + clrsIndex[0] = 0; + pntsIndex[1] = 1; + clrsIndex[1] = 1; + pntsIndex[2] = 3; + clrsIndex[2] = 3; + pntsIndex[3] = 2; + clrsIndex[3] = 2; + + pntsIndex[4] = 1; + clrsIndex[4] = 1; + pntsIndex[5] = 2; + clrsIndex[5] = 2; + pntsIndex[6] = 0; + clrsIndex[6] = 0; + pntsIndex[7] = 3; + clrsIndex[7] = 3; + + setCoordinates(0, verts); + setCoordinateIndices(0, pntsIndex); + setColors(0, colors); + setColorIndices(0, clrsIndex); + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/picking/TetrahedronIPA.java b/src/main/java/org/jdesktop/j3d/examples/picking/TetrahedronIPA.java new file mode 100644 index 0000000..3daec58 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/picking/TetrahedronIPA.java @@ -0,0 +1,83 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.picking; + +import org.jogamp.java3d.GeometryArray; +import org.jogamp.java3d.IndexedPointArray; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3f; + +class TetrahedronIPA extends IndexedPointArray { + + TetrahedronIPA() { + super(4, GeometryArray.COORDINATES | GeometryArray.COLOR_3, 4); + + Point3f verts[] = new Point3f[4]; + Color3f colors[] = new Color3f[4]; + + verts[0] = new Point3f(1.0f,1.0f,1.0f); + verts[1] = new Point3f(1.0f,-1.0f,-1.0f); + verts[2] = new Point3f(-1.0f,-1.0f,1.0f); + verts[3] = new Point3f(-1.0f,1.0f,-1.0f); + + colors[0] = new Color3f(1.0f, 0.0f, 0.0f); + colors[1] = new Color3f(0.0f, 1.0f, 0.0f); + colors[2] = new Color3f(0.0f, 0.0f, 1.0f); + colors[3] = new Color3f(1.0f, 1.0f, 0.0f); + + int pntsIndex[] = new int[4]; + int clrsIndex[] = new int[4]; + + pntsIndex[0] = clrsIndex[0] = 0; + pntsIndex[1] = clrsIndex[1] = 1; + pntsIndex[2] = clrsIndex[2] = 2; + pntsIndex[3] = clrsIndex[3] = 3; + + setCoordinates(0, verts); + setCoordinateIndices(0, pntsIndex); + setColors(0, colors); + setColorIndices(0, clrsIndex); + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/picking/TetrahedronITA.java b/src/main/java/org/jdesktop/j3d/examples/picking/TetrahedronITA.java new file mode 100644 index 0000000..b4d7a48 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/picking/TetrahedronITA.java @@ -0,0 +1,106 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.picking; + +import org.jogamp.java3d.GeometryArray; +import org.jogamp.java3d.IndexedTriangleArray; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3f; + +class TetrahedronITA extends IndexedTriangleArray { + + TetrahedronITA() { + super(4, GeometryArray.COORDINATES | GeometryArray.COLOR_3, 12); + + Point3f verts[] = new Point3f[4]; + Color3f colors[] = new Color3f[4]; + + verts[0] = new Point3f(1.0f,1.0f,1.0f); + verts[1] = new Point3f(1.0f,-1.0f,-1.0f); + verts[2] = new Point3f(-1.0f,-1.0f,1.0f); + verts[3] = new Point3f(-1.0f,1.0f,-1.0f); + + colors[0] = new Color3f(1.0f, 0.0f, 0.0f); + colors[1] = new Color3f(0.0f, 1.0f, 0.0f); + colors[2] = new Color3f(0.0f, 0.0f, 1.0f); + colors[3] = new Color3f(1.0f, 1.0f, 0.0f); + + int pntsIndex[] = new int[12]; + int clrsIndex[] = new int[12]; + + pntsIndex[0] = 2; + clrsIndex[0] = 0; + pntsIndex[1] = 1; + clrsIndex[1] = 0; + pntsIndex[2] = 0; + clrsIndex[2] = 0; + + pntsIndex[3] = 3; + clrsIndex[3] = 1; + pntsIndex[4] = 2; + clrsIndex[4] = 1; + pntsIndex[5] = 0; + clrsIndex[5] = 1; + + pntsIndex[6] = 1; + clrsIndex[6] = 2; + pntsIndex[7] = 2; + clrsIndex[7] = 2; + pntsIndex[8] = 3; + clrsIndex[8] = 2; + + pntsIndex[9] = 1; + clrsIndex[9] = 3; + pntsIndex[10] = 3; + clrsIndex[10] = 3; + pntsIndex[11] = 0; + clrsIndex[11] = 3; + + setCoordinates(0, verts); + setCoordinateIndices(0, pntsIndex); + setColors(0, colors); + setColorIndices(0, clrsIndex); + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/picking/TetrahedronLA.java b/src/main/java/org/jdesktop/j3d/examples/picking/TetrahedronLA.java new file mode 100644 index 0000000..52ed5b6 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/picking/TetrahedronLA.java @@ -0,0 +1,106 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.picking; + +import org.jogamp.java3d.GeometryArray; +import org.jogamp.java3d.LineArray; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3f; + +class TetrahedronLA extends LineArray { + + TetrahedronLA() { + super(12, GeometryArray.COORDINATES | GeometryArray.COLOR_3); + + Point3f verts[] = new Point3f[4]; + Color3f colors[] = new Color3f[4]; + + verts[0] = new Point3f(1.0f,1.0f,1.0f); + verts[1] = new Point3f(1.0f,-1.0f,-1.0f); + verts[2] = new Point3f(-1.0f,-1.0f,1.0f); + verts[3] = new Point3f(-1.0f,1.0f,-1.0f); + + colors[0] = new Color3f(1.0f, 0.0f, 0.0f); + colors[1] = new Color3f(0.0f, 1.0f, 0.0f); + colors[2] = new Color3f(0.0f, 0.0f, 1.0f); + colors[3] = new Color3f(1.0f, 1.0f, 0.0f); + + Point3f pnts[] = new Point3f[12]; + Color3f clrs[] = new Color3f[12]; + + pnts[0] = verts[0]; + clrs[0] = colors[0]; + pnts[1] = verts[1]; + clrs[1] = colors[1]; + + pnts[2] = verts[1]; + clrs[2] = colors[1]; + pnts[3] = verts[2]; + clrs[3] = colors[2]; + + pnts[4] = verts[2]; + clrs[4] = colors[2]; + pnts[5] = verts[0]; + clrs[5] = colors[0]; + + pnts[6] = verts[1]; + clrs[6] = colors[1]; + pnts[7] = verts[3]; + clrs[7] = colors[3]; + + pnts[8] = verts[2]; + clrs[8] = colors[2]; + pnts[9] = verts[3]; + clrs[9] = colors[3]; + + pnts[10] = verts[0]; + clrs[10] = colors[0]; + pnts[11] = verts[3]; + clrs[11] = colors[3]; + + setCoordinates(0, pnts); + setColors(0, clrs); + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/picking/TetrahedronLSA.java b/src/main/java/org/jdesktop/j3d/examples/picking/TetrahedronLSA.java new file mode 100644 index 0000000..5d598fd --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/picking/TetrahedronLSA.java @@ -0,0 +1,96 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.picking; + +import org.jogamp.java3d.GeometryArray; +import org.jogamp.java3d.LineStripArray; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3f; + +class TetrahedronLSA extends LineStripArray { + private static final int[] lineLengths = { + 4, 4 + }; + TetrahedronLSA() { + super(8, GeometryArray.COORDINATES | GeometryArray.COLOR_3, lineLengths); + + Point3f verts[] = new Point3f[4]; + Color3f colors[] = new Color3f[4]; + + verts[0] = new Point3f(1.0f,1.0f,1.0f); + verts[1] = new Point3f(1.0f,-1.0f,-1.0f); + verts[2] = new Point3f(-1.0f,-1.0f,1.0f); + verts[3] = new Point3f(-1.0f,1.0f,-1.0f); + + colors[0] = new Color3f(1.0f, 0.0f, 0.0f); + colors[1] = new Color3f(0.0f, 1.0f, 0.0f); + colors[2] = new Color3f(0.0f, 0.0f, 1.0f); + colors[3] = new Color3f(1.0f, 1.0f, 0.0f); + + Point3f pnts[] = new Point3f[8]; + Color3f clrs[] = new Color3f[8]; + + pnts[0] = verts[0]; + clrs[0] = colors[0]; + pnts[1] = verts[1]; + clrs[1] = colors[1]; + pnts[2] = verts[3]; + clrs[2] = colors[3]; + pnts[3] = verts[2]; + clrs[3] = colors[2]; + + pnts[4] = verts[1]; + clrs[4] = colors[1]; + pnts[5] = verts[2]; + clrs[5] = colors[2]; + pnts[6] = verts[0]; + clrs[6] = colors[0]; + pnts[7] = verts[3]; + clrs[7] = colors[3]; + + setCoordinates(0, pnts); + setColors(0, clrs); + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/picking/TetrahedronPA.java b/src/main/java/org/jdesktop/j3d/examples/picking/TetrahedronPA.java new file mode 100644 index 0000000..137efef --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/picking/TetrahedronPA.java @@ -0,0 +1,73 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.picking; + +import org.jogamp.java3d.GeometryArray; +import org.jogamp.java3d.PointArray; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3f; + +class TetrahedronPA extends PointArray { + + TetrahedronPA() { + super(4, GeometryArray.COORDINATES | GeometryArray.COLOR_3); + + Point3f verts[] = new Point3f[4]; + Color3f colors[] = new Color3f[4]; + + verts[0] = new Point3f(1.0f,1.0f,1.0f); + verts[1] = new Point3f(1.0f,-1.0f,-1.0f); + verts[2] = new Point3f(-1.0f,-1.0f,1.0f); + verts[3] = new Point3f(-1.0f,1.0f,-1.0f); + + colors[0] = new Color3f(1.0f, 0.0f, 0.0f); + colors[1] = new Color3f(0.0f, 1.0f, 0.0f); + colors[2] = new Color3f(0.0f, 0.0f, 1.0f); + colors[3] = new Color3f(1.0f, 1.0f, 0.0f); + + setCoordinates(0, verts); + setColors(0, colors); + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/picking/TetrahedronTA.java b/src/main/java/org/jdesktop/j3d/examples/picking/TetrahedronTA.java new file mode 100644 index 0000000..aeaef87 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/picking/TetrahedronTA.java @@ -0,0 +1,104 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.picking; + +import org.jogamp.java3d.GeometryArray; +import org.jogamp.java3d.TriangleArray; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3f; + +class TetrahedronTA extends TriangleArray { + + TetrahedronTA() { + super(12, GeometryArray.COORDINATES | GeometryArray.COLOR_3); + + Point3f verts[] = new Point3f[4]; + Color3f colors[] = new Color3f[4]; + + verts[0] = new Point3f(1.0f,1.0f,1.0f); + verts[1] = new Point3f(1.0f,-1.0f,-1.0f); + verts[2] = new Point3f(-1.0f,-1.0f,1.0f); + verts[3] = new Point3f(-1.0f,1.0f,-1.0f); + + colors[0] = new Color3f(1.0f, 0.0f, 0.0f); + colors[1] = new Color3f(0.0f, 1.0f, 0.0f); + colors[2] = new Color3f(0.0f, 0.0f, 1.0f); + colors[3] = new Color3f(1.0f, 1.0f, 0.0f); + + Point3f pnts[] = new Point3f[12]; + Color3f clrs[] = new Color3f[12]; + + pnts[0] = verts[2]; + clrs[0] = colors[0]; + pnts[1] = verts[1]; + clrs[1] = colors[0]; + pnts[2] = verts[0]; + clrs[2] = colors[0]; + + pnts[3] = verts[3]; + clrs[3] = colors[1]; + pnts[4] = verts[2]; + clrs[4] = colors[1]; + pnts[5] = verts[0]; + clrs[5] = colors[1]; + + pnts[6] = verts[1]; + clrs[6] = colors[2]; + pnts[7] = verts[2]; + clrs[7] = colors[2]; + pnts[8] = verts[3]; + clrs[8] = colors[2]; + + pnts[9] = verts[1]; + clrs[9] = colors[3]; + pnts[10] = verts[3]; + clrs[10] = colors[3]; + pnts[11] = verts[0]; + clrs[11] = colors[3]; + + setCoordinates(0, pnts); + setColors(0, clrs); + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/picking/TickTockPicking.form b/src/main/java/org/jdesktop/j3d/examples/picking/TickTockPicking.form new file mode 100644 index 0000000..8d60ac0 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/picking/TickTockPicking.form @@ -0,0 +1,36 @@ +<?xml version="1.0" encoding="UTF-8" ?> + +<Form version="1.0" type="org.netbeans.modules.form.forminfo.JFrameFormInfo"> + <Properties> + <Property name="defaultCloseOperation" type="int" value="3"/> + <Property name="title" type="java.lang.String" value="TickTockPicking"/> + </Properties> + <SyntheticProperties> + <SyntheticProperty name="formSizePolicy" type="int" value="1"/> + </SyntheticProperties> + <AuxValues> + <AuxValue name="FormSettings_generateMnemonicsCode" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_listenerGenerationStyle" type="java.lang.Integer" value="0"/> + <AuxValue name="FormSettings_variablesLocal" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_variablesModifier" type="java.lang.Integer" value="2"/> + <AuxValue name="designerSize" type="java.awt.Dimension" value="-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,1,44,0,0,1,-112"/> + </AuxValues> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + <SubComponents> + <Container class="javax.swing.JPanel" name="drawingPanel"> + <Properties> + <Property name="preferredSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor"> + <Dimension value="[700, 700]"/> + </Property> + </Properties> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout" value="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription"> + <BorderConstraints direction="Center"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + </Container> + </SubComponents> +</Form> diff --git a/src/main/java/org/jdesktop/j3d/examples/picking/TickTockPicking.java b/src/main/java/org/jdesktop/j3d/examples/picking/TickTockPicking.java new file mode 100644 index 0000000..b9d76f9 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/picking/TickTockPicking.java @@ -0,0 +1,488 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.picking; + +import java.awt.GraphicsConfiguration; + +import org.jdesktop.j3d.examples.Resources; +import org.jogamp.java3d.Alpha; +import org.jogamp.java3d.AmbientLight; +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.Background; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.ColoringAttributes; +import org.jogamp.java3d.DirectionalLight; +import org.jogamp.java3d.Group; +import org.jogamp.java3d.Material; +import org.jogamp.java3d.PointAttributes; +import org.jogamp.java3d.PolygonAttributes; +import org.jogamp.java3d.RotationInterpolator; +import org.jogamp.java3d.Shape3D; +import org.jogamp.java3d.TextureAttributes; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.TransparencyAttributes; +import org.jogamp.java3d.utils.image.TextureLoader; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Vector3d; +import org.jogamp.vecmath.Vector3f; + +public class TickTockPicking extends javax.swing.JFrame { + + private SimpleUniverse univ = null; + private BranchGroup scene = null; + // path the the texture map image + private java.net.URL texImage = null; + + public BranchGroup createSceneGraph(Canvas3D c) { + // Create the root of the branch graph + BranchGroup objRoot = new BranchGroup(); + + // Create a Transformgroup to scale all objects so they + // appear in the scene. + TransformGroup objScale = new TransformGroup(); + Transform3D t3d = new Transform3D(); + t3d.setScale(0.4); + objScale.setTransform(t3d); + objRoot.addChild(objScale); + + // Create a bounds for the background and behaviors + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + + // Set up the background + Color3f bgColor = new Color3f(0.05f, 0.05f, 0.2f); + Background bg = new Background(bgColor); + bg.setApplicationBounds(bounds); + objScale.addChild(bg); + + // Set up the global lights + Color3f lColor1 = new Color3f(0.7f, 0.7f, 0.7f); + Vector3f lDir1 = new Vector3f(-1.0f, -1.0f, -1.0f); + Color3f alColor = new Color3f(0.2f, 0.2f, 0.2f); + + AmbientLight aLgt = new AmbientLight(alColor); + aLgt.setInfluencingBounds(bounds); + DirectionalLight lgt1 = new DirectionalLight(lColor1, lDir1); + lgt1.setInfluencingBounds(bounds); + objScale.addChild(aLgt); + objScale.addChild(lgt1); + + // Create a pair of transform group nodes and initialize them to + // identity. Enable the TRANSFORM_WRITE capability so that + // our behaviors can modify them at runtime. Add them to the + // root of the subgraph. + TransformGroup objTrans1 = new TransformGroup(); + objTrans1.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + objScale.addChild(objTrans1); + + TransformGroup objTrans2 = new TransformGroup(); + objTrans2.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + objTrans1.addChild(objTrans2); + + // Create the positioning and scaling transform group node. + Transform3D t = new Transform3D(); + t.set(0.3, new Vector3d(0.0, -1.5, 0.0)); + TransformGroup objTrans3 = new TransformGroup(t); + objTrans2.addChild(objTrans3); + + // Create a simple shape leaf node, set it's appearance, and + // add it to the scene graph. + Shape3D shape = new Cube(); + Appearance a = new Appearance(); + Color3f black = new Color3f(0.0f, 0.0f, 0.0f); + Color3f white = new Color3f(1.0f, 1.0f, 1.0f); + Color3f objColor = new Color3f(0.8f, 0.0f, 0.0f); + a.setMaterial(new Material(objColor, black, objColor, + white, 80.0f)); + shape.setAppearance(a); + shape.setCapability(shape.ALLOW_APPEARANCE_READ); + shape.setCapability(shape.ALLOW_APPEARANCE_WRITE); + objTrans3.addChild(shape); + + // Create a new Behavior object that will perform the desired + // rotation on the specified transform object and add it into + // the scene graph. + Transform3D yAxis1 = new Transform3D(); + yAxis1.rotX(Math.PI/2.0); + Alpha tickTockAlpha = new Alpha(-1, Alpha.INCREASING_ENABLE | + Alpha.DECREASING_ENABLE, + 0, 0, + 5000, 2500, 200, + 5000, 2500, 200); + + RotationInterpolator tickTock = + new RotationInterpolator(tickTockAlpha, objTrans1, yAxis1, + -(float) Math.PI/2.0f, + (float) Math.PI/2.0f); + tickTock.setSchedulingBounds(bounds); + objTrans2.addChild(tickTock); + + // Create a new Behavior object that will perform the desired + // rotation on the specified transform object and add it into + // the scene graph. + Transform3D yAxis2 = new Transform3D(); + Alpha rotationAlpha = new Alpha(-1, Alpha.INCREASING_ENABLE, + 0, 0, + 4000, 0, 0, + 0, 0, 0); + + RotationInterpolator rotator = + new RotationInterpolator(rotationAlpha, objTrans2, yAxis2, + 0.0f, (float) Math.PI*2.0f); + rotator.setSchedulingBounds(bounds); + objTrans2.addChild(rotator); + + // Now create the simple picking behavior + PickHighlightBehavior pickBeh = new + PickHighlightBehavior(c, objRoot, bounds); + + // Create a bunch of objects with a behavior and add them + // into the scene graph. + + int row, col; + Appearance[][] app = new Appearance[3][3]; + + for (row = 0; row < 3; row++) + for (col = 0; col < 3; col++) + app[row][col] = createAppearance(row * 3 + col); + + for (int i = 0; i < 3; i++) { + double ypos = (double)(i - 1) * 1.5; + for (int j = 0; j < 3; j++) { + double xpos = (double)(j - 1) * 1.5; + objScale.addChild(createObject(app[i][j], 0.3, xpos, ypos)); + } + } + + // Have Java 3D perform optimizations on this scene graph. + objRoot.compile(); + + return objRoot; + } + + + private Appearance createAppearance(int idx) { + Appearance app = new Appearance(); + + // Globally used colors + Color3f black = new Color3f(0.0f, 0.0f, 0.0f); + Color3f white = new Color3f(1.0f, 1.0f, 1.0f); + + switch (idx) { + // Unlit solid + case 0: + { + // Set up the coloring properties + Color3f objColor = new Color3f(1.0f, 0.2f, 0.4f); + ColoringAttributes ca = new ColoringAttributes(); + ca.setColor(objColor); + app.setColoringAttributes(ca); + break; + } + + + // Unlit wire frame + case 1: + { + // Set up the coloring properties + Color3f objColor = new Color3f(1.0f, 0.4f, 0.0f); + ColoringAttributes ca = new ColoringAttributes(); + ca.setColor(objColor); + app.setColoringAttributes(ca); + + // Set up the polygon attributes + PolygonAttributes pa = new PolygonAttributes(); + pa.setPolygonMode(pa.POLYGON_LINE); + pa.setCullFace(pa.CULL_NONE); + app.setPolygonAttributes(pa); + break; + } + + // Unlit points + case 2: + { + // Set up the coloring properties + Color3f objColor = new Color3f(1.0f, 1.0f, 0.0f); + ColoringAttributes ca = new ColoringAttributes(); + ca.setColor(objColor); + app.setColoringAttributes(ca); + + // Set up the polygon attributes + PolygonAttributes pa = new PolygonAttributes(); + pa.setPolygonMode(pa.POLYGON_POINT); + pa.setCullFace(pa.CULL_NONE); + app.setPolygonAttributes(pa); + + // Set up point attributes + PointAttributes pta = new PointAttributes(); + pta.setPointSize(5.0f); + app.setPointAttributes(pta); + break; + } + + // Lit solid + case 3: + { + // Set up the material properties + Color3f objColor = new Color3f(0.8f, 0.0f, 0.0f); + app.setMaterial(new Material(objColor, black, objColor, + white, 80.0f)); + break; + } + + // Texture mapped, lit solid + case 4: + { + // Set up the texture map + TextureLoader tex = new TextureLoader(texImage, this); + app.setTexture(tex.getTexture()); + + TextureAttributes texAttr = new TextureAttributes(); + texAttr.setTextureMode(TextureAttributes.MODULATE); + app.setTextureAttributes(texAttr); + + // Set up the material properties + app.setMaterial(new Material(white, black, white, black, 1.0f)); + break; + } + + // Transparent, lit solid + case 5: + { + // Set up the transparency properties + TransparencyAttributes ta = new TransparencyAttributes(); + ta.setTransparencyMode(ta.BLENDED); + ta.setTransparency(0.6f); + app.setTransparencyAttributes(ta); + + // Set up the polygon attributes + PolygonAttributes pa = new PolygonAttributes(); + pa.setCullFace(pa.CULL_NONE); + app.setPolygonAttributes(pa); + + // Set up the material properties + Color3f objColor = new Color3f(0.7f, 0.8f, 1.0f); + app.setMaterial(new Material(objColor, black, objColor, + black, 1.0f)); + break; + } + + // Lit solid, no specular + case 6: + { + // Set up the material properties + Color3f objColor = new Color3f(0.8f, 0.0f, 0.0f); + app.setMaterial(new Material(objColor, black, objColor, + black, 80.0f)); + break; + } + + // Lit solid, specular only + case 7: + { + // Set up the material properties + Color3f objColor = new Color3f(0.8f, 0.0f, 0.0f); + app.setMaterial(new Material(black, black, black, + white, 80.0f)); + break; + } + + // Another lit solid with a different color + case 8: + { + // Set up the material properties + Color3f objColor = new Color3f(0.8f, 0.8f, 0.0f); + app.setMaterial(new Material(objColor, black, objColor, + white, 80.0f)); + break; + } + + default: + { + ColoringAttributes ca = new ColoringAttributes(); + ca.setColor(new Color3f(0.0f, 1.0f, 0.0f)); + app.setColoringAttributes(ca); + } + } + + return app; + } + + + private Group createObject(Appearance app, double scale, + double xpos, double ypos) { + + // Create a transform group node to scale and position the object. + Transform3D t = new Transform3D(); + t.set(scale, new Vector3d(xpos, ypos, 0.0)); + TransformGroup objTrans = new TransformGroup(t); + + // Create a second transform group node and initialize it to the + // identity. Enable the TRANSFORM_WRITE capability so that + // our behavior code can modify it at runtime. + TransformGroup spinTg = new TransformGroup(); + spinTg.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + spinTg.setCapability(TransformGroup.ALLOW_TRANSFORM_READ); + + // Create a simple shape leaf node and set the appearance + Shape3D shape = new Tetrahedron(); + shape.setAppearance(app); + shape.setCapability(shape.ALLOW_APPEARANCE_READ); + shape.setCapability(shape.ALLOW_APPEARANCE_WRITE); + + // add it to the scene graph. + spinTg.addChild(shape); + + // Create a new Behavior object that will perform the desired + // operation on the specified transform object and add it into + // the scene graph. + Transform3D yAxis = new Transform3D(); + Alpha rotationAlpha = new Alpha(-1, Alpha.INCREASING_ENABLE, + 0, 0, + 5000, 0, 0, + 0, 0, 0); + + RotationInterpolator rotator = + new RotationInterpolator(rotationAlpha, spinTg, yAxis, + 0.0f, (float) Math.PI*2.0f); + + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + + rotator.setSchedulingBounds(bounds); + + // Add the behavior and the transform group to the object + objTrans.addChild(rotator); + objTrans.addChild(spinTg); + + return objTrans; + } + + private Canvas3D createUniverse() { + // Get the preferred graphics configuration for the default screen + GraphicsConfiguration config = + SimpleUniverse.getPreferredConfiguration(); + + // Create a Canvas3D using the preferred configuration + Canvas3D c = new Canvas3D(config); + + // Create simple universe with view branch + univ = new SimpleUniverse(c); + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + univ.getViewingPlatform().setNominalViewingTransform(); + + // Ensure at least 5 msec per frame (i.e., < 200Hz) + univ.getViewer().getView().setMinimumFrameCycleTime(5); + + return c; + } + + /** + * Creates new form HelloUniverse + */ + public TickTockPicking() { + + // the path to the image for an applet + texImage = Resources.getResource("resources/images/stone.jpg"); + if (texImage == null) { + System.err.println("resources/images/stone.jpg not found"); + System.exit(1); + } + // Initialize the GUI components + initComponents(); + + // Create Canvas3D and SimpleUniverse; add canvas to drawing panel + Canvas3D c = createUniverse(); + drawingPanel.add(c, java.awt.BorderLayout.CENTER); + + // Create the content branch and add it to the universe + scene = createSceneGraph(c); + univ.addBranchGraph(scene); + } + + // ---------------------------------------------------------------- + + /** This method is called from within the constructor to + * initialize the form. + * WARNING: Do NOT modify this code. The content of this method is + * always regenerated by the Form Editor. + */ + // <editor-fold defaultstate="collapsed" desc=" Generated Code ">//GEN-BEGIN:initComponents + private void initComponents() { + drawingPanel = new javax.swing.JPanel(); + + setDefaultCloseOperation(javax.swing.WindowConstants.EXIT_ON_CLOSE); + setTitle("TickTockPicking"); + drawingPanel.setLayout(new java.awt.BorderLayout()); + + drawingPanel.setPreferredSize(new java.awt.Dimension(700, 700)); + getContentPane().add(drawingPanel, java.awt.BorderLayout.CENTER); + + pack(); + }// </editor-fold>//GEN-END:initComponents + + /** + * @param args the command line arguments + */ + public static void main(String args[]) {System.setProperty("sun.awt.noerasebackground", "true"); + java.awt.EventQueue.invokeLater(new Runnable() { + public void run() { + new TickTockPicking().setVisible(true); + } + }); + } + + // Variables declaration - do not modify//GEN-BEGIN:variables + private javax.swing.JPanel drawingPanel; + // End of variables declaration//GEN-END:variables + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/platform_geometry/SimpleGeometry.java b/src/main/java/org/jdesktop/j3d/examples/platform_geometry/SimpleGeometry.java new file mode 100644 index 0000000..5cb03a5 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/platform_geometry/SimpleGeometry.java @@ -0,0 +1,213 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.platform_geometry; + +import java.applet.Applet; +import java.awt.BorderLayout; +import java.awt.GraphicsConfiguration; + +import org.jogamp.java3d.Alpha; +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.RotationInterpolator; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.TransparencyAttributes; +import org.jogamp.java3d.utils.applet.MainFrame; +import org.jogamp.java3d.utils.behaviors.mouse.MouseTranslate; +import org.jogamp.java3d.utils.geometry.ColorCube; +import org.jogamp.java3d.utils.geometry.Cylinder; +import org.jogamp.java3d.utils.universe.PlatformGeometry; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.java3d.utils.universe.ViewingPlatform; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Vector3d; + +/** + * This class demonstrates the use of the Universe builder for stand-alone + * applications along with the use of the PlatformGeometry node that is + * present in the Java 3D Universe Builder utility. The standard + * HelloWorld application is brought up. A transparent cylinder has been + * added to the PlatfromGeometry node of the ViewingPlatform and the + * MouseTranslate utility has been used to allow this sphere to be dragged + * around the canvas. + */ +public class SimpleGeometry extends Applet { + + SimpleUniverse u = null; + + public BranchGroup createSceneGraph() { + // Create the root of the branch graph + BranchGroup objRoot = new BranchGroup(); + + // Create a Transformgroup to scale all objects so they + // appear in the scene. + TransformGroup objScale = new TransformGroup(); + Transform3D t3d = new Transform3D(); + t3d.setScale(0.4); + objScale.setTransform(t3d); + objRoot.addChild(objScale); + + // Create the transform group node and initialize it to the + // identity. Enable the TRANSFORM_WRITE capability so that + // our behavior code can modify it at runtime. Add it to the + // root of the subgraph. + TransformGroup objTrans = new TransformGroup(); + objTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + objScale.addChild(objTrans); + + // Create a simple shape leaf node, add it to the scene graph. + objTrans.addChild(new ColorCube()); + + // Create a new Behavior object that will perform the desired + // operation on the specified transform object and add it into + // the scene graph. + Transform3D yAxis = new Transform3D(); + Alpha rotationAlpha = new Alpha(-1, Alpha.INCREASING_ENABLE, + 0, 0, + 4000, 0, 0, + 0, 0, 0); + + RotationInterpolator rotator = + new RotationInterpolator(rotationAlpha, objTrans, yAxis, + 0.0f, (float) Math.PI*2.0f); + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + rotator.setSchedulingBounds(bounds); + objTrans.addChild(rotator); + + + // Have Java 3D perform optimizations on this scene graph. + objRoot.compile(); + + return objRoot; + } + + /* + * Create the geometry to add to the platform geometry. + */ + PlatformGeometry createAimer() { + + PlatformGeometry pg = new PlatformGeometry(); + + // This TransformGroup will be used by the MouseTranslate + // utiltiy to move the cylinder around the canvas. when the + // the user holds down mouse button 3. + TransformGroup moveTG = new TransformGroup(); + moveTG.setCapability(TransformGroup.ALLOW_TRANSFORM_READ); + moveTG.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + MouseTranslate mouseT = new MouseTranslate(moveTG); + moveTG.addChild(mouseT); + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + mouseT.setSchedulingBounds(bounds); + pg.addChild(moveTG); + + // This TransformGroup is used to place the cylinder in the scene. + // The cylinder will be rotated 90 degrees so it will appear as + // a circle on the screen (could be made into a nice gun site...). + // The cylinder is also displaced a little in Z so it is in front + // of the viewer. + Transform3D xForm = new Transform3D(); + xForm.rotX(Math.PI/2.0); + xForm.setTranslation(new Vector3d(0.0, 0.0, -0.7)); + TransformGroup placementTG = new TransformGroup(xForm); + moveTG.addChild(placementTG); + + // Create the cylinder - make it thin and transparent. + Appearance cylinderAppearance = new Appearance(); + TransparencyAttributes transAttrs = + new TransparencyAttributes(TransparencyAttributes.FASTEST, 0.5f); + // cylinderAppearance.setTransparencyAttributes(transAttrs); + Cylinder aimer = new Cylinder(0.06f, 0.005f, 0, cylinderAppearance); + placementTG.addChild(aimer); + + return pg; + } + + public void init() {System.setProperty("sun.awt.noerasebackground", "true"); + + setLayout(new BorderLayout()); + GraphicsConfiguration config = + SimpleUniverse.getPreferredConfiguration(); + + Canvas3D c = new Canvas3D(config); + add("Center", c); + + // Create a simple scene and attach it to the virtual universe + BranchGroup scene = createSceneGraph(); + + u = new SimpleUniverse(c); + + PlatformGeometry pg = createAimer(); + + // Now set the just created PlatformGeometry. + ViewingPlatform vp = u.getViewingPlatform(); + vp.setPlatformGeometry(pg); + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + u.getViewingPlatform().setNominalViewingTransform(); + + // Add everthing to the scene graph - it will now be displayed. + u.addBranchGraph(scene); + } + + public SimpleGeometry(String[] args) { + } + + public SimpleGeometry() { + } + + public void destroy() { + u.cleanup(); + } + + public static void main(String[] args) {System.setProperty("sun.awt.noerasebackground", "true"); + new MainFrame(new SimpleGeometry(args), 256, 256); + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/print_canvas3d/ImageDisplayer.java b/src/main/java/org/jdesktop/j3d/examples/print_canvas3d/ImageDisplayer.java new file mode 100644 index 0000000..36dfeb0 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/print_canvas3d/ImageDisplayer.java @@ -0,0 +1,138 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.print_canvas3d; + +import java.awt.Color; +import java.awt.Dimension; +import java.awt.Graphics; +import java.awt.event.ActionEvent; +import java.awt.event.ActionListener; +import java.awt.event.WindowAdapter; +import java.awt.event.WindowEvent; +import java.awt.image.BufferedImage; + +import javax.swing.JFrame; +import javax.swing.JMenu; +import javax.swing.JMenuBar; +import javax.swing.JMenuItem; +import javax.swing.JPanel; +import javax.swing.JScrollPane; +import javax.swing.JSeparator; + +class ImageDisplayer extends JFrame implements ActionListener { + BufferedImage bImage; + + private class ImagePanel extends JPanel { + public void paint(Graphics g) { + g.setColor(Color.black); + g.fillRect(0, 0, getSize().width, getSize().height); + g.drawImage(bImage, 0, 0, this); + } + + private ImagePanel() { + setPreferredSize(new Dimension(bImage.getWidth(), + bImage.getHeight())); + } + } + + private JMenuItem printItem; + private JMenuItem closeItem; + + private void freeResources() { + this.removeAll(); + this.setVisible(false); + bImage = null; + } + + public void actionPerformed (ActionEvent event) { + Object target = event.getSource(); + + if (target == printItem) { + new ImagePrinter(bImage).print(); + } + else if (target == closeItem) { + freeResources(); + } + } + + private JMenuBar createMenuBar() { + JMenuBar menuBar = new JMenuBar(); + JMenu fileMenu = new JMenu("File"); + printItem = new JMenuItem("Print..."); + printItem.addActionListener(this); + closeItem = new JMenuItem("Close"); + closeItem.addActionListener(this); + fileMenu.add(printItem); + fileMenu.add(new JSeparator()); + fileMenu.add(closeItem); + menuBar.add(fileMenu); + return menuBar; + } + + ImageDisplayer(BufferedImage bImage) { + this.bImage = bImage; + this.setTitle("Off-screen Canvas3D Snapshot"); + + // Create and initialize menu bar + this.setJMenuBar(createMenuBar()); + + // Create scroll pane, and embedded image panel + ImagePanel imagePanel = new ImagePanel(); + JScrollPane scrollPane = new JScrollPane(imagePanel); + scrollPane.getViewport().setPreferredSize(new Dimension(700, 700)); + + // Handle the close event + this.addWindowListener(new WindowAdapter() { + public void windowClosing(WindowEvent winEvent) { + freeResources(); + } + }); + + // Add scroll pane to the frame and make it visible + this.getContentPane().add(scrollPane); + this.pack(); + this.setVisible(true); + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/print_canvas3d/ImagePrinter.java b/src/main/java/org/jdesktop/j3d/examples/print_canvas3d/ImagePrinter.java new file mode 100644 index 0000000..85b00ac --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/print_canvas3d/ImagePrinter.java @@ -0,0 +1,115 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.print_canvas3d; + +import java.awt.Graphics; +import java.awt.Graphics2D; +import java.awt.Image; +import java.awt.geom.AffineTransform; +import java.awt.image.BufferedImage; +import java.awt.image.ImageObserver; +import java.awt.print.PageFormat; +import java.awt.print.Printable; +import java.awt.print.PrinterException; +import java.awt.print.PrinterJob; + +class ImagePrinter implements Printable, ImageObserver { + BufferedImage bImage; + + public int print(Graphics g, PageFormat pf, int pi) + throws PrinterException { + + + if (pi >= 1) { + return Printable.NO_SUCH_PAGE; + } + + Graphics2D g2d = (Graphics2D)g; + //g2d.translate(pf.getImageableX(), pf.getImageableY()); + AffineTransform t2d = new AffineTransform(); + t2d.translate(pf.getImageableX(), pf.getImageableY()); + double xscale = pf.getImageableWidth() / (double)bImage.getWidth(); + double yscale = pf.getImageableHeight() / (double)bImage.getHeight(); + double scale = Math.min(xscale, yscale); + t2d.scale(scale, scale); + try { + g2d.drawImage(bImage,t2d, this); + } + catch (Exception ex) { + ex.printStackTrace(); + return Printable.NO_SUCH_PAGE; + } + return Printable.PAGE_EXISTS; + } + + void print() { + PrinterJob printJob = PrinterJob.getPrinterJob(); + PageFormat pageFormat = printJob.defaultPage(); + pageFormat.setOrientation(PageFormat.LANDSCAPE); + pageFormat = printJob.validatePage(pageFormat); + printJob.setPrintable(this, pageFormat); + if (printJob.printDialog()) { + try { + printJob.print(); + } + catch (PrinterException ex) { + ex.printStackTrace(); + } + } + } + + public boolean imageUpdate(Image img, + int infoflags, + int x, + int y, + int width, + int height) { + return false; + } + + ImagePrinter(BufferedImage bImage) { + this.bImage = bImage; + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/print_canvas3d/OffScreenCanvas3D.java b/src/main/java/org/jdesktop/j3d/examples/print_canvas3d/OffScreenCanvas3D.java new file mode 100644 index 0000000..782e5ad --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/print_canvas3d/OffScreenCanvas3D.java @@ -0,0 +1,84 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.print_canvas3d; + +import java.awt.GraphicsConfiguration; +import java.awt.image.BufferedImage; + +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.ImageComponent; +import org.jogamp.java3d.ImageComponent2D; + + +class OffScreenCanvas3D extends Canvas3D { + OffScreenCanvas3D(GraphicsConfiguration graphicsConfiguration, + boolean offScreen) { + + super(graphicsConfiguration, offScreen); + } + + BufferedImage doRender(int width, int height) { + + BufferedImage bImage = + new BufferedImage(width, height, BufferedImage.TYPE_INT_ARGB); + + ImageComponent2D buffer = + new ImageComponent2D(ImageComponent.FORMAT_RGBA, bImage); + + setOffScreenBuffer(buffer); + renderOffScreenBuffer(); + waitForOffScreenRendering(); + bImage = getOffScreenBuffer().getImage(); + + // To release the reference of buffer inside Java 3D. + setOffScreenBuffer(null); + + return bImage; + } + + public void postSwap() { + // No-op since we always wait for off-screen rendering to complete + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/print_canvas3d/PrintCanvas3D.form b/src/main/java/org/jdesktop/j3d/examples/print_canvas3d/PrintCanvas3D.form new file mode 100644 index 0000000..5150ee2 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/print_canvas3d/PrintCanvas3D.form @@ -0,0 +1,74 @@ +<?xml version="1.0" encoding="UTF-8" ?> + +<Form version="1.0" type="org.netbeans.modules.form.forminfo.JFrameFormInfo"> + <NonVisualComponents> + <Menu class="javax.swing.JMenuBar" name="jMenuBar1"> + <SubComponents> + <Menu class="javax.swing.JMenu" name="fileMenu"> + <Properties> + <Property name="text" type="java.lang.String" value="File"/> + </Properties> + <SubComponents> + <MenuItem class="javax.swing.JMenuItem" name="snapShotMenuItem"> + <Properties> + <Property name="text" type="java.lang.String" value="Snapshot"/> + </Properties> + <Events> + <EventHandler event="actionPerformed" listener="java.awt.event.ActionListener" parameters="java.awt.event.ActionEvent" handler="snapShotMenuItemActionPerformed"/> + </Events> + </MenuItem> + <MenuItem class="javax.swing.JMenuItem" name="printMenuItem"> + <Properties> + <Property name="text" type="java.lang.String" value="Print"/> + </Properties> + <Events> + <EventHandler event="actionPerformed" listener="java.awt.event.ActionListener" parameters="java.awt.event.ActionEvent" handler="printMenuItemActionPerformed"/> + </Events> + </MenuItem> + <MenuItem class="javax.swing.JMenuItem" name="exitMenuItem"> + <Properties> + <Property name="text" type="java.lang.String" value="Exit"/> + </Properties> + <Events> + <EventHandler event="actionPerformed" listener="java.awt.event.ActionListener" parameters="java.awt.event.ActionEvent" handler="exitMenuItemActionPerformed"/> + </Events> + </MenuItem> + </SubComponents> + </Menu> + </SubComponents> + </Menu> + </NonVisualComponents> + <Properties> + <Property name="defaultCloseOperation" type="int" value="3"/> + <Property name="title" type="java.lang.String" value="Window Title"/> + </Properties> + <SyntheticProperties> + <SyntheticProperty name="menuBar" type="java.lang.String" value="jMenuBar1"/> + <SyntheticProperty name="formSizePolicy" type="int" value="1"/> + </SyntheticProperties> + <AuxValues> + <AuxValue name="FormSettings_generateMnemonicsCode" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_listenerGenerationStyle" type="java.lang.Integer" value="0"/> + <AuxValue name="FormSettings_variablesLocal" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_variablesModifier" type="java.lang.Integer" value="2"/> + <AuxValue name="designerSize" type="java.awt.Dimension" value="-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,1,44,0,0,1,-112"/> + </AuxValues> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + <SubComponents> + <Container class="javax.swing.JPanel" name="drawingPanel"> + <Properties> + <Property name="preferredSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor"> + <Dimension value="[500, 500]"/> + </Property> + </Properties> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout" value="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription"> + <BorderConstraints direction="Center"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + </Container> + </SubComponents> +</Form> diff --git a/src/main/java/org/jdesktop/j3d/examples/print_canvas3d/PrintCanvas3D.java b/src/main/java/org/jdesktop/j3d/examples/print_canvas3d/PrintCanvas3D.java new file mode 100644 index 0000000..23b881f --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/print_canvas3d/PrintCanvas3D.java @@ -0,0 +1,402 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.print_canvas3d; + +import java.awt.Dimension; +import java.awt.GraphicsConfiguration; +import java.awt.GraphicsEnvironment; +import java.awt.Point; +import java.awt.image.BufferedImage; +import java.io.FileNotFoundException; +import java.net.MalformedURLException; +import java.net.URL; + +import javax.swing.JPopupMenu; + +import org.jdesktop.j3d.examples.Resources; +import org.jogamp.java3d.AmbientLight; +import org.jogamp.java3d.Background; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.DirectionalLight; +import org.jogamp.java3d.GraphicsConfigTemplate3D; +import org.jogamp.java3d.Screen3D; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.loaders.IncorrectFormatException; +import org.jogamp.java3d.loaders.ParsingErrorException; +import org.jogamp.java3d.loaders.Scene; +import org.jogamp.java3d.loaders.objectfile.ObjectFile; +import org.jogamp.java3d.utils.behaviors.mouse.MouseRotate; +import org.jogamp.java3d.utils.behaviors.mouse.MouseTranslate; +import org.jogamp.java3d.utils.behaviors.mouse.MouseZoom; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Vector3f; + +public class PrintCanvas3D extends javax.swing.JFrame { + + private static final boolean noTriangulate = false; + private static final boolean noStripify = false; + private static final double creaseAngle = 60.0; + private Canvas3D onScreenCanvas3D; + private OffScreenCanvas3D offScreenCanvas3D; + private URL filename = null; + private static final int OFF_SCREEN_SCALE = 3; + + private SimpleUniverse univ = null; + + public BranchGroup createSceneGraph(String args[]) { + // Create the root of the branch graph + BranchGroup objRoot = new BranchGroup(); + + // Create a Transformgroup to scale all objects so they + // appear in the scene. + TransformGroup objScale = new TransformGroup(); + Transform3D t3d = new Transform3D(); + t3d.setScale(0.7); + objScale.setTransform(t3d); + objRoot.addChild(objScale); + + // Create the transform group node and initialize it to the + // identity. Enable the TRANSFORM_WRITE capability so that + // our behavior code can modify it at runtime. Add it to the + // root of the subgraph. + TransformGroup objTrans = new TransformGroup(); + objTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + objTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_READ); + objScale.addChild(objTrans); + + int flags = ObjectFile.RESIZE; + if (!noTriangulate) flags |= ObjectFile.TRIANGULATE; + if (!noStripify) flags |= ObjectFile.STRIPIFY; + ObjectFile f = + new ObjectFile(flags, + (float)(creaseAngle * Math.PI / 180.0)); + Scene scene = null; + try { + scene = f.load(filename); + } + catch (FileNotFoundException e) { + System.err.println(e); + System.exit(1); + } + catch (ParsingErrorException e) { + System.err.println(e); + System.exit(1); + } + catch (IncorrectFormatException e) { + System.err.println(e); + System.exit(1); + } + + objTrans.addChild(scene.getSceneGroup()); + + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + + // Create the rotate behavior node + MouseRotate behavior = new MouseRotate(); + behavior.setTransformGroup(objTrans); + objTrans.addChild(behavior); + behavior.setSchedulingBounds(bounds); + + // Create the zoom behavior node + MouseZoom behavior2 = new MouseZoom(); + behavior2.setTransformGroup(objTrans); + objTrans.addChild(behavior2); + behavior2.setSchedulingBounds(bounds); + + // Create the translate behavior node + MouseTranslate behavior3 = new MouseTranslate(); + behavior3.setTransformGroup(objTrans); + objTrans.addChild(behavior3); + behavior3.setSchedulingBounds(bounds); + + + // Set up the background + Color3f bgColor = new Color3f(0.05f, 0.05f, 0.5f); + Background bgNode = new Background(bgColor); + bgNode.setApplicationBounds(bounds); + objRoot.addChild(bgNode); + + // Set up the ambient light + Color3f ambientColor = new Color3f(0.1f, 0.1f, 0.1f); + AmbientLight ambientLightNode = new AmbientLight(ambientColor); + ambientLightNode.setInfluencingBounds(bounds); + objRoot.addChild(ambientLightNode); + + // Set up the directional lights + Color3f light1Color = new Color3f(1.0f, 1.0f, 0.9f); + Vector3f light1Direction = new Vector3f(4.0f, -7.0f, -12.0f); + Color3f light2Color = new Color3f(0.3f, 0.3f, 0.4f); + Vector3f light2Direction = new Vector3f(-6.0f, -2.0f, -1.0f); + + DirectionalLight light1 + = new DirectionalLight(light1Color, light1Direction); + light1.setInfluencingBounds(bounds); + objRoot.addChild(light1); + + DirectionalLight light2 + = new DirectionalLight(light2Color, light2Direction); + light2.setInfluencingBounds(bounds); + objRoot.addChild(light2); + + return objRoot; + } + + private void usage() { + System.out.println("Usage: java PrintCanvas3D <.obj file>"); + System.exit(0); + } // End of usage + + private OffScreenCanvas3D createOffScreenCanvas(Canvas3D onScreenCanvas3D) { + // Create the off-screen Canvas3D object + // request an offscreen Canvas3D with a single buffer configuration + GraphicsConfigTemplate3D template = new GraphicsConfigTemplate3D(); + template.setDoubleBuffer(GraphicsConfigTemplate3D.UNNECESSARY); + GraphicsConfiguration gc = + GraphicsEnvironment.getLocalGraphicsEnvironment(). + getDefaultScreenDevice().getBestConfiguration(template); + + offScreenCanvas3D = new OffScreenCanvas3D(gc, true); + // Set the off-screen size based on a scale factor times the + // on-screen size + Screen3D sOn = onScreenCanvas3D.getScreen3D(); + Screen3D sOff = offScreenCanvas3D.getScreen3D(); + Dimension dim = sOn.getSize(); + dim.width *= OFF_SCREEN_SCALE; + dim.height *= OFF_SCREEN_SCALE; + sOff.setSize(dim); + sOff.setPhysicalScreenWidth(sOn.getPhysicalScreenWidth() * + OFF_SCREEN_SCALE); + sOff.setPhysicalScreenHeight(sOn.getPhysicalScreenHeight() * + OFF_SCREEN_SCALE); + + // attach the offscreen canvas to the view + univ.getViewer().getView().addCanvas3D(offScreenCanvas3D); + + return offScreenCanvas3D; + + } + + private Canvas3D createUniverse() { + GraphicsConfiguration config = + SimpleUniverse.getPreferredConfiguration(); + + Canvas3D c = new Canvas3D(config); + + univ = new SimpleUniverse(c); + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + univ.getViewingPlatform().setNominalViewingTransform(); + + // Ensure at least 5 msec per frame (i.e., < 200Hz) + univ.getViewer().getView().setMinimumFrameCycleTime(5); + + return c; + } + + /** + * Creates new form PrintCanvas3D + */ + public PrintCanvas3D(String args[]) { + + if (args.length == 0) { + filename = Resources.getResource("resources/geometry/beethoven.obj"); + if (filename == null) { + System.err.println("resources/geometry/beethoven.obj not found"); + System.exit(1); + } + } else { + for (int i = 0 ; i < args.length ; i++) { + if (args[i].startsWith("-")) { + System.err.println("Argument '" + args[i] + "' ignored."); + } else { + try{ + filename = new URL(args[i]); + } + catch (MalformedURLException e) { + System.err.println(e.getMessage()); + System.exit(1); + } + } + } + } + + if (filename == null) { + usage(); + } + + // Initialize the GUI components + JPopupMenu.setDefaultLightWeightPopupEnabled(false); + initComponents(); + + // Create Canvas3D and SimpleUniverse; add canvas to drawing panel + onScreenCanvas3D = createUniverse(); + drawingPanel.add(onScreenCanvas3D, java.awt.BorderLayout.CENTER); + + // Create the content branch and add it to the universe + BranchGroup scene = createSceneGraph(args); + + // Create the off-screen Canvas3D object + createOffScreenCanvas(onScreenCanvas3D); + + univ.addBranchGraph(scene); + } + + // ---------------------------------------------------------------- + + /** This method is called from within the constructor to + * initialize the form. + * WARNING: Do NOT modify this code. The content of this method is + * always regenerated by the Form Editor. + */ + // <editor-fold defaultstate="collapsed" desc=" Generated Code ">//GEN-BEGIN:initComponents + private void initComponents() { + drawingPanel = new javax.swing.JPanel(); + jMenuBar1 = new javax.swing.JMenuBar(); + fileMenu = new javax.swing.JMenu(); + snapShotMenuItem = new javax.swing.JMenuItem(); + printMenuItem = new javax.swing.JMenuItem(); + exitMenuItem = new javax.swing.JMenuItem(); + + setDefaultCloseOperation(javax.swing.WindowConstants.EXIT_ON_CLOSE); + setTitle("Window Title"); + drawingPanel.setLayout(new java.awt.BorderLayout()); + + drawingPanel.setPreferredSize(new java.awt.Dimension(500, 500)); + getContentPane().add(drawingPanel, java.awt.BorderLayout.CENTER); + + fileMenu.setText("File"); + snapShotMenuItem.setText("Snapshot"); + snapShotMenuItem.addActionListener(new java.awt.event.ActionListener() { + public void actionPerformed(java.awt.event.ActionEvent evt) { + snapShotMenuItemActionPerformed(evt); + } + }); + + fileMenu.add(snapShotMenuItem); + + printMenuItem.setText("Print"); + printMenuItem.addActionListener(new java.awt.event.ActionListener() { + public void actionPerformed(java.awt.event.ActionEvent evt) { + printMenuItemActionPerformed(evt); + } + }); + + fileMenu.add(printMenuItem); + + exitMenuItem.setText("Exit"); + exitMenuItem.addActionListener(new java.awt.event.ActionListener() { + public void actionPerformed(java.awt.event.ActionEvent evt) { + exitMenuItemActionPerformed(evt); + } + }); + + fileMenu.add(exitMenuItem); + + jMenuBar1.add(fileMenu); + + setJMenuBar(jMenuBar1); + + pack(); + }// </editor-fold>//GEN-END:initComponents + + private void printMenuItemActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_printMenuItemActionPerformed + Point loc = onScreenCanvas3D.getLocationOnScreen(); + offScreenCanvas3D.setOffScreenLocation(loc); + Dimension dim = onScreenCanvas3D.getSize(); + dim.width *= OFF_SCREEN_SCALE; + dim.height *= OFF_SCREEN_SCALE; + BufferedImage bImage = + offScreenCanvas3D.doRender(dim.width, dim.height); + + new ImagePrinter(bImage).print(); + + }//GEN-LAST:event_printMenuItemActionPerformed + + private void snapShotMenuItemActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_snapShotMenuItemActionPerformed + Point loc = onScreenCanvas3D.getLocationOnScreen(); + offScreenCanvas3D.setOffScreenLocation(loc); + Dimension dim = onScreenCanvas3D.getSize(); + dim.width *= OFF_SCREEN_SCALE; + dim.height *= OFF_SCREEN_SCALE; + BufferedImage bImage = + offScreenCanvas3D.doRender(dim.width, dim.height); + + new ImageDisplayer(bImage); + + + }//GEN-LAST:event_snapShotMenuItemActionPerformed + + private void exitMenuItemActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_exitMenuItemActionPerformed + System.exit(0); + }//GEN-LAST:event_exitMenuItemActionPerformed + + /** + * @param args the command line arguments + */ + public static void main(final String args[]) { + java.awt.EventQueue.invokeLater(new Runnable() { + public void run() { + new PrintCanvas3D(args).setVisible(true);; + } + }); + } + + // Variables declaration - do not modify//GEN-BEGIN:variables + private javax.swing.JPanel drawingPanel; + private javax.swing.JMenuItem exitMenuItem; + private javax.swing.JMenu fileMenu; + private javax.swing.JMenuBar jMenuBar1; + private javax.swing.JMenuItem printMenuItem; + private javax.swing.JMenuItem snapShotMenuItem; + // End of variables declaration//GEN-END:variables + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/pure_immediate/PureImmediate.form b/src/main/java/org/jdesktop/j3d/examples/pure_immediate/PureImmediate.form new file mode 100644 index 0000000..3c5f559 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/pure_immediate/PureImmediate.form @@ -0,0 +1,36 @@ +<?xml version="1.0" encoding="UTF-8" ?> + +<Form version="1.0" type="org.netbeans.modules.form.forminfo.JFrameFormInfo"> + <Properties> + <Property name="defaultCloseOperation" type="int" value="3"/> + <Property name="title" type="java.lang.String" value="PureImmediate"/> + </Properties> + <SyntheticProperties> + <SyntheticProperty name="formSizePolicy" type="int" value="1"/> + </SyntheticProperties> + <AuxValues> + <AuxValue name="FormSettings_generateMnemonicsCode" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_listenerGenerationStyle" type="java.lang.Integer" value="0"/> + <AuxValue name="FormSettings_variablesLocal" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_variablesModifier" type="java.lang.Integer" value="2"/> + <AuxValue name="designerSize" type="java.awt.Dimension" value="-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,1,44,0,0,1,-112"/> + </AuxValues> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + <SubComponents> + <Container class="javax.swing.JPanel" name="drawingPanel"> + <Properties> + <Property name="preferredSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor"> + <Dimension value="[250, 250]"/> + </Property> + </Properties> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout" value="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription"> + <BorderConstraints direction="Center"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + </Container> + </SubComponents> +</Form> diff --git a/src/main/java/org/jdesktop/j3d/examples/pure_immediate/PureImmediate.java b/src/main/java/org/jdesktop/j3d/examples/pure_immediate/PureImmediate.java new file mode 100644 index 0000000..7648cba --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/pure_immediate/PureImmediate.java @@ -0,0 +1,186 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.pure_immediate; + +import java.awt.GraphicsConfiguration; + +import org.jogamp.java3d.Alpha; +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.Geometry; +import org.jogamp.java3d.GraphicsContext3D; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.utils.geometry.ColorCube; +import org.jogamp.java3d.utils.universe.SimpleUniverse; + +/** + * Pure immediate mode example program. In pure immediate mode, the + * renderer must be stopped on the Canvas being rendered into. In our + * example, this is done immediately after the canvas is created. A + * separate thread is started up to do the immediate mode rendering. + */ +public class PureImmediate extends javax.swing.JFrame implements Runnable { + + + private SimpleUniverse univ = null; + private BranchGroup scene = null; + + private Canvas3D canvas; + private GraphicsContext3D gc = null; + private Geometry cube = null; + private Transform3D cmt = new Transform3D(); + + // One rotation (2*PI radians) every 6 seconds + private Alpha rotAlpha = new Alpha(-1, 6000); + + // + // Renders a single frame by clearing the canvas, drawing the + // geometry, and swapping the draw and display buffer. + // + public void render() { + if (gc == null) { + // Set up Graphics context + gc = canvas.getGraphicsContext3D(); + gc.setAppearance(new Appearance()); + + // Set up geometry + cube = new ColorCube(0.4).getGeometry(); + } + + // Compute angle of rotation based on alpha value + double angle = rotAlpha.value() * 2.0*Math.PI; + cmt.rotY(angle); + + // Render the geometry for this frame + gc.clear(); + gc.setModelTransform(cmt); + gc.draw(cube); + canvas.swap(); + } + + // + // Run method for our immediate mode rendering thread. + // + public void run() { + System.out.println("PureImmediate.run: starting main loop"); + while (true) { + render(); + Thread.yield(); + } + } + + + private void createUniverse() { + // Get the preferred graphics configuration for the default screen + GraphicsConfiguration config = + SimpleUniverse.getPreferredConfiguration(); + + // Create a Canvas3D using the preferred configuration + canvas = new Canvas3D(config); + canvas.stopRenderer(); + // Create simple universe with view branch + univ = new SimpleUniverse(canvas); + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + univ.getViewingPlatform().setNominalViewingTransform(); + + // Ensure at least 5 msec per frame (i.e., < 200Hz) + univ.getViewer().getView().setMinimumFrameCycleTime(5); + } + + /** + * Creates new form PureImmediate + */ + public PureImmediate() { + // Initialize the GUI components + initComponents(); + + // Create Canvas3D and SimpleUniverse; add canvas to drawing panel + createUniverse(); + drawingPanel.add(canvas, java.awt.BorderLayout.CENTER); + + // Start a new thread that will continuously render + new Thread(this).start(); + } + + // ---------------------------------------------------------------- + + /** This method is called from within the constructor to + * initialize the form. + * WARNING: Do NOT modify this code. The content of this method is + * always regenerated by the Form Editor. + */ + // <editor-fold defaultstate="collapsed" desc=" Generated Code ">//GEN-BEGIN:initComponents + private void initComponents() { + drawingPanel = new javax.swing.JPanel(); + + setDefaultCloseOperation(javax.swing.WindowConstants.EXIT_ON_CLOSE); + setTitle("PureImmediate"); + drawingPanel.setLayout(new java.awt.BorderLayout()); + + drawingPanel.setPreferredSize(new java.awt.Dimension(250, 250)); + getContentPane().add(drawingPanel, java.awt.BorderLayout.CENTER); + + pack(); + }// </editor-fold>//GEN-END:initComponents + + /** + * @param args the command line arguments + */ + public static void main(String args[]) {System.setProperty("sun.awt.noerasebackground", "true"); + java.awt.EventQueue.invokeLater(new Runnable() { + public void run() { + new PureImmediate().setVisible(true); + } + }); + } + + // Variables declaration - do not modify//GEN-BEGIN:variables + private javax.swing.JPanel drawingPanel; + // End of variables declaration//GEN-END:variables + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/pure_immediate/PureImmediateStereo.form b/src/main/java/org/jdesktop/j3d/examples/pure_immediate/PureImmediateStereo.form new file mode 100644 index 0000000..dd881b5 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/pure_immediate/PureImmediateStereo.form @@ -0,0 +1,36 @@ +<?xml version="1.0" encoding="UTF-8" ?> + +<Form version="1.0" type="org.netbeans.modules.form.forminfo.JFrameFormInfo"> + <Properties> + <Property name="defaultCloseOperation" type="int" value="3"/> + <Property name="title" type="java.lang.String" value="PureImmediateStereo"/> + </Properties> + <SyntheticProperties> + <SyntheticProperty name="formSizePolicy" type="int" value="1"/> + </SyntheticProperties> + <AuxValues> + <AuxValue name="FormSettings_generateMnemonicsCode" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_listenerGenerationStyle" type="java.lang.Integer" value="0"/> + <AuxValue name="FormSettings_variablesLocal" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_variablesModifier" type="java.lang.Integer" value="2"/> + <AuxValue name="designerSize" type="java.awt.Dimension" value="-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,1,44,0,0,1,-112"/> + </AuxValues> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + <SubComponents> + <Container class="javax.swing.JPanel" name="drawingPanel"> + <Properties> + <Property name="preferredSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor"> + <Dimension value="[512, 256]"/> + </Property> + </Properties> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout" value="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription"> + <BorderConstraints direction="Center"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + </Container> + </SubComponents> +</Form> diff --git a/src/main/java/org/jdesktop/j3d/examples/pure_immediate/PureImmediateStereo.java b/src/main/java/org/jdesktop/j3d/examples/pure_immediate/PureImmediateStereo.java new file mode 100644 index 0000000..9e0f0e5 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/pure_immediate/PureImmediateStereo.java @@ -0,0 +1,308 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.pure_immediate; + +import java.awt.GraphicsConfiguration; +import java.awt.GraphicsEnvironment; +import java.util.Map; + +import org.jogamp.java3d.Alpha; +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.DirectionalLight; +import org.jogamp.java3d.GraphicsConfigTemplate3D; +import org.jogamp.java3d.GraphicsContext3D; +import org.jogamp.java3d.Material; +import org.jogamp.java3d.Shape3D; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.utils.geometry.Cone; +import org.jogamp.java3d.utils.geometry.Primitive; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Vector3f; + +/** + * Pure immediate mode stereo example program for stereo. In pure + * immediate mode, the renderer must be stopped on the Canvas being + * rendered into. In our example, this is done immediately after the + * canvas is created. A separate thread is started up to do the + * immediate mode rendering. + */ + +public class PureImmediateStereo extends javax.swing.JFrame implements Runnable { + + private SimpleUniverse univ = null; + private BranchGroup scene = null; + + // Set this to true when the graphics card use shared z buffer + // in stereo mode. + public static String defaultSharedStereoZbuffer = Boolean.TRUE.toString(); + + private boolean sharedStereoZbuffer; + private boolean stereoSupport; + private Canvas3D canvas; + private GraphicsContext3D gc; + private Shape3D leftConeBody, rightConeBody; + private Shape3D leftConeCap, rightConeCap; + private Transform3D cmt = new Transform3D(); + private Vector3f leftTrans, rightTrans; + + // One rotation (2*PI radians) every 6 seconds + private Alpha rotAlpha = new Alpha(-1, 6000); + private double angle; + + // Compute data which is common for both + // left and right eye + void computeSharedData() { + // Compute angle of rotation based on alpha value + angle = rotAlpha.value() * 2.0*Math.PI; + cmt.rotY(angle); + } + + // Render the geometry in right eye + void renderLeft() { + cmt.setTranslation(leftTrans); + gc.setModelTransform(cmt); + + if (sharedStereoZbuffer) { + // Graphics card shared same z buffer in stereo mode, + // in this case we have to explicitly clearing both + // frame buffers. + gc.clear(); + } + gc.draw(leftConeBody); + gc.draw(leftConeCap); + } + + // Render the geometry for right eye + void renderRight() { + cmt.setTranslation(rightTrans); + gc.setModelTransform(cmt); + + if (sharedStereoZbuffer) { + // Graphics card shared same z buffer in stereo mode, + // in this case we have to explicitly clearing both + // frame buffers. + gc.clear(); + } + gc.draw(rightConeBody); + gc.draw(rightConeCap); + } + + // + // Run method for our immediate mode rendering thread. + // + public void run() { + // Set up Graphics context + gc = canvas.getGraphicsContext3D(); + + // We always need to set this for PureImmediate + // stereo mode + gc.setBufferOverride(true); + + Color3f lightColor = new Color3f(1, 1, 1); + Vector3f lightDir = new Vector3f(0, 0, -1); + DirectionalLight light = new DirectionalLight(lightColor, + lightDir); + + gc.addLight(light); + + Appearance redApp = new Appearance(); + Appearance greenApp = new Appearance(); + Color3f ambientColor = new Color3f(0, 0, 0); + Color3f emissiveColor = new Color3f(0, 0, 0); + Color3f diffuseColor = new Color3f(1, 0, 0); + Color3f specularColor = new Color3f(1, 1, 1); + redApp.setMaterial(new Material(ambientColor, emissiveColor, + diffuseColor, specularColor, 5)); + diffuseColor = new Color3f(0, 1, 0); + + greenApp.setMaterial(new Material(ambientColor, emissiveColor, + diffuseColor, specularColor, 5)); + + // Set up geometry + Cone leftCone = new Cone(0.4f, 0.6f, + Primitive.GENERATE_NORMALS, redApp); + Cone rightCone = new Cone(0.4f, 0.6f, + Primitive.GENERATE_NORMALS, greenApp); + leftConeBody = leftCone.getShape(Cone.BODY); + leftConeCap = leftCone.getShape(Cone.CAP); + + rightConeBody = rightCone.getShape(Cone.BODY); + rightConeCap = rightCone.getShape(Cone.CAP); + leftTrans = new Vector3f(-0.6f, 0, 0); + rightTrans = new Vector3f(0.6f, 0, 0); + + + while (true) { + // compute data which is can be used + // for both left and right eye + computeSharedData(); + + if (stereoSupport) { + if (!sharedStereoZbuffer) { + gc.setStereoMode(GraphicsContext3D.STEREO_BOTH); + // This clear both left and right buffers, we + // must set STEREO_BOTH before it. Otherwise + // it only clear LEFT or RIGHT buffer unless + // this is invoke twice for each buffer. + gc.clear(); + } + + gc.setStereoMode(GraphicsContext3D.STEREO_LEFT); + renderLeft(); + + gc.setStereoMode(GraphicsContext3D.STEREO_RIGHT); + renderRight(); + } else { + gc.clear(); + renderLeft(); + } + + // This swap both left and right buffers so + // there is no need to set STEREO_BOTH before it + canvas.swap(); + + // Be polite to other threads ! + Thread.yield(); + } + } + + + private void createUniverse() { + // Preferred to use Stereo + GraphicsConfigTemplate3D gct = new GraphicsConfigTemplate3D(); + gct.setStereo(GraphicsConfigTemplate3D.PREFERRED); + + GraphicsConfiguration config = + GraphicsEnvironment.getLocalGraphicsEnvironment().getDefaultScreenDevice().getBestConfiguration(gct); + + canvas = new Canvas3D(config); + Map map = canvas.queryProperties(); + + stereoSupport = canvas.getStereoAvailable(); + + if (stereoSupport) { + System.out.println("This machine support stereo, you should see a red cone on the left and green cone on the right."); + // User can overide the above default behavior using + // java3d property. + String str = System.getProperty("j3d.sharedstereozbuffer", + defaultSharedStereoZbuffer); + sharedStereoZbuffer = (new Boolean(str)).booleanValue(); + } else { + System.out.println("Stereo is not support, you should only see the left red cone."); + } + + if (!canvas.getDoubleBufferAvailable()) { + System.out.println("Double buffer is not support !"); + } + + // we must stop the Renderer in PureImmediate mode + canvas.stopRenderer(); + + // Create simple universe with view branch + univ = new SimpleUniverse(canvas); + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + univ.getViewingPlatform().setNominalViewingTransform(); + + // Ensure at least 5 msec per frame (i.e., < 200Hz) + univ.getViewer().getView().setMinimumFrameCycleTime(5); + + // Start a new thread that will continuously render + (new Thread(this)).start(); + } + + /** + * Creates new form PureImmediateStereo + */ + public PureImmediateStereo() { + // Initialize the GUI components + initComponents(); + + // Create Canvas3D and SimpleUniverse; add canvas to drawing panel + createUniverse(); + drawingPanel.add(canvas, java.awt.BorderLayout.CENTER); + } + + // ---------------------------------------------------------------- + + /** This method is called from within the constructor to + * initialize the form. + * WARNING: Do NOT modify this code. The content of this method is + * always regenerated by the Form Editor. + */ + // <editor-fold defaultstate="collapsed" desc=" Generated Code ">//GEN-BEGIN:initComponents + private void initComponents() { + drawingPanel = new javax.swing.JPanel(); + + setDefaultCloseOperation(javax.swing.WindowConstants.EXIT_ON_CLOSE); + setTitle("PureImmediateStereo"); + drawingPanel.setLayout(new java.awt.BorderLayout()); + + drawingPanel.setPreferredSize(new java.awt.Dimension(512, 256)); + getContentPane().add(drawingPanel, java.awt.BorderLayout.CENTER); + + pack(); + }// </editor-fold>//GEN-END:initComponents + + /** + * @param args the command line arguments + */ + public static void main(String args[]) {System.setProperty("sun.awt.noerasebackground", "true"); + java.awt.EventQueue.invokeLater(new Runnable() { + public void run() { + new PureImmediateStereo().setVisible(true); + } + }); + } + + // Variables declaration - do not modify//GEN-BEGIN:variables + private javax.swing.JPanel drawingPanel; + // End of variables declaration//GEN-END:variables + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/read_raster/ReadRaster.java b/src/main/java/org/jdesktop/j3d/examples/read_raster/ReadRaster.java new file mode 100644 index 0000000..780e3fe --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/read_raster/ReadRaster.java @@ -0,0 +1,236 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.read_raster; + +import java.applet.Applet; +import java.awt.BorderLayout; +import java.awt.GraphicsConfiguration; +import java.awt.image.BufferedImage; +import java.util.Enumeration; + +import org.jogamp.java3d.Alpha; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.GraphicsContext3D; +import org.jogamp.java3d.ImageComponent; +import org.jogamp.java3d.ImageComponent2D; +import org.jogamp.java3d.Raster; +import org.jogamp.java3d.RotationInterpolator; +import org.jogamp.java3d.Shape3D; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.utils.applet.MainFrame; +import org.jogamp.java3d.utils.geometry.ColorCube; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Point3f; +import org.jogamp.vecmath.Vector3d; + +public class ReadRaster extends Applet { + + private SimpleUniverse u = null; + + public BranchGroup createSceneGraph(BufferedImage bImage, + Raster readRaster) { + + // Create the root of the branch graph + BranchGroup objRoot = new BranchGroup(); + + // Create a Raster shape. Add it to the root of the subgraph + + ImageComponent2D drawImageComponent = new ImageComponent2D( + ImageComponent.FORMAT_RGB, bImage, true, true); + + Raster drawRaster= new Raster(new Point3f(0.0f, 0.0f, 0.0f), + Raster.RASTER_COLOR, 0, 0, bImage.getWidth(), + bImage.getHeight(), drawImageComponent, null); + Shape3D shape = new Shape3D(drawRaster); + drawRaster.setCapability(Raster.ALLOW_IMAGE_WRITE); + objRoot.addChild(shape); + + // Ceate the transform greup node and initialize it to the + // identity. Enable the TRANSFORM_WRITE capability so that + // our behavior code can modify it at runtime. Add it to the + // root of the subgraph. + TransformGroup objTrans = new TransformGroup(); + objTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + + TransformGroup cubeScale = new TransformGroup(); + Transform3D t3d = new Transform3D(); + t3d.setTranslation(new Vector3d(-0.5, 0.5, 0.0)); + cubeScale.setTransform(t3d); + + cubeScale.addChild(objTrans); + objRoot.addChild(cubeScale); + + // Create a simple shape leaf node, add it to the scene graph. + objTrans.addChild(new ColorCube(0.3)); + + // Create a new Behavior object that will perform the desired + // operation on the specified transform object and add it into + // the scene graph. + Transform3D yAxis = new Transform3D(); + Alpha rotationAlpha = new Alpha(-1, Alpha.INCREASING_ENABLE, + 0, 0, + 4000, 0, 0, + 0, 0, 0); + myRotationInterpolator rotator = + new myRotationInterpolator(drawRaster, readRaster, + rotationAlpha, objTrans, yAxis, + 0.0f, (float) Math.PI*2.0f); + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + rotator.setSchedulingBounds(bounds); + objTrans.addChild(rotator); + + // Have Java 3D perform optimizations on this scene graph. + objRoot.compile(); + + return objRoot; + } + + public ReadRaster() { + } + + public void init() {System.setProperty("sun.awt.noerasebackground", "true"); + + int width = 128; + int height = 128; + + ImageComponent2D readImageComponent = new ImageComponent2D( + ImageComponent.FORMAT_RGB, width, height, false, true); + + Raster readRaster = new Raster(new Point3f(0.0f,0.0f,0.0f), + Raster.RASTER_COLOR, 0, 0, width, + height, readImageComponent, null); + + setLayout(new BorderLayout()); + GraphicsConfiguration config = + SimpleUniverse.getPreferredConfiguration(); + + Canvas3D c = new myCanvas3D(config, readRaster); + add("Center", c); + + // Create a simple scene and attach it to the virtual universe + BufferedImage bImage = new BufferedImage(width, height, + BufferedImage.TYPE_INT_RGB); + + BranchGroup scene = createSceneGraph(bImage, readRaster); + u = new SimpleUniverse(c); + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + u.getViewingPlatform().setNominalViewingTransform(); + + u.addBranchGraph(scene); + } + + public void destroy() { + u.cleanup(); + } + + // + // The following allows ReadRaster to be run as an application + // as well as an applet + // + public static void main(String[] args) {System.setProperty("sun.awt.noerasebackground", "true"); + new MainFrame(new ReadRaster(), 256, 256); + } +} + + +class myCanvas3D extends Canvas3D { + + Raster readRaster; + GraphicsContext3D gc; + + public myCanvas3D(GraphicsConfiguration graphicsConfiguration, + Raster readRaster) { + + super(graphicsConfiguration); + this.readRaster = readRaster; + gc = getGraphicsContext3D(); + } + + public void postSwap() { + super.postSwap(); + synchronized(readRaster) { + gc.readRaster(readRaster); + } + } +} + + +class myRotationInterpolator extends RotationInterpolator { + Point3f wPos = new Point3f(0.025f, -0.025f, 0.0f); + Raster drawRaster; + Raster readRaster; + BufferedImage bImage; + ImageComponent2D newImageComponent; + + public myRotationInterpolator(Raster drawRaster, Raster readRaster, + Alpha alpha, + TransformGroup target, + Transform3D axisOfRotation, + float minimumAngle, + float maximumAngle) { + + super(alpha, target, axisOfRotation, minimumAngle, maximumAngle); + this.drawRaster = drawRaster; + this.readRaster = readRaster; + } + + public void processStimulus(Enumeration criteria) { + + synchronized(readRaster) { + bImage = readRaster.getImage().getImage(); + } + newImageComponent = new ImageComponent2D(ImageComponent.FORMAT_RGB, + bImage, true, true); + drawRaster.setImage(newImageComponent); + super.processStimulus(criteria); + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/sound/AudioReverberate.java b/src/main/java/org/jdesktop/j3d/examples/sound/AudioReverberate.java new file mode 100644 index 0000000..f54b43f --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/sound/AudioReverberate.java @@ -0,0 +1,177 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.sound; + +import java.net.URL; +import java.util.Enumeration; + +import org.jogamp.java3d.AuralAttributes; +import org.jogamp.java3d.Behavior; +import org.jogamp.java3d.MediaContainer; +import org.jogamp.java3d.PointSound; +import org.jogamp.java3d.WakeupOnBehaviorPost; +import org.jogamp.java3d.WakeupOnElapsedTime; +import org.jogamp.vecmath.Point3f; + +/* + * Pick the JavaSound reverb type that matches the input parameters + * as best as possible. + * + * Hae Reverb Types Size Persistance Delay + * ================ ----------- ------------ ----------- + * 1 None (dry) + * 2 "Closet" very small very short <.5 fast smooth + * 3 "Garage" med. large medium 1.0 medium + * 4 "Acoustic Lab" med. small short .5 med. fast + * 5 "Cavern" large long >2.0 very slow + * 6 "Dungeon" medium med. long 1.5 med. slow + * + * + * Order is NOT controllable, nor does it have a natural parallel. + * For this reason Order and Reflection are tied together as to + * affect 'Decay Speed'. This speed paired with the size of the + * space implied by the Delay parameter determine the JavaSound + * Reverb type that is set: + * + * | Short: Long: + * Speed | Coeff <= 0.9 Coeff > 0.9 + * Size | Order <= 8 Order > 8 + * --------------------------------------------------------------- + * small (<100ms) | 2 "Closet" 4 "Acoustic Lab" + * medium (<500ms) | 3 "Garage" 6 "Dungeon" + * large (>500ms) | 6 "Dungeon" 5 "Cavern" + */ +// User defined audio behavior class +public class AudioReverberate extends Behavior { + WakeupOnElapsedTime wt; + WakeupOnBehaviorPost wp; + PointSound psound = new PointSound(); + AuralAttributes sScape = null; + static int WAKEUP_SOUND = 0; + long dur; + long time; + boolean firstTime = true; + URL url = null; + int lCount = 0; + int loopCount = 0; + + // Override Behavior's initialize method to setup wakeup criteria + public void initialize() { + MediaContainer sample = new MediaContainer(); + sample.setCacheEnable(true); + sample.setURLObject(url); + psound.setSoundData(sample); + Point3f soundPos = new Point3f(-23.0f, 0.0f, 0.0f); + psound.setPosition(soundPos); + psound.setLoop(3); + firstTime = true; + System.out.println("Reverb Name Size Reflect Order Delay "); + System.out.println("----------- ---- ------- ----- ----- "); + WakeupOnElapsedTime wp = new WakeupOnElapsedTime(5000); + wakeupOn(wp); + } + + // Override Behavior's stimulus method to handle the event + public void processStimulus(Enumeration criteria) { + // time = System.currentTimeMillis(); + if (firstTime) { + wt = new WakeupOnElapsedTime(10000); + firstTime = false; + } + else + psound.setEnable(false) ; + + if (++lCount > 6) + lCount = 1; + + if (lCount == 1) { + sScape.setReverbDelay(10.0f) ; + sScape.setReflectionCoefficient(0.5f) ; + sScape.setReverbOrder(5) ; + System.out.println("Closet sm 0.5 5 10.0 "); + } + else if (lCount == 2) { + sScape.setReverbDelay(10.0f) ; + sScape.setReflectionCoefficient(0.999f) ; + sScape.setReverbOrder(9) ; + System.out.println("Acoustic Lab sm 0.999 9 10.0 "); + } + else if (lCount == 3) { + sScape.setReverbDelay(200.0f) ; + sScape.setReflectionCoefficient(0.4f) ; + sScape.setReverbOrder(3) ; + System.out.println("Garage med 0.4 3 200.0 "); + } + else if (lCount == 4) { + sScape.setReverbDelay(200.0f) ; + sScape.setReflectionCoefficient(0.99f) ; + sScape.setReverbOrder(10) ; + System.out.println("Dungeon med 0.99 10 200.0 "); + } + else if (lCount == 5) { + sScape.setReverbDelay(600.0f) ; + sScape.setReflectionCoefficient(0.33f) ; + sScape.setReverbOrder(7) ; + System.out.println("Dungeon lrg 0.33 7 600.0 "); + } + else if (lCount == 6) { + sScape.setReverbDelay(600.0f) ; + sScape.setReflectionCoefficient(1.0f) ; + sScape.setReverbOrder(20) ; + System.out.println("Cavern lrg 1.0 20 600.0 "); + } + psound.setEnable(true); + wakeupOn(wt); + } + + // + // Constructor for rotation behavior. Parameter: front and back Sound nodes + // + public AudioReverberate(PointSound psound, URL url, AuralAttributes sscape) { + this.psound = psound; + this.url = url; + this.sScape = sscape; + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/sound/BackgroundSoundBehavior.java b/src/main/java/org/jdesktop/j3d/examples/sound/BackgroundSoundBehavior.java new file mode 100644 index 0000000..bc8f5e6 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/sound/BackgroundSoundBehavior.java @@ -0,0 +1,85 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.sound; + +import java.net.URL; +import java.util.Enumeration; + +import org.jogamp.java3d.BackgroundSound; +import org.jogamp.java3d.Behavior; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.Bounds; +import org.jogamp.java3d.MediaContainer; +import org.jogamp.java3d.WakeupCondition; +import org.jogamp.java3d.WakeupOnElapsedFrames; +import org.jogamp.vecmath.Point3d; + +public class BackgroundSoundBehavior extends Behavior { + + private WakeupCondition condition = new WakeupOnElapsedFrames(0); + + /** Creates a new instance of BackgroundSoundBehavior */ + public BackgroundSoundBehavior(BackgroundSound bgs, URL url) { + + Bounds b = new BoundingSphere(new Point3d(), 20); + bgs.setSoundData(new MediaContainer(url)); + bgs.setEnable(true); + bgs.setPause(false); + bgs.setLoop(-1); + bgs.setContinuousEnable(true); + bgs.setSchedulingBounds(b); + + } + + public void initialize() { + + wakeupOn(condition); + } + + public void processStimulus(Enumeration enumeration) { + wakeupOn(condition); + } + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/sound/BackgroundSoundTest.form b/src/main/java/org/jdesktop/j3d/examples/sound/BackgroundSoundTest.form new file mode 100644 index 0000000..9a2f209 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/sound/BackgroundSoundTest.form @@ -0,0 +1,37 @@ +<?xml version="1.0" encoding="UTF-8" ?> + +<Form version="1.0" type="org.netbeans.modules.form.forminfo.JFrameFormInfo"> + <Properties> + <Property name="defaultCloseOperation" type="int" value="3"/> + <Property name="title" type="java.lang.String" value="BackgroundSoundTest"/> + </Properties> + <SyntheticProperties> + <SyntheticProperty name="formSizePolicy" type="int" value="1"/> + </SyntheticProperties> + <AuxValues> + <AuxValue name="FormSettings_generateMnemonicsCode" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_layoutCodeTarget" type="java.lang.Integer" value="2"/> + <AuxValue name="FormSettings_listenerGenerationStyle" type="java.lang.Integer" value="0"/> + <AuxValue name="FormSettings_variablesLocal" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_variablesModifier" type="java.lang.Integer" value="2"/> + <AuxValue name="designerSize" type="java.awt.Dimension" value="-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,1,44,0,0,1,-112"/> + </AuxValues> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + <SubComponents> + <Container class="javax.swing.JPanel" name="drawingPanel"> + <Properties> + <Property name="preferredSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor"> + <Dimension value="[800, 600]"/> + </Property> + </Properties> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout" value="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription"> + <BorderConstraints direction="Center"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + </Container> + </SubComponents> +</Form> diff --git a/src/main/java/org/jdesktop/j3d/examples/sound/BackgroundSoundTest.java b/src/main/java/org/jdesktop/j3d/examples/sound/BackgroundSoundTest.java new file mode 100644 index 0000000..b2011d0 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/sound/BackgroundSoundTest.java @@ -0,0 +1,289 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ +package org.jdesktop.j3d.examples.sound; + +import java.awt.GraphicsConfiguration; +import java.net.URL; + +import org.jdesktop.j3d.examples.Resources; +import org.jogamp.java3d.AmbientLight; +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.BackgroundSound; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.Bounds; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.ColoringAttributes; +import org.jogamp.java3d.DirectionalLight; +import org.jogamp.java3d.LineArray; +import org.jogamp.java3d.LineAttributes; +import org.jogamp.java3d.Material; +import org.jogamp.java3d.PolygonAttributes; +import org.jogamp.java3d.Shape3D; +import org.jogamp.java3d.Sound; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.utils.behaviors.keyboard.KeyNavigatorBehavior; +import org.jogamp.java3d.utils.geometry.ColorCube; +import org.jogamp.java3d.utils.geometry.Sphere; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.java3d.utils.universe.Viewer; +import org.jogamp.java3d.utils.universe.ViewingPlatform; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Vector3f; + +/** + * This is a test for a BackgroundSound. + * This program is ported from an earlier version of BackgroundSoundTest, in the j3d-incubator project, + * contributed by David Grace ([email protected]). + * + */ +public class BackgroundSoundTest extends javax.swing.JFrame { + + private URL url = null; + private SimpleUniverse univ = null; + private BranchGroup scene = null; + + //The activation radius for the ViewPlatform + private float activationRadius = 1; + + private Shape3D getDefaultGrid(int noOfLines, double size, double height){ + + Shape3D shape = new Shape3D(); + double lineLength = noOfLines * size / 2; + LineArray la = new LineArray(noOfLines * 4, LineArray.COORDINATES); + int count = 0; + for (int i=0; i<noOfLines; i++){ + la.setCoordinate(count, new Point3d(-lineLength, height, i*size - lineLength)); + count++; + la.setCoordinate(count, new Point3d(lineLength, height, i*size - lineLength)); + count++; + } + for (int i=0; i<noOfLines; i++){ + la.setCoordinate(count, new Point3d(i*size - lineLength, height, -lineLength)); + count++; + la.setCoordinate(count, new Point3d(i*size - lineLength, height, lineLength)); + count++; + } + shape.setGeometry(la); + Appearance a = new Appearance(); + ColoringAttributes ca = new ColoringAttributes(); + ca.setColor(0.3f, 0.3f, 0.3f); + a.setColoringAttributes(ca); + LineAttributes sla = new LineAttributes(); + sla.setLineWidth(1.0f); + a.setLineAttributes(sla); + shape.setAppearance(a); + + return shape; + } + + + private Sphere createSoundBoundingGeometry(Sound sound){ + Bounds bounds = sound.getSchedulingBounds(); + assert ((bounds != null) && (bounds instanceof BoundingSphere)); + BoundingSphere bs = (BoundingSphere) bounds; + float radius = (float) bs.getRadius(); + + return getSphere(radius); + } + + private Sphere getSphere(float radius){ + + Appearance a = new Appearance(); + Material m = new Material(); + + m.setDiffuseColor(1, 0, 0); + m.setAmbientColor(1, 0, 0); + m.setShininess(8); + a.setMaterial(m); + + PolygonAttributes pa = new PolygonAttributes(); + pa.setPolygonMode(PolygonAttributes.POLYGON_LINE); + pa.setCullFace(PolygonAttributes.CULL_NONE); + a.setPolygonAttributes(pa); + return new Sphere(radius, a); + } + + private TransformGroup createSoundNodeGeometry(float x, float y, float z){ + + TransformGroup rootTransformGroup = new TransformGroup(); + Transform3D t3D = new Transform3D(); + t3D.setTranslation(new Vector3f(x, y, z)); + rootTransformGroup.setTransform(t3D); + ColorCube cc = new ColorCube(0.1); + rootTransformGroup.addChild(cc); + return rootTransformGroup; + } + + + public BranchGroup createSceneGraph() { + // Create the root of the branch graph + BranchGroup objRoot = new BranchGroup(); + + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + + AmbientLight al = new AmbientLight(); + al.setInfluencingBounds(bounds); + + DirectionalLight dl = new DirectionalLight(); + dl.setDirection(-1, -1, -1); + dl.setInfluencingBounds(bounds); + objRoot.addChild(al); + objRoot.addChild(dl); + + /* + * Create Sound and Behavior objects that will play the sound + */ + BackgroundSound bgs = new BackgroundSound(); + BackgroundSoundBehavior player = new BackgroundSoundBehavior( bgs, url); + player.setSchedulingBounds(bounds); + objRoot.addChild(bgs); + objRoot.addChild(player); + + objRoot.addChild(getDefaultGrid(40, 1, -1)); + objRoot.addChild(createSoundNodeGeometry(0, 0, 0)); + objRoot.addChild(createSoundBoundingGeometry(bgs)); + return objRoot; + } + + + private Canvas3D createUniverse() { + // Get the preferred graphics configuration for the default screen + GraphicsConfiguration config = + SimpleUniverse.getPreferredConfiguration(); + + // Create a Canvas3D using the preferred configuration + Canvas3D c = new Canvas3D(config); + + // Create simple universe with view branch + univ = new SimpleUniverse(c); + + ViewingPlatform viewingPlatform = univ.getViewingPlatform(); + TransformGroup viewingPlatformTransformGroup = viewingPlatform.getViewPlatformTransform(); + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + viewingPlatform.setNominalViewingTransform(); + + Viewer viewer = univ.getViewer(); + + viewer.createAudioDevice(); + viewer.getView().setBackClipDistance(1000.0f); + + // Ensure at least 50 msec per frame. + viewer.getView().setMinimumFrameCycleTime(30); + + viewer.getView().getViewPlatform().setActivationRadius(activationRadius); + + BranchGroup bg = new BranchGroup(); + KeyNavigatorBehavior knb = new KeyNavigatorBehavior(c, viewingPlatformTransformGroup); + Bounds b = new BoundingSphere(new Point3d(), Double.POSITIVE_INFINITY); + knb.setSchedulingBounds(b); + bg.addChild(knb); + univ.addBranchGraph(bg); + + return c; + } + + /** + * Creates new form BackgroundSoundTest + */ + public BackgroundSoundTest() { + // Initialize the GUI components + initComponents(); + + url = Resources.getResource("resources/audio/magic_bells.wav"); + if (url == null) { + System.err.println("resources/audio/magic_bells.wav not found"); + System.exit(1); + } + + // Create Canvas3D and SimpleUniverse; add canvas to drawing panel + Canvas3D c = createUniverse(); + drawingPanel.add(c, java.awt.BorderLayout.CENTER); + + // Create the content branch and add it to the universe + scene = createSceneGraph(); + univ.addBranchGraph(scene); + } + + // ---------------------------------------------------------------- + + /** This method is called from within the constructor to + * initialize the form. + * WARNING: Do NOT modify this code. The content of this method is + * always regenerated by the Form Editor. + */ + // <editor-fold defaultstate="collapsed" desc=" Generated Code ">//GEN-BEGIN:initComponents + private void initComponents() { + drawingPanel = new javax.swing.JPanel(); + + setDefaultCloseOperation(javax.swing.WindowConstants.EXIT_ON_CLOSE); + setTitle("BackgroundSoundTest"); + drawingPanel.setLayout(new java.awt.BorderLayout()); + + drawingPanel.setPreferredSize(new java.awt.Dimension(800, 600)); + getContentPane().add(drawingPanel, java.awt.BorderLayout.CENTER); + + pack(); + }// </editor-fold>//GEN-END:initComponents + + /** + * @param args the command line arguments + */ + public static void main(String args[]) {System.setProperty("sun.awt.noerasebackground", "true"); + java.awt.EventQueue.invokeLater(new Runnable() { + public void run() { + new BackgroundSoundTest().setVisible(true); + } + }); + } + + // Variables declaration - do not modify//GEN-BEGIN:variables + private javax.swing.JPanel drawingPanel; + // End of variables declaration//GEN-END:variables + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/sound/PointSoundBehavior.java b/src/main/java/org/jdesktop/j3d/examples/sound/PointSoundBehavior.java new file mode 100644 index 0000000..754847c --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/sound/PointSoundBehavior.java @@ -0,0 +1,89 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.sound; + +import java.net.URL; +import java.util.Enumeration; + +import org.jogamp.java3d.Behavior; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.Bounds; +import org.jogamp.java3d.MediaContainer; +import org.jogamp.java3d.PointSound; +import org.jogamp.java3d.WakeupCondition; +import org.jogamp.java3d.WakeupOnElapsedFrames; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Point3f; + +public class PointSoundBehavior extends Behavior { + + private WakeupCondition condition = new WakeupOnElapsedFrames(0); + + /** Creates a new instance of PointSoundBehavior */ + public PointSoundBehavior(PointSound ps, URL url, Point3f pos) { + + Bounds b = new BoundingSphere(new Point3d(), 40); + ps.setSoundData(new MediaContainer(url)); + ps.setPosition(pos); + float distanceAtZero = 30; + ps.setDistanceGain(new float []{0, distanceAtZero}, new float []{1, 0}); + ps.setEnable(true); + ps.setPause(false); + ps.setContinuousEnable(true); + ps.setSchedulingBounds(b); + ps.setLoop(-1); + + } + + public void initialize() { + + wakeupOn(condition); + } + + public void processStimulus(Enumeration enumeration) { + wakeupOn(condition); + } + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/sound/PointSoundTest.form b/src/main/java/org/jdesktop/j3d/examples/sound/PointSoundTest.form new file mode 100644 index 0000000..41f5f7d --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/sound/PointSoundTest.form @@ -0,0 +1,37 @@ +<?xml version="1.0" encoding="UTF-8" ?> + +<Form version="1.0" type="org.netbeans.modules.form.forminfo.JFrameFormInfo"> + <Properties> + <Property name="defaultCloseOperation" type="int" value="3"/> + <Property name="title" type="java.lang.String" value="PointSound Test"/> + </Properties> + <SyntheticProperties> + <SyntheticProperty name="formSizePolicy" type="int" value="1"/> + </SyntheticProperties> + <AuxValues> + <AuxValue name="FormSettings_generateMnemonicsCode" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_layoutCodeTarget" type="java.lang.Integer" value="2"/> + <AuxValue name="FormSettings_listenerGenerationStyle" type="java.lang.Integer" value="0"/> + <AuxValue name="FormSettings_variablesLocal" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_variablesModifier" type="java.lang.Integer" value="2"/> + <AuxValue name="designerSize" type="java.awt.Dimension" value="-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,1,44,0,0,1,-112"/> + </AuxValues> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + <SubComponents> + <Container class="javax.swing.JPanel" name="drawingPanel"> + <Properties> + <Property name="preferredSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor"> + <Dimension value="[800, 600]"/> + </Property> + </Properties> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout" value="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription"> + <BorderConstraints direction="Center"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + </Container> + </SubComponents> +</Form> diff --git a/src/main/java/org/jdesktop/j3d/examples/sound/PointSoundTest.java b/src/main/java/org/jdesktop/j3d/examples/sound/PointSoundTest.java new file mode 100644 index 0000000..a39bc87 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/sound/PointSoundTest.java @@ -0,0 +1,318 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.sound; + +import java.awt.GraphicsConfiguration; +import java.net.URL; + +import org.jdesktop.j3d.examples.Resources; +import org.jogamp.java3d.AmbientLight; +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.Bounds; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.ColoringAttributes; +import org.jogamp.java3d.DirectionalLight; +import org.jogamp.java3d.Group; +import org.jogamp.java3d.LineArray; +import org.jogamp.java3d.LineAttributes; +import org.jogamp.java3d.Material; +import org.jogamp.java3d.PointSound; +import org.jogamp.java3d.PolygonAttributes; +import org.jogamp.java3d.Shape3D; +import org.jogamp.java3d.Sound; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.utils.behaviors.keyboard.KeyNavigatorBehavior; +import org.jogamp.java3d.utils.geometry.ColorCube; +import org.jogamp.java3d.utils.geometry.Sphere; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.java3d.utils.universe.Viewer; +import org.jogamp.java3d.utils.universe.ViewingPlatform; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Point3f; +import org.jogamp.vecmath.Vector3f; + +/** + * This is a test for a PointSound. + * This program is ported from an earlier version of PointSoundTest, in the j3d-incubator project, + * contributed by David Grace ([email protected]). + * + */ +public class PointSoundTest extends javax.swing.JFrame { + + private URL url = null; + private SimpleUniverse univ = null; + private BranchGroup scene = null; + + //The activation radius for the ViewPlatform + private float activationRadius = 1; + + private Shape3D getDefaultGrid(int noOfLines, double size, double height){ + + Shape3D shape = new Shape3D(); + double lineLength = noOfLines * size / 2; + LineArray la = new LineArray(noOfLines * 4, LineArray.COORDINATES); + int count = 0; + for (int i=0; i<noOfLines; i++){ + la.setCoordinate(count, new Point3d(-lineLength, height, i*size - lineLength)); + count++; + la.setCoordinate(count, new Point3d(lineLength, height, i*size - lineLength)); + count++; + } + for (int i=0; i<noOfLines; i++){ + la.setCoordinate(count, new Point3d(i*size - lineLength, height, -lineLength)); + count++; + la.setCoordinate(count, new Point3d(i*size - lineLength, height, lineLength)); + count++; + } + shape.setGeometry(la); + Appearance a = new Appearance(); + ColoringAttributes ca = new ColoringAttributes(); + ca.setColor(0.3f, 0.3f, 0.3f); + a.setColoringAttributes(ca); + LineAttributes sla = new LineAttributes(); + sla.setLineWidth(1.0f); + a.setLineAttributes(sla); + shape.setAppearance(a); + + return shape; + } + + private Group createSoundBoundingGeometries(PointSound ps) { + Group group = new Group(); + Sphere sphere1 = getInnerBoundingSphere(ps); + group.addChild(sphere1); + + assert(ps.getDistanceGainLength() == 2); + + // create geometry for outer Bounding Sphere + float [] ds = new float [ps.getDistanceGainLength()]; + float [] as = new float [ps.getDistanceGainLength()]; + ps.getDistanceGain(ds, as); + float distanceAtZero = ds[ps.getDistanceGainLength() - 1]; + + Sphere sphere2 = getSphere(distanceAtZero, false); + group.addChild(sphere2); + + return group; + } + + private Sphere getInnerBoundingSphere(Sound sound){ + Bounds bounds = sound.getSchedulingBounds(); + assert ((bounds != null) && (bounds instanceof BoundingSphere)); + BoundingSphere bs = (BoundingSphere) bounds; + float radius = (float) bs.getRadius(); + + return getSphere(radius, true); + } + + private Sphere getSphere(float radius, boolean inner){ + + Appearance a = new Appearance(); + Material m = new Material(); + + if (inner) { + m.setDiffuseColor(1, 0, 0); + m.setAmbientColor(1, 0, 0); + m.setShininess(8); + } else { + m.setDiffuseColor(0, 1, 0); + m.setAmbientColor(0, 1, 0); + m.setShininess(8); + } + a.setMaterial(m); + + PolygonAttributes pa = new PolygonAttributes(); + pa.setPolygonMode(PolygonAttributes.POLYGON_LINE); + pa.setCullFace(PolygonAttributes.CULL_NONE); + a.setPolygonAttributes(pa); + return new Sphere(radius, a); + } + + private TransformGroup createSoundNodeGeometry(float x, float y, float z){ + + TransformGroup rootTransformGroup = new TransformGroup(); + Transform3D t3D = new Transform3D(); + t3D.setTranslation(new Vector3f(x, y, z)); + rootTransformGroup.setTransform(t3D); + ColorCube cc = new ColorCube(0.1); + rootTransformGroup.addChild(cc); + return rootTransformGroup; + } + + + public BranchGroup createSceneGraph() { + // Create the root of the branch graph + BranchGroup objRoot = new BranchGroup(); + + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + + AmbientLight al = new AmbientLight(); + al.setInfluencingBounds(bounds); + + DirectionalLight dl = new DirectionalLight(); + dl.setDirection(-1, -1, -1); + dl.setInfluencingBounds(bounds); + objRoot.addChild(al); + objRoot.addChild(dl); + + /* + * Create Sound and Behavior objects that will play the sound + */ + PointSound ps = new PointSound(); + PointSoundBehavior player = new PointSoundBehavior( ps, url, new Point3f(0.0f, 0.0f, 0.0f)); + player.setSchedulingBounds(bounds); + objRoot.addChild(ps); + objRoot.addChild(player); + + objRoot.addChild(getDefaultGrid(40, 1, -1)); + objRoot.addChild(createSoundNodeGeometry(0, 0, 0)); + objRoot.addChild(createSoundBoundingGeometries(ps)); + return objRoot; + } + + + private Canvas3D createUniverse() { + // Get the preferred graphics configuration for the default screen + GraphicsConfiguration config = + SimpleUniverse.getPreferredConfiguration(); + + // Create a Canvas3D using the preferred configuration + Canvas3D c = new Canvas3D(config); + + // Create simple universe with view branch + univ = new SimpleUniverse(c); + + ViewingPlatform viewingPlatform = univ.getViewingPlatform(); + TransformGroup viewingPlatformTransformGroup = viewingPlatform.getViewPlatformTransform(); + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + viewingPlatform.setNominalViewingTransform(); + + Viewer viewer = univ.getViewer(); + + viewer.createAudioDevice(); + viewer.getView().setBackClipDistance(1000.0f); + + // Ensure at least 50 msec per frame. + viewer.getView().setMinimumFrameCycleTime(30); + + viewer.getView().getViewPlatform().setActivationRadius(activationRadius); + + BranchGroup bg = new BranchGroup(); + KeyNavigatorBehavior knb = new KeyNavigatorBehavior(c, viewingPlatformTransformGroup); + Bounds b = new BoundingSphere(new Point3d(), Double.POSITIVE_INFINITY); + knb.setSchedulingBounds(b); + bg.addChild(knb); + univ.addBranchGraph(bg); + + return c; + } + + + /** + * Creates new form PointSoundTest + */ + public PointSoundTest() { + // Initialize the GUI components + initComponents(); + + url = Resources.getResource("resources/audio/magic_bells.wav"); + if (url == null) { + System.err.println("resources/audio/magic_bells.wav not found"); + System.exit(1); + } + + // Create Canvas3D and SimpleUniverse; add canvas to drawing panel + Canvas3D c = createUniverse(); + drawingPanel.add(c, java.awt.BorderLayout.CENTER); + + // Create the content branch and add it to the universe + scene = createSceneGraph(); + univ.addBranchGraph(scene); + + } + + // ---------------------------------------------------------------- + + /** This method is called from within the constructor to + * initialize the form. + * WARNING: Do NOT modify this code. The content of this method is + * always regenerated by the Form Editor. + */ + // <editor-fold defaultstate="collapsed" desc=" Generated Code ">//GEN-BEGIN:initComponents + private void initComponents() { + drawingPanel = new javax.swing.JPanel(); + + setDefaultCloseOperation(javax.swing.WindowConstants.EXIT_ON_CLOSE); + setTitle("PointSound Test"); + drawingPanel.setLayout(new java.awt.BorderLayout()); + + drawingPanel.setPreferredSize(new java.awt.Dimension(800, 600)); + getContentPane().add(drawingPanel, java.awt.BorderLayout.CENTER); + + pack(); + }// </editor-fold>//GEN-END:initComponents + + /** + * @param args the command line arguments + */ + public static void main(String args[]) {System.setProperty("sun.awt.noerasebackground", "true"); + java.awt.EventQueue.invokeLater(new Runnable() { + public void run() { + new PointSoundTest().setVisible(true); + } + }); + } + + // Variables declaration - do not modify//GEN-BEGIN:variables + private javax.swing.JPanel drawingPanel; + // End of variables declaration//GEN-END:variables + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/sound/ReverberateSound.java b/src/main/java/org/jdesktop/j3d/examples/sound/ReverberateSound.java new file mode 100644 index 0000000..9cf7ad0 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/sound/ReverberateSound.java @@ -0,0 +1,202 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.sound; + +/* + * ReverberateSound + * + * Same as MoveSound except this calls UniverseBuilderJS to use the + * JavaSoundMixer AudioDevice rather than the HolosketchMixer device. + * + * NOTE: To run this anywhere but the Solaris Eng Menlo Park network + * the URL path must be set to the java3d/javaone directory. + */ + +import java.applet.Applet; +import java.awt.BorderLayout; +import java.awt.GraphicsConfiguration; +import java.net.URL; + +import javax.swing.JOptionPane; + +import org.jdesktop.j3d.examples.Resources; +import org.jogamp.java3d.Alpha; +import org.jogamp.java3d.AudioDevice; +import org.jogamp.java3d.AuralAttributes; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.PointSound; +import org.jogamp.java3d.RotationInterpolator; +import org.jogamp.java3d.Soundscape; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.utils.applet.MainFrame; +import org.jogamp.java3d.utils.geometry.ColorCube; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.vecmath.Point3d; + +public class ReverberateSound extends Applet { + + // File name of sound sample + private static URL url = null; + private SimpleUniverse u = null; + + public BranchGroup createSceneGraph() { + // Create the root of the subgraph + BranchGroup objRoot = new BranchGroup(); + + // Create the transform group node and initialize it to the identity. + // Enable the TRANSFORM_WRITE capability so that our behavior code + // can modify it at runtime. Add it to the root of the subgraph. + TransformGroup objTrans = new TransformGroup(); + objTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + objRoot.addChild(objTrans); + + // Create a simple shape leaf node and add it into the scene graph. + objTrans.addChild(new ColorCube(0.4)); + + // Create a new Behavior object that will perform the desired + // operation on the specified transform object and add it into the + // scene graph. + Transform3D yAxis = new Transform3D(); + Alpha rotation = new Alpha(-1, Alpha.INCREASING_ENABLE, + 0, 0, + 20000, 0, 0, + 0, 0, 0); + RotationInterpolator rotator = + new RotationInterpolator(rotation, + objTrans, yAxis, + 0.0f, (float) Math.PI*2.0f); + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + rotator.setSchedulingBounds(bounds); + objTrans.addChild(rotator); + + // + // Create an AuralAttribute with reverb params set + // + Soundscape soundScape2 = new Soundscape(); + AuralAttributes attributes2 = new AuralAttributes(); + attributes2.setReverbOrder(6); + attributes2.setCapability(AuralAttributes.ALLOW_REVERB_ORDER_WRITE); + attributes2.setCapability(AuralAttributes.ALLOW_REVERB_DELAY_WRITE); + attributes2.setCapability(AuralAttributes.ALLOW_REFLECTION_COEFFICIENT_WRITE); + soundScape2.setApplicationBounds(bounds); + soundScape2.setAuralAttributes(attributes2); + objRoot.addChild(soundScape2); + + // + // Create a sound node and add it to the scene graph + // + PointSound sound = new PointSound(); + sound.setCapability(PointSound.ALLOW_ENABLE_WRITE); + sound.setCapability(PointSound.ALLOW_INITIAL_GAIN_WRITE); + sound.setCapability(PointSound.ALLOW_SOUND_DATA_WRITE); + sound.setCapability(PointSound.ALLOW_DURATION_READ); + sound.setCapability(PointSound.ALLOW_POSITION_WRITE); + sound.setCapability(PointSound.ALLOW_LOOP_WRITE); + sound.setSchedulingBounds(bounds); + + objTrans.addChild(sound); + // + // Create a new Behavior object that will play the sound + // + AudioReverberate player = new AudioReverberate(sound, url, attributes2); + player.setSchedulingBounds(bounds); + objTrans.addChild(player); + + return objRoot; + } + + public ReverberateSound() { + } + + public void init() {System.setProperty("sun.awt.noerasebackground", "true"); + url = Resources.getResource("resources/audio/hello_universe.au"); + if (url == null) { + System.err.println("resources/audio/hello_universe.au not found"); + System.exit(1); + } + + setLayout(new BorderLayout()); + GraphicsConfiguration config = + SimpleUniverse.getPreferredConfiguration(); + + Canvas3D c = new Canvas3D(config); + add("Center", c); + + /* + * Create a simple scene and attach it to the virtual universe + */ + u = new SimpleUniverse(c); + AudioDevice audioDev = u.getViewer().createAudioDevice(); + BranchGroup scene = createSceneGraph(); + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + u.getViewingPlatform().setNominalViewingTransform(); + + u.addBranchGraph(scene); + + JOptionPane.showMessageDialog(this, + ("This program is still a work in progress.\n" + + "Please check back in Java 3D 1.5.\n"), + "Incomplete Work", + JOptionPane.INFORMATION_MESSAGE); + } + + public void destroy() { + u.cleanup(); + } + + // + // The following allows ReverberateSound to be run as an application + // as well as an applet + // + public static void main(String[] args) {System.setProperty("sun.awt.noerasebackground", "true"); + new MainFrame(new ReverberateSound(), 256, 256); + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/sound/SimpleSounds.java b/src/main/java/org/jdesktop/j3d/examples/sound/SimpleSounds.java new file mode 100644 index 0000000..c5df424 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/sound/SimpleSounds.java @@ -0,0 +1,262 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.sound; + +import java.applet.Applet; +import java.awt.BorderLayout; +import java.awt.GraphicsConfiguration; +import java.net.URL; + +import javax.swing.JOptionPane; + +import org.jdesktop.j3d.examples.Resources; +import org.jogamp.java3d.Alpha; +import org.jogamp.java3d.AudioDevice; +import org.jogamp.java3d.BackgroundSound; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.PointSound; +import org.jogamp.java3d.RotationInterpolator; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.utils.applet.MainFrame; +import org.jogamp.java3d.utils.geometry.ColorCube; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.vecmath.Point3d; + +/* + * This Java3D program: + * Creates an instance of the JavaSoundMixer AudioDevice, initializing it + * and attaching it to the PhysicalEnvironment by using + * SimpleUniverse. + * Creates one cached Background and two cached Point sound sources. + * Creates and executes a custom behavior (SimpleSoundsBehavior) that + * starts the sound playing and transforms the PointSound source + * by modifying the TransformGroup that contains the Sound nodes. + * + * Usage: + * java SimpleSounds [URLpath [name1 [name2 [name2]]]] + * + * The first optional command line parameter is the URL path to directory + * containing "file:" or "http:" and then directory path string. + * If you are using the suppled default sound files in the same directory + * as this test program then only the URLpath need be supplied on the + * command line. + * If this parameter is not included then the current path to the directory + * this program is running in is used for an application + * and the codebase is used for an applet. + * The second thru fourth optional command line parameters are sound file names + * If not given, the default file names are: + * techno_machine.au + * hello_universe.au + * roar.au + * that correspond to the 3 'voice' quality, 8-bit, u-law, 8-kHz samples + * included in the same directory as this test program. + * + * Java Sound engine has been advertised to support the following 8- and 16- + * bit, linear and u-law, mono and stereo sound sample file formats: AU, + * AIFF, WAV, and PCM. Non-cached MIDI and RMF files are also supported. + * Neither compressed formats (DVI, GSM, MOD) nor A-law formated files are + * supported at this time, but they will be converted. + */ + +public class SimpleSounds extends Applet { + + private static URL[] url = new URL[3]; + private SimpleUniverse u = null; + + public BranchGroup createSceneGraph() { + // Create the root of the subgraph + BranchGroup objRoot = new BranchGroup(); + + // Create the transform group node and initialize it to the identity. + // Enable the TRANSFORM_WRITE capability so that our behavior code + // can modify it at runtime. Add it to the root of the subgraph. + TransformGroup objTrans = new TransformGroup(); + objTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + objRoot.addChild(objTrans); + + // Create a simple shape leaf node and add it into the scene graph. + objTrans.addChild(new ColorCube(0.4)); + + // Create a new Behavior object that will perform the desired + // operation on the specified transform object and add it into the + // scene graph. + Transform3D yAxis = new Transform3D(); + Alpha rotation = new Alpha(-1, Alpha.INCREASING_ENABLE, + 0, 0, + 20000, 0, 0, + 0, 0, 0); + RotationInterpolator rotator = + new RotationInterpolator(rotation, + objTrans, yAxis, + 0.0f, (float) Math.PI*2.0f); + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + rotator.setSchedulingBounds(bounds); + objTrans.addChild(rotator); + /* + * Create a sound node and add it to the scene graph + */ + BackgroundSound sound1 = new BackgroundSound(); + PointSound sound2 = new PointSound(); + PointSound sound3 = new PointSound(); + sound1.setCapability(PointSound.ALLOW_ENABLE_WRITE); + sound1.setCapability(PointSound.ALLOW_INITIAL_GAIN_WRITE); + sound1.setCapability(PointSound.ALLOW_SOUND_DATA_WRITE); + sound1.setCapability(PointSound.ALLOW_SCHEDULING_BOUNDS_WRITE); + sound1.setCapability(PointSound.ALLOW_CONT_PLAY_WRITE); + sound1.setCapability(PointSound.ALLOW_RELEASE_WRITE); + sound1.setCapability(PointSound.ALLOW_DURATION_READ); + sound1.setCapability(PointSound.ALLOW_IS_PLAYING_READ); + sound1.setCapability(PointSound.ALLOW_LOOP_WRITE); + sound2.setCapability(PointSound.ALLOW_ENABLE_WRITE); + sound2.setCapability(PointSound.ALLOW_INITIAL_GAIN_WRITE); + sound2.setCapability(PointSound.ALLOW_SOUND_DATA_WRITE); + sound2.setCapability(PointSound.ALLOW_SCHEDULING_BOUNDS_WRITE); + sound2.setCapability(PointSound.ALLOW_CONT_PLAY_WRITE); + sound2.setCapability(PointSound.ALLOW_RELEASE_WRITE); + sound2.setCapability(PointSound.ALLOW_DURATION_READ); + sound2.setCapability(PointSound.ALLOW_IS_PLAYING_READ); + sound2.setCapability(PointSound.ALLOW_POSITION_WRITE); + sound2.setCapability(PointSound.ALLOW_LOOP_WRITE); + sound3.setCapability(PointSound.ALLOW_ENABLE_WRITE); + sound3.setCapability(PointSound.ALLOW_INITIAL_GAIN_WRITE); + sound3.setCapability(PointSound.ALLOW_SOUND_DATA_WRITE); + sound3.setCapability(PointSound.ALLOW_SCHEDULING_BOUNDS_WRITE); + sound3.setCapability(PointSound.ALLOW_CONT_PLAY_WRITE); + sound3.setCapability(PointSound.ALLOW_RELEASE_WRITE); + sound3.setCapability(PointSound.ALLOW_DURATION_READ); + sound3.setCapability(PointSound.ALLOW_IS_PLAYING_READ); + sound3.setCapability(PointSound.ALLOW_POSITION_WRITE); + + BoundingSphere soundBounds = + new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + sound1.setSchedulingBounds(soundBounds); + sound2.setSchedulingBounds(soundBounds); + sound3.setSchedulingBounds(soundBounds); + objTrans.addChild(sound1); + objTrans.addChild(sound2); + objTrans.addChild(sound3); + + + /* + * Create a new Behavior object that will play the sound + */ + SimpleSoundsBehavior player = new SimpleSoundsBehavior( + sound1, sound2, sound3, + url[0], url[1], url[2], soundBounds); + player.setSchedulingBounds(soundBounds); + objTrans.addChild(player); + + // Let Java 3D perform optimizations on this scene graph. + objRoot.compile(); + + return objRoot; + } + + public SimpleSounds() { + } + + public void init() {System.setProperty("sun.awt.noerasebackground", "true"); + + setLayout(new BorderLayout()); + GraphicsConfiguration config = + SimpleUniverse.getPreferredConfiguration(); + + Canvas3D c = new Canvas3D(config); + add("Center", c); + + url[0] = Resources.getResource("resources/audio/techno_machine.au"); + if (url == null) { + System.err.println("resources/audio/techno_machine.au not found"); + System.exit(1); + } + + url[1] = Resources.getResource("resources/audio/hello_universe.au"); + if (url == null) { + System.err.println("resources/audio/hello_universe.au not found"); + System.exit(1); + } + + url[2] = Resources.getResource("resources/audio/roar.au"); + if (url == null) { + System.err.println("resources/audio/roar.au not found"); + System.exit(1); + } + + /* + * Create a simple scene and attach it to the virtual universe + */ + u = new SimpleUniverse(c); + AudioDevice audioDev = u.getViewer().createAudioDevice(); + BranchGroup scene = createSceneGraph(); + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + u.getViewingPlatform().setNominalViewingTransform(); + + u.addBranchGraph(scene); + + JOptionPane.showMessageDialog(this, + ("This program is still a work in progress.\n" + + "Please check back in Java 3D 1.5.\n"), + "Incomplete Work", + JOptionPane.INFORMATION_MESSAGE); + } + + public void destroy() { + u.cleanup(); + } + + /* + * The following allows SimpleSounds to be run as an application + * as well as an applet + */ + public static void main(String[] args) {System.setProperty("sun.awt.noerasebackground", "true"); + new MainFrame(new SimpleSounds(), args, 256, 256); + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/sound/SimpleSoundsBehavior.java b/src/main/java/org/jdesktop/j3d/examples/sound/SimpleSoundsBehavior.java new file mode 100644 index 0000000..3c7560e --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/sound/SimpleSoundsBehavior.java @@ -0,0 +1,187 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.sound; + +import java.net.URL; +import java.util.Enumeration; + +import org.jogamp.java3d.BackgroundSound; +import org.jogamp.java3d.Behavior; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.MediaContainer; +import org.jogamp.java3d.PointSound; +import org.jogamp.java3d.Sound; +import org.jogamp.java3d.WakeupOnBehaviorPost; +import org.jogamp.java3d.WakeupOnElapsedTime; +import org.jogamp.vecmath.Point3f; + +// User defined audio behavior class +public class SimpleSoundsBehavior extends Behavior { + WakeupOnElapsedTime wt; + WakeupOnBehaviorPost wp; + BackgroundSound sound1 = new BackgroundSound(); + PointSound sound2 = new PointSound(); + PointSound sound3 = new PointSound(); + static int WAKEUP_SOUND = 0; + int soundIndex = 0; + URL URLName1; + URL URLName2; + URL URLName3; + BoundingSphere bounds; + + // Override Behavior's initialize method to setup wakeup criteria + public void initialize() { + MediaContainer sample1 = new MediaContainer(); + MediaContainer sample2 = new MediaContainer(); + MediaContainer sample3 = new MediaContainer(); + sample1.setCapability(MediaContainer.ALLOW_URL_WRITE); + sample1.setCapability(MediaContainer.ALLOW_URL_READ); + sample1.setURLObject(URLName1); + //sample1.setCacheEnable(false); + sound1.setLoop(0); + sound1.setContinuousEnable(false); + sound1.setReleaseEnable(false); + sound1.setSoundData(sample1); + sound1.setInitialGain(0.7f); + sample2.setCapability(MediaContainer.ALLOW_URL_WRITE); + sample2.setCapability(MediaContainer.ALLOW_URL_READ); + sample2.setURLObject(URLName2); + sound2.setLoop(Sound.INFINITE_LOOPS); + sound2.setContinuousEnable(false); + sound2.setReleaseEnable(false); + sound2.setSoundData(sample2); + sound2.setInitialGain(2.0f); + Point3f sound2Pos = new Point3f(-30.0f, 0.0f, 0.0f); + sound2.setPosition(sound2Pos); + sample3.setCapability(MediaContainer.ALLOW_URL_WRITE); + sample3.setCapability(MediaContainer.ALLOW_URL_READ); + sample3.setURLObject(URLName3); + sound3.setContinuousEnable(false); + sound3.setReleaseEnable(false); + sound3.setSoundData(sample3); + sound3.setInitialGain(4.0f); + Point3f sound3Pos = new Point3f(30.0f, 0.0f, 0.0f); + sound3.setPosition(sound3Pos); + + wt = new WakeupOnElapsedTime(2000); + WakeupOnElapsedTime wp = new WakeupOnElapsedTime(5000); + wakeupOn(wp); + } + + // Override Behavior's stimulus method to handle the event + public void processStimulus(Enumeration criteria) { + + switch (soundIndex) + { + // Active + case 0: + // System.out.println("****Enable First Sound"); + sound1.setEnable(true); + wakeupOn(wt); + break; + case 1: + // System.out.println("********Enable Second Sound"); + sound2.setEnable(true); + wakeupOn(wt); + break; + case 2: + case 4: + case 6: + case 8: + case 10: + // System.out.println("************Enable Third Sound"); + sound3.setEnable(true); + wakeupOn(wt); + break; + case 3: + case 5: + case 7: + case 9: + // System.out.println("************Disable Third Sound"); + sound3.setEnable(false); + wakeupOn(wt); + break; + + case 11: + // System.out.println("********Disable Second Sound"); + sound2.setEnable(false) ; + wakeupOn(wt); + break; + case 12: + // System.out.println("****Disable First Sound"); + sound1.setEnable(false) ; + System.out.println("SimpleSounds: test complete"); + wt = new WakeupOnElapsedTime(400000); + wakeupOn(wt); + break; + + default: + break; + } + soundIndex++; + } + + // + // Constructor for rotation behavior. + // Parameters: sound node + // sample file name + // sound node's bounds + // + public SimpleSoundsBehavior(BackgroundSound sound1, + PointSound sound2, + PointSound sound3, + URL urlName1, + URL urlName2, + URL urlName3, + BoundingSphere soundBounds) { + this.sound1 = sound1; + this.sound2 = sound2; + this.sound3 = sound3; + this.URLName1 = urlName1; + this.URLName2 = urlName2; + this.URLName3 = urlName3; + this.bounds = (BoundingSphere)soundBounds.clone(); + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/sphere_motion/SphereMotion.form b/src/main/java/org/jdesktop/j3d/examples/sphere_motion/SphereMotion.form new file mode 100644 index 0000000..036d770 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/sphere_motion/SphereMotion.form @@ -0,0 +1,36 @@ +<?xml version="1.0" encoding="UTF-8" ?> + +<Form version="1.0" type="org.netbeans.modules.form.forminfo.JFrameFormInfo"> + <Properties> + <Property name="defaultCloseOperation" type="int" value="3"/> + <Property name="title" type="java.lang.String" value="SphereMotion"/> + </Properties> + <SyntheticProperties> + <SyntheticProperty name="formSizePolicy" type="int" value="1"/> + </SyntheticProperties> + <AuxValues> + <AuxValue name="FormSettings_generateMnemonicsCode" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_listenerGenerationStyle" type="java.lang.Integer" value="0"/> + <AuxValue name="FormSettings_variablesLocal" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_variablesModifier" type="java.lang.Integer" value="2"/> + <AuxValue name="designerSize" type="java.awt.Dimension" value="-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,1,44,0,0,1,-112"/> + </AuxValues> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + <SubComponents> + <Container class="javax.swing.JPanel" name="drawingPanel"> + <Properties> + <Property name="preferredSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor"> + <Dimension value="[700, 700]"/> + </Property> + </Properties> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout" value="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription"> + <BorderConstraints direction="Center"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + </Container> + </SubComponents> +</Form> diff --git a/src/main/java/org/jdesktop/j3d/examples/sphere_motion/SphereMotion.java b/src/main/java/org/jdesktop/j3d/examples/sphere_motion/SphereMotion.java new file mode 100644 index 0000000..f98085b --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/sphere_motion/SphereMotion.java @@ -0,0 +1,365 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.sphere_motion; + +import java.awt.GraphicsConfiguration; + +import org.jogamp.java3d.Alpha; +import org.jogamp.java3d.AmbientLight; +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.Background; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.ColoringAttributes; +import org.jogamp.java3d.DirectionalLight; +import org.jogamp.java3d.Light; +import org.jogamp.java3d.Material; +import org.jogamp.java3d.PointLight; +import org.jogamp.java3d.PositionInterpolator; +import org.jogamp.java3d.RotationInterpolator; +import org.jogamp.java3d.SpotLight; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.utils.geometry.Sphere; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Point3f; +import org.jogamp.vecmath.Vector3d; +import org.jogamp.vecmath.Vector3f; + +public class SphereMotion extends javax.swing.JFrame { + + private SimpleUniverse univ = null; + private BranchGroup scene = null; + + // Constants for type of light to use + private static final int DIRECTIONAL_LIGHT = 0; + private static final int POINT_LIGHT = 1; + private static final int SPOT_LIGHT = 2; + + // Flag indicates type of lights: directional, point, or spot + // lights. This flag is set based on command line argument + private static int lightType = POINT_LIGHT; + + public BranchGroup createSceneGraph() { + Color3f eColor = new Color3f(0.0f, 0.0f, 0.0f); + Color3f sColor = new Color3f(1.0f, 1.0f, 1.0f); + Color3f objColor = new Color3f(0.6f, 0.6f, 0.6f); + Color3f lColor1 = new Color3f(1.0f, 0.0f, 0.0f); + Color3f lColor2 = new Color3f(0.0f, 1.0f, 0.0f); + Color3f alColor = new Color3f(0.2f, 0.2f, 0.2f); + Color3f bgColor = new Color3f(0.05f, 0.05f, 0.2f); + + Transform3D t; + + // Create the root of the branch graph + BranchGroup objRoot = new BranchGroup(); + + // Create a Transformgroup to scale all objects so they + // appear in the scene. + TransformGroup objScale = new TransformGroup(); + Transform3D t3d = new Transform3D(); + t3d.setScale(0.4); + objScale.setTransform(t3d); + objRoot.addChild(objScale); + + // Create a bounds for the background and lights + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + + // Set up the background + Background bg = new Background(bgColor); + bg.setApplicationBounds(bounds); + objScale.addChild(bg); + + // Create a Sphere object, generate one copy of the sphere, + // and add it into the scene graph. + Material m = new Material(objColor, eColor, objColor, sColor, 100.0f); + Appearance a = new Appearance(); + m.setLightingEnable(true); + a.setMaterial(m); + Sphere sph = new Sphere(1.0f, Sphere.GENERATE_NORMALS, 80, a); + objScale.addChild(sph); + + // Create the transform group node for the each light and initialize + // it to the identity. Enable the TRANSFORM_WRITE capability so that + // our behavior code can modify it at runtime. Add them to the root + // of the subgraph. + TransformGroup l1RotTrans = new TransformGroup(); + l1RotTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + objScale.addChild(l1RotTrans); + + TransformGroup l2RotTrans = new TransformGroup(); + l2RotTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + objScale.addChild(l2RotTrans); + + // Create transformations for the positional lights + t = new Transform3D(); + Vector3d lPos1 = new Vector3d(0.0, 0.0, 2.0); + t.set(lPos1); + TransformGroup l1Trans = new TransformGroup(t); + l1RotTrans.addChild(l1Trans); + + t = new Transform3D(); + Vector3d lPos2 = new Vector3d(0.5, 0.8, 2.0); + t.set(lPos2); + TransformGroup l2Trans = new TransformGroup(t); + l2RotTrans.addChild(l2Trans); + + // Create Geometry for point lights + ColoringAttributes caL1 = new ColoringAttributes(); + ColoringAttributes caL2 = new ColoringAttributes(); + caL1.setColor(lColor1); + caL2.setColor(lColor2); + Appearance appL1 = new Appearance(); + Appearance appL2 = new Appearance(); + appL1.setColoringAttributes(caL1); + appL2.setColoringAttributes(caL2); + l1Trans.addChild(new Sphere(0.05f, appL1)); + l2Trans.addChild(new Sphere(0.05f, appL2)); + + // Create lights + AmbientLight aLgt = new AmbientLight(alColor); + + Light lgt1 = null; + Light lgt2 = null; + + Point3f lPoint = new Point3f(0.0f, 0.0f, 0.0f); + Point3f atten = new Point3f(1.0f, 0.0f, 0.0f); + Vector3f lDirect1 = new Vector3f(lPos1); + Vector3f lDirect2 = new Vector3f(lPos2); + lDirect1.negate(); + lDirect2.negate(); + + switch (lightType) { + case DIRECTIONAL_LIGHT: + lgt1 = new DirectionalLight(lColor1, lDirect1); + lgt2 = new DirectionalLight(lColor2, lDirect2); + break; + case POINT_LIGHT: + lgt1 = new PointLight(lColor1, lPoint, atten); + lgt2 = new PointLight(lColor2, lPoint, atten); + break; + case SPOT_LIGHT: + lgt1 = new SpotLight(lColor1, lPoint, atten, lDirect1, + 25.0f * (float)Math.PI / 180.0f, 10.0f); + lgt2 = new SpotLight(lColor2, lPoint, atten, lDirect2, + 25.0f * (float)Math.PI / 180.0f, 10.0f); + break; + } + + // Set the influencing bounds + aLgt.setInfluencingBounds(bounds); + lgt1.setInfluencingBounds(bounds); + lgt2.setInfluencingBounds(bounds); + + // Add the lights into the scene graph + objScale.addChild(aLgt); + l1Trans.addChild(lgt1); + l2Trans.addChild(lgt2); + + // Create a new Behavior object that will perform the desired + // operation on the specified transform object and add it into the + // scene graph. + Transform3D yAxis = new Transform3D(); + Alpha rotor1Alpha = new Alpha(-1, Alpha.INCREASING_ENABLE, + 0, 0, + 4000, 0, 0, + 0, 0, 0); + RotationInterpolator rotator1 = + new RotationInterpolator(rotor1Alpha, + l1RotTrans, + yAxis, + 0.0f, (float) Math.PI*2.0f); + rotator1.setSchedulingBounds(bounds); + l1RotTrans.addChild(rotator1); + + // Create a new Behavior object that will perform the desired + // operation on the specified transform object and add it into the + // scene graph. + Alpha rotor2Alpha = new Alpha(-1, Alpha.INCREASING_ENABLE, + 0, 0, + 1000, 0, 0, + 0, 0, 0); + RotationInterpolator rotator2 = + new RotationInterpolator(rotor2Alpha, + l2RotTrans, + yAxis, + 0.0f, 0.0f); + bounds = new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + rotator2.setSchedulingBounds(bounds); + l2RotTrans.addChild(rotator2); + + // Create a position interpolator and attach it to the view + // platform + TransformGroup vpTrans = + univ.getViewingPlatform().getViewPlatformTransform(); + Transform3D axisOfTranslation = new Transform3D(); + Alpha transAlpha = new Alpha(-1, + Alpha.INCREASING_ENABLE | + Alpha.DECREASING_ENABLE, + 0, 0, + 5000, 0, 0, + 5000, 0, 0); + axisOfTranslation.rotY(-Math.PI/2.0); + PositionInterpolator translator = + new PositionInterpolator(transAlpha, + vpTrans, + axisOfTranslation, + 2.0f, 3.5f); + translator.setSchedulingBounds(bounds); + objScale.addChild(translator); + + // Let Java 3D perform optimizations on this scene graph. + objRoot.compile(); + + return objRoot; + } + + private Canvas3D createUniverse() { + // Get the preferred graphics configuration for the default screen + GraphicsConfiguration config = + SimpleUniverse.getPreferredConfiguration(); + + // Create a Canvas3D using the preferred configuration + Canvas3D c = new Canvas3D(config); + + // Create simple universe with view branch + univ = new SimpleUniverse(c); + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + univ.getViewingPlatform().setNominalViewingTransform(); + + // Ensure at least 5 msec per frame (i.e., < 200Hz) + univ.getViewer().getView().setMinimumFrameCycleTime(5); + + return c; + } + + /** + * Creates new form SphereMotion + */ + public SphereMotion(final String[] args) { + + // Parse the Input Arguments + String usage = "Usage: java SphereMotion [-point | -spot | -dir]"; + for (int i = 0; i < args.length; i++) { + if (args[i].startsWith("-")) { + if (args[i].equals("-point")) { + System.out.println("Using point lights"); + lightType = POINT_LIGHT; + } + else if (args[i].equals("-spot")) { + System.out.println("Using spot lights"); + lightType = SPOT_LIGHT; + } + else if (args[i].equals("-dir")) { + System.out.println("Using directional lights"); + lightType = DIRECTIONAL_LIGHT; + } + else { + System.out.println(usage); + System.exit(0); + } + } + else { + System.out.println(usage); + System.exit(0); + } + } + + // Initialize the GUI components + initComponents(); + + // Create Canvas3D and SimpleUniverse; add canvas to drawing panel + Canvas3D c = createUniverse(); + drawingPanel.add(c, java.awt.BorderLayout.CENTER); + + // Create the content branch and add it to the universe + scene = createSceneGraph(); + univ.addBranchGraph(scene); + } + + // ---------------------------------------------------------------- + + /** This method is called from within the constructor to + * initialize the form. + * WARNING: Do NOT modify this code. The content of this method is + * always regenerated by the Form Editor. + */ + // <editor-fold defaultstate="collapsed" desc=" Generated Code ">//GEN-BEGIN:initComponents + private void initComponents() { + drawingPanel = new javax.swing.JPanel(); + + setDefaultCloseOperation(javax.swing.WindowConstants.EXIT_ON_CLOSE); + setTitle("SphereMotion"); + drawingPanel.setLayout(new java.awt.BorderLayout()); + + drawingPanel.setPreferredSize(new java.awt.Dimension(700, 700)); + getContentPane().add(drawingPanel, java.awt.BorderLayout.CENTER); + + pack(); + }// </editor-fold>//GEN-END:initComponents + + /** + * @param args the command line arguments + */ + public static void main(final String args[]) { + java.awt.EventQueue.invokeLater(new Runnable() { + public void run() { + SphereMotion sphereMotion = new SphereMotion(args); + sphereMotion.setVisible(true); + } + }); + } + + // Variables declaration - do not modify//GEN-BEGIN:variables + private javax.swing.JPanel drawingPanel; + // End of variables declaration//GEN-END:variables + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/sphere_motion/SphereMotionGL2ES2.java b/src/main/java/org/jdesktop/j3d/examples/sphere_motion/SphereMotionGL2ES2.java new file mode 100644 index 0000000..547c998 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/sphere_motion/SphereMotionGL2ES2.java @@ -0,0 +1,363 @@ +/* + * Copyright (c) 2016 JogAmp Community. All rights reserved. + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * This code is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 only, as + * published by the Free Software Foundation. Sun designates this + * particular file as subject to the "Classpath" exception as provided + * by Sun in the LICENSE file that accompanied this code. + * + * This code is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + * version 2 for more details (a copy is included in the LICENSE file that + * accompanied this code). + * + * You should have received a copy of the GNU General Public License version + * 2 along with this work; if not, write to the Free Software Foundation, + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. + * + */ + +package org.jdesktop.j3d.examples.sphere_motion; + +import java.awt.GraphicsConfiguration; +import java.io.File; +import java.io.IOException; + +import org.jdesktop.j3d.examples.gl2es2pipeline.SimpleShaderAppearance; +import org.jogamp.java3d.Alpha; +import org.jogamp.java3d.AmbientLight; +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.Background; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.ColoringAttributes; +import org.jogamp.java3d.DirectionalLight; +import org.jogamp.java3d.GLSLShaderProgram; +import org.jogamp.java3d.Light; +import org.jogamp.java3d.Material; +import org.jogamp.java3d.PointLight; +import org.jogamp.java3d.PositionInterpolator; +import org.jogamp.java3d.RotationInterpolator; +import org.jogamp.java3d.Shader; +import org.jogamp.java3d.ShaderAppearance; +import org.jogamp.java3d.ShaderProgram; +import org.jogamp.java3d.SourceCodeShader; +import org.jogamp.java3d.SpotLight; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.utils.geometry.Sphere; +import org.jogamp.java3d.utils.shader.StringIO; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Point3f; +import org.jogamp.vecmath.Vector3d; +import org.jogamp.vecmath.Vector3f; + +public class SphereMotionGL2ES2 extends javax.swing.JFrame +{ + + private SimpleUniverse univ = null; + private BranchGroup scene = null; + + // Constants for type of light to use + private static final int DIRECTIONAL_LIGHT = 0; + private static final int POINT_LIGHT = 1; + private static final int SPOT_LIGHT = 2; + + // Flag indicates type of lights: directional, point, or spot + // lights. This flag is set based on command line argument + private static int lightType = POINT_LIGHT; + + public BranchGroup createSceneGraph() + { + Color3f eColor = new Color3f(0.0f, 0.0f, 0.0f); + Color3f sColor = new Color3f(1.0f, 1.0f, 1.0f); + Color3f objColor = new Color3f(0.6f, 0.6f, 0.6f); + Color3f lColor1 = new Color3f(1.0f, 0.0f, 0.0f); + Color3f lColor2 = new Color3f(0.0f, 1.0f, 0.0f); + Color3f alColor = new Color3f(0.2f, 0.2f, 0.2f); + Color3f bgColor = new Color3f(0.05f, 0.05f, 0.2f); + + Transform3D t; + + // Create the root of the branch graph + BranchGroup objRoot = new BranchGroup(); + + // Create a Transformgroup to scale all objects so they + // appear in the scene. + TransformGroup objScale = new TransformGroup(); + Transform3D t3d = new Transform3D(); + t3d.setScale(0.4); + objScale.setTransform(t3d); + objRoot.addChild(objScale); + + // Create a bounds for the background and lights + BoundingSphere bounds = new BoundingSphere(new Point3d(0.0, 0.0, 0.0), 100.0); + + // Set up the background + Background bg = new Background(bgColor); + bg.setApplicationBounds(bounds); + objScale.addChild(bg); + + // Create a Sphere object, generate one copy of the sphere, + // and add it into the scene graph. + ShaderAppearance a = new ShaderAppearance(); + Material m = new Material(objColor, eColor, objColor, sColor, 100.0f); + m.setLightingEnable(true); + String vertexProgram = null; + String fragmentProgram = null; + try + { + vertexProgram = StringIO.readFully( + new File(System.getProperty("user.dir") + "/src/classes/org/jdesktop/j3d/examples/sphere_motion/phong_gl2es2.vert")); + fragmentProgram = StringIO.readFully( + new File(System.getProperty("user.dir") + "/src/classes/org/jdesktop/j3d/examples/sphere_motion/phong_gl2es2.frag")); + } + catch (IOException e) + { + throw new RuntimeException(e); + } + Shader[] shaders = new Shader[2]; + shaders[0] = new SourceCodeShader(Shader.SHADING_LANGUAGE_GLSL, Shader.SHADER_TYPE_VERTEX, vertexProgram); + shaders[1] = new SourceCodeShader(Shader.SHADING_LANGUAGE_GLSL, Shader.SHADER_TYPE_FRAGMENT, fragmentProgram); + ShaderProgram shaderProgram = new GLSLShaderProgram(); + shaderProgram.setShaders(shaders); + + a.setShaderProgram(shaderProgram); + a.setMaterial(m); + Sphere sph = new Sphere(1.0f, Sphere.GENERATE_NORMALS, 200, a); + objScale.addChild(sph); + + // Create the transform group node for the each light and initialize + // it to the identity. Enable the TRANSFORM_WRITE capability so that + // our behavior code can modify it at runtime. Add them to the root + // of the subgraph. + TransformGroup l1RotTrans = new TransformGroup(); + l1RotTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + objScale.addChild(l1RotTrans); + + TransformGroup l2RotTrans = new TransformGroup(); + l2RotTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + objScale.addChild(l2RotTrans); + + // Create transformations for the positional lights + t = new Transform3D(); + Vector3d lPos1 = new Vector3d(0.0, 0.0, 2.0); + t.set(lPos1); + TransformGroup l1Trans = new TransformGroup(t); + l1RotTrans.addChild(l1Trans); + + t = new Transform3D(); + Vector3d lPos2 = new Vector3d(0.5, 0.8, 2.0); + t.set(lPos2); + TransformGroup l2Trans = new TransformGroup(t); + l2RotTrans.addChild(l2Trans); + + // Create Geometry for point lights + ColoringAttributes caL1 = new ColoringAttributes(); + ColoringAttributes caL2 = new ColoringAttributes(); + caL1.setColor(lColor1); + caL2.setColor(lColor2); + Appearance appL1 = new SimpleShaderAppearance(false, false); + Appearance appL2 = new SimpleShaderAppearance(false, false); + appL1.setColoringAttributes(caL1); + appL2.setColoringAttributes(caL2); + l1Trans.addChild(new Sphere(0.05f, appL1)); + l2Trans.addChild(new Sphere(0.05f, appL2)); + + // Create lights + AmbientLight aLgt = new AmbientLight(alColor); + + Light lgt1 = null; + Light lgt2 = null; + + Point3f lPoint = new Point3f(0.0f, 0.0f, 0.0f); + Point3f atten = new Point3f(1.0f, 0.0f, 0.0f); + Vector3f lDirect1 = new Vector3f(lPos1); + Vector3f lDirect2 = new Vector3f(lPos2); + lDirect1.negate(); + lDirect2.negate(); + + switch (lightType) + { + case DIRECTIONAL_LIGHT: + lgt1 = new DirectionalLight(lColor1, lDirect1); + lgt2 = new DirectionalLight(lColor2, lDirect2); + break; + case POINT_LIGHT: + lgt1 = new PointLight(lColor1, lPoint, atten); + lgt2 = new PointLight(lColor2, lPoint, atten); + break; + case SPOT_LIGHT: + lgt1 = new SpotLight(lColor1, lPoint, atten, lDirect1, 25.0f * (float) Math.PI / 180.0f, 10.0f); + lgt2 = new SpotLight(lColor2, lPoint, atten, lDirect2, 25.0f * (float) Math.PI / 180.0f, 10.0f); + break; + } + + // Set the influencing bounds + aLgt.setInfluencingBounds(bounds); + lgt1.setInfluencingBounds(bounds); + lgt2.setInfluencingBounds(bounds); + + // Add the lights into the scene graph + objScale.addChild(aLgt); + l1Trans.addChild(lgt1); + l2Trans.addChild(lgt2); + + // Create a new Behavior object that will perform the desired + // operation on the specified transform object and add it into the + // scene graph. + Transform3D yAxis = new Transform3D(); + Alpha rotor1Alpha = new Alpha(-1, Alpha.INCREASING_ENABLE, 0, 0, 4000, 0, 0, 0, 0, 0); + RotationInterpolator rotator1 = new RotationInterpolator(rotor1Alpha, l1RotTrans, yAxis, 0.0f, (float) Math.PI * 2.0f); + rotator1.setSchedulingBounds(bounds); + l1RotTrans.addChild(rotator1); + + // Create a new Behavior object that will perform the desired + // operation on the specified transform object and add it into the + // scene graph. + Alpha rotor2Alpha = new Alpha(-1, Alpha.INCREASING_ENABLE, 0, 0, 1000, 0, 0, 0, 0, 0); + RotationInterpolator rotator2 = new RotationInterpolator(rotor2Alpha, l2RotTrans, yAxis, 0.0f, 0.0f); + bounds = new BoundingSphere(new Point3d(0.0, 0.0, 0.0), 100.0); + rotator2.setSchedulingBounds(bounds); + l2RotTrans.addChild(rotator2); + + // Create a position interpolator and attach it to the view + // platform + TransformGroup vpTrans = univ.getViewingPlatform().getViewPlatformTransform(); + Transform3D axisOfTranslation = new Transform3D(); + Alpha transAlpha = new Alpha(-1, Alpha.INCREASING_ENABLE | Alpha.DECREASING_ENABLE, 0, 0, 5000, 0, 0, 5000, 0, 0); + axisOfTranslation.rotY(-Math.PI / 2.0); + PositionInterpolator translator = new PositionInterpolator(transAlpha, vpTrans, axisOfTranslation, 2.0f, 3.5f); + translator.setSchedulingBounds(bounds); + objScale.addChild(translator); + + // Let Java 3D perform optimizations on this scene graph. + objRoot.compile(); + + return objRoot; + } + + private Canvas3D createUniverse() + { + // Get the preferred graphics configuration for the default screen + GraphicsConfiguration config = SimpleUniverse.getPreferredConfiguration(); + + // Create a Canvas3D using the preferred configuration + Canvas3D c = new Canvas3D(config); + + // Create simple universe with view branch + univ = new SimpleUniverse(c); + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + univ.getViewingPlatform().setNominalViewingTransform(); + + // Ensure at least 5 msec per frame (i.e., < 200Hz) + univ.getViewer().getView().setMinimumFrameCycleTime(5); + + return c; + } + + /** + * Creates new form SphereMotion + */ + public SphereMotionGL2ES2(final String[] args) + { + + // Parse the Input Arguments + String usage = "Usage: java SphereMotion [-point | -spot | -dir]"; + for (int i = 0; i < args.length; i++) + { + if (args[i].startsWith("-")) + { + if (args[i].equals("-point")) + { + System.out.println("Using point lights"); + lightType = POINT_LIGHT; + } + else if (args[i].equals("-spot")) + { + System.out.println("Using spot lights"); + lightType = SPOT_LIGHT; + } + else if (args[i].equals("-dir")) + { + System.out.println("Using directional lights"); + lightType = DIRECTIONAL_LIGHT; + } + else + { + System.out.println(usage); + System.exit(0); + } + } + else + { + System.out.println(usage); + System.exit(0); + } + } + + // Initialize the GUI components + initComponents(); + + // Create Canvas3D and SimpleUniverse; add canvas to drawing panel + Canvas3D c = createUniverse(); + drawingPanel.add(c, java.awt.BorderLayout.CENTER); + + // Create the content branch and add it to the universe + scene = createSceneGraph(); + univ.addBranchGraph(scene); + } + + // ---------------------------------------------------------------- + + /** This method is called from within the constructor to + * initialize the form. + * WARNING: Do NOT modify this code. The content of this method is + * always regenerated by the Form Editor. + */ + // <editor-fold defaultstate="collapsed" desc=" Generated Code ">//GEN-BEGIN:initComponents + private void initComponents() + { + drawingPanel = new javax.swing.JPanel(); + + setDefaultCloseOperation(javax.swing.WindowConstants.EXIT_ON_CLOSE); + setTitle("SphereMotionGL2ES2"); + drawingPanel.setLayout(new java.awt.BorderLayout()); + + drawingPanel.setPreferredSize(new java.awt.Dimension(700, 700)); + getContentPane().add(drawingPanel, java.awt.BorderLayout.CENTER); + + pack(); + }// </editor-fold>//GEN-END:initComponents + + /** + * @param args the command line arguments + */ + public static void main(final String args[]) + { + System.setProperty("sun.awt.noerasebackground", "true"); + System.setProperty("j3d.rend", "jogl2es2"); + System.setProperty("j3d.displaylist", "false"); + java.awt.EventQueue.invokeLater(new Runnable() { + @Override + public void run() + { + SphereMotionGL2ES2 sphereMotion = new SphereMotionGL2ES2(args); + sphereMotion.setVisible(true); + } + }); + } + + // Variables declaration - do not modify//GEN-BEGIN:variables + private javax.swing.JPanel drawingPanel; + // End of variables declaration//GEN-END:variables + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/sphere_motion/SphereMotionGL2ES3_Texture.java b/src/main/java/org/jdesktop/j3d/examples/sphere_motion/SphereMotionGL2ES3_Texture.java new file mode 100644 index 0000000..a1cee22 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/sphere_motion/SphereMotionGL2ES3_Texture.java @@ -0,0 +1,376 @@ +/* + * Copyright (c) 2016 JogAmp Community. All rights reserved. + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * This code is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 only, as + * published by the Free Software Foundation. Sun designates this + * particular file as subject to the "Classpath" exception as provided + * by Sun in the LICENSE file that accompanied this code. + * + * This code is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + * version 2 for more details (a copy is included in the LICENSE file that + * accompanied this code). + * + * You should have received a copy of the GNU General Public License version + * 2 along with this work; if not, write to the Free Software Foundation, + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. + * + */ +package org.jdesktop.j3d.examples.sphere_motion; + +import java.awt.GraphicsConfiguration; +import java.io.File; +import java.io.IOException; + +import org.jdesktop.j3d.examples.Resources; +import org.jdesktop.j3d.examples.gl2es2pipeline.SimpleShaderAppearance; +import org.jogamp.java3d.Alpha; +import org.jogamp.java3d.AmbientLight; +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.Background; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.ColoringAttributes; +import org.jogamp.java3d.DirectionalLight; +import org.jogamp.java3d.GLSLShaderProgram; +import org.jogamp.java3d.Light; +import org.jogamp.java3d.Material; +import org.jogamp.java3d.PointLight; +import org.jogamp.java3d.PositionInterpolator; +import org.jogamp.java3d.RotationInterpolator; +import org.jogamp.java3d.Shader; +import org.jogamp.java3d.ShaderAppearance; +import org.jogamp.java3d.ShaderAttributeSet; +import org.jogamp.java3d.ShaderAttributeValue; +import org.jogamp.java3d.ShaderProgram; +import org.jogamp.java3d.SourceCodeShader; +import org.jogamp.java3d.SpotLight; +import org.jogamp.java3d.Texture; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.utils.geometry.Sphere; +import org.jogamp.java3d.utils.image.TextureLoader; +import org.jogamp.java3d.utils.shader.StringIO; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Point3f; +import org.jogamp.vecmath.Vector3d; +import org.jogamp.vecmath.Vector3f; + +public class SphereMotionGL2ES3_Texture extends javax.swing.JFrame +{ + + private SimpleUniverse univ = null; + private BranchGroup scene = null; + + // Constants for type of light to use + private static final int DIRECTIONAL_LIGHT = 0; + private static final int POINT_LIGHT = 1; + private static final int SPOT_LIGHT = 2; + + // Flag indicates type of lights: directional, point, or spot + // lights. This flag is set based on command line argument + private static int lightType = POINT_LIGHT; + + public BranchGroup createSceneGraph() + { + Color3f eColor = new Color3f(0.0f, 0.0f, 0.0f); + Color3f sColor = new Color3f(1.0f, 1.0f, 1.0f); + Color3f objColor = new Color3f(0.6f, 0.6f, 0.6f); + Color3f lColor1 = new Color3f(1.0f, 0.0f, 0.0f); + Color3f lColor2 = new Color3f(0.0f, 1.0f, 0.0f); + Color3f alColor = new Color3f(0.2f, 0.2f, 0.2f); + Color3f bgColor = new Color3f(0.05f, 0.05f, 0.2f); + + Transform3D t; + + // Create the root of the branch graph + BranchGroup objRoot = new BranchGroup(); + + // Create a Transformgroup to scale all objects so they + // appear in the scene. + TransformGroup objScale = new TransformGroup(); + Transform3D t3d = new Transform3D(); + t3d.setScale(0.4); + objScale.setTransform(t3d); + objRoot.addChild(objScale); + + // Create a bounds for the background and lights + BoundingSphere bounds = new BoundingSphere(new Point3d(0.0, 0.0, 0.0), 100.0); + + // Set up the background + Background bg = new Background(bgColor); + bg.setApplicationBounds(bounds); + objScale.addChild(bg); + + // Create a Sphere object, generate one copy of the sphere, + // and add it into the scene graph. + ShaderAppearance a = new ShaderAppearance(); + Material m = new Material(objColor, eColor, objColor, sColor, 100.0f); + m.setLightingEnable(true); + String vertexProgram = null; + String fragmentProgram = null; + try + { + vertexProgram = StringIO.readFully( + new File(System.getProperty("user.dir") + "/src/classes/org/jdesktop/j3d/examples/sphere_motion/phong_gl2es2_texture.vert")); + fragmentProgram = StringIO.readFully( + new File(System.getProperty("user.dir") + "/src/classes/org/jdesktop/j3d/examples/sphere_motion/phong_gl2es2_texture.frag")); + } + catch (IOException e) + { + throw new RuntimeException(e); + } + Shader[] shaders = new Shader[2]; + shaders[0] = new SourceCodeShader(Shader.SHADING_LANGUAGE_GLSL, Shader.SHADER_TYPE_VERTEX, vertexProgram); + shaders[1] = new SourceCodeShader(Shader.SHADING_LANGUAGE_GLSL, Shader.SHADER_TYPE_FRAGMENT, fragmentProgram); + ShaderProgram shaderProgram = new GLSLShaderProgram(); + shaderProgram.setShaders(shaders); + shaderProgram.setShaderAttrNames(new String[] { "BaseMap" }); + + a.setShaderProgram(shaderProgram); + + ShaderAttributeSet shaderAttributeSet = new ShaderAttributeSet(); + shaderAttributeSet.put(new ShaderAttributeValue("BaseMap", new Integer(0))); + a.setShaderAttributeSet(shaderAttributeSet); + + + a.setMaterial(m); + Texture txtr = new TextureLoader(Resources.getResource("resources/images/earth.jpg"), this).getTexture(); + a.setTexture(txtr); + Sphere sph = new Sphere(1.0f, Sphere.GENERATE_NORMALS | Sphere.GENERATE_TEXTURE_COORDS, 200, a); + objScale.addChild(sph); + + // Create the transform group node for the each light and initialize + // it to the identity. Enable the TRANSFORM_WRITE capability so that + // our behavior code can modify it at runtime. Add them to the root + // of the subgraph. + TransformGroup l1RotTrans = new TransformGroup(); + l1RotTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + objScale.addChild(l1RotTrans); + + TransformGroup l2RotTrans = new TransformGroup(); + l2RotTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + objScale.addChild(l2RotTrans); + + // Create transformations for the positional lights + t = new Transform3D(); + Vector3d lPos1 = new Vector3d(0.0, 0.0, 2.0); + t.set(lPos1); + TransformGroup l1Trans = new TransformGroup(t); + l1RotTrans.addChild(l1Trans); + + t = new Transform3D(); + Vector3d lPos2 = new Vector3d(0.5, 0.8, 2.0); + t.set(lPos2); + TransformGroup l2Trans = new TransformGroup(t); + l2RotTrans.addChild(l2Trans); + + // Create Geometry for point lights + ColoringAttributes caL1 = new ColoringAttributes(); + ColoringAttributes caL2 = new ColoringAttributes(); + caL1.setColor(lColor1); + caL2.setColor(lColor2); + Appearance appL1 = new SimpleShaderAppearance(false, false); + Appearance appL2 = new SimpleShaderAppearance(false, false); + appL1.setColoringAttributes(caL1); + appL2.setColoringAttributes(caL2); + l1Trans.addChild(new Sphere(0.05f, appL1)); + l2Trans.addChild(new Sphere(0.05f, appL2)); + + // Create lights + AmbientLight aLgt = new AmbientLight(alColor); + + Light lgt1 = null; + Light lgt2 = null; + + Point3f lPoint = new Point3f(0.0f, 0.0f, 0.0f); + Point3f atten = new Point3f(1.0f, 0.0f, 0.0f); + Vector3f lDirect1 = new Vector3f(lPos1); + Vector3f lDirect2 = new Vector3f(lPos2); + lDirect1.negate(); + lDirect2.negate(); + + switch (lightType) + { + case DIRECTIONAL_LIGHT: + lgt1 = new DirectionalLight(lColor1, lDirect1); + lgt2 = new DirectionalLight(lColor2, lDirect2); + break; + case POINT_LIGHT: + lgt1 = new PointLight(lColor1, lPoint, atten); + lgt2 = new PointLight(lColor2, lPoint, atten); + break; + case SPOT_LIGHT: + lgt1 = new SpotLight(lColor1, lPoint, atten, lDirect1, 25.0f * (float) Math.PI / 180.0f, 10.0f); + lgt2 = new SpotLight(lColor2, lPoint, atten, lDirect2, 25.0f * (float) Math.PI / 180.0f, 10.0f); + break; + } + + // Set the influencing bounds + aLgt.setInfluencingBounds(bounds); + lgt1.setInfluencingBounds(bounds); + lgt2.setInfluencingBounds(bounds); + + // Add the lights into the scene graph + objScale.addChild(aLgt); + l1Trans.addChild(lgt1); + l2Trans.addChild(lgt2); + + // Create a new Behavior object that will perform the desired + // operation on the specified transform object and add it into the + // scene graph. + Transform3D yAxis = new Transform3D(); + Alpha rotor1Alpha = new Alpha(-1, Alpha.INCREASING_ENABLE, 0, 0, 4000, 0, 0, 0, 0, 0); + RotationInterpolator rotator1 = new RotationInterpolator(rotor1Alpha, l1RotTrans, yAxis, 0.0f, (float) Math.PI * 2.0f); + rotator1.setSchedulingBounds(bounds); + l1RotTrans.addChild(rotator1); + + // Create a new Behavior object that will perform the desired + // operation on the specified transform object and add it into the + // scene graph. + Alpha rotor2Alpha = new Alpha(-1, Alpha.INCREASING_ENABLE, 0, 0, 1000, 0, 0, 0, 0, 0); + RotationInterpolator rotator2 = new RotationInterpolator(rotor2Alpha, l2RotTrans, yAxis, 0.0f, 0.0f); + bounds = new BoundingSphere(new Point3d(0.0, 0.0, 0.0), 100.0); + rotator2.setSchedulingBounds(bounds); + l2RotTrans.addChild(rotator2); + + // Create a position interpolator and attach it to the view + // platform + TransformGroup vpTrans = univ.getViewingPlatform().getViewPlatformTransform(); + Transform3D axisOfTranslation = new Transform3D(); + Alpha transAlpha = new Alpha(-1, Alpha.INCREASING_ENABLE | Alpha.DECREASING_ENABLE, 0, 0, 5000, 0, 0, 5000, 0, 0); + axisOfTranslation.rotY(-Math.PI / 2.0); + PositionInterpolator translator = new PositionInterpolator(transAlpha, vpTrans, axisOfTranslation, 2.0f, 3.5f); + translator.setSchedulingBounds(bounds); + objScale.addChild(translator); + + // Let Java 3D perform optimizations on this scene graph. + objRoot.compile(); + + return objRoot; + } + + private Canvas3D createUniverse() + { + // Get the preferred graphics configuration for the default screen + GraphicsConfiguration config = SimpleUniverse.getPreferredConfiguration(); + + // Create a Canvas3D using the preferred configuration + Canvas3D c = new Canvas3D(config); + + // Create simple universe with view branch + univ = new SimpleUniverse(c); + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + univ.getViewingPlatform().setNominalViewingTransform(); + + // Ensure at least 5 msec per frame (i.e., < 200Hz) + univ.getViewer().getView().setMinimumFrameCycleTime(5); + + return c; + } + + /** + * Creates new form SphereMotion + */ + public SphereMotionGL2ES3_Texture(final String[] args) + { + + // Parse the Input Arguments + String usage = "Usage: java SphereMotion [-point | -spot | -dir]"; + for (int i = 0; i < args.length; i++) + { + if (args[i].startsWith("-")) + { + if (args[i].equals("-point")) + { + System.out.println("Using point lights"); + lightType = POINT_LIGHT; + } + else if (args[i].equals("-spot")) + { + System.out.println("Using spot lights"); + lightType = SPOT_LIGHT; + } + else if (args[i].equals("-dir")) + { + System.out.println("Using directional lights"); + lightType = DIRECTIONAL_LIGHT; + } + else + { + System.out.println(usage); + System.exit(0); + } + } + else + { + System.out.println(usage); + System.exit(0); + } + } + + // Initialize the GUI components + initComponents(); + + // Create Canvas3D and SimpleUniverse; add canvas to drawing panel + Canvas3D c = createUniverse(); + drawingPanel.add(c, java.awt.BorderLayout.CENTER); + + // Create the content branch and add it to the universe + scene = createSceneGraph(); + univ.addBranchGraph(scene); + } + + // ---------------------------------------------------------------- + + /** This method is called from within the constructor to + * initialize the form. + * WARNING: Do NOT modify this code. The content of this method is + * always regenerated by the Form Editor. + */ + // <editor-fold defaultstate="collapsed" desc=" Generated Code ">//GEN-BEGIN:initComponents + private void initComponents() + { + drawingPanel = new javax.swing.JPanel(); + + setDefaultCloseOperation(javax.swing.WindowConstants.EXIT_ON_CLOSE); + setTitle("SphereMotionGL2ES2_Texture"); + drawingPanel.setLayout(new java.awt.BorderLayout()); + + drawingPanel.setPreferredSize(new java.awt.Dimension(700, 700)); + getContentPane().add(drawingPanel, java.awt.BorderLayout.CENTER); + + pack(); + }// </editor-fold>//GEN-END:initComponents + + /** + * @param args the command line arguments + */ + public static void main(final String args[]) + { + System.setProperty("sun.awt.noerasebackground", "true"); + System.setProperty("j3d.rend", "jogl2es2"); + System.setProperty("j3d.displaylist", "false"); + java.awt.EventQueue.invokeLater(new Runnable() { + @Override + public void run() + { + SphereMotionGL2ES3_Texture sphereMotion = new SphereMotionGL2ES3_Texture(args); + sphereMotion.setVisible(true); + } + }); + } + + // Variables declaration - do not modify//GEN-BEGIN:variables + private javax.swing.JPanel drawingPanel; + // End of variables declaration//GEN-END:variables + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/sphere_motion/SphereMotionGLSL_FFP.java b/src/main/java/org/jdesktop/j3d/examples/sphere_motion/SphereMotionGLSL_FFP.java new file mode 100644 index 0000000..ce1fdc0 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/sphere_motion/SphereMotionGLSL_FFP.java @@ -0,0 +1,361 @@ +/* + * Copyright (c) 2016 JogAmp Community. All rights reserved. + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * This code is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 only, as + * published by the Free Software Foundation. Sun designates this + * particular file as subject to the "Classpath" exception as provided + * by Sun in the LICENSE file that accompanied this code. + * + * This code is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + * version 2 for more details (a copy is included in the LICENSE file that + * accompanied this code). + * + * You should have received a copy of the GNU General Public License version + * 2 along with this work; if not, write to the Free Software Foundation, + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. + * + */ + +package org.jdesktop.j3d.examples.sphere_motion; + +import java.awt.GraphicsConfiguration; +import java.io.File; +import java.io.IOException; + +import org.jogamp.java3d.Alpha; +import org.jogamp.java3d.AmbientLight; +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.Background; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.ColoringAttributes; +import org.jogamp.java3d.DirectionalLight; +import org.jogamp.java3d.GLSLShaderProgram; +import org.jogamp.java3d.Light; +import org.jogamp.java3d.Material; +import org.jogamp.java3d.PointLight; +import org.jogamp.java3d.PositionInterpolator; +import org.jogamp.java3d.RotationInterpolator; +import org.jogamp.java3d.Shader; +import org.jogamp.java3d.ShaderAppearance; +import org.jogamp.java3d.ShaderProgram; +import org.jogamp.java3d.SourceCodeShader; +import org.jogamp.java3d.SpotLight; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.utils.geometry.Sphere; +import org.jogamp.java3d.utils.shader.StringIO; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Point3f; +import org.jogamp.vecmath.Vector3d; +import org.jogamp.vecmath.Vector3f; + +public class SphereMotionGLSL_FFP extends javax.swing.JFrame +{ + + private SimpleUniverse univ = null; + private BranchGroup scene = null; + + // Constants for type of light to use + private static final int DIRECTIONAL_LIGHT = 0; + private static final int POINT_LIGHT = 1; + private static final int SPOT_LIGHT = 2; + + // Flag indicates type of lights: directional, point, or spot + // lights. This flag is set based on command line argument + private static int lightType = POINT_LIGHT; + + public BranchGroup createSceneGraph() + { + Color3f eColor = new Color3f(0.0f, 0.0f, 0.0f); + Color3f sColor = new Color3f(1.0f, 1.0f, 1.0f); + Color3f objColor = new Color3f(0.6f, 0.6f, 0.6f); + Color3f lColor1 = new Color3f(1.0f, 0.0f, 0.0f); + Color3f lColor2 = new Color3f(0.0f, 1.0f, 0.0f); + Color3f alColor = new Color3f(0.2f, 0.2f, 0.2f); + Color3f bgColor = new Color3f(0.05f, 0.05f, 0.2f); + + Transform3D t; + + // Create the root of the branch graph + BranchGroup objRoot = new BranchGroup(); + + // Create a Transformgroup to scale all objects so they + // appear in the scene. + TransformGroup objScale = new TransformGroup(); + Transform3D t3d = new Transform3D(); + t3d.setScale(0.4); + objScale.setTransform(t3d); + objRoot.addChild(objScale); + + // Create a bounds for the background and lights + BoundingSphere bounds = new BoundingSphere(new Point3d(0.0, 0.0, 0.0), 100.0); + + // Set up the background + Background bg = new Background(bgColor); + bg.setApplicationBounds(bounds); + objScale.addChild(bg); + + // Create a Sphere object, generate one copy of the sphere, + // and add it into the scene graph. + ShaderAppearance a = new ShaderAppearance(); + Material m = new Material(objColor, eColor, objColor, sColor, 100.0f); + m.setLightingEnable(true); + String vertexProgram = null; + String fragmentProgram = null; + try + { + vertexProgram = StringIO.readFully( + new File(System.getProperty("user.dir") + "/src/classes/org/jdesktop/j3d/examples/sphere_motion/phong_ffp.vert")); + fragmentProgram = StringIO.readFully( + new File(System.getProperty("user.dir") + "/src/classes/org/jdesktop/j3d/examples/sphere_motion/phong_ffp.frag")); + } + catch (IOException e) + { + throw new RuntimeException(e); + } + Shader[] shaders = new Shader[2]; + shaders[0] = new SourceCodeShader(Shader.SHADING_LANGUAGE_GLSL, Shader.SHADER_TYPE_VERTEX, vertexProgram); + shaders[1] = new SourceCodeShader(Shader.SHADING_LANGUAGE_GLSL, Shader.SHADER_TYPE_FRAGMENT, fragmentProgram); + ShaderProgram shaderProgram = new GLSLShaderProgram(); + shaderProgram.setShaders(shaders); + + a.setShaderProgram(shaderProgram); + a.setMaterial(m); + Sphere sph = new Sphere(1.0f, Sphere.GENERATE_NORMALS, 200, a); + objScale.addChild(sph); + + // Create the transform group node for the each light and initialize + // it to the identity. Enable the TRANSFORM_WRITE capability so that + // our behavior code can modify it at runtime. Add them to the root + // of the subgraph. + TransformGroup l1RotTrans = new TransformGroup(); + l1RotTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + objScale.addChild(l1RotTrans); + + TransformGroup l2RotTrans = new TransformGroup(); + l2RotTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + objScale.addChild(l2RotTrans); + + // Create transformations for the positional lights + t = new Transform3D(); + Vector3d lPos1 = new Vector3d(0.0, 0.0, 2.0); + t.set(lPos1); + TransformGroup l1Trans = new TransformGroup(t); + l1RotTrans.addChild(l1Trans); + + t = new Transform3D(); + Vector3d lPos2 = new Vector3d(0.5, 0.8, 2.0); + t.set(lPos2); + TransformGroup l2Trans = new TransformGroup(t); + l2RotTrans.addChild(l2Trans); + + // Create Geometry for point lights + ColoringAttributes caL1 = new ColoringAttributes(); + ColoringAttributes caL2 = new ColoringAttributes(); + caL1.setColor(lColor1); + caL2.setColor(lColor2); + Appearance appL1 = new Appearance(); + Appearance appL2 = new Appearance(); + appL1.setColoringAttributes(caL1); + appL2.setColoringAttributes(caL2); + l1Trans.addChild(new Sphere(0.05f, appL1)); + l2Trans.addChild(new Sphere(0.05f, appL2)); + + // Create lights + AmbientLight aLgt = new AmbientLight(alColor); + + Light lgt1 = null; + Light lgt2 = null; + + Point3f lPoint = new Point3f(0.0f, 0.0f, 0.0f); + Point3f atten = new Point3f(1.0f, 0.0f, 0.0f); + Vector3f lDirect1 = new Vector3f(lPos1); + Vector3f lDirect2 = new Vector3f(lPos2); + lDirect1.negate(); + lDirect2.negate(); + + switch (lightType) + { + case DIRECTIONAL_LIGHT: + lgt1 = new DirectionalLight(lColor1, lDirect1); + lgt2 = new DirectionalLight(lColor2, lDirect2); + break; + case POINT_LIGHT: + lgt1 = new PointLight(lColor1, lPoint, atten); + lgt2 = new PointLight(lColor2, lPoint, atten); + break; + case SPOT_LIGHT: + lgt1 = new SpotLight(lColor1, lPoint, atten, lDirect1, 25.0f * (float) Math.PI / 180.0f, 10.0f); + lgt2 = new SpotLight(lColor2, lPoint, atten, lDirect2, 25.0f * (float) Math.PI / 180.0f, 10.0f); + break; + } + + // Set the influencing bounds + aLgt.setInfluencingBounds(bounds); + lgt1.setInfluencingBounds(bounds); + lgt2.setInfluencingBounds(bounds); + + // Add the lights into the scene graph + objScale.addChild(aLgt); + l1Trans.addChild(lgt1); + l2Trans.addChild(lgt2); + + + // Create a new Behavior object that will perform the desired + // operation on the specified transform object and add it into the + // scene graph. + Transform3D yAxis = new Transform3D(); + Alpha rotor1Alpha = new Alpha(-1, Alpha.INCREASING_ENABLE, 0, 0, 4000, 0, 0, 0, 0, 0); + RotationInterpolator rotator1 = new RotationInterpolator(rotor1Alpha, l1RotTrans, yAxis, 0.0f, (float) Math.PI * 2.0f); + rotator1.setSchedulingBounds(bounds); + l1RotTrans.addChild(rotator1); + + // Create a new Behavior object that will perform the desired + // operation on the specified transform object and add it into the + // scene graph. + Alpha rotor2Alpha = new Alpha(-1, Alpha.INCREASING_ENABLE, 0, 0, 1000, 0, 0, 0, 0, 0); + RotationInterpolator rotator2 = new RotationInterpolator(rotor2Alpha, l2RotTrans, yAxis, 0.0f, 0.0f); + bounds = new BoundingSphere(new Point3d(0.0, 0.0, 0.0), 100.0); + rotator2.setSchedulingBounds(bounds); + l2RotTrans.addChild(rotator2); + + // Create a position interpolator and attach it to the view + // platform + TransformGroup vpTrans = univ.getViewingPlatform().getViewPlatformTransform(); + Transform3D axisOfTranslation = new Transform3D(); + Alpha transAlpha = new Alpha(-1, Alpha.INCREASING_ENABLE | Alpha.DECREASING_ENABLE, 0, 0, 5000, 0, 0, 5000, 0, 0); + axisOfTranslation.rotY(-Math.PI / 2.0); + PositionInterpolator translator = new PositionInterpolator(transAlpha, vpTrans, axisOfTranslation, 2.0f, 3.5f); + translator.setSchedulingBounds(bounds); + objScale.addChild(translator); + + // Let Java 3D perform optimizations on this scene graph. + objRoot.compile(); + + return objRoot; + } + + private Canvas3D createUniverse() + { + // Get the preferred graphics configuration for the default screen + GraphicsConfiguration config = SimpleUniverse.getPreferredConfiguration(); + + // Create a Canvas3D using the preferred configuration + Canvas3D c = new Canvas3D(config); + + // Create simple universe with view branch + univ = new SimpleUniverse(c); + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + univ.getViewingPlatform().setNominalViewingTransform(); + + // Ensure at least 5 msec per frame (i.e., < 200Hz) + univ.getViewer().getView().setMinimumFrameCycleTime(5); + + return c; + } + + /** + * Creates new form SphereMotion + */ + public SphereMotionGLSL_FFP(final String[] args) + { + + // Parse the Input Arguments + String usage = "Usage: java SphereMotion [-point | -spot | -dir]"; + for (int i = 0; i < args.length; i++) + { + if (args[i].startsWith("-")) + { + if (args[i].equals("-point")) + { + System.out.println("Using point lights"); + lightType = POINT_LIGHT; + } + else if (args[i].equals("-spot")) + { + System.out.println("Using spot lights"); + lightType = SPOT_LIGHT; + } + else if (args[i].equals("-dir")) + { + System.out.println("Using directional lights"); + lightType = DIRECTIONAL_LIGHT; + } + else + { + System.out.println(usage); + System.exit(0); + } + } + else + { + System.out.println(usage); + System.exit(0); + } + } + + // Initialize the GUI components + initComponents(); + + // Create Canvas3D and SimpleUniverse; add canvas to drawing panel + Canvas3D c = createUniverse(); + drawingPanel.add(c, java.awt.BorderLayout.CENTER); + + // Create the content branch and add it to the universe + scene = createSceneGraph(); + univ.addBranchGraph(scene); + } + + // ---------------------------------------------------------------- + + /** This method is called from within the constructor to + * initialize the form. + * WARNING: Do NOT modify this code. The content of this method is + * always regenerated by the Form Editor. + */ + // <editor-fold defaultstate="collapsed" desc=" Generated Code ">//GEN-BEGIN:initComponents + private void initComponents() + { + drawingPanel = new javax.swing.JPanel(); + + setDefaultCloseOperation(javax.swing.WindowConstants.EXIT_ON_CLOSE); + setTitle("SphereMotionGLSL_FFP"); + drawingPanel.setLayout(new java.awt.BorderLayout()); + + drawingPanel.setPreferredSize(new java.awt.Dimension(700, 700)); + getContentPane().add(drawingPanel, java.awt.BorderLayout.CENTER); + + pack(); + }// </editor-fold>//GEN-END:initComponents + + /** + * @param args the command line arguments + */ + public static void main(final String args[]) + { + System.setProperty("sun.awt.noerasebackground", "true"); + java.awt.EventQueue.invokeLater(new Runnable() { + @Override + public void run() + { + SphereMotionGLSL_FFP sphereMotion = new SphereMotionGLSL_FFP(args); + sphereMotion.setVisible(true); + } + }); + } + + // Variables declaration - do not modify//GEN-BEGIN:variables + private javax.swing.JPanel drawingPanel; + // End of variables declaration//GEN-END:variables + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/sphere_motion/phong_ffp.frag b/src/main/java/org/jdesktop/j3d/examples/sphere_motion/phong_ffp.frag new file mode 100644 index 0000000..ba72696 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/sphere_motion/phong_ffp.frag @@ -0,0 +1,66 @@ +#version 120 + +// Per-pixel normal (input from vertex shader) +varying vec3 normalDirection; +varying vec3 viewDirection; +varying vec4 position; + +const int numberOfLights = 2; + +void main() +{ + vec3 lightDirection; + float attenuation; + + // initialize total lighting with ambient lighting + vec3 totalLighting = vec3(gl_FrontMaterial.emission) + (vec3(gl_LightModel.ambient) * vec3(gl_FrontMaterial.ambient)); + + for (int index = 0; index < numberOfLights; index++) // for all light sources + { + if (0.0 == gl_LightSource[index].position.w) // directional light? + { + attenuation = 1.0; // no attenuation + lightDirection = normalize(vec3(gl_LightSource[index].position)); + } + else // point light or spotlight (or other kind of light) + { + vec3 positionToLightSource = vec3(gl_LightSource[index].position - position); + float distance = length(positionToLightSource); + lightDirection = normalize(positionToLightSource); + attenuation = 1.0 / (gl_LightSource[index].constantAttenuation + + gl_LightSource[index].linearAttenuation * distance + + gl_LightSource[index].quadraticAttenuation * distance * distance); + + + if (gl_LightSource[index].spotCutoff <= 90.0) // spotlight? + { + float clampedCosine = max(0.0, dot(-lightDirection, normalize(gl_LightSource[index].spotDirection))); + if (clampedCosine < cos(radians(gl_LightSource[index].spotCutoff))) // outside of spotlight cone? + { + attenuation = 0.0; + } + else + { + attenuation = attenuation * pow(clampedCosine, gl_LightSource[index].spotExponent); + } + } + } + + vec3 diffuseReflection = attenuation * vec3(gl_LightSource[index].diffuse) * vec3(gl_FrontMaterial.diffuse)* max(0.0, dot(normalDirection, lightDirection)); + + vec3 specularReflection; + if (dot(normalDirection, lightDirection) < 0.0) // light source on the wrong side? + { + specularReflection = vec3(0.0, 0.0, 0.0); // no specular reflection + } + else // light source on the right side + { + specularReflection = attenuation * vec3(gl_LightSource[index].specular) * vec3(gl_FrontMaterial.specular) + * pow(max(0.0, dot(reflect(-lightDirection, normalDirection), viewDirection)), gl_FrontMaterial.shininess); + } + + totalLighting = totalLighting + diffuseReflection + specularReflection; + } + + gl_FragColor = vec4(totalLighting, 1.0); +} diff --git a/src/main/java/org/jdesktop/j3d/examples/sphere_motion/phong_ffp.vert b/src/main/java/org/jdesktop/j3d/examples/sphere_motion/phong_ffp.vert new file mode 100644 index 0000000..caf1732 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/sphere_motion/phong_ffp.vert @@ -0,0 +1,19 @@ + + +// A GLSL vertex program for doing Phone shading (per-fragment lighting) + +// Per-pixel normal (output to fragment shader) +varying vec3 normalDirection; +varying vec3 viewDirection; +varying vec4 position; + +void main() +{ + normalDirection = normalize(vec3(gl_NormalMatrix * gl_Normal)); + vec3 v = vec3(gl_ModelViewMatrix * gl_Vertex); + viewDirection = normalize(-v.xyz); + position = vec4(v,1); + + // Transform the vertex + gl_Position = gl_ModelViewProjectionMatrix * gl_Vertex; +} diff --git a/src/main/java/org/jdesktop/j3d/examples/sphere_motion/phong_gl2es2.frag b/src/main/java/org/jdesktop/j3d/examples/sphere_motion/phong_gl2es2.frag new file mode 100644 index 0000000..af65808 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/sphere_motion/phong_gl2es2.frag @@ -0,0 +1,96 @@ +#version 120 + +// Per-pixel normal (input from vertex shader) +varying vec3 normalDirection; +varying vec3 viewDirection; +varying vec4 position; + +uniform vec4 glLightModelambient; + + +struct material +{ + int lightEnabled; + vec4 ambient; + vec4 diffuse; + vec4 emission;// note vec4 extra 1.0 sent through for ease + vec3 specular; + float shininess; +}; +uniform material glFrontMaterial; + +struct lightSource +{ + int enabled; + vec4 position; + vec4 diffuse; + vec4 specular; + float constantAttenuation, linearAttenuation, quadraticAttenuation; + float spotCutoff, spotExponent; + vec3 spotDirection; +}; + +uniform int numberOfLights; +const int maxLights = 2; +uniform lightSource glLightSource[maxLights]; + +void main() +{ + vec3 lightDirection; + float attenuation; + + // initialize total lighting with ambient lighting + vec3 totalLighting = vec3(glFrontMaterial.emission) + (vec3(glLightModelambient) * vec3(glFrontMaterial.ambient)); + + for (int index = 0; index < numberOfLights; index++) // for all light sources + { + if(glLightSource[index].enabled == 1) + { + if (0.0 == glLightSource[index].position.w) // directional light? + { + attenuation = 1.0; // no attenuation + lightDirection = normalize(vec3(glLightSource[index].position)); + + } + else // point light or spotlight (or other kind of light) + { + vec3 positionToLightSource = vec3(glLightSource[index].position - position); + float distance = length(positionToLightSource); + lightDirection = normalize(positionToLightSource); + attenuation = 1.0 / (glLightSource[index].constantAttenuation + + glLightSource[index].linearAttenuation * distance + + glLightSource[index].quadraticAttenuation * distance * distance); + + if (glLightSource[index].spotCutoff <= 90.0) // spotlight? + { + float clampedCosine = max(0.0, dot(-lightDirection, normalize(glLightSource[index].spotDirection))); + if (clampedCosine < cos(radians(glLightSource[index].spotCutoff))) // outside of spotlight cone? + { + attenuation = 0.0; + } + else + { + attenuation = attenuation * pow(clampedCosine, glLightSource[index].spotExponent); + } + } + } + + vec3 diffuseReflection = attenuation * vec3(glLightSource[index].diffuse) * vec3(glFrontMaterial.diffuse)* max(0.0, dot(normalDirection, lightDirection)); + + vec3 specularReflection; + if (dot(normalDirection, lightDirection) < 0.0) // light source on the wrong side? + { + specularReflection = vec3(0.0, 0.0, 0.0); // no specular reflection + } + else // light source on the right side + { + specularReflection = attenuation * vec3(glLightSource[index].specular) * vec3(glFrontMaterial.specular) + * pow(max(0.0, dot(reflect(-lightDirection, normalDirection), viewDirection)), glFrontMaterial.shininess); + } + + totalLighting = totalLighting + diffuseReflection + specularReflection; + } + } + + gl_FragColor = vec4(totalLighting, 1.0); +} diff --git a/src/main/java/org/jdesktop/j3d/examples/sphere_motion/phong_gl2es2.vert b/src/main/java/org/jdesktop/j3d/examples/sphere_motion/phong_gl2es2.vert new file mode 100644 index 0000000..4d8fb67 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/sphere_motion/phong_gl2es2.vert @@ -0,0 +1,31 @@ +// GL2ES2: Java3D built-in attributes, these are calculated and passsed in if declared here +attribute vec4 glVertex; +attribute vec3 glNormal; + +// GL2ES2: Java3D built-in uniforms, these are calculated and passsed in if declared here +uniform mat4 glModelViewProjectionMatrix; +uniform mat4 glModelViewMatrix; +uniform mat3 glNormalMatrix; + + +// Per-pixel normal (output to fragment shader) +varying vec3 normalDirection; +varying vec3 viewDirection; +varying vec4 position; + +void main() +{ + normalDirection = normalize(vec3(glNormalMatrix * glNormal)); + vec3 v = vec3(glModelViewMatrix * glVertex); + viewDirection = normalize(-v.xyz); + position = vec4(v,1); + + // Transform the vertex + gl_Position = glModelViewProjectionMatrix * glVertex; +} + + + + + + diff --git a/src/main/java/org/jdesktop/j3d/examples/sphere_motion/phong_gl2es2_texture.frag b/src/main/java/org/jdesktop/j3d/examples/sphere_motion/phong_gl2es2_texture.frag new file mode 100644 index 0000000..2b1a258 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/sphere_motion/phong_gl2es2_texture.frag @@ -0,0 +1,105 @@ +#version 120 + +// Per-pixel normal (input from vertex shader) +varying vec3 normalDirection; +varying vec3 viewDirection; +varying vec4 position; + +varying vec2 glTexCoord0; +uniform sampler2D BaseMap; + +uniform vec4 glLightModelambient; + + +struct material +{ + int lightEnabled; + vec4 ambient; + vec4 diffuse; + vec4 emission; + vec3 specular; + float shininess; +}; +uniform material glFrontMaterial; + +struct lightSource +{ + int enabled; + vec4 position; + vec4 diffuse; + vec4 specular; + float constantAttenuation, linearAttenuation, quadraticAttenuation; + float spotCutoff, spotExponent; + vec3 spotDirection; +}; + +uniform int numberOfLights; +const int maxLights = 2; +uniform lightSource glLightSource[maxLights]; + +void main() +{ + vec4 baseMap = texture2D( BaseMap, glTexCoord0.st ); + + vec3 lightDirection; + float attenuation; + + // initialize total lighting with ambient lighting + vec3 totalDiffuseLighting = vec3(glFrontMaterial.emission) + (vec3(glLightModelambient) * vec3(glFrontMaterial.ambient)); + vec3 totalSpecularLighting; + + for (int index = 0; index < numberOfLights; index++) // for all light sources + { + if(glLightSource[index].enabled == 1) + { + if (0.0 == glLightSource[index].position.w) // directional light? + { + attenuation = 1.0; // no attenuation + lightDirection = normalize(vec3(glLightSource[index].position)); + + } + else // point light or spotlight (or other kind of light) + { + vec3 positionToLightSource = vec3(glLightSource[index].position - position); + float distance = length(positionToLightSource); + lightDirection = normalize(positionToLightSource); + attenuation = 1.0 / (glLightSource[index].constantAttenuation + + glLightSource[index].linearAttenuation * distance + + glLightSource[index].quadraticAttenuation * distance * distance); + + if (glLightSource[index].spotCutoff <= 90.0) // spotlight? + { + float clampedCosine = max(0.0, dot(-lightDirection, normalize(glLightSource[index].spotDirection))); + if (clampedCosine < cos(radians(glLightSource[index].spotCutoff))) // outside of spotlight cone? + { + attenuation = 0.0; + } + else + { + attenuation = attenuation * pow(clampedCosine, glLightSource[index].spotExponent); + } + } + } + + vec3 diffuseReflection = attenuation * vec3(glLightSource[index].diffuse) * vec3(glFrontMaterial.diffuse)* max(0.0, dot(normalDirection, lightDirection)); + + vec3 specularReflection; + if (dot(normalDirection, lightDirection) < 0.0) // light source on the wrong side? + { + specularReflection = vec3(0.0, 0.0, 0.0); // no specular reflection + } + else // light source on the right side + { + specularReflection = attenuation * vec3(glLightSource[index].specular) * vec3(glFrontMaterial.specular) + * pow(max(0.0, dot(reflect(-lightDirection, normalDirection), viewDirection)), glFrontMaterial.shininess); + } + + totalDiffuseLighting = totalDiffuseLighting + diffuseReflection; + totalSpecularLighting = totalSpecularLighting + specularReflection; + } + } + + totalDiffuseLighting = totalDiffuseLighting * baseMap.rgb; + + gl_FragColor = vec4(totalDiffuseLighting + totalSpecularLighting, 1.0); +} diff --git a/src/main/java/org/jdesktop/j3d/examples/sphere_motion/phong_gl2es2_texture.vert b/src/main/java/org/jdesktop/j3d/examples/sphere_motion/phong_gl2es2_texture.vert new file mode 100644 index 0000000..7e492e3 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/sphere_motion/phong_gl2es2_texture.vert @@ -0,0 +1,35 @@ +// GL2ES2: Java3D built-in attributes, these are calculated and passsed in if declared here +attribute vec4 glVertex; +attribute vec3 glNormal; +attribute vec2 glMultiTexCoord0; + +// GL2ES2: Java3D built-in uniforms, these are calculated and passsed in if declared here +uniform mat4 glModelViewProjectionMatrix; +uniform mat4 glModelViewMatrix; +uniform mat3 glNormalMatrix; + + +// Per-pixel normal (output to fragment shader) +varying vec3 normalDirection; +varying vec3 viewDirection; +varying vec4 position; + +varying vec2 glTexCoord0; + +void main() +{ + normalDirection = normalize(vec3(glNormalMatrix * glNormal)); + vec3 v = vec3(glModelViewMatrix * glVertex); + viewDirection = normalize(-v.xyz); + position = vec4(v,1); + glTexCoord0 = glMultiTexCoord0.st; + + // Transform the vertex + gl_Position = glModelViewProjectionMatrix * glVertex; +} + + + + + + diff --git a/src/main/java/org/jdesktop/j3d/examples/spline_anim/SplineAnim.java b/src/main/java/org/jdesktop/j3d/examples/spline_anim/SplineAnim.java new file mode 100644 index 0000000..4b4d28f --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/spline_anim/SplineAnim.java @@ -0,0 +1,631 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.spline_anim; + +import java.applet.Applet; +import java.awt.Button; +import java.awt.Choice; +import java.awt.FlowLayout; +import java.awt.Frame; +import java.awt.GraphicsConfiguration; +import java.awt.GridBagConstraints; +import java.awt.GridBagLayout; +import java.awt.ItemSelectable; +import java.awt.Label; +import java.awt.Panel; +import java.awt.Scrollbar; +import java.awt.event.ActionEvent; +import java.awt.event.ActionListener; +import java.awt.event.AdjustmentEvent; +import java.awt.event.AdjustmentListener; +import java.awt.event.ItemEvent; +import java.awt.event.ItemListener; + +import org.jogamp.java3d.Alpha; +import org.jogamp.java3d.AmbientLight; +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.Background; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.ColoringAttributes; +import org.jogamp.java3d.DirectionalLight; +import org.jogamp.java3d.Light; +import org.jogamp.java3d.Material; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.utils.applet.MainFrame; +import org.jogamp.java3d.utils.behaviors.interpolators.KBKeyFrame; +import org.jogamp.java3d.utils.behaviors.interpolators.KBRotPosScaleSplinePathInterpolator; +import org.jogamp.java3d.utils.behaviors.vp.OrbitBehavior; +import org.jogamp.java3d.utils.geometry.Cone; +import org.jogamp.java3d.utils.geometry.Sphere; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.java3d.utils.universe.ViewingPlatform; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Point3f; +import org.jogamp.vecmath.Vector3d; +import org.jogamp.vecmath.Vector3f; + + + +/* + * This program demonstrates the use of KBRotPosScaleSplinePathInterpolator + * in order to to do spline animation paths using Kochanek-Bartels (also + * known as TCB or Tension-Continuity-Bias ) splines. A cone red cone + * is animated along a spline path specified by 5 knot points, which + * are showns as cyan spheres. + * + * Use the left mouse button to changes orientation of scene. + * Use the middle mouse button to zoom in/out + * Use the right mouse button to pan the scene + */ +public class SplineAnim extends Applet implements ActionListener, + AdjustmentListener, + ItemListener { + + // 3D Canvas + Canvas3D canvas; + + // UI Components + Panel controlPanel; + Panel canvasPanel; + Button animateButton; + Choice interpChoice; + Scrollbar speedSlider; + Label speedLabel; + Label interpLabel; + + // Scene Graph + BoundingSphere bounds; + BranchGroup root; + BranchGroup behaviorBranch; + Transform3D sceneTransform; + TransformGroup sceneTransformGroup; + Transform3D objTransform; + TransformGroup objTransformGroup; + Transform3D lightTransform1; + Transform3D lightTransform2; + TransformGroup light1TransformGroup; + TransformGroup light2TransformGroup; + + // Key Frames & Interpolator + int duration = 5000; + Alpha animAlpha; + Transform3D yAxis; + KBKeyFrame[] linearKeyFrames = new KBKeyFrame[6]; + KBKeyFrame[] splineKeyFrames = new KBKeyFrame[6]; + KBRotPosScaleSplinePathInterpolator splineInterpolator; + KBRotPosScaleSplinePathInterpolator linearInterpolator; + + // Data: Knot positions & transform groups + Vector3f pos0 = new Vector3f(-5.0f, -5.0f, 0.0f); + Vector3f pos1 = new Vector3f(-5.0f, 5.0f, 0.0f); + Vector3f pos2 = new Vector3f( 0.0f, 5.0f, 0.0f); + Vector3f pos3 = new Vector3f( 0.0f, -5.0f, 0.0f); + Vector3f pos4 = new Vector3f( 5.0f, -5.0f, 0.0f); + Vector3f pos5 = new Vector3f( 5.0f, 5.0f, 0.0f); + TransformGroup k0TransformGroup; + TransformGroup k1TransformGroup; + TransformGroup k2TransformGroup; + TransformGroup k3TransformGroup; + TransformGroup k4TransformGroup; + TransformGroup k5TransformGroup; + + // Flags + boolean animationOn = true; + boolean linear = false; + + private SimpleUniverse u = null; + + public SplineAnim() { + } + + public void init() {System.setProperty("sun.awt.noerasebackground", "true"); + this.setLayout(new FlowLayout()); + + // Create the canvas and the UI + canvasPanel = new Panel(); + controlPanel = new Panel(); + createCanvasPanel(canvasPanel); + this.add(canvasPanel); + createControlPanel(controlPanel); + this.add(controlPanel); + + // Create the scene. + BranchGroup scene = createSceneGraph(); + + // Setup keyframe data for our animation + setupSplineKeyFrames (); + setupLinearKeyFrames (); + + // Setup alpha, create the interpolators and start them. We + // create both a linear and a spline interpolator and turn on + // one depending on user selection. The default is spline. + setupAnimationData (); + createInterpolators(); + startInterpolator(); + + // Add viewing platform + u = new SimpleUniverse(canvas); + + // add mouse behaviors to ViewingPlatform + ViewingPlatform viewingPlatform = u.getViewingPlatform(); + + viewingPlatform.setNominalViewingTransform(); + + // add orbit behavior to the ViewingPlatform + OrbitBehavior orbit = new OrbitBehavior(canvas, + OrbitBehavior.REVERSE_ALL); + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0, 0.0, 0.0), 100.0); + orbit.setSchedulingBounds(bounds); + viewingPlatform.setViewPlatformBehavior(orbit); + + u.addBranchGraph(scene); + } + + public void destroy() { + u.cleanup(); + } + + /* + * This creates the control panel which contains a choice menu to + * toggle between spline and linear interpolation, a slider to + * adjust the speed of the animation and a animation start/stop + * button. + */ + private void createControlPanel(Panel p) { + + GridBagLayout gl = new GridBagLayout(); + GridBagConstraints gbc = new GridBagConstraints(); + + p.setLayout (gl); + gbc.weightx = 100; gbc.weighty = 100; + gbc.fill = GridBagConstraints.BOTH; + + gbc.gridx = 0; gbc.gridy = 0; + gbc.gridwidth = 1; gbc.gridheight = 1; + interpLabel = new Label("Interpolation Type", Label.LEFT); + p.add(interpLabel, gbc); + + gbc.gridx = 1; gbc.gridy = 0; + gbc.gridwidth = 1; gbc.gridheight = 1; + interpChoice = new Choice(); + interpChoice.add("Spline"); + interpChoice.add("Linear"); + p.add(interpChoice, gbc); + interpChoice.addItemListener (this); + + gbc.gridx = 0; gbc.gridy = 2; + gbc.gridwidth = 2; gbc.gridheight = 1; + speedSlider = new Scrollbar(Scrollbar.HORIZONTAL, 2, 1, 0, 11); + speedSlider.setUnitIncrement (1); + p.add(speedSlider, gbc); + speedSlider.addAdjustmentListener(this); + + gbc.gridx = 0; gbc.gridy = 3; + gbc.gridwidth = 2; gbc.gridheight = 1; + speedLabel = new Label(" - Animation Speed +", Label.CENTER); + p.add(speedLabel, gbc); + + gbc.gridx = 0; gbc.gridy = 5; + gbc.gridwidth = 2; gbc.gridheight = 1; + animateButton = new Button("Stop Animation"); + p.add(animateButton, gbc); + animateButton.addActionListener (this); + + + } + + /* + * This creates the Java3D canvas + */ + private void createCanvasPanel(Panel p) { + + GridBagLayout gl = new GridBagLayout(); + GridBagConstraints gbc = new GridBagConstraints(); + + p.setLayout(gl); + gbc.gridx = 0; gbc.gridy = 0; + gbc.gridwidth = 5; gbc.gridheight = 5; + GraphicsConfiguration config = + SimpleUniverse.getPreferredConfiguration(); + + canvas = new Canvas3D(config); + canvas.setSize(490,490); + p.add(canvas,gbc); + + } + + /* + * This creates the scene with 5 knot points represented by cyan + * spheres, a cone obejct that will be transformed, and two directional + * lights + and ambient light. + */ + public BranchGroup createSceneGraph() { + + // Colors for lights and objects + Color3f aColor = new Color3f(0.2f, 0.2f, 0.2f); + Color3f eColor = new Color3f(0.0f, 0.0f, 0.0f); + Color3f sColor = new Color3f(1.0f, 1.0f, 1.0f); + Color3f coneColor = new Color3f(0.9f, 0.1f, 0.1f); + Color3f sphereColor= new Color3f(0.1f, 0.7f, 0.9f); + Color3f bgColor = new Color3f(0.0f, 0.0f, 0.0f); + Color3f lightColor = new Color3f(1.0f, 1.0f, 1.0f); + + // Root of the branch grsph + BranchGroup root = new BranchGroup(); + + // Create transforms such that all objects appears in the scene + sceneTransform = new Transform3D(); + sceneTransform.setScale(0.14f); + Transform3D yrot = new Transform3D(); + yrot.rotY(-Math.PI/5.0d); + sceneTransform.mul(yrot); + sceneTransformGroup = new TransformGroup(sceneTransform); + sceneTransformGroup.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + sceneTransformGroup.setCapability(TransformGroup.ALLOW_TRANSFORM_READ); + root.addChild(sceneTransformGroup); + + // Create bounds for the background and lights + bounds = new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0f); + + // Set up the background + Background bg = new Background(bgColor); + bg.setApplicationBounds(bounds); + sceneTransformGroup.addChild(bg); + + // Create the transform group node for the lights + lightTransform1 = new Transform3D(); + lightTransform2 = new Transform3D(); + Vector3d lightPos1 = new Vector3d(0.0, 0.0, 2.0); + Vector3d lightPos2 = new Vector3d(1.0, 0.0, -2.0); + lightTransform1.set(lightPos1); + lightTransform2.set(lightPos2); + light1TransformGroup = new TransformGroup(lightTransform1); + light2TransformGroup = new TransformGroup(lightTransform2); + sceneTransformGroup.addChild(light1TransformGroup); + sceneTransformGroup.addChild(light2TransformGroup); + + // Create lights + AmbientLight ambLight = new AmbientLight(aColor); + Light dirLight1; + Light dirLight2; + + Vector3f lightDir1 = new Vector3f(lightPos1); + Vector3f lightDir2 = new Vector3f(lightPos2); + lightDir1.negate(); + lightDir2.negate(); + dirLight1 = new DirectionalLight(lightColor, lightDir1); + dirLight2 = new DirectionalLight(lightColor, lightDir2); + + // Set the influencing bounds + ambLight.setInfluencingBounds(bounds); + dirLight1.setInfluencingBounds(bounds); + dirLight2.setInfluencingBounds(bounds); + + // Add the lights into the scene graph + sceneTransformGroup.addChild(ambLight); + sceneTransformGroup.addChild(dirLight1); + sceneTransformGroup.addChild(dirLight2); + + // Create a cone and add it to the scene graph. + objTransform = new Transform3D(); + objTransformGroup = new TransformGroup(objTransform); + objTransformGroup.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + sceneTransformGroup.addChild(objTransformGroup); + + Material m = new Material(coneColor, eColor, coneColor, sColor, 100.0f); + Appearance a = new Appearance(); + m.setLightingEnable(true); + a.setMaterial(m); + Cone cone = new Cone(0.4f, 1.0f); + cone.setAppearance(a); + objTransformGroup.addChild(cone); + + // Create transform groups for each knot point + // knot point 0 + Transform3D t3dKnot = new Transform3D(); + t3dKnot.set (pos0); + TransformGroup k0TransformGroup = new TransformGroup(t3dKnot); + sceneTransformGroup.addChild(k0TransformGroup); + + // knot point 1 + t3dKnot = new Transform3D(); + t3dKnot.set (pos1); + TransformGroup k1TransformGroup = new TransformGroup(t3dKnot); + sceneTransformGroup.addChild(k1TransformGroup); + + // knot point 2 + t3dKnot = new Transform3D(); + t3dKnot.set (pos2); + TransformGroup k2TransformGroup = new TransformGroup(t3dKnot); + sceneTransformGroup.addChild(k2TransformGroup); + + // knot point 3 + t3dKnot = new Transform3D(); + t3dKnot.set (pos3); + TransformGroup k3TransformGroup = new TransformGroup(t3dKnot); + sceneTransformGroup.addChild(k3TransformGroup); + + // knot point 4 + t3dKnot = new Transform3D(); + t3dKnot.set (pos4); + TransformGroup k4TransformGroup = new TransformGroup(t3dKnot); + sceneTransformGroup.addChild(k4TransformGroup); + + // knot point 5 + t3dKnot = new Transform3D(); + t3dKnot.set (pos5); + TransformGroup k5TransformGroup = new TransformGroup(t3dKnot); + sceneTransformGroup.addChild(k5TransformGroup); + + // Create spheres for each knot point's transform group + ColoringAttributes sphereColorAttr = new ColoringAttributes(); + sphereColorAttr.setColor(sphereColor); + Appearance sphereAppearance = new Appearance(); + sphereAppearance.setColoringAttributes(sphereColorAttr); + k0TransformGroup.addChild(new Sphere(0.10f, sphereAppearance)); + k1TransformGroup.addChild(new Sphere(0.10f, sphereAppearance)); + k2TransformGroup.addChild(new Sphere(0.10f, sphereAppearance)); + k3TransformGroup.addChild(new Sphere(0.10f, sphereAppearance)); + k4TransformGroup.addChild(new Sphere(0.10f, sphereAppearance)); + k5TransformGroup.addChild(new Sphere(0.10f, sphereAppearance)); + + return root; + } + + /* + * This sets up the key frame data for the spline interpolator. Each knot + * point has a scale and rotation component specified. The second argument + * to KBKeyFrame (in this case 0) tells the interpolator that this is + * to be interpolated using splines. The last three arguments to + * KBKeyFrame are Tension, Continuity, and Bias components for each + * key frame. + */ + private void setupSplineKeyFrames () { + // Prepare spline keyframe data + Point3f p = new Point3f (pos0); // position + float head = (float)Math.PI/2.0f; // heading + float pitch = 0.0f; // pitch + float bank = 0.0f; // bank + Point3f s = new Point3f(1.0f, 1.0f, 1.0f); // uniform scale + splineKeyFrames[0] = + new KBKeyFrame(0.0f, 0, p, head, pitch, bank, s, 0.0f, 0.0f, 0.0f); + + p = new Point3f (pos1); + head = 0.0f; // heading + pitch = 0.0f; // pitch + bank = (float)-Math.PI/2.0f; // bank + s = new Point3f(1.0f, 1.0f, 1.0f); // uniform scale + splineKeyFrames[1] = + new KBKeyFrame(0.2f, 0, p, head, pitch, bank, s, 0.0f, 0.0f, 0.0f); + + p = new Point3f (pos2); + head = 0.0f; // heading + pitch = 0.0f; // pitch + bank = 0.0f; // bank + s = new Point3f(0.7f, 0.7f, 0.7f); // uniform scale + splineKeyFrames[2] = + new KBKeyFrame(0.4f, 0, p, head, pitch, bank, s, 0.0f, 0.0f, 0.0f); + + p = new Point3f (pos3); + head = (float)Math.PI/2.0f; // heading + pitch = 0.0f; // pitch + bank = (float)Math.PI/2.0f; // bank + s = new Point3f(0.5f, 0.5f, 0.5f); // uniform scale + splineKeyFrames[3] = + new KBKeyFrame(0.6f, 0, p, head, pitch, bank, s, 0.0f, 0.0f, 0.0f); + + p = new Point3f (pos4); + head = (float)-Math.PI/2.0f; // heading + pitch = (float)-Math.PI/2.0f; // pitch + bank = (float)Math.PI/2.0f; // bank + s = new Point3f(0.4f, 0.4f, 0.4f); // uniform scale + splineKeyFrames[4] = + new KBKeyFrame(0.8f, 0, p, head, pitch, bank, s, 0.0f, 0.0f, 0.0f); + + p = new Point3f (pos5); + head = 0.0f; // heading + pitch = 0.0f; // pitch + bank = 0.0f; // bank + s = new Point3f(1.0f, 1.0f, 1.0f); // uniform scale + splineKeyFrames[5] = + new KBKeyFrame(1.0f, 0, p, head, pitch, bank, s, 0.0f, 0.0f, 0.0f); + } + + /* + * This sets up the key frame data for the linear interpolator. Each knot + * point has a scale and rotation component specified. The second argument + * to KBKeyFrame (in this case 1) tells the interpolator that this is + * to be interpolated linearly. The last three arguments to TCBKeyFrame + * are Tension, Continuity, and Bias components for each key frame. + */ + private void setupLinearKeyFrames () { + // Prepare linear keyframe data + Point3f p = new Point3f (pos0); + float head = 0.0f; // heading + float pitch = 0.0f; // pitch + float bank = 0.0f; // bank + Point3f s = new Point3f(1.0f, 1.0f, 1.0f); // uniform scale + linearKeyFrames[0] = + new KBKeyFrame(0.0f, 1, p, head, pitch, bank, s, 0.0f, 0.0f, 0.0f); + + p = new Point3f (pos1); + linearKeyFrames[1] = + new KBKeyFrame(0.2f, 1, p, head, pitch, bank, s, 0.0f, 0.0f, 0.0f); + + p = new Point3f (pos2); + linearKeyFrames[2] = + new KBKeyFrame(0.4f, 1, p, head, pitch, bank, s, 0.0f, 0.0f, 0.0f); + + p = new Point3f (pos3); + linearKeyFrames[3] = + new KBKeyFrame(0.6f, 1, p, head, pitch, bank, s, 0.0f, 0.0f, 0.0f); + + p = new Point3f (pos4); + linearKeyFrames[4] = + new KBKeyFrame(0.8f, 1, p, head, pitch, bank, s, 0.0f, 0.0f, 0.0f); + + p = new Point3f (pos5); + linearKeyFrames[5] = + new KBKeyFrame(1.0f, 1, p, head, pitch, bank, s, 0.0f, 0.0f, 0.0f); + } + + + /* + * This sets up alpha for the interpolator + */ + private void setupAnimationData () { + yAxis = new Transform3D(); + animAlpha = new Alpha (-1,Alpha.INCREASING_ENABLE,0,0,duration,0,0,0,0,0); + } + + /* + * create a spline and a linear interpolator, but we will activate only + * one in startInterpolator() + */ + private void createInterpolators () { + + behaviorBranch = new BranchGroup(); + + // create spline interpolator + splineInterpolator = + new KBRotPosScaleSplinePathInterpolator(animAlpha, objTransformGroup, + yAxis, splineKeyFrames); + splineInterpolator.setSchedulingBounds(bounds); + behaviorBranch.addChild(splineInterpolator); + + // create linear interpolator + linearInterpolator = + new KBRotPosScaleSplinePathInterpolator(animAlpha, objTransformGroup, + yAxis, linearKeyFrames); + linearInterpolator.setSchedulingBounds(bounds); + behaviorBranch.addChild(linearInterpolator); + objTransformGroup.addChild(behaviorBranch); + + } + + /* + * This activates one of the interpolators depending on the state of the + * linear boolean flag which may be toggled by the user using the choice + * menu. + */ + public void startInterpolator () { + if (animationOn) { + if (linear) { + splineInterpolator.setEnable(false); + linearInterpolator.setEnable(true); + } else { + linearInterpolator.setEnable(false); + splineInterpolator.setEnable(true); + } + } + } + + + /* + * Toggle animation + */ + public void actionPerformed (ActionEvent event) { + Object source = event.getSource(); + if (source == animateButton) { + try { + // toggle animation + if (animationOn) { + animationOn = false; + splineInterpolator.setEnable(false); + linearInterpolator.setEnable(false); + animateButton.setLabel("Start Animation"); + } else { + animationOn = true; + startInterpolator(); + animateButton.setLabel("Stop Animation"); + } + } catch (Exception e) { + System.err.println ("Exception " + e); + } + } + } + + /* + * Toggle the interpolators + */ + public void itemStateChanged (ItemEvent event) { + Object source = event.getSource(); + ItemSelectable ie = event.getItemSelectable(); + if (source == interpChoice) { + try { + if (ie.getSelectedObjects()[0] == "Spline") { + linear = false; + } + if (ie.getSelectedObjects()[0] == "Linear") { + linear = true; + } + startInterpolator(); + } catch (Exception e) { + System.err.println ("Exception " + e); + } + } + } + + + /* + * Adjust the speed of the animations + */ + public void adjustmentValueChanged (AdjustmentEvent e) { + int value = e.getValue(); + duration = 6000 - (500 * value); + animAlpha.setIncreasingAlphaDuration(duration); + } + + + + public static void main(String[] args) {System.setProperty("sun.awt.noerasebackground", "true"); + Frame frame = new MainFrame(new SplineAnim(), 500, 600); + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/stencil/StencilOutline.java b/src/main/java/org/jdesktop/j3d/examples/stencil/StencilOutline.java new file mode 100644 index 0000000..3c7b405 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/stencil/StencilOutline.java @@ -0,0 +1,524 @@ +/* + * Copyright (c) 2016 JogAmp Community. All rights reserved. + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * This code is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 only, as + * published by the Free Software Foundation. Sun designates this + * particular file as subject to the "Classpath" exception as provided + * by Sun in the LICENSE file that accompanied this code. + * + * This code is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + * version 2 for more details (a copy is included in the LICENSE file that + * accompanied this code). + * + * You should have received a copy of the GNU General Public License version + * 2 along with this work; if not, write to the Free Software Foundation, + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. + * + */ + +package org.jdesktop.j3d.examples.stencil; + +import java.awt.GraphicsConfiguration; +import java.awt.GraphicsEnvironment; +import java.io.FileNotFoundException; +import java.net.MalformedURLException; +import java.net.URL; +import java.util.Enumeration; + +import javax.swing.JOptionPane; + +import org.jdesktop.j3d.examples.Resources; +import org.jogamp.java3d.Alpha; +import org.jogamp.java3d.AmbientLight; +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.Background; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.ColoringAttributes; +import org.jogamp.java3d.DirectionalLight; +import org.jogamp.java3d.GraphicsConfigTemplate3D; +import org.jogamp.java3d.Group; +import org.jogamp.java3d.LineAttributes; +import org.jogamp.java3d.Material; +import org.jogamp.java3d.Node; +import org.jogamp.java3d.PolygonAttributes; +import org.jogamp.java3d.RenderingAttributes; +import org.jogamp.java3d.RotationInterpolator; +import org.jogamp.java3d.ShaderAppearance; +import org.jogamp.java3d.ShaderError; +import org.jogamp.java3d.ShaderErrorListener; +import org.jogamp.java3d.ShaderProgram; +import org.jogamp.java3d.Shape3D; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.loaders.IncorrectFormatException; +import org.jogamp.java3d.loaders.ParsingErrorException; +import org.jogamp.java3d.loaders.Scene; +import org.jogamp.java3d.loaders.objectfile.ObjectFile; +import org.jogamp.java3d.utils.behaviors.vp.OrbitBehavior; +import org.jogamp.java3d.utils.universe.PlatformGeometry; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.java3d.utils.universe.ViewingPlatform; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Vector3f; + +/** + * Simple Java 3D example program to display an .obj object with shader programs. + * And then add a stencil based outline around it + */ +public class StencilOutline extends javax.swing.JFrame +{ + + private String shaderName = "polkadot3d"; + private boolean spin = false; + private boolean noTriangulate = false; + private boolean noStripify = false; + private double creaseAngle = 60.0; + private URL filename = null; + + private SimpleUniverse univ = null; + private BranchGroup scene = null; + + public BranchGroup createSceneGraph() + { + // Create the root of the branch graph + BranchGroup objRoot = new BranchGroup(); + + // Create a Transformgroup to scale all objects so they + // appear in the scene. + TransformGroup objScale = new TransformGroup(); + Transform3D t3d = new Transform3D(); + t3d.setScale(0.7); + objScale.setTransform(t3d); + objRoot.addChild(objScale); + + // Create the transform group node and initialize it to the + // identity. Enable the TRANSFORM_WRITE capability so that + // our behavior code can modify it at runtime. Add it to the + // root of the subgraph. + TransformGroup objTrans = new TransformGroup(); + objTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + objTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_READ); + objScale.addChild(objTrans); + + int flags = ObjectFile.RESIZE; + if (!noTriangulate) + flags |= ObjectFile.TRIANGULATE; + if (!noStripify) + flags |= ObjectFile.STRIPIFY; + ObjectFile f = new ObjectFile(flags, (float) (creaseAngle * Math.PI / 180.0)); + Scene s = null; + try + { + s = f.load(filename); + } + catch (FileNotFoundException e) + { + System.err.println(e); + System.exit(1); + } + catch (ParsingErrorException e) + { + System.err.println(e); + System.exit(1); + } + catch (IncorrectFormatException e) + { + System.err.println(e); + System.exit(1); + } + + //Uncomment to use the gl2es2 pipeline, also see other commented code + // Set vertex and fragment shader program for all Shape3D nodes in scene + /* String vertexProgram = null; + String fragmentProgram = null; + try + { + vertexProgram = StringIO.readFully(new File( + System.getProperty("user.dir") + "/src/classes/org/jdesktop/j3d/examples/gl2es2pipeline/" + shaderName + ".vert")); + fragmentProgram = StringIO.readFully(new File( + System.getProperty("user.dir") + "/src/classes/org/jdesktop/j3d/examples/gl2es2pipeline/" + shaderName + ".frag")); + } + catch (IOException e) + { + throw new RuntimeException(e); + } + Shader[] shaders = new Shader[2]; + shaders[0] = new SourceCodeShader(Shader.SHADING_LANGUAGE_GLSL, Shader.SHADER_TYPE_VERTEX, vertexProgram); + shaders[1] = new SourceCodeShader(Shader.SHADING_LANGUAGE_GLSL, Shader.SHADER_TYPE_FRAGMENT, fragmentProgram); + ShaderProgram shaderProgram = new GLSLShaderProgram(); + + + shaderProgram.setShaders(shaders); + setShaderProgram(s.getSceneGroup(), shaderProgram);*/ + + setOutline(s.getSceneGroup()); + + objTrans.addChild(s.getSceneGroup()); + + BoundingSphere bounds = new BoundingSphere(new Point3d(0.0, 0.0, 0.0), 100.0); + + if (spin) + { + Transform3D yAxis = new Transform3D(); + Alpha rotationAlpha = new Alpha(-1, Alpha.INCREASING_ENABLE, 0, 0, 4000, 0, 0, 0, 0, 0); + + RotationInterpolator rotator = new RotationInterpolator(rotationAlpha, objTrans, yAxis, 0.0f, (float) Math.PI * 2.0f); + rotator.setSchedulingBounds(bounds); + objTrans.addChild(rotator); + } + + // Set up the background + Color3f bgColor = new Color3f(0.05f, 0.05f, 0.5f); + Background bgNode = new Background(bgColor); + bgNode.setApplicationBounds(bounds); + objRoot.addChild(bgNode); + + return objRoot; + } + + private Canvas3D createUniverse() + { + // Critical!!! notice this is not using this call, but explicitly asks for a stencil buffer + //GraphicsConfiguration config = SimpleUniverse.getPreferredConfiguration(); + GraphicsConfigTemplate3D template = new GraphicsConfigTemplate3D(); + template.setStencilSize(16); + // Return the GraphicsConfiguration that best fits our needs. + GraphicsConfiguration config = GraphicsEnvironment.getLocalGraphicsEnvironment().getDefaultScreenDevice() + .getBestConfiguration(template); + + // Create a Canvas3D using the preferred configuration + Canvas3D canvas3d = new Canvas3D(config); + + // Create simple universe with view branch + univ = new SimpleUniverse(canvas3d); + BoundingSphere bounds = new BoundingSphere(new Point3d(0.0, 0.0, 0.0), 100.0); + + // Add a ShaderErrorListener + univ.addShaderErrorListener(new ShaderErrorListener() { + @Override + public void errorOccurred(ShaderError error) + { + error.printVerbose(); + JOptionPane.showMessageDialog(StencilOutline.this, error.toString(), "ShaderError", JOptionPane.ERROR_MESSAGE); + } + }); + + // add mouse behaviors to the ViewingPlatform + ViewingPlatform viewingPlatform = univ.getViewingPlatform(); + + PlatformGeometry pg = new PlatformGeometry(); + + // Set up the ambient light + Color3f ambientColor = new Color3f(0.1f, 0.1f, 0.1f); + AmbientLight ambientLightNode = new AmbientLight(ambientColor); + ambientLightNode.setInfluencingBounds(bounds); + pg.addChild(ambientLightNode); + + // Set up the directional lights + Color3f light1Color = new Color3f(1.0f, 1.0f, 0.9f); + Vector3f light1Direction = new Vector3f(1.0f, 1.0f, 1.0f); + Color3f light2Color = new Color3f(1.0f, 1.0f, 1.0f); + Vector3f light2Direction = new Vector3f(-1.0f, -1.0f, -1.0f); + + DirectionalLight light1 = new DirectionalLight(light1Color, light1Direction); + light1.setInfluencingBounds(bounds); + pg.addChild(light1); + + DirectionalLight light2 = new DirectionalLight(light2Color, light2Direction); + light2.setInfluencingBounds(bounds); + pg.addChild(light2); + + viewingPlatform.setPlatformGeometry(pg); + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + viewingPlatform.setNominalViewingTransform(); + + if (!spin) + { + OrbitBehavior orbit = new OrbitBehavior(canvas3d, OrbitBehavior.REVERSE_ALL); + orbit.setSchedulingBounds(bounds); + viewingPlatform.setViewPlatformBehavior(orbit); + } + + // Ensure at least 5 msec per frame (i.e., < 200Hz) + univ.getViewer().getView().setMinimumFrameCycleTime(5); + + return canvas3d; + } + + private static void usage() + { + System.out.println("Usage: java ObjLoadGLSL [-s] [-S shaderName] [-n] [-t] [-c degrees] <.obj file>"); + System.out.println(" -s Spin (no user interaction)"); + System.out.println(" -S Set shader name (default is 'simple')"); + System.out.println(" -n No triangulation"); + System.out.println(" -t No stripification"); + System.out.println(" -c Set crease angle for normal generation (default is 60 without"); + System.out.println(" smoothing group info, otherwise 180 within smoothing groups)"); + System.exit(0); + } // End of usage + + // Set shader program for all nodes in specified branch graph + private void setShaderProgram(BranchGroup g, ShaderProgram shaderProgram) + { + ShaderAppearance myApp = new ShaderAppearance(); + Material mat = new Material(); + myApp.setShaderProgram(shaderProgram); + myApp.setMaterial(mat); + setShaderProgram(g, myApp); + } + + // Recursively set shader program for all children of specified group + private void setShaderProgram(Group g, ShaderAppearance myApp) + { + + Enumeration<Node> e = g.getAllChildren(); + while (e.hasMoreElements()) + { + Node n = e.nextElement(); + if (n instanceof Group) + { + setShaderProgram((Group) n, myApp); + } + else if (n instanceof Shape3D) + { + Shape3D s = (Shape3D) n; + s.setAppearance(myApp); + } + } + } + + private Color3f c = new Color3f(1.0f, 1.0f, 0); + private int outlineStencilMask = (int) (c.x * 255) + (int) (c.y * 255) + (int) (c.z * 255); + + // Recursively set an outline onto all Shape3D nodes + private void setOutline(Group g) + { + + Enumeration<Node> e = g.getAllChildren(); + while (e.hasMoreElements()) + { + Node n = e.nextElement(); + if (n instanceof Group) + { + setOutline((Group) n); + } + else if (n instanceof Shape3D) + { + // start by giving the current appearance a rendering attribute + Shape3D s = (Shape3D) n; + Appearance sapp = s.getAppearance(); + + // get and ensure rend atts exist + RenderingAttributes ra1 = sapp.getRenderingAttributes(); + if (ra1 == null) + { + ra1 = new RenderingAttributes(); + sapp.setRenderingAttributes(ra1); + } + + ra1.setStencilEnable(true); + ra1.setStencilWriteMask(outlineStencilMask); + ra1.setStencilFunction(RenderingAttributes.ALWAYS, outlineStencilMask, outlineStencilMask); + ra1.setStencilOp(RenderingAttributes.STENCIL_REPLACE, // + RenderingAttributes.STENCIL_REPLACE, // + RenderingAttributes.STENCIL_REPLACE); + + sapp.setRenderingAttributes(ra1); + + // now attach an outline shape + Shape3D outliner = new Shape3D(); + + //////////////////////////////// + //Outliner gear, note empty geom should be ignored + + //Uncomment to use the gl2es2 pipeline, also see other commented code + //Appearance app = new SimpleShaderAppearance(c); + + //Comment to use the gl2es2 pipeline, also see other commented code + Appearance app = new Appearance(); + + // lineAntialiasing MUST be true, to force this to be done during rendering pass (otherwise it's hidden) + LineAttributes la = new LineAttributes(4, LineAttributes.PATTERN_SOLID, true); + app.setLineAttributes(la); + PolygonAttributes pa = new PolygonAttributes(PolygonAttributes.POLYGON_LINE, PolygonAttributes.CULL_BACK, 0.0f, true, 0.0f); + app.setPolygonAttributes(pa); + ColoringAttributes colorAtt = new ColoringAttributes(c, ColoringAttributes.FASTEST); + app.setColoringAttributes(colorAtt); + + RenderingAttributes ra2 = new RenderingAttributes(); + ra2.setStencilEnable(true); + ra2.setStencilWriteMask(outlineStencilMask); + ra2.setStencilFunction(RenderingAttributes.NOT_EQUAL, outlineStencilMask, outlineStencilMask); + ra2.setStencilOp(RenderingAttributes.STENCIL_KEEP, // + RenderingAttributes.STENCIL_KEEP, // + RenderingAttributes.STENCIL_KEEP); + + // draw it even when hidden, which we don't want now + ra2.setDepthBufferEnable(false); + ra2.setDepthTestFunction(RenderingAttributes.ALWAYS); + + app.setRenderingAttributes(ra2); + + outliner.setAppearance(app); + + // use the same geometry ass teh shape we are outlining! + outliner.setGeometry(s.getGeometry()); + + g.addChild(outliner); + + } + } + } + + /** + * Creates new form ObjLoadGLSL + */ + public StencilOutline(String args[]) + { + if (args.length != 0) + { + for (int i = 0; i < args.length; i++) + { + if (args[i].startsWith("-")) + { + if (args[i].equals("-s")) + { + spin = true; + } + else if (args[i].equals("-n")) + { + noTriangulate = true; + } + else if (args[i].equals("-t")) + { + noStripify = true; + } + else if (args[i].equals("-c")) + { + if (i < args.length - 1) + { + creaseAngle = (new Double(args[++i])).doubleValue(); + } + else + usage(); + } + else if (args[i].equals("-S")) + { + if (i < args.length - 1) + { + shaderName = args[++i]; + } + else + usage(); + } + else + { + usage(); + } + } + else + { + try + { + if ((args[i].indexOf("file:") == 0) || (args[i].indexOf("http") == 0)) + { + filename = new URL(args[i]); + } + else if (args[i].charAt(0) != '/') + { + filename = new URL("file:./" + args[i]); + } + else + { + filename = new URL("file:" + args[i]); + } + } + catch (MalformedURLException e) + { + System.err.println(e); + System.exit(1); + } + } + } + } + + if (filename == null) + { + filename = Resources.getResource("resources/geometry/galleon.obj"); + if (filename == null) + { + System.err.println("resources/geometry/galleon.obj not found"); + System.exit(1); + } + } + + // Initialize the GUI components + initComponents(); + + // Create Canvas3D and SimpleUniverse; add canvas to drawing panel + Canvas3D c = createUniverse(); + drawingPanel.add(c, java.awt.BorderLayout.CENTER); + + // Create the content branch and add it to the universe + scene = createSceneGraph(); + univ.addBranchGraph(scene); + } + + // ---------------------------------------------------------------- + + /** This method is called from within the constructor to + * initialize the form. + * WARNING: Do NOT modify this code. The content of this method is + * always regenerated by the Form Editor. + */ + // <editor-fold defaultstate="collapsed" desc=" Generated Code ">//GEN-BEGIN:initComponents + private void initComponents() + { + drawingPanel = new javax.swing.JPanel(); + + setDefaultCloseOperation(javax.swing.WindowConstants.EXIT_ON_CLOSE); + setTitle("StencilOutline"); + drawingPanel.setLayout(new java.awt.BorderLayout()); + + drawingPanel.setPreferredSize(new java.awt.Dimension(700, 700)); + getContentPane().add(drawingPanel, java.awt.BorderLayout.CENTER); + + pack(); + }// </editor-fold>//GEN-END:initComponents + + /** + * @param args the command line arguments + */ + public static void main(final String args[]) + { + System.setProperty("sun.awt.noerasebackground", "true"); + + System.setProperty("j3d.stencilClear", "true"); + + //Uncomment to use the gl2es2 pipeline, also see other commented code + //System.setProperty("j3d.rend", "jogl2es2"); + + java.awt.EventQueue.invokeLater(new Runnable() { + @Override + public void run() + { + StencilOutline objLoadGLSL = new StencilOutline(args); + objLoadGLSL.setVisible(true); + } + }); + } + + // Variables declaration - do not modify//GEN-BEGIN:variables + private javax.swing.JPanel drawingPanel; + // End of variables declaration//GEN-END:variables + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/swing_interaction/SwingInteraction.form b/src/main/java/org/jdesktop/j3d/examples/swing_interaction/SwingInteraction.form new file mode 100644 index 0000000..591580c --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/swing_interaction/SwingInteraction.form @@ -0,0 +1,82 @@ +<?xml version="1.0" encoding="UTF-8" ?> + +<Form version="1.0" type="org.netbeans.modules.form.forminfo.JFrameFormInfo"> + <NonVisualComponents> + <Menu class="javax.swing.JMenuBar" name="jMenuBar1"> + <SubComponents> + <Menu class="javax.swing.JMenu" name="fileMenu"> + <Properties> + <Property name="text" type="java.lang.String" value="File"/> + </Properties> + <SubComponents> + <MenuItem class="javax.swing.JMenuItem" name="exitMenuItem"> + <Properties> + <Property name="text" type="java.lang.String" value="Exit"/> + </Properties> + <Events> + <EventHandler event="actionPerformed" listener="java.awt.event.ActionListener" parameters="java.awt.event.ActionEvent" handler="exitMenuItemActionPerformed"/> + </Events> + </MenuItem> + </SubComponents> + </Menu> + </SubComponents> + </Menu> + </NonVisualComponents> + <Properties> + <Property name="defaultCloseOperation" type="int" value="3"/> + <Property name="title" type="java.lang.String" value="Swing Interaction Test"/> + </Properties> + <SyntheticProperties> + <SyntheticProperty name="menuBar" type="java.lang.String" value="jMenuBar1"/> + <SyntheticProperty name="formSizePolicy" type="int" value="1"/> + </SyntheticProperties> + <AuxValues> + <AuxValue name="FormSettings_generateMnemonicsCode" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_listenerGenerationStyle" type="java.lang.Integer" value="0"/> + <AuxValue name="FormSettings_variablesLocal" type="java.lang.Boolean" value="false"/> + <AuxValue name="FormSettings_variablesModifier" type="java.lang.Integer" value="2"/> + <AuxValue name="designerSize" type="java.awt.Dimension" value="-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,1,44,0,0,1,-112"/> + </AuxValues> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + <SubComponents> + <Container class="javax.swing.JPanel" name="guiPanel"> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout" value="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription"> + <BorderConstraints direction="North"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout"/> + <SubComponents> + <Component class="javax.swing.JButton" name="rotateButton"> + <Properties> + <Property name="text" type="java.lang.String" value="Rotate"/> + </Properties> + <Events> + <EventHandler event="actionPerformed" listener="java.awt.event.ActionListener" parameters="java.awt.event.ActionEvent" handler="rotateButtonActionPerformed"/> + </Events> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout" value="org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription"> + <GridBagConstraints gridX="-1" gridY="-1" gridWidth="1" gridHeight="1" fill="2" ipadX="0" ipadY="0" insetsTop="4" insetsLeft="4" insetsBottom="4" insetsRight="4" anchor="10" weightX="0.0" weightY="0.0"/> + </Constraint> + </Constraints> + </Component> + </SubComponents> + </Container> + <Container class="javax.swing.JPanel" name="drawingPanel"> + <Properties> + <Property name="preferredSize" type="java.awt.Dimension" editor="org.netbeans.beaninfo.editors.DimensionEditor"> + <Dimension value="[500, 500]"/> + </Property> + </Properties> + <Constraints> + <Constraint layoutClass="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout" value="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription"> + <BorderConstraints direction="Center"/> + </Constraint> + </Constraints> + + <Layout class="org.netbeans.modules.form.compat2.layouts.DesignBorderLayout"/> + </Container> + </SubComponents> +</Form> diff --git a/src/main/java/org/jdesktop/j3d/examples/swing_interaction/SwingInteraction.java b/src/main/java/org/jdesktop/j3d/examples/swing_interaction/SwingInteraction.java new file mode 100644 index 0000000..e360059 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/swing_interaction/SwingInteraction.java @@ -0,0 +1,259 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.swing_interaction; + +import java.awt.GraphicsConfiguration; +import java.util.Enumeration; + +import javax.swing.JPopupMenu; + +import org.jogamp.java3d.Behavior; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.WakeupCriterion; +import org.jogamp.java3d.WakeupOnBehaviorPost; +import org.jogamp.java3d.utils.geometry.ColorCube; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.vecmath.Point3d; + +/** + * Simple Java 3D test program created in NetBeans to illustrate interacting + * with a Java 3D scene graph from an Swing-based program. + */ +public class SwingInteraction extends javax.swing.JFrame { + + private SimpleUniverse univ = null; + private BranchGroup scene = null; + + private TransformGroup objTrans; + private RotateBehavior awtBehavior; + + public BranchGroup createSceneGraph() { + // Create the root of the branch graph + BranchGroup objRoot = new BranchGroup(); + + // Create the transform group node and initialize it to the + // identity. Enable the TRANSFORM_WRITE capability so that + // our behavior code can modify it at runtime. Add it to the + // root of the subgraph. + objTrans = new TransformGroup(); + objTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + objRoot.addChild(objTrans); + + // Create a simple shape leaf node, add it to the scene graph. + objTrans.addChild(new ColorCube(0.4)); + + // create the RotateBehavior + awtBehavior = new RotateBehavior(objTrans); + BoundingSphere bounds = new BoundingSphere(new Point3d(0.0, 0.0, 0.0), + 100.0); + awtBehavior.setSchedulingBounds(bounds); + objRoot.addChild(awtBehavior); + + return objRoot; + } + + private Canvas3D createUniverse() { + GraphicsConfiguration config = + SimpleUniverse.getPreferredConfiguration(); + + Canvas3D c = new Canvas3D(config); + + univ = new SimpleUniverse(c); + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + univ.getViewingPlatform().setNominalViewingTransform(); + + // Ensure at least 5 msec per frame (i.e., < 200Hz) + univ.getViewer().getView().setMinimumFrameCycleTime(5); + + return c; + } + + /** + * Creates new form SwingInteraction + */ + public SwingInteraction() { + // Initialize the GUI components + JPopupMenu.setDefaultLightWeightPopupEnabled(false); + initComponents(); + + // Create Canvas3D and SimpleUniverse; add canvas to drawing panel + Canvas3D c = createUniverse(); + drawingPanel.add(c, java.awt.BorderLayout.CENTER); + + // Create the content branch and add it to the universe + scene = createSceneGraph(); + univ.addBranchGraph(scene); + } + + /** + * Behavior class that waits for a behavior post from the AWT event handler + */ + class RotateBehavior extends Behavior { + + private TransformGroup transformGroup; + private Transform3D trans = new Transform3D(); + private WakeupCriterion criterion; + private float angle = 0.0f; + + private final int ROTATE = 1; + + // create a new RotateBehavior + RotateBehavior(TransformGroup tg) { + transformGroup = tg; + } + + // initialize behavior to wakeup on a behavior post with id = ROTATE + public void initialize() { + criterion = new WakeupOnBehaviorPost(this, ROTATE); + wakeupOn(criterion); + } + + // processStimulus to rotate the cube + public void processStimulus(Enumeration criteria) { + angle += Math.toRadians(10.0); + trans.rotY(angle); + transformGroup.setTransform(trans); + wakeupOn(criterion); + } + + // when the mouse is clicked, postId for the behavior + void rotate() { + postId(ROTATE); + } + } + + // ---------------------------------------------------------------- + + /** This method is called from within the constructor to + * initialize the form. + * WARNING: Do NOT modify this code. The content of this method is + * always regenerated by the Form Editor. + */ + // <editor-fold defaultstate="collapsed" desc=" Generated Code ">//GEN-BEGIN:initComponents + private void initComponents() { + java.awt.GridBagConstraints gridBagConstraints; + + guiPanel = new javax.swing.JPanel(); + rotateButton = new javax.swing.JButton(); + drawingPanel = new javax.swing.JPanel(); + jMenuBar1 = new javax.swing.JMenuBar(); + fileMenu = new javax.swing.JMenu(); + exitMenuItem = new javax.swing.JMenuItem(); + + setDefaultCloseOperation(javax.swing.WindowConstants.EXIT_ON_CLOSE); + setTitle("Swing Interaction Test"); + guiPanel.setLayout(new java.awt.GridBagLayout()); + + rotateButton.setText("Rotate"); + rotateButton.addActionListener(new java.awt.event.ActionListener() { + public void actionPerformed(java.awt.event.ActionEvent evt) { + rotateButtonActionPerformed(evt); + } + }); + + gridBagConstraints = new java.awt.GridBagConstraints(); + gridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL; + gridBagConstraints.insets = new java.awt.Insets(4, 4, 4, 4); + guiPanel.add(rotateButton, gridBagConstraints); + + getContentPane().add(guiPanel, java.awt.BorderLayout.NORTH); + + drawingPanel.setLayout(new java.awt.BorderLayout()); + + drawingPanel.setPreferredSize(new java.awt.Dimension(500, 500)); + getContentPane().add(drawingPanel, java.awt.BorderLayout.CENTER); + + fileMenu.setText("File"); + exitMenuItem.setText("Exit"); + exitMenuItem.addActionListener(new java.awt.event.ActionListener() { + public void actionPerformed(java.awt.event.ActionEvent evt) { + exitMenuItemActionPerformed(evt); + } + }); + + fileMenu.add(exitMenuItem); + + jMenuBar1.add(fileMenu); + + setJMenuBar(jMenuBar1); + + pack(); + }// </editor-fold>//GEN-END:initComponents + + private void rotateButtonActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_rotateButtonActionPerformed + awtBehavior.rotate(); + }//GEN-LAST:event_rotateButtonActionPerformed + + private void exitMenuItemActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_exitMenuItemActionPerformed + System.exit(0); + }//GEN-LAST:event_exitMenuItemActionPerformed + + /** + * @param args the command line arguments + */ + public static void main(String args[]) {System.setProperty("sun.awt.noerasebackground", "true"); + java.awt.EventQueue.invokeLater(new Runnable() { + public void run() { + new SwingInteraction().setVisible(true); + } + }); + } + + // Variables declaration - do not modify//GEN-BEGIN:variables + private javax.swing.JPanel drawingPanel; + private javax.swing.JMenuItem exitMenuItem; + private javax.swing.JMenu fileMenu; + private javax.swing.JPanel guiPanel; + private javax.swing.JMenuBar jMenuBar1; + private javax.swing.JButton rotateButton; + // End of variables declaration//GEN-END:variables + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/text2d/MoverBehavior.java b/src/main/java/org/jdesktop/j3d/examples/text2d/MoverBehavior.java new file mode 100644 index 0000000..6005d5b --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/text2d/MoverBehavior.java @@ -0,0 +1,151 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.text2d; + +import java.awt.AWTEvent; +import java.awt.event.KeyEvent; +import java.util.Enumeration; + +import org.jogamp.java3d.Behavior; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.Bounds; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.WakeupCondition; +import org.jogamp.java3d.WakeupCriterion; +import org.jogamp.java3d.WakeupOnAWTEvent; +import org.jogamp.java3d.WakeupOr; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Vector3f; + +// Mover behavior class - used to allow viewer to move using arrow keys +class MoverBehavior extends Behavior +{ + WakeupOnAWTEvent w1 = new WakeupOnAWTEvent(KeyEvent.KEY_PRESSED); + WakeupCriterion[] w2 = {w1}; + WakeupCondition w = new WakeupOr(w2); + TransformGroup viewTransformGroup; + double rotation = 0.0; // holds current rotation radians + + public void initialize() { + // Establish initial wakeup criteria + wakeupOn(w); + } + + + /** + * Override Behavior's stimulus method to handle the event. + */ + public void processStimulus(Enumeration criteria) { + WakeupOnAWTEvent ev; + WakeupCriterion genericEvt; + AWTEvent[] events; + + while (criteria.hasMoreElements()) { + genericEvt = (WakeupCriterion) criteria.nextElement(); + if (genericEvt instanceof WakeupOnAWTEvent) { + ev = (WakeupOnAWTEvent) genericEvt; + events = ev.getAWTEvent(); + processManualEvent(events); + } + } + // Set wakeup criteria for next time + wakeupOn(w); + } + + + /** + * Process a keyboard event to move or rotate the viewer. + */ + void processManualEvent(AWTEvent[] events) { + + for (int i = 0; i < events.length; ++i) { + if (events[i] instanceof KeyEvent) { + KeyEvent event = (KeyEvent)events[i]; + if (event.getKeyCode() == KeyEvent.VK_EQUALS) { + continue; + } + Transform3D t = new Transform3D(); + viewTransformGroup.getTransform(t); + Vector3f viewDir = new Vector3f(0f, 0f, -1f); + Vector3f translation = new Vector3f(); + t.get(translation); + t.transform(viewDir); + if (event.getKeyCode() == KeyEvent.VK_UP) { + translation.x += viewDir.x; + translation.y += viewDir.y; + translation.z += viewDir.z; + } + else if (event.getKeyCode() == KeyEvent.VK_DOWN) { + translation.x -= viewDir.x; + translation.y -= viewDir.y; + translation.z -= viewDir.z; + } + else if (event.getKeyCode() == KeyEvent.VK_RIGHT) { + rotation += -.1; + } + else if (event.getKeyCode() == KeyEvent.VK_LEFT) { + rotation += .1; + } + t.rotY(rotation); + t.setTranslation(translation); + viewTransformGroup.setTransform(t); + } + } + } + + + /** + * Constructor + */ + public MoverBehavior(TransformGroup trans) { + viewTransformGroup = trans; + Bounds bound = new BoundingSphere(new Point3d(0.0,0.0,0.0),10000.0); + this.setSchedulingBounds(bound); + } +} + + + diff --git a/src/main/java/org/jdesktop/j3d/examples/text2d/Text2DTest.java b/src/main/java/org/jdesktop/j3d/examples/text2d/Text2DTest.java new file mode 100644 index 0000000..49a0ac2 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/text2d/Text2DTest.java @@ -0,0 +1,205 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.text2d; + +import java.applet.Applet; +import java.awt.BorderLayout; +import java.awt.Font; +import java.awt.GraphicsConfiguration; + +import org.jogamp.java3d.Alpha; +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.PolygonAttributes; +import org.jogamp.java3d.RotationInterpolator; +import org.jogamp.java3d.Shape3D; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.utils.applet.MainFrame; +import org.jogamp.java3d.utils.geometry.Text2D; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Vector3f; + +public class Text2DTest extends Applet { + + private SimpleUniverse u = null; + + public BranchGroup createSceneGraph() { + // Create the root of the branch graph + BranchGroup objRoot = new BranchGroup(); + + // Create a Transformgroup to scale all objects so they + // appear in the scene. + TransformGroup objScale = new TransformGroup(); + Transform3D t3d = new Transform3D(); + t3d.setScale(0.4); + objScale.setTransform(t3d); + objRoot.addChild(objScale); + + // Create the transform group node and initialize it to the + // identity. Enable the TRANSFORM_WRITE capability so that + // our behavior code can modify it at runtime. Add it to the + // root of the subgraph. + TransformGroup objTrans = new TransformGroup(); + objTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + + TransformGroup textTranslationGroup; + Transform3D textTranslation; + float yPos = -.5f; + Shape3D textObject = new Text2D("Rotating Yellow Text", + new Color3f(1f, 1f, 0f), + "Serif", + 60, + Font.BOLD); + Appearance app = textObject.getAppearance(); + + PolygonAttributes pa = app.getPolygonAttributes(); + if (pa == null) + pa = new PolygonAttributes(); + pa.setCullFace(PolygonAttributes.CULL_NONE); + if (app.getPolygonAttributes() == null) + app.setPolygonAttributes(pa); + objTrans.addChild(textObject); + + + textTranslation = new Transform3D(); + textTranslation.setTranslation(new Vector3f(0f, yPos, 0f)); + textTranslationGroup = new TransformGroup(textTranslation); + textTranslationGroup.addChild(objTrans); + objScale.addChild(textTranslationGroup); + yPos += .5f; + + /* Blue 40point text*/ + textObject = new Text2D("Blue 40point Text", + new Color3f(0f, 0f, 1f), + "Serif", + 40, + Font.BOLD); + textTranslation = new Transform3D(); + textTranslation.setTranslation(new Vector3f(0f, yPos, 0f)); + textTranslationGroup = new TransformGroup(textTranslation); + textTranslationGroup.addChild(textObject); + objScale.addChild(textTranslationGroup); + yPos += .5f; + + /* Green italic text*/ + textObject = new Text2D("Green Italic Text", + new Color3f(0f, 1f, 0f), + "Serif", + 70, + Font.ITALIC); + textTranslation = new Transform3D(); + textTranslation.setTranslation(new Vector3f(0f, yPos, 0f)); + textTranslationGroup = new TransformGroup(textTranslation); + textTranslationGroup.addChild(textObject); + objScale.addChild(textTranslationGroup); + yPos += .5f; + + + // Create a new Behavior object that will perform the desired + // operation on the specified transform object and add it into + // the scene graph. + Transform3D yAxis = new Transform3D(); + Alpha rotationAlpha = new Alpha(-1, Alpha.INCREASING_ENABLE, + 0, 0, + 4000, 0, 0, + 0, 0, 0); + + RotationInterpolator rotator = + new RotationInterpolator(rotationAlpha, objTrans, yAxis, + 0.0f, (float) Math.PI*2.0f); + rotator.setSchedulingBounds(bounds); + objTrans.addChild(rotator); + + return objRoot; + } + + public Text2DTest() { + } + + public void init() {System.setProperty("sun.awt.noerasebackground", "true"); + setLayout(new BorderLayout()); + GraphicsConfiguration config = + SimpleUniverse.getPreferredConfiguration(); + + Canvas3D c = new Canvas3D(config); + add("Center", c); + + // Create a simple scene and attach it to the virtual universe + BranchGroup scene = createSceneGraph(); + u = new SimpleUniverse(c); + MoverBehavior navigator = + new MoverBehavior(u.getViewingPlatform().getViewPlatformTransform()); + scene.addChild(navigator); + + // Have Java 3D perform optimizations on this scene graph. + scene.compile(); + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + u.getViewingPlatform().setNominalViewingTransform(); + + u.addBranchGraph(scene); + } + + public void destroy() { + u.cleanup(); + } + + // + // The following allows HelloUniverse to be run as an application + // as well as an applet + // + public static void main(String[] args) {System.setProperty("sun.awt.noerasebackground", "true"); + new MainFrame(new Text2DTest(), 256, 256); + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/text3d/Text3DLoad.java b/src/main/java/org/jdesktop/j3d/examples/text3d/Text3DLoad.java new file mode 100644 index 0000000..a61531e --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/text3d/Text3DLoad.java @@ -0,0 +1,308 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.text3d; + +import java.applet.Applet; +import java.awt.BorderLayout; +import java.awt.Button; +import java.awt.Font; +import java.awt.GraphicsConfiguration; +import java.awt.Panel; +import java.awt.event.ActionEvent; +import java.awt.event.ActionListener; + +import org.jogamp.java3d.Alpha; +import org.jogamp.java3d.AmbientLight; +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.Background; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.DirectionalLight; +import org.jogamp.java3d.Font3D; +import org.jogamp.java3d.FontExtrusion; +import org.jogamp.java3d.Material; +import org.jogamp.java3d.RotationInterpolator; +import org.jogamp.java3d.Shape3D; +import org.jogamp.java3d.Text3D; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.utils.applet.MainFrame; +import org.jogamp.java3d.utils.behaviors.vp.OrbitBehavior; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.java3d.utils.universe.ViewingPlatform; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Point3f; +import org.jogamp.vecmath.Vector3f; + +public class Text3DLoad extends Applet implements ActionListener { + + private String fontName = "TestFont"; + private String textString = null; + private double tessellation = 0.0; + + private SimpleUniverse u; + + private Button button; + private boolean behaviorsOn = false; + private OrbitBehavior orbit; + + public BranchGroup createSceneGraph() { + float sl = textString.length(); + // Create the root of the branch graph + BranchGroup objRoot = new BranchGroup(); + + // Create a Transformgroup to scale all objects so they + // appear in the scene. + TransformGroup objScale = new TransformGroup(); + Transform3D t3d = new Transform3D(); + // Assuming uniform size chars, set scale to fit string in view + t3d.setScale(1.2/sl); + objScale.setTransform(t3d); + objRoot.addChild(objScale); + + // Create the transform group node and initialize it to the + // identity. Enable the TRANSFORM_WRITE capability so that + // our behavior code can modify it at runtime. Add it to the + // root of the subgraph. + TransformGroup objTrans = new TransformGroup(); + objTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + objTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_READ); + objScale.addChild(objTrans); + + Font3D f3d; + if (tessellation > 0.0) { + f3d = new Font3D(new Font(fontName, Font.PLAIN, 2), + tessellation, + new FontExtrusion()); + } + else { + f3d = new Font3D(new Font(fontName, Font.PLAIN, 2), + new FontExtrusion()); + } + Text3D txt = new Text3D(f3d, textString, + new Point3f( -sl/2.0f, -1.f, -1.f)); + Shape3D sh = new Shape3D(); + Appearance app = new Appearance(); + Material mm = new Material(); + mm.setLightingEnable(true); + app.setMaterial(mm); + sh.setGeometry(txt); + sh.setAppearance(app); + objTrans.addChild(sh); + + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + + if (false) { + Transform3D yAxis = new Transform3D(); + Alpha rotationAlpha = new Alpha(-1, Alpha.INCREASING_ENABLE, + 0, 0, + 4000, 0, 0, + 0, 0, 0); + + RotationInterpolator rotator = + new RotationInterpolator(rotationAlpha, objTrans, yAxis, + 0.0f, (float) Math.PI*2.0f); + rotator.setSchedulingBounds(bounds); + objTrans.addChild(rotator); + } + + // Set up the background + Color3f bgColor = new Color3f(0.05f, 0.05f, 0.5f); + Background bgNode = new Background(bgColor); + bgNode.setApplicationBounds(bounds); + objRoot.addChild(bgNode); + + // Set up the ambient light + Color3f ambientColor = new Color3f(0.3f, 0.3f, 0.3f); + AmbientLight ambientLightNode = new AmbientLight(ambientColor); + ambientLightNode.setInfluencingBounds(bounds); + objRoot.addChild(ambientLightNode); + + // Set up the directional lights + Color3f light1Color = new Color3f(1.0f, 1.0f, 0.9f); + Vector3f light1Direction = new Vector3f(1.0f, 1.0f, 1.0f); + Color3f light2Color = new Color3f(1.0f, 1.0f, 0.9f); + Vector3f light2Direction = new Vector3f(-1.0f, -1.0f, -1.0f); + + DirectionalLight light1 + = new DirectionalLight(light1Color, light1Direction); + light1.setInfluencingBounds(bounds); + objRoot.addChild(light1); + + DirectionalLight light2 + = new DirectionalLight(light2Color, light2Direction); + light2.setInfluencingBounds(bounds); + objRoot.addChild(light2); + + return objRoot; + } + + private void usage() + { + System.out.println( + "Usage: java Text3DLoad [-f fontname] [-t tessellation] [<text>]"); + System.exit(0); + } // End of usage + + public Text3DLoad() {} + + public Text3DLoad(String args[]) { + + if (args.length == 0) { +// usage(); + textString = "Java3D"; + } + else { + for (int i = 0 ; i < args.length ; i++) { + if (args[i].startsWith("-")) { + if (args[i].equals("-f")) { + if (i < args.length - 1) { + fontName = args[++i]; + } + else { + usage(); + } + } + else if (args[i].equals("-t")) { + if (i < args.length - 1) { + tessellation = Double.parseDouble(args[++i]); + } + else { + usage(); + } + } + else { + System.err.println("Argument '" + args[i] + + "' ignored."); + } + } + else { + textString = args[i]; + } + } + } + + if (textString == null) { + usage(); + } + + } + + public void init() {System.setProperty("sun.awt.noerasebackground", "true"); + + if (textString == null) { + textString = "Java3D"; + } + setLayout(new BorderLayout()); + + button = new Button("remove behaviors"); + button.addActionListener(this); + Panel p = new Panel(); + p.add(button); + add("South", p); + + GraphicsConfiguration config = + SimpleUniverse.getPreferredConfiguration(); + + Canvas3D c = new Canvas3D(config); + add("Center", c); + + // Create a simple scene and attach it to the virtual universe + BranchGroup scene = createSceneGraph(); + + // create a SimpleUniverse with 4 TransformGroups for the mouse + // behaviors + u = new SimpleUniverse(c); + + // add the behaviors to the ViewingPlatform + ViewingPlatform viewingPlatform = u.getViewingPlatform(); + + viewingPlatform.setNominalViewingTransform(); + + // add orbit behavior to ViewingPlatform + orbit = new OrbitBehavior(c, OrbitBehavior.REVERSE_ALL | + OrbitBehavior.STOP_ZOOM); + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0, 0.0, 0.0), 100.0); + orbit.setSchedulingBounds(bounds); + viewingPlatform.setViewPlatformBehavior(orbit); + + behaviorsOn = true; + + + u.addBranchGraph(scene); + } + + public void destroy() { + u.cleanup(); + } + + public void actionPerformed(ActionEvent e) { + if (e.getSource() == button) { + ViewingPlatform v = u.getViewingPlatform(); + if (behaviorsOn) { + v.setViewPlatformBehavior(null); + button.setLabel("add behaviors"); + behaviorsOn = false; + } + else { + v.setViewPlatformBehavior(orbit); + button.setLabel("remove behaviors"); + behaviorsOn = true; + } + } + } + + // + // The following allows Text3DLoad to be run as an application + // as well as an applet + // + public static void main(String[] args) {System.setProperty("sun.awt.noerasebackground", "true"); + new MainFrame(new Text3DLoad(args), 700, 700); + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/texture/MultiTextureTest.java b/src/main/java/org/jdesktop/j3d/examples/texture/MultiTextureTest.java new file mode 100644 index 0000000..49f9406 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/texture/MultiTextureTest.java @@ -0,0 +1,344 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.texture; + +import java.applet.Applet; +import java.awt.BorderLayout; +import java.awt.Choice; +import java.awt.GraphicsConfiguration; +import java.awt.event.ItemEvent; +import java.awt.event.ItemListener; +import java.awt.image.BufferedImage; + +import org.jdesktop.j3d.examples.Resources; +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.DirectionalLight; +import org.jogamp.java3d.ImageComponent; +import org.jogamp.java3d.ImageComponent2D; +import org.jogamp.java3d.Texture; +import org.jogamp.java3d.Texture2D; +import org.jogamp.java3d.TextureAttributes; +import org.jogamp.java3d.TextureUnitState; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.utils.applet.MainFrame; +import org.jogamp.java3d.utils.behaviors.vp.OrbitBehavior; +import org.jogamp.java3d.utils.geometry.Box; +import org.jogamp.java3d.utils.image.TextureLoader; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.java3d.utils.universe.ViewingPlatform; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Vector3f; + +public class MultiTextureTest extends Applet implements ItemListener{ + + Choice choice; + TextureUnitState textureUnitState[] = new TextureUnitState[2]; + Texture stoneTex; + Texture skyTex; + Texture lightTex; + + private java.net.URL stoneImage = null; + private java.net.URL skyImage = null; + + private SimpleUniverse u = null; + + public Texture createLightMap(){ + + int width = 128; + int height = 128; + BufferedImage bimage = new BufferedImage(width, height, BufferedImage.TYPE_INT_RGB); + int [] rgbArray = new int[width * height]; + int index, index2; + int rgbInc = 256 / (width / 2 - 20); + int rgbValue = 0; + int k = width/2 - 5; + int i, j, rgb; + + rgb = 0xff; + rgbValue = rgb | (rgb << 8) | (rgb << 16) | (rgb << 24); + for ( i = width / 2 - 1, j = 0; j < 10; j++, i--) { + rgbArray[i] = rgbValue; + } + + for (; i > 8; i--, rgb -= rgbInc) { + rgbValue = rgb | (rgb << 8) | (rgb << 16) | (rgb << 24); + rgbArray[i] = rgbValue; + } + + for (; i >= 0; i--) { + rgbArray[i] = rgbValue; + } + + for (i = 0; i < width/2; i++) { + rgbValue = rgbArray[i]; + index = i; + index2 = (width - i - 1); + for (j = 0; j < height; j++) { + rgbArray[index] = rgbArray[index2] = rgbValue; + index += width; + index2 += width; + } + } + + bimage.setRGB(0, 0, width, height, rgbArray, 0, width); + + + ImageComponent2D grayImage = new ImageComponent2D(ImageComponent.FORMAT_RGB, bimage, true, true); + + lightTex = new Texture2D(Texture.BASE_LEVEL, Texture.RGB, width, height); + lightTex.setImage(0, grayImage); + + return lightTex; + } + + + public BranchGroup createSceneGraph() { + // Create the root of the branch graph + BranchGroup objRoot = new BranchGroup(); + + // Create a Transformgroup to scale all objects so they + // appear in the scene. + TransformGroup objScale = new TransformGroup(); + Transform3D t3d = new Transform3D(); + t3d.setScale(0.4); + objScale.setTransform(t3d); + objRoot.addChild(objScale); + + TransformGroup objTrans = new TransformGroup(); + //write-enable for behaviors + objTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + objTrans.setCapability( TransformGroup.ALLOW_TRANSFORM_READ ); + objTrans.setCapability(TransformGroup.ENABLE_PICK_REPORTING); + objScale.addChild(objTrans); + + Appearance ap = new Appearance(); + + // load textures + TextureAttributes texAttr1 = new TextureAttributes(); + texAttr1.setTextureMode(TextureAttributes.DECAL); + TextureAttributes texAttr2 = new TextureAttributes(); + texAttr2.setTextureMode(TextureAttributes.MODULATE); + + TextureLoader tex = new TextureLoader(stoneImage, new String("RGB"), + TextureLoader.BY_REFERENCE | TextureLoader.Y_UP, + this); + if (tex == null) + return null; + stoneTex = tex.getTexture(); + + tex = new TextureLoader(skyImage, new String("RGB"), + TextureLoader.BY_REFERENCE | TextureLoader.Y_UP, + this); + if (tex == null) + return null; + skyTex = tex.getTexture(); + + lightTex = createLightMap(); + + + textureUnitState[0] = new TextureUnitState(stoneTex, texAttr1, null); + textureUnitState[0].setCapability(TextureUnitState.ALLOW_STATE_WRITE); + + textureUnitState[1] = new TextureUnitState(lightTex, texAttr2, null); + textureUnitState[1].setCapability(TextureUnitState.ALLOW_STATE_WRITE); + + ap.setTextureUnitState(textureUnitState); + + //Create a Box + Box BoxObj = new Box(1.5f, 1.5f, 0.8f, Box.GENERATE_NORMALS | + Box.GENERATE_TEXTURE_COORDS | + Box.GENERATE_TEXTURE_COORDS_Y_UP, ap, 2); + // add it to the scene graph. + objTrans.addChild(BoxObj); + + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + + //Shine it with two lights. + Color3f lColor1 = new Color3f(0.7f, 0.7f, 0.7f); + Color3f lColor2 = new Color3f(0.2f, 0.2f, 0.1f); + Vector3f lDir1 = new Vector3f(-1.0f, -1.0f, -1.0f); + Vector3f lDir2 = new Vector3f(0.0f, 0.0f, -1.0f); + DirectionalLight lgt1 = new DirectionalLight(lColor1, lDir1); + DirectionalLight lgt2 = new DirectionalLight(lColor2, lDir2); + lgt1.setInfluencingBounds(bounds); + lgt2.setInfluencingBounds(bounds); + objScale.addChild(lgt1); + objScale.addChild(lgt2); + + // Let Java 3D perform optimizations on this scene graph. + objRoot.compile(); + + return objRoot; + } + + public MultiTextureTest (){ + } + + public MultiTextureTest(java.net.URL stoneURL, java.net.URL skyURL) { + stoneImage = stoneURL; + skyImage = skyURL; + } + + public void init() {System.setProperty("sun.awt.noerasebackground", "true"); + if (stoneImage == null) { + // the path to the image for an applet + stoneImage = Resources.getResource("resources/images/stone.jpg"); + if (stoneImage == null) { + System.err.println("resources/images/stone.jpg not found"); + System.exit(1); + } + + if (skyImage == null) { + // the path to the image for an applet + skyImage = Resources.getResource("resources/images/bg.jpg"); + if (skyImage == null) { + System.err.println("resources/images/bg.jpg not found"); + System.exit(1); + } + } + } + + setLayout(new BorderLayout()); + GraphicsConfiguration config = + SimpleUniverse.getPreferredConfiguration(); + + Canvas3D c = new Canvas3D(config); + add("Center", c); + + BranchGroup scene = createSceneGraph(); + u = new SimpleUniverse(c); + + ViewingPlatform viewingPlatform = u.getViewingPlatform(); + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + viewingPlatform.setNominalViewingTransform(); + + // add orbit behavior but disable translate + OrbitBehavior orbit = + new OrbitBehavior(c, OrbitBehavior.REVERSE_ALL | + OrbitBehavior.DISABLE_TRANSLATE); + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0, 0.0, 0.0), 100.0); + orbit.setSchedulingBounds(bounds); + viewingPlatform.setViewPlatformBehavior(orbit); + + u.addBranchGraph(scene); + + // create the gui + choice = new Choice(); + choice.addItem("stone + light"); + choice.addItem("stone"); + choice.addItem("lightMap"); + choice.addItem("sky"); + choice.addItem("stone + sky"); + choice.addItemListener(this); + add("North", choice); + + } + + public void destroy() { + // Cleanup reference to Java3D + textureUnitState = new TextureUnitState[2]; + u.cleanup(); + } + + public void itemStateChanged(ItemEvent e) + { + int index = choice.getSelectedIndex(); + + switch (index) { + case 0 : /* stone + light */ + textureUnitState[0].setTexture(stoneTex); + textureUnitState[1].setTexture(lightTex); + break; + case 1 : /* stone */ + textureUnitState[0].setTexture(stoneTex); + textureUnitState[1].setTexture(null); + break; + case 2 : /* light */ + textureUnitState[0].setTexture(null); + textureUnitState[1].setTexture(lightTex); + break; + case 3 : /* sky */ + textureUnitState[0].setTexture(null); + textureUnitState[1].setTexture(skyTex); + break; + case 4 : /* stone + sky */ + textureUnitState[0].setTexture(stoneTex); + textureUnitState[1].setTexture(skyTex); + break; + default: /* both */ + break; + } + } + + public static void main(String argv[]) +{ + java.net.URL stoneURL = null; + java.net.URL skyURL = null; + // the path to the image for an application + + stoneURL = Resources.getResource("resources/images/stone.jpg"); + if (stoneURL == null) { + System.err.println("resources/images/stone.jpg not found"); + System.exit(1); + } + + skyURL = Resources.getResource("resources/images/bg.jpg"); + if (skyURL == null) { + System.err.println("resources/images/bg.jpg not found"); + System.exit(1); + } + + new MainFrame(new MultiTextureTest(stoneURL, skyURL), 750, 750); + } +} + diff --git a/src/main/java/org/jdesktop/j3d/examples/texture/TextureImage.java b/src/main/java/org/jdesktop/j3d/examples/texture/TextureImage.java new file mode 100644 index 0000000..59f8aa5 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/texture/TextureImage.java @@ -0,0 +1,196 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.texture; + +import java.applet.Applet; +import java.awt.BorderLayout; +import java.awt.GraphicsConfiguration; + +import org.jdesktop.j3d.examples.Resources; +import org.jogamp.java3d.Alpha; +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.RotationInterpolator; +import org.jogamp.java3d.Texture; +import org.jogamp.java3d.TextureAttributes; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.utils.applet.MainFrame; +import org.jogamp.java3d.utils.geometry.Box; +import org.jogamp.java3d.utils.image.TextureLoader; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.vecmath.Point3d; + +public class TextureImage extends Applet { + + private static final String defaultFileName = "resources/images/stone.jpg"; + private java.net.URL texImage = null; + + private SimpleUniverse u = null; + + public BranchGroup createSceneGraph() { + // Create the root of the branch graph + BranchGroup objRoot = new BranchGroup(); + + // Create the transform group node and initialize it to the + // identity. Enable the TRANSFORM_WRITE capability so that + // our behavior code can modify it at runtime. Add it to the + // root of the subgraph. + TransformGroup objTrans = new TransformGroup(); + objTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + objRoot.addChild(objTrans); + + // Create appearance object for textured cube + Appearance app = new Appearance(); + Texture tex = new TextureLoader(texImage, + TextureLoader.BY_REFERENCE | TextureLoader.Y_UP, + this).getTexture(); + app.setTexture(tex); + TextureAttributes texAttr = new TextureAttributes(); + texAttr.setTextureMode(TextureAttributes.MODULATE); + app.setTextureAttributes(texAttr); + + // Create textured cube and add it to the scene graph. + Box textureCube = new Box(0.4f, 0.4f, 0.4f, + Box.GENERATE_TEXTURE_COORDS | + Box.GENERATE_TEXTURE_COORDS_Y_UP, app); + objTrans.addChild(textureCube); + + // Create a new Behavior object that will perform the desired + // operation on the specified transform object and add it into + // the scene graph. + Transform3D yAxis = new Transform3D(); + Alpha rotationAlpha = new Alpha(-1, Alpha.INCREASING_ENABLE, + 0, 0, + 4000, 0, 0, + 0, 0, 0); + + RotationInterpolator rotator = + new RotationInterpolator(rotationAlpha, objTrans, yAxis, + 0.0f, (float) Math.PI*2.0f); + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + rotator.setSchedulingBounds(bounds); + objTrans.addChild(rotator); + + // Have Java 3D perform optimizations on this scene graph. + objRoot.compile(); + + return objRoot; + } + + public TextureImage() { + } + + public TextureImage(java.net.URL url) { + texImage = url; + } + + public void init() {System.setProperty("sun.awt.noerasebackground", "true"); + if (texImage == null) { + // the path to the image for an applet + texImage = Resources.getResource(defaultFileName); + if (texImage == null) { + System.err.println(defaultFileName + " not found"); + System.exit(1); + } + } + setLayout(new BorderLayout()); + GraphicsConfiguration config = + SimpleUniverse.getPreferredConfiguration(); + + Canvas3D c = new Canvas3D(config); + add("Center", c); + + // Create a simple scene and attach it to the virtual universe + BranchGroup scene = createSceneGraph(); + u = new SimpleUniverse(c); + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + u.getViewingPlatform().setNominalViewingTransform(); + + u.addBranchGraph(scene); + } + + public void destroy() { + u.cleanup(); + } + + // + // The following allows TextureImage to be run as an application + // as well as an applet + // + public static void main(String[] args) {System.setProperty("sun.awt.noerasebackground", "true"); + java.net.URL url = null; + if (args.length > 0) { + try { + final String name = args[0]; + if (name.startsWith("http:") || + name.startsWith("https:") || + name.startsWith("ftp:") || + name.startsWith("file:")) { + url = new java.net.URL(name); + } else { + url = new java.net.URL("file:" + name); + } + } catch (java.net.MalformedURLException ex) { + System.out.println(ex.getMessage()); + System.exit(1); + } + } else { + // the path to the image for an application + url = Resources.getResource(defaultFileName); + if (url == null) { + System.err.println(defaultFileName + " not found"); + System.exit(1); + } + } + new MainFrame(new TextureImage(url), 256, 256); + } + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/texture/TextureImageNPOT.java b/src/main/java/org/jdesktop/j3d/examples/texture/TextureImageNPOT.java new file mode 100644 index 0000000..f55493c --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/texture/TextureImageNPOT.java @@ -0,0 +1,249 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.texture; + +import java.applet.Applet; +import java.awt.BorderLayout; +import java.awt.GraphicsConfiguration; +import java.util.Map; + +import javax.swing.JOptionPane; + +import org.jdesktop.j3d.examples.Resources; +import org.jogamp.java3d.Alpha; +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.RotationInterpolator; +import org.jogamp.java3d.ScaleInterpolator; +import org.jogamp.java3d.Texture; +import org.jogamp.java3d.TextureAttributes; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.utils.applet.MainFrame; +import org.jogamp.java3d.utils.geometry.Box; +import org.jogamp.java3d.utils.image.TextureLoader; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.vecmath.Point3d; + +public class TextureImageNPOT extends Applet { + + private static final String defaultFileName = "resources/images/Java3d.jpg"; + private java.net.URL texImage = null; + + private SimpleUniverse u = null; + private boolean allowNonPowerOfTwo = true; + private boolean mipmap = true; + + public BranchGroup createSceneGraph() { + // Create the root of the branch graph + BranchGroup objRoot = new BranchGroup(); + + // Create the transform group node and initialize it to the + // identity. Enable the TRANSFORM_WRITE capability so that + // our behavior code can modify it at runtime. Add it to the + // root of the subgraph. + TransformGroup objTrans = new TransformGroup(); + objTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + objRoot.addChild(objTrans); + + // Create the scaling transform group node and initialize it to the + // identity. Enable the TRANSFORM_WRITE capability so that + // our behavior code can modify it at runtime. Add it to the + // objTrans group + TransformGroup objScale = new TransformGroup(); + objScale.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + objTrans.addChild(objScale); + + // Create appearance object for textured cube + Appearance app = new Appearance(); + int flags = TextureLoader.BY_REFERENCE | TextureLoader.Y_UP; + + if (allowNonPowerOfTwo) { + flags |= TextureLoader.ALLOW_NON_POWER_OF_TWO; + } + if (mipmap) { + flags |= TextureLoader.GENERATE_MIPMAP; + } + Texture tex = new TextureLoader(texImage, flags, this).getTexture(); + tex.setMagFilter(Texture.BASE_LEVEL_LINEAR); + if (mipmap) { + tex.setMinFilter(Texture.MULTI_LEVEL_LINEAR); + } else { + tex.setMinFilter(Texture.BASE_LEVEL_LINEAR); + } + app.setTexture(tex); + TextureAttributes texAttr = new TextureAttributes(); + texAttr.setTextureMode(TextureAttributes.MODULATE); + app.setTextureAttributes(texAttr); + + // Create textured cube and add it to the scene graph. + Box textureCube = new Box(0.4f, 0.4f, 0.4f, + Box.GENERATE_TEXTURE_COORDS | + Box.GENERATE_TEXTURE_COORDS_Y_UP, app); + objScale.addChild(textureCube); + + // Create a new Behavior object that will perform the desired + // operation on the specified transform object and add it into + // the scene graph. + Transform3D yAxis = new Transform3D(); + Alpha rotationAlpha = new Alpha(-1, Alpha.INCREASING_ENABLE, + 0, 0, + 50000, 0, 0, + 0, 0, 0); + + RotationInterpolator rotator = + new RotationInterpolator(rotationAlpha, objTrans, yAxis, + 0.0f, (float) Math.PI*2.0f); + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + rotator.setSchedulingBounds(bounds); + objTrans.addChild(rotator); + + // Create a new Behavior object that will perform the desired + // operation on the specified transform object and add it into + // the scene graph. + Alpha scaleAlpha = new Alpha(-1, + Alpha.INCREASING_ENABLE | Alpha.DECREASING_ENABLE, + 0, 0, + 8000, 0, 0, + 8000, 0, 0); + + ScaleInterpolator scaler = + new ScaleInterpolator(scaleAlpha, objScale, yAxis, + 0.01f, 1.5f); + scaler.setSchedulingBounds(bounds); + objScale.addChild(scaler); + + // Have Java 3D perform optimizations on this scene graph. + objRoot.compile(); + + return objRoot; + } + + public TextureImageNPOT() { + } + + public TextureImageNPOT(java.net.URL url) { + texImage = url; + } + + public void init() {System.setProperty("sun.awt.noerasebackground", "true"); + if (texImage == null) { + // the path to the image for an applet + texImage = Resources.getResource(defaultFileName); + if (texImage == null) { + System.err.println(defaultFileName + " not found"); + System.exit(1); + } + } + setLayout(new BorderLayout()); + GraphicsConfiguration config = + SimpleUniverse.getPreferredConfiguration(); + + Canvas3D c = new Canvas3D(config); + + Map map = c.queryProperties(); + Boolean value = (Boolean) map.get("textureNonPowerOfTwoAvailable"); + String errorStr = null; + if (value == null) { + errorStr = "Canvas3D: textureNonPowerOfTwoAvailable property not found"; + } else if (!value) { + errorStr = "Non-power-of-two textures are not available"; + } + + if (errorStr != null) { + String errorMessage = errorStr + "\n" + + "You should expect to see a white cube as a result"; +// System.err.println(errorMessage); + JOptionPane.showMessageDialog(this, + errorMessage, + "Insufficient Capabilities", + JOptionPane.ERROR_MESSAGE); + } + + add("Center", c); + + // Create a simple scene and attach it to the virtual universe + BranchGroup scene = createSceneGraph(); + u = new SimpleUniverse(c); + + // This will move the ViewPlatform back a bit so the + // objects in the scene can be viewed. + u.getViewingPlatform().setNominalViewingTransform(); + + u.addBranchGraph(scene); + } + + public void destroy() { + u.cleanup(); + } + + // + // The following allows TextureImageNPOT to be run as an application + // as well as an applet + // + public static void main(String[] args) {System.setProperty("sun.awt.noerasebackground", "true"); + java.net.URL url = null; + if (args.length > 0) { + try { + url = new java.net.URL("file:" + args[0]); + } catch (java.net.MalformedURLException ex) { + System.out.println(ex.getMessage()); + System.exit(1); + } + } else { + // the path to the image for an application + url = Resources.getResource(defaultFileName); + if (url == null) { + System.err.println(defaultFileName + " not found"); + System.exit(1); + } + } + new MainFrame(new TextureImageNPOT(url), 512, 512); + } + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/texture_by_ref/AnimateTexturesBehavior.java b/src/main/java/org/jdesktop/j3d/examples/texture_by_ref/AnimateTexturesBehavior.java new file mode 100644 index 0000000..a0fb1e1 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/texture_by_ref/AnimateTexturesBehavior.java @@ -0,0 +1,323 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.texture_by_ref; + +import java.awt.image.BufferedImage; +import java.util.Enumeration; + +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.Behavior; +import org.jogamp.java3d.ImageComponent; +import org.jogamp.java3d.ImageComponent2D; +import org.jogamp.java3d.Texture2D; +import org.jogamp.java3d.WakeupCriterion; +import org.jogamp.java3d.WakeupOnElapsedFrames; +import org.jogamp.java3d.utils.image.TextureLoader; + +public class AnimateTexturesBehavior extends Behavior { + + + // what image are we on + private int current; + private int max; + + // the images + private ImageComponent2D[] images; + + // the target + private Texture2D texture; + private Appearance appearance; + + // the wakeup criterion + private WakeupCriterion wakeupC; + + // are the images flipped? + private boolean flip; + + // need the current type because by copy changes all images + // to TYPE_INT_ARGB + private int currentType; + + // for custom types + public static final int TYPE_CUSTOM_RGBA = 0x01; + public static final int TYPE_CUSTOM_RGB = 0x02; + + private int customType; + + // create a new AnimateTextureBehavior + // initialize the images + public AnimateTexturesBehavior(Texture2D texP, + java.net.URL[] fnames, + Appearance appP, + TextureByReference applet) { + int size = fnames.length; + images = new ImageComponent2D[size]; + BufferedImage bImage; + TextureLoader loader; + for (int i = 0; i < size; i++) { + loader = new TextureLoader(fnames[i], + TextureLoader.BY_REFERENCE | + TextureLoader.Y_UP, applet); + images[i] = loader.getImage(); + bImage = images[i].getImage(); + + // convert the image to TYPE_4BYTE_ABGR + currentType = BufferedImage.TYPE_4BYTE_ABGR; + bImage = ImageOps.convertImage(bImage, currentType); + // flip the image + flip = true; + ImageOps.flipImage(bImage); + + // set the image on the ImageComponent to the new one + images[i].set(bImage); + + images[i].setCapability(ImageComponent.ALLOW_IMAGE_READ); + images[i].setCapability(ImageComponent.ALLOW_FORMAT_READ); + } + texture = texP; + current = 0; + max = size; + wakeupC = new WakeupOnElapsedFrames(20); + appearance = appP; + } + + // initialize to the first image + public void initialize() { + texture.setImage(0, images[current]); + if (current < max-1) current++; + else current = 0; + wakeupOn(wakeupC); + } + + // procesStimulus changes the ImageComponent of the texture + public void processStimulus(Enumeration criteria) { + // ImageOps.printType(images[current].getImage()); + texture.setImage(0, images[current]); + appearance.setTexture(texture); + if (current < max-1) current++; + else current = 0; + wakeupOn(wakeupC); + } + + // flip the image -- useful depending on yUp + public void setFlipImages(boolean b) { + // double check that flipping is necessary + if (b != flip) { + BufferedImage bImage; + + // these are the same for all images so get info once + int format = images[0].getFormat(); + boolean byRef = images[0].isByReference(); + boolean yUp = images[0].isYUp(); + + // flip all the images + // have to new ImageComponents because can't set the image at runtime + for (int i = 0; i < images.length; i++) { + bImage = images[i].getImage(); + ImageOps.flipImage(bImage); + // if we are byRef and the bImage type does not match currentType + // we need to convert it. If we are not byRef we will + // save converting until it is changed to byRef + if (byRef && bImage.getType() != currentType) { + if (currentType != BufferedImage.TYPE_CUSTOM) { + bImage = ImageOps.convertImage(bImage, currentType); + } + else if (customType == this.TYPE_CUSTOM_RGBA) { + bImage = ImageOps.convertToCustomRGBA(bImage); + } + else { + bImage = ImageOps.convertToCustomRGB(bImage); + } + } + images[i] = new ImageComponent2D(format, bImage, byRef, yUp); + images[i].setCapability(ImageComponent.ALLOW_IMAGE_READ); + images[i].setCapability(ImageComponent.ALLOW_FORMAT_READ); + } + + // set flip to new value + flip = b; + } + } + + // create new ImageComponents with yUp set to the parameter. yUp on + // an ImageComponent cannot be changed at runtim + public void setYUp(boolean b) { + // double check that changing yUp is necessary + if (b != images[0].isYUp()) { + + // these are the same for all images so get info once + int format = images[0].getFormat(); + boolean byRef = images[0].isByReference(); + + // reset yUp on all the images -- have to new ImageComponents because + // cannot change the value at runtime + for (int i = 0; i < images.length; i++) { + // if we are byRef and the bImage type does not match currentType + // we need to convert it. If we are not byRef we will + // save converting until it is changed to byRef + BufferedImage bImage = images[i].getImage(); + if (byRef && bImage.getType() != currentType) { + // bImage = ImageOps.convertImage(bImage, currentType); + if (currentType != BufferedImage.TYPE_CUSTOM) { + bImage = ImageOps.convertImage(bImage, currentType); + } + else if (customType == this.TYPE_CUSTOM_RGBA) { + bImage = ImageOps.convertToCustomRGBA(bImage); + } + else { + bImage = ImageOps.convertToCustomRGB(bImage); + } + } + images[i] = new ImageComponent2D(format, bImage, + byRef, b); + images[i].setCapability(ImageComponent.ALLOW_IMAGE_READ); + images[i].setCapability(ImageComponent.ALLOW_FORMAT_READ); + } + } + } + + // create new ImageComponents with ByReference set by parameter. + // by reference cannot be changed on an image component at runtime + public void setByReference(boolean b) { + // double check that changing is necessary + if (b != images[0].isByReference()) { + + // these are the same for all images so get info once + int format = images[0].getFormat(); + boolean yUp = images[0].isYUp(); + + // reset yUp on all the images + // have to new ImageComponents because cannot set value + for (int i = 0; i < images.length; i++) { + // if the bImage type does not match currentType and we are setting + // to byRef we need to convert it + BufferedImage bImage = images[i].getImage(); + if (bImage.getType() != currentType && b) { + // bImage = ImageOps.convertImage(bImage, currentType); + if (currentType != BufferedImage.TYPE_CUSTOM) { + bImage = ImageOps.convertImage(bImage, currentType); + } + else if (customType == this.TYPE_CUSTOM_RGBA) { + bImage = ImageOps.convertToCustomRGBA(bImage); + } + else { + bImage = ImageOps.convertToCustomRGB(bImage); + } + } + images[i] = new ImageComponent2D(format, bImage, b, yUp); + images[i].setCapability(ImageComponent.ALLOW_IMAGE_READ); + images[i].setCapability(ImageComponent.ALLOW_FORMAT_READ); + } + } + } + + // make a new wakeup criterion object based on the new delay time + public void setFrameDelay(int delay) { + wakeupC = new WakeupOnElapsedFrames(delay); + } + + //change the type of image + public void setImageType(int newType) { + currentType = newType; + + // only need to change the images if we are byRef otherwise will change + // them when we chnage to byRef + if (images[0].isByReference() == true) { + // this information is the same for all + int format = images[0].getFormat(); + boolean yUp = images[0].isYUp(); + boolean byRef = true; + for (int i = 0; i < images.length; i++) { + BufferedImage bImage = images[i].getImage(); + bImage = ImageOps.convertImage(bImage, currentType); + images[i] = new ImageComponent2D(format, bImage, byRef, yUp); + images[i].setCapability(ImageComponent.ALLOW_IMAGE_READ); + images[i].setCapability(ImageComponent.ALLOW_FORMAT_READ); + } + } + } + + public void setImageTypeCustomRGBA() { + currentType = BufferedImage.TYPE_CUSTOM; + customType = this.TYPE_CUSTOM_RGBA; + + // only need to change images if we are byRef otherwise will change + // them when we change to byRef + if (images[0].isByReference()) { + // this information is the same for all + int format = images[0].getFormat(); + boolean yUp = images[0].isYUp(); + boolean byRef = true; + for (int i = 0; i < images.length; i++) { + BufferedImage bImage = images[i].getImage(); + bImage = ImageOps.convertToCustomRGBA(bImage); + images[i] = new ImageComponent2D(format, bImage, byRef, yUp); + images[i].setCapability(ImageComponent.ALLOW_IMAGE_READ); + images[i].setCapability(ImageComponent.ALLOW_FORMAT_READ); + } + } + } + + public void setImageTypeCustomRGB() { + currentType = BufferedImage.TYPE_CUSTOM; + customType = this.TYPE_CUSTOM_RGB; + + // only need to change images if we are byRef otherwise will change + // them when we change to byRef + if (images[0].isByReference()) { + // this information is the same for all + int format = images[0].getFormat(); + boolean yUp = images[0].isYUp(); + boolean byRef = true; + for (int i = 0; i < images.length; i++) { + BufferedImage bImage = images[i].getImage(); + bImage = ImageOps.convertToCustomRGB(bImage); + images[i] = new ImageComponent2D(format, bImage, byRef, yUp); + images[i].setCapability(ImageComponent.ALLOW_IMAGE_READ); + images[i].setCapability(ImageComponent.ALLOW_FORMAT_READ); + } + } + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/texture_by_ref/ImageOps.java b/src/main/java/org/jdesktop/j3d/examples/texture_by_ref/ImageOps.java new file mode 100644 index 0000000..aa689b6 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/texture_by_ref/ImageOps.java @@ -0,0 +1,181 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.texture_by_ref; + +import java.awt.Transparency; +import java.awt.color.ColorSpace; +import java.awt.image.BufferedImage; +import java.awt.image.ColorModel; +import java.awt.image.ComponentColorModel; +import java.awt.image.DataBuffer; +import java.awt.image.DataBufferByte; +import java.awt.image.Raster; +import java.awt.image.WritableRaster; + +// some useful, static image operations + +public class ImageOps { + + // flip the image + public static void flipImage(BufferedImage bImage) { + int width = bImage.getWidth(); + int height = bImage.getHeight(); + int[] rgbArray = new int[width*height]; + bImage.getRGB(0, 0, width, height, rgbArray, 0, width); + int[] tempArray = new int[width*height]; + int y2 = 0; + for (int y = height-1; y >= 0; y--) { + for (int x = 0; x < width; x++) { + tempArray[y2*width+x] = rgbArray[y*width+x]; + } + y2++; + } + bImage.setRGB(0, 0, width, height, tempArray, 0, width); + } + + + // convert the image to a specified BufferedImage type and return it + public static BufferedImage convertImage(BufferedImage bImage, int type) { + int width = bImage.getWidth(); + int height = bImage.getHeight(); + BufferedImage newImage = new BufferedImage(width, height, type); + int[] rgbArray = new int[width*height]; + bImage.getRGB(0, 0, width, height, rgbArray, 0, width); + newImage.setRGB(0, 0, width, height, rgbArray, 0, width); + return newImage; + } + + // print out some of the types of BufferedImages + static void printType(BufferedImage bImage) { + int type = bImage.getType(); + if (type == BufferedImage.TYPE_4BYTE_ABGR) { + System.out.println("TYPE_4BYTE_ABGR"); + } + else if (type == BufferedImage.TYPE_INT_ARGB) { + System.out.println("TYPE_INT_ARGB"); + } + else if (type == BufferedImage.TYPE_3BYTE_BGR) { + System.out.println("TYPE_3BYTE_BGR"); + } + else if (type == BufferedImage.TYPE_CUSTOM) { + System.out.println("TYPE_CUSTOM"); + } + else System.out.println(type); + } + + public static BufferedImage convertToCustomRGBA(BufferedImage bImage) { + if (bImage.getType() != BufferedImage.TYPE_INT_ARGB) { + ImageOps.convertImage(bImage, BufferedImage.TYPE_INT_ARGB); + } + + int width = bImage.getWidth(); + int height = bImage.getHeight(); + + ColorSpace cs = ColorSpace.getInstance(ColorSpace.CS_sRGB); + int[] nBits = {8, 8, 8, 8}; + ColorModel cm = new ComponentColorModel(cs, nBits, true, false, + Transparency.OPAQUE, 0); + int[] bandOffset = {0, 1, 2, 3}; + + WritableRaster newRaster = + Raster.createInterleavedRaster(DataBuffer.TYPE_BYTE, width, height, + width*4, 4, bandOffset, null); + byte[] byteData = ((DataBufferByte)newRaster.getDataBuffer()).getData(); + Raster origRaster = bImage.getData(); + int[] pixel = new int[4]; + int k = 0; + for (int j = 0; j < height; j++) { + for (int i = 0; i < width; i++) { + pixel = origRaster.getPixel(i, j, pixel); + byteData[k++] = (byte)(pixel[0]); + byteData[k++] = (byte)(pixel[1]); + byteData[k++] = (byte)(pixel[2]); + byteData[k++] = (byte)(pixel[3]); + } + } + BufferedImage newImage = new BufferedImage(cm, newRaster, false, null); +// if (newImage.getType() == BufferedImage.TYPE_CUSTOM) { +// System.out.println("Type is custom"); +// } + return newImage; + } + + public static BufferedImage convertToCustomRGB(BufferedImage bImage) { + if (bImage.getType() != BufferedImage.TYPE_INT_ARGB) { + ImageOps.convertImage(bImage, BufferedImage.TYPE_INT_ARGB); + } + + int width = bImage.getWidth(); + int height = bImage.getHeight(); + + ColorSpace cs = ColorSpace.getInstance(ColorSpace.CS_sRGB); + int[] nBits = {8, 8, 8}; + ColorModel cm = new ComponentColorModel(cs, nBits, false, false, + Transparency.OPAQUE, 0); + int[] bandOffset = {0, 1, 2}; + + WritableRaster newRaster = + Raster.createInterleavedRaster(DataBuffer.TYPE_BYTE, width, height, + width*3, 3, bandOffset, null); + byte[] byteData = ((DataBufferByte)newRaster.getDataBuffer()).getData(); + Raster origRaster = bImage.getData(); + int[] pixel = new int[4]; + int k = 0; + for (int j = 0; j < height; j++) { + for (int i = 0; i < width; i++) { + pixel = origRaster.getPixel(i, j, pixel); + byteData[k++] = (byte)(pixel[0]); + byteData[k++] = (byte)(pixel[1]); + byteData[k++] = (byte)(pixel[2]); + } + } + BufferedImage newImage = new BufferedImage(cm, newRaster, false, null); +// if (newImage.getType() == BufferedImage.TYPE_CUSTOM) { +// System.out.println("Type is custom"); +// } + return newImage; + } +} + diff --git a/src/main/java/org/jdesktop/j3d/examples/texture_by_ref/Tetrahedron.java b/src/main/java/org/jdesktop/j3d/examples/texture_by_ref/Tetrahedron.java new file mode 100644 index 0000000..063529c --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/texture_by_ref/Tetrahedron.java @@ -0,0 +1,228 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.texture_by_ref; + +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.Shape3D; +import org.jogamp.java3d.TriangleArray; +import org.jogamp.vecmath.Point2f; +import org.jogamp.vecmath.Point3f; +import org.jogamp.vecmath.TexCoord2f; +import org.jogamp.vecmath.Vector3f; + + +public class Tetrahedron extends Shape3D { + + private static final float sqrt3 = (float) Math.sqrt(3.0); + private static final float sqrt3_3 = sqrt3 / 3.0f; + private static final float sqrt24_3 = (float) Math.sqrt(24.0) / 3.0f; + + private static final float ycenter = 0.5f * sqrt24_3; + private static final float zcenter = -sqrt3_3; + + private static final Point3f p1 = new Point3f(-1.0f, -ycenter, -zcenter); + private static final Point3f p2 = new Point3f(1.0f, -ycenter, -zcenter); + private static final Point3f p3 = new Point3f(0.0f, -ycenter, -sqrt3 - zcenter); + private static final Point3f p4 = new Point3f(0.0f, sqrt24_3 - ycenter, 0.0f); + + private static final Point3f[] verts = { + p1, p2, p4, // front face + p1, p4, p3, // left, back face + p2, p3, p4, // right, back face + p1, p3, p2, // bottom face + }; + + private Point2f texCoord[] = { + new Point2f(-0.25f, 0.0f), + new Point2f(1.25f, 0.0f), + new Point2f(0.5f, 2.0f), + }; + + private TriangleArray geometryByRef; + private TriangleArray geometryByCopy; + + // for geometry by reference + private Point3f[] verticesArray = new Point3f[12]; + private TexCoord2f[] textureCoordsArray = new TexCoord2f[12]; + private Vector3f[] normalsArray = new Vector3f[12]; + + // default to geometry by copy + public Tetrahedron() { + this(false); + } + + // creates a tetrahedron with geometry by reference or by copy depending on + // the byRef parameter + public Tetrahedron(boolean byRef) { + if (byRef) { + createGeometryByRef(); + this.setGeometry(geometryByRef); + } + else { + createGeometryByCopy(); + this.setGeometry(geometryByCopy); + } + this.setCapability(Shape3D.ALLOW_GEOMETRY_READ); + this.setCapability(Shape3D.ALLOW_GEOMETRY_WRITE); + setAppearance(new Appearance()); + } + + // create the geometry by reference and + // store it in the geometryByRef variable + public void createGeometryByRef() { +// System.out.println("createGeometryByRef"); + geometryByRef = new TriangleArray(12, TriangleArray.COORDINATES | + TriangleArray.NORMALS | + TriangleArray.TEXTURE_COORDINATE_2 | + TriangleArray.BY_REFERENCE); + + int i; + + // the coordinates + for (i = 0; i < 12; i++) { + verticesArray[i] = new Point3f(verts[i]); + } + geometryByRef.setCoordRef3f(verticesArray); +// System.out.println("coordinates set"); +// Point3f[] temp1 = geometryByRef.getCoordRef3f(); +// for (i = 0; i < 12; i++) { +// System.out.println(temp1[i]); +// } + + // the texture coordinates + for (i = 0; i < 12; i++) { + textureCoordsArray[i] = new TexCoord2f(texCoord[i%3]); + } + geometryByRef.setTexCoordRef2f(0, textureCoordsArray); +// System.out.println("texture coords set"); +// TexCoord2f[] temp2 = geometryByRef.getTexCoordRef2f(0); +// for (i = 0; i < 12; i++) { +// System.out.println(temp2[i]); +// } + + // the normals + Vector3f normal = new Vector3f(); + Vector3f v1 = new Vector3f(); + Vector3f v2 = new Vector3f(); + Point3f[] pts = new Point3f[3]; + for (int face = 0; face < 4; face++) { + pts[0] = new Point3f(verts[face*3]); + pts[1] = new Point3f(verts[face*3+1]); + pts[2] = new Point3f(verts[face*3+2]); + v1.sub(pts[1], pts[0]); + v2.sub(pts[2], pts[0]); + normal.cross(v1, v2); + normal.normalize(); + for (i = 0; i < 3; i++) { + normalsArray[face*3+i] = new Vector3f(normal); + } + } + geometryByRef.setNormalRef3f(normalsArray); +// System.out.println("normals set"); +// Vector3f[] temp3 = geometryByRef.getNormalRef3f(); +// for (i = 0; i < 12; i++) { +// System.out.println(temp3[i]); +// } + } + + // create the geometry by copy and store it in the geometryByCopy variable + public void createGeometryByCopy() { + int i; + geometryByCopy = new TriangleArray(12, TriangleArray.COORDINATES | + TriangleArray.NORMALS | + TriangleArray.TEXTURE_COORDINATE_2); + + geometryByCopy.setCoordinates(0, verts); + + for (i = 0; i < 12; i++) { + geometryByCopy.setTextureCoordinate(0, i, + new TexCoord2f(texCoord[i%3])); + } + + int face; + Vector3f normal = new Vector3f(); + Vector3f v1 = new Vector3f(); + Vector3f v2 = new Vector3f(); + Point3f [] pts = new Point3f[3]; + for (i = 0; i < 3; i++) pts[i] = new Point3f(); + + for (face = 0; face < 4; face++) { + geometryByCopy.getCoordinates(face*3, pts); + v1.sub(pts[1], pts[0]); + v2.sub(pts[2], pts[0]); + normal.cross(v1, v2); + normal.normalize(); + for (i = 0; i < 3; i++) { + geometryByCopy.setNormal((face * 3 + i), normal); + } + } + } + + // set the geometry to geometryByRef or geometryByCopy depending on the + // parameter. Create geometryByRef or geometryByCopy if necessary + public void setByReference(boolean b) { +// System.out.println("Tetrahedron.setByReference " + b); + // by reference is true + if (b) { + // if there is no geometryByRef, create it + if (geometryByRef == null) { + createGeometryByRef(); + } + // set the geometry + this.setGeometry(geometryByRef); + } + // by reference is false + else { + // if there is no geometryByCopy, create it + if (geometryByCopy == null) { + createGeometryByCopy(); + } + // set the geometry + this.setGeometry(geometryByCopy); + } + } +} + + diff --git a/src/main/java/org/jdesktop/j3d/examples/texture_by_ref/TextureByReference.java b/src/main/java/org/jdesktop/j3d/examples/texture_by_ref/TextureByReference.java new file mode 100644 index 0000000..b30b9a2 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/texture_by_ref/TextureByReference.java @@ -0,0 +1,581 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.texture_by_ref; + +import java.applet.Applet; +import java.awt.BorderLayout; +import java.awt.Component; +import java.awt.Dimension; +import java.awt.GraphicsConfiguration; +import java.awt.GridBagConstraints; +import java.awt.GridBagLayout; +import java.awt.event.ActionEvent; +import java.awt.event.ActionListener; +import java.awt.event.ItemEvent; +import java.awt.event.ItemListener; +import java.awt.image.BufferedImage; + +import javax.swing.BoxLayout; +import javax.swing.ButtonGroup; +import javax.swing.JButton; +import javax.swing.JCheckBox; +import javax.swing.JLabel; +import javax.swing.JPanel; +import javax.swing.JRadioButton; +import javax.swing.JSlider; +import javax.swing.event.ChangeEvent; +import javax.swing.event.ChangeListener; + +import org.jdesktop.j3d.examples.Resources; +import org.jogamp.java3d.Alpha; +import org.jogamp.java3d.AmbientLight; +import org.jogamp.java3d.Appearance; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.DirectionalLight; +import org.jogamp.java3d.ImageComponent2D; +import org.jogamp.java3d.Material; +import org.jogamp.java3d.RotationInterpolator; +import org.jogamp.java3d.Texture; +import org.jogamp.java3d.Texture2D; +import org.jogamp.java3d.TextureAttributes; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.utils.applet.MainFrame; +import org.jogamp.java3d.utils.image.TextureLoader; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.vecmath.Color3f; +import org.jogamp.vecmath.Point3d; +import org.jogamp.vecmath.Vector3f; + + +public class TextureByReference extends Applet +implements ItemListener, ActionListener, ChangeListener { + + // need reference to animation behavior + private AnimateTexturesBehavior animate; + + // need reference to tetrahedron + private Tetrahedron tetra; + + // the gui buttons + private JCheckBox flipB; + private JRadioButton texByRef; + private JRadioButton texByCopy; + private JRadioButton geomByRef; + private JRadioButton geomByCopy; + private JRadioButton img4ByteABGR; + private JRadioButton img3ByteBGR; + private JRadioButton imgIntARGB; + private JRadioButton imgCustomRGBA; + private JRadioButton imgCustomRGB; + private JRadioButton yUp; + private JRadioButton yDown; + private JButton animationB; + private JSlider frameDelay; + + private SimpleUniverse universe = null; + + // image files used for the Texture animation for the applet, + // or if no parameters are passed in for the application + public static final String[] defaultFiles = { + "resources/images/animation1.gif", + "resources/images/animation2.gif", + "resources/images/animation3.gif", + "resources/images/animation4.gif", + "resources/images/animation5.gif", + "resources/images/animation6.gif", + "resources/images/animation7.gif", + "resources/images/animation8.gif", + "resources/images/animation9.gif", + "resources/images/animation10.gif"}; + + private java.net.URL[] urls = null; + + + public TextureByReference() { + } + + public TextureByReference(java.net.URL[] fnamesP) { + urls = fnamesP; + } + + public void init() {System.setProperty("sun.awt.noerasebackground", "true"); + if (urls == null) { + urls = new java.net.URL[defaultFiles.length]; + for (int i = 0; i < defaultFiles.length; i++) { + urls[i] = Resources.getResource(defaultFiles[i]); + if (urls[i] == null) { + System.err.println(defaultFiles[i] + " not found"); + System.exit(1); + } + /* + try { + urls[i] = new java.net.URL(getCodeBase().toString() + + defaultFiles[i]); + } + catch (java.net.MalformedURLException ex) { + System.out.println(ex.getMessage()); + System.exit(1); + } + */ + } + } + setLayout(new BorderLayout()); + GraphicsConfiguration config = SimpleUniverse.getPreferredConfiguration(); + + Canvas3D canvas = new Canvas3D(config); + + add("Center", canvas); + + // create a simple scene graph and attach it to a simple universe + BranchGroup scene = createSceneGraph(); + universe = new SimpleUniverse(canvas); + universe.getViewingPlatform().setNominalViewingTransform(); + universe.addBranchGraph(scene); + + // create the gui + JPanel gui = buildGui(); + + this.add("South", gui); + } + + public void destroy() { + universe.cleanup(); + } + + public JPanel buildGui() { + flipB = new JCheckBox("flip image", true); + flipB.addItemListener(this); + javax.swing.Box flipBox = new javax.swing.Box(BoxLayout.Y_AXIS); + flipBox.add(flipB); + Component strut1 = flipBox.createVerticalStrut(flipB.getPreferredSize().height); + Component strut2 = flipBox.createVerticalStrut(flipB.getPreferredSize().height); + Component strut3 = flipBox.createVerticalStrut(flipB.getPreferredSize().height); + Component strut4 = flipBox.createVerticalStrut(flipB.getPreferredSize().height); + Component strut5 = flipBox.createVerticalStrut(flipB.getPreferredSize().height); + flipBox.add(strut1); + flipBox.add(strut2); + flipBox.add(strut3); + flipBox.add(strut4); + flipBox.add(strut5); + + yUp = new JRadioButton("y up"); + yUp.addActionListener(this); + yUp.setSelected(true); + yDown = new JRadioButton("y down"); + yDown.addActionListener(this); + ButtonGroup yGroup = new ButtonGroup(); + yGroup.add(yUp); + yGroup.add(yDown); + JLabel yLabel = new JLabel("Image Orientation:"); + javax.swing.Box yBox = new javax.swing.Box(BoxLayout.Y_AXIS); + yBox.add(yLabel); + yBox.add(yUp); + yBox.add(yDown); + strut1 = yBox.createVerticalStrut(yUp.getPreferredSize().height); + strut2 = yBox.createVerticalStrut(yUp.getPreferredSize().height); + strut3 = yBox.createVerticalStrut(yUp.getPreferredSize().height); + yBox.add(strut1); + yBox.add(strut2); + yBox.add(strut3); + + texByRef = new JRadioButton("by reference"); + texByRef.addActionListener(this); + texByRef.setSelected(true); + texByCopy = new JRadioButton("by copy"); + texByCopy.addActionListener(this); + ButtonGroup texGroup = new ButtonGroup(); + texGroup.add(texByRef); + texGroup.add(texByCopy); + JLabel texLabel = new JLabel("Texture:*"); + javax.swing.Box texBox = new javax.swing.Box(BoxLayout.Y_AXIS); + texBox.add(texLabel); + texBox.add(texByRef); + texBox.add(texByCopy); + strut1 = texBox.createVerticalStrut(texByRef.getPreferredSize().height); + strut2 = texBox.createVerticalStrut(texByRef.getPreferredSize().height); + strut3 = texBox.createVerticalStrut(texByRef.getPreferredSize().height); + texBox.add(strut1); + texBox.add(strut2); + texBox.add(strut3); + + geomByRef = new JRadioButton("by reference"); + geomByRef.addActionListener(this); + geomByRef.setSelected(true); + geomByCopy = new JRadioButton("by copy"); + geomByCopy.addActionListener(this); + ButtonGroup geomGroup = new ButtonGroup(); + geomGroup.add(geomByRef); + geomGroup.add(geomByCopy); + JLabel geomLabel = new JLabel("Geometry:"); + javax.swing.Box geomBox = new javax.swing.Box(BoxLayout.Y_AXIS); + geomBox.add(geomLabel); + geomBox.add(geomByRef); + geomBox.add(geomByCopy); + strut1 = geomBox.createVerticalStrut(geomByRef.getPreferredSize().height); + strut2 = geomBox.createVerticalStrut(geomByRef.getPreferredSize().height); + strut3 = geomBox.createVerticalStrut(geomByRef.getPreferredSize().height); + geomBox.add(strut1); + geomBox.add(strut2); + geomBox.add(strut3); + + img4ByteABGR = new JRadioButton("TYPE_4BYTE_ABGR"); + img4ByteABGR.addActionListener(this); + img4ByteABGR.setSelected(true); + img3ByteBGR = new JRadioButton("TYPE_3BYTE_BGR"); + img3ByteBGR.addActionListener(this); + imgIntARGB = new JRadioButton("TYPE_INT_ARGB"); + imgIntARGB.addActionListener(this); + imgCustomRGBA = new JRadioButton("TYPE_CUSTOM RGBA"); + imgCustomRGBA.addActionListener(this); + imgCustomRGB = new JRadioButton("TYPE_CUSTOM RGB"); + imgCustomRGB.addActionListener(this); + ButtonGroup imgGroup = new ButtonGroup(); + imgGroup.add(img4ByteABGR); + imgGroup.add(img3ByteBGR); + imgGroup.add(imgIntARGB); + imgGroup.add(imgCustomRGBA); + imgGroup.add(imgCustomRGB); + JLabel imgLabel = new JLabel("Image Type:*"); + javax.swing.Box imgBox = new javax.swing.Box(BoxLayout.Y_AXIS); + imgBox.add(imgLabel); + imgBox.add(img4ByteABGR); + imgBox.add(img3ByteBGR); + imgBox.add(imgIntARGB); + imgBox.add(imgCustomRGBA); + imgBox.add(imgCustomRGB); + + javax.swing.Box topBox = new javax.swing.Box(BoxLayout.X_AXIS); + topBox.add(flipBox); + topBox.add(texBox); + topBox.add(geomBox); + topBox.add(yBox); + Component strut = topBox.createRigidArea(new Dimension(10, 10)); + topBox.add(strut); + topBox.add(imgBox); + + frameDelay = new JSlider(0, 50, 0); + frameDelay.addChangeListener(this); + frameDelay.setSnapToTicks(true); + frameDelay.setPaintTicks(true); + frameDelay.setPaintLabels(true); + frameDelay.setMajorTickSpacing(10); + frameDelay.setMinorTickSpacing(1); + frameDelay.setValue(20); + JLabel delayL = new JLabel("frame delay"); + javax.swing.Box delayBox = new javax.swing.Box(BoxLayout.X_AXIS); + delayBox.add(delayL); + delayBox.add(frameDelay); + + animationB = new JButton(" stop animation "); + animationB.addActionListener(this); + + JLabel texInfo1 = new JLabel("*To use ImageComponent by reference feature, use TYPE_4BYTE_ABGR on Solaris"); + JLabel texInfo2 = new JLabel("and TYPE_3BYTE_BGR on Windows"); + + JPanel buttonP = new JPanel(); + GridBagLayout gridbag = new GridBagLayout(); + GridBagConstraints c = new GridBagConstraints(); + buttonP.setLayout(gridbag); + c.anchor = GridBagConstraints.CENTER; + c.gridwidth = GridBagConstraints.REMAINDER; + gridbag.setConstraints(topBox, c); + buttonP.add(topBox); + gridbag.setConstraints(delayBox, c); + buttonP.add(delayBox); + gridbag.setConstraints(animationB, c); + buttonP.add(animationB); + gridbag.setConstraints(texInfo1, c); + buttonP.add(texInfo1); + gridbag.setConstraints(texInfo2, c); + buttonP.add(texInfo2); + + return buttonP; + + } + + public BranchGroup createSceneGraph() { + + // create the root of the branch group + BranchGroup objRoot = new BranchGroup(); + + // create the transform group node and initialize it + // enable the TRANSFORM_WRITE capability so that it can be modified + // at runtime. Add it to the root of the subgraph + Transform3D rotate = new Transform3D(); + TransformGroup objTrans = new TransformGroup(rotate); + objTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + objRoot.addChild(objTrans); + + // bounds + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + + // set up some light + Color3f lColor1 = new Color3f(0.7f, 0.7f, 0.7f); + Vector3f lDir1 = new Vector3f(-1.0f, -0.5f, -1.0f); + Color3f alColor = new Color3f(0.2f, 0.2f, 0.2f); + + AmbientLight aLgt = new AmbientLight(alColor); + aLgt.setInfluencingBounds(bounds); + DirectionalLight lgt1 = new DirectionalLight(lColor1, lDir1); + lgt1.setInfluencingBounds(bounds); + objRoot.addChild(aLgt); + objRoot.addChild(lgt1); + + + Appearance appearance = new Appearance(); + + // enable the TEXTURE_WRITE so we can modify it at runtime + appearance.setCapability(Appearance.ALLOW_TEXTURE_WRITE); + + // load the first texture + TextureLoader loader = new TextureLoader(urls[0], + TextureLoader.BY_REFERENCE | + TextureLoader.Y_UP, + this); + // get the texture from the loader + Texture2D tex = (Texture2D)loader.getTexture(); + + // get the BufferedImage to convert to TYPE_4BYTE_ABGR and flip + // get the ImageComponent because we need it anyway + ImageComponent2D imageComp = (ImageComponent2D)tex.getImage(0); + BufferedImage bImage = imageComp.getImage(); + // convert the image + bImage = ImageOps.convertImage(bImage, BufferedImage.TYPE_4BYTE_ABGR); + // flip the image + ImageOps.flipImage(bImage); + imageComp.set(bImage); + + tex.setCapability(Texture.ALLOW_IMAGE_WRITE); + tex.setBoundaryModeS(Texture.CLAMP); + tex.setBoundaryModeT(Texture.CLAMP); + tex.setBoundaryColor(1.0f, 1.0f, 1.0f, 1.0f); + + // set the image of the texture + tex.setImage(0, imageComp); + + // set the texture on the appearance + appearance.setTexture(tex); + + // set texture attributes + TextureAttributes texAttr = new TextureAttributes(); + texAttr.setTextureMode(TextureAttributes.MODULATE); + appearance.setTextureAttributes(texAttr); + + // set material properties + Color3f black = new Color3f(0.0f, 0.0f, 0.0f); + Color3f white = new Color3f(1.0f, 1.0f, 1.0f); + appearance.setMaterial(new Material(white, black, white, black, 1.0f)); + + // create a scale transform + Transform3D scale = new Transform3D(); + scale.set(.6); + TransformGroup objScale = new TransformGroup(scale); + objTrans.addChild(objScale); + + tetra = new Tetrahedron(true); + tetra.setAppearance(appearance); + objScale.addChild(tetra); + + // create the behavior + animate = new AnimateTexturesBehavior(tex, + urls, + appearance, + this); + animate.setSchedulingBounds(bounds); + + objTrans.addChild(animate); + + // add a rotation behavior so we can see all sides of the tetrahedron + Transform3D yAxis = new Transform3D(); + Alpha rotorAlpha = new Alpha(-1, Alpha.INCREASING_ENABLE, + 0, 0, + 4000, 0, 0, + 0, 0, 0); + RotationInterpolator rotator = + new RotationInterpolator(rotorAlpha, + objTrans, + yAxis, + 0.0f, (float) Math.PI*2.0f); + rotator.setSchedulingBounds(bounds); + objTrans.addChild(rotator); + + + // have java3d perform optimizations on this scene graph + objRoot.compile(); + + return objRoot; + } + + // callback for the animation button and delay text field + public void actionPerformed(ActionEvent e) { + Object o = e.getSource(); + + // for the animation button + if (o == animationB) { + if (animate.getEnable()) { + animate.setEnable(false); + animationB.setText("start animation"); + } + else { + animate.setEnable(true); + animationB.setText(" stop animation "); + } + } + + // for the texByRef button + else if (o == texByRef && texByRef.isSelected()) { + animate.setByReference(true); + } + // texByCopy button + else if (o == texByCopy && texByCopy.isSelected()) { + animate.setByReference(false); + } + // yUp button + else if (o == yUp && yUp.isSelected()) { + animate.setYUp(true); + } + // ydown button + else if (o == yDown && yDown.isSelected()) { + animate.setYUp(false); + } + //geomByRef button + else if (o == geomByRef) { + tetra.setByReference(true); + } + // geomByCopy button + else if (o == geomByCopy) { + tetra.setByReference(false); + } + // TYPE_INT_ARGB + else if (o == imgIntARGB) { + animate.setImageType(BufferedImage.TYPE_INT_ARGB); + } + // TYPE_4BYTE_ABGR + else if (o == img4ByteABGR) { + animate.setImageType(BufferedImage.TYPE_4BYTE_ABGR); + } + // TYPE_3BYTE_BGR + else if (o == img3ByteBGR) { + animate.setImageType(BufferedImage.TYPE_3BYTE_BGR); + } + // TYPE_CUSTOM RGBA + else if (o == imgCustomRGBA) { + animate.setImageTypeCustomRGBA(); + } + // TYPE_CUSTOM RGB + else if (o == imgCustomRGB) { + animate.setImageTypeCustomRGB(); + } + } + + // callback for the checkboxes + public void itemStateChanged(ItemEvent e) { + Object o = e.getSource(); + // for the flip checkbox + if (o == flipB) { + if (e.getStateChange() == ItemEvent.DESELECTED) { + animate.setFlipImages(false); + } + else animate.setFlipImages(true); + } + } + + // callback for the slider + public void stateChanged(ChangeEvent e) { + Object o = e.getSource(); + // for the frame delay + if (o == frameDelay) { + animate.setFrameDelay(frameDelay.getValue()); + } + } + + // allows TextureByReference to be run as an application as well as an applet + public static void main(String[] args) {System.setProperty("sun.awt.noerasebackground", "true"); + java.net.URL fnames[] = null; + if (args.length > 1) { + fnames = new java.net.URL[args.length]; + for (int i = 0; i < args.length; i++) { + try { + fnames[i] = new java.net.URL("file:" + args[i]); + } + catch (java.net.MalformedURLException ex) { + System.out.println(ex.getMessage()); + } + } + } + else { + fnames = new java.net.URL[TextureByReference.defaultFiles.length]; + for (int i = 0; i < TextureByReference.defaultFiles.length; i++) { + fnames[i] = Resources.getResource(defaultFiles[i]); + if (fnames[i] == null) { + System.err.println(TextureByReference.defaultFiles[i] + " not found"); + System.exit(1); + } + +/* + try { + fnames[i] = new java.net.URL("file:" + + TextureByReference.defaultFiles[i]); + } + catch (java.net.MalformedURLException ex) { + System.out.println(ex.getMessage()); + System.exit(1); + } + */ + } + } + new MainFrame((new TextureByReference(fnames)), 650, 750); + } +} + + + + + + diff --git a/src/main/java/org/jdesktop/j3d/examples/virtual_input_device/ButtonPositionControls.java b/src/main/java/org/jdesktop/j3d/examples/virtual_input_device/ButtonPositionControls.java new file mode 100644 index 0000000..82f3393 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/virtual_input_device/ButtonPositionControls.java @@ -0,0 +1,214 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.virtual_input_device; + +import java.awt.BorderLayout; +import java.awt.Button; +import java.awt.GridLayout; +import java.awt.Panel; +import java.awt.event.MouseEvent; +import java.awt.event.MouseListener; + +import org.jogamp.java3d.InputDevice; +import org.jogamp.vecmath.Vector3f; + +public class ButtonPositionControls extends Panel implements PositionControls, MouseListener { + private final static int STILL=0; + private final static int MOVING_UP=1; + private final static int MOVING_DOWN=2; + private final static int MOVING_LEFT=3; + private final static int MOVING_RIGHT=4; + private final static int MOVING_FORWARD=5; + private final static int MOVING_BACK=6; + + // initial mode + private int mode = STILL; + + Vector3f position = new Vector3f(); + Vector3f orig_position = new Vector3f(); + + private Button leftB = new Button("Move Left"); + private Button rightB = new Button("Move Right"); + private Button upB = new Button("Move Up"); + private Button downB = new Button("Move Down"); + + private Button forwardB = new Button("Move Forward"); + private Button backwardB = new Button("Move Back"); + + private Button reset = new Button("Reset"); + private InputDevice device; + + private float step_rate = 0.0023f; // movement rate per millisecond + private long time_last_state_change = System.currentTimeMillis(); + + // the constructor arguments are the intitial X, Y, and Z positions + public ButtonPositionControls( float x, float y, float z ) { + + // up, down, right, and left movement buttons + Panel panPanel = new Panel(); + panPanel.setLayout( new BorderLayout() ); + panPanel.add("North", upB); + panPanel.add("East", rightB); + panPanel.add("South", downB); + panPanel.add("West", leftB); + + // forward, backward, and reset buttons + Panel p = new Panel(); + p.setLayout( new GridLayout(0,1,0,0) ); + p.add(forwardB); + p.add(backwardB); + p.add(reset); + + // set the initial position + position.x = x; + position.y = y; + position.z = z; + orig_position.set(position); + + // add a mouse listener to each button + upB.addMouseListener(this); + downB.addMouseListener(this); + leftB.addMouseListener(this); + rightB.addMouseListener(this); + forwardB.addMouseListener(this); + backwardB.addMouseListener(this); + reset.addMouseListener(this); + + this.setLayout( new BorderLayout() ); + add("East", p ); + add("West", panPanel ); + } + + public void setDevice ( InputDevice device) { + this.device = device; + } + + public void getPosition(Vector3f pos ) { + calculateMotion(); + pos.set(position); + } + + public void setPosition(Vector3f pos ) { + position.set(pos); + } + + public void setStepRate( float stepRate ) { + step_rate = stepRate; + } + + private void calculateMotion() { + + long current_time = System.currentTimeMillis(); + long elapsed_time = current_time - time_last_state_change; + + switch(mode) { + case STILL: + break; + case MOVING_LEFT: + position.x = orig_position.x - step_rate*elapsed_time; + break; + case MOVING_RIGHT: + position.x = orig_position.x + step_rate*elapsed_time; + break; + case MOVING_UP: + position.y = orig_position.y + step_rate*elapsed_time; + break; + case MOVING_DOWN: + position.y = orig_position.y - step_rate*elapsed_time; + break; + case MOVING_FORWARD: + position.z = orig_position.z - step_rate*elapsed_time; + break; + case MOVING_BACK: + position.z = orig_position.z + step_rate*elapsed_time; + break; + default: + throw( new RuntimeException("Unknown motion")); + } + } + + public void mouseClicked( MouseEvent e ) { + } + + public void mouseEntered( MouseEvent e ) { + } + + public void mouseExited( MouseEvent e ) { + } + + public void mousePressed( MouseEvent e ) { + if (e.getSource()==leftB && mode != MOVING_LEFT) { + time_last_state_change = System.currentTimeMillis(); + mode = MOVING_LEFT; + orig_position.set(position); + } else if (e.getSource()==rightB && mode != MOVING_RIGHT) { + time_last_state_change = System.currentTimeMillis(); + mode = MOVING_RIGHT; + orig_position.set(position); + } else if (e.getSource()==upB && mode != MOVING_UP) { + time_last_state_change = System.currentTimeMillis(); + mode = MOVING_UP; + orig_position.set(position); + } else if (e.getSource()==downB && mode != MOVING_DOWN) { + time_last_state_change = System.currentTimeMillis(); + mode = MOVING_DOWN; + orig_position.set(position); + } else if (e.getSource()==forwardB && mode != MOVING_FORWARD) { + time_last_state_change = System.currentTimeMillis(); + mode = MOVING_FORWARD; + orig_position.set(position); + } else if (e.getSource()==backwardB && mode != MOVING_BACK) { + time_last_state_change = System.currentTimeMillis(); + mode = MOVING_BACK; + orig_position.set(position); + } else if (e.getSource()==reset) { + device.setNominalPositionAndOrientation(); + } + } + + public void mouseReleased( MouseEvent e ) { + mode = STILL; + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/virtual_input_device/PositionControls.java b/src/main/java/org/jdesktop/j3d/examples/virtual_input_device/PositionControls.java new file mode 100644 index 0000000..eeff16d --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/virtual_input_device/PositionControls.java @@ -0,0 +1,69 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.virtual_input_device; + +import org.jogamp.vecmath.Vector3f; + +// Classes that implement this interface must be a +// subclass of java.awt.Component +public interface PositionControls { + + /** + * Get the position + */ + public void getPosition( Vector3f pos); + + /** + * Set the position + */ + public void setPosition( Vector3f pos); + + /** + * Increment added to position each time mouse is pressed + * or if the mouse is held down each time the Sensor is + * read + */ + public void setStepRate( float stepRate ); +} diff --git a/src/main/java/org/jdesktop/j3d/examples/virtual_input_device/README.txt b/src/main/java/org/jdesktop/j3d/examples/virtual_input_device/README.txt new file mode 100644 index 0000000..f769dac --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/virtual_input_device/README.txt @@ -0,0 +1,195 @@ + Java 3D (TM) Input Device Driver Development Guide + +Topics + + * Write Once, Run Anywhere (TM) + * Overview of the InputDevice and Sensor APIs + * Recipe for an Application Program that Uses Input Devices + * Location for Installation of Device Drivers + * Using a Preexistent Native Driver + * Package Naming Conventions + * Device Driver Constructor + * Driver Scheduling and Blocking Semantics + + +Write Once, Run Anywhere + +Platform independence is the cornerstone of the Java (TM) platform. +This vision now extends to external input devices as well. The +overarching goal of the Java 3D input device architecture is to enable +Java programs that use devices to run in a platform independent +manner. + +We encourage developers to use Java APIs for their drivers. APIs such +as the javax.comm API allow platform independent access to serial and +parallel ports. However, even if a driver is partially written with +native code, the Java 3D InputDevice interface is layered on top of the +driver such that once the native portion of the driver has been +installed into the local JRE, the application code is platform +independent. + +In a future release, the Java 3D team is going to release a registry +mechanism that will reside in the JRE as part of the Java 3D +installation and allow registration of device drivers. The +SimpleUniverse utility will be modified to allow querying of devices by +generic characteristics, and will subsequently look up and instantiate +the appropriate device driver registered with the registry mechanism. +The Java 3D team also expects to release a set of generic mappings for +devices. This will enable applications to count on the same behavior +from different drivers for similar types of devices. There will also +be personalized profiles that enable a user to specify device mappings +for features like dominant hand preference and eye position. + + +Overview of the InputDevice and Sensor APIs + +Java 3D abstracts the concept of a device via the InputDevice +interface. The developer's implementation of the InputDevice interface +is layered on top of the device driver. The device may be a real +device such as a joystick or it may be a virtual device such as a piece +of Java code that does transform calculations. + +A device sends data back to Java 3D by placing values into Sensor +objects which the device code manages and updates. The Sensor class +encapsulates a transform and a timestamp. The transform is specified +in the TrackerBase coordinate system. + +Java 3D schedules calls to the device's pollAndProcessInput routine, +which is a method in the InputDevice interface. This method is +responsible for updating the devices sensor values. The sensors' +values and time stamps are read by a user's behavior code and/or each +frame (by the Java 3D implementation) when head tracking is enabled. +There are several options for scheduling, and they are detailed in the +InputDevice javadoc and in the section below entitled "Driver +Scheduling and Blocking Semantics." + +Please read the javadocs for InputDevice and Sensor for more detailed +information. There is also a sample program in the Java 3D release +called VirtualInputDevice, which implements these concepts in Java code. + + +Recipe for an Application Program that Uses Input Devices + +Please see the Java 3D example program in the examples directory called +VirtualInputDevice for an example of using this code recipe: + 1) Implement the InputDevice interface with a class of your own + 2) Call the device's constructor from your main program + 3) Call initialize() on the device + 4) Call PhysicalEnvironment.addInputDevice(InputDevice) or if you are + using SimpleUniverse, call SimpleUniverse.getViewer(). + getPhysicalEnvironment().addInputDevice(InputDevice) + 5) Assuming you want to modify the viewer's transform with the device: + add a WakeupOnElapsedFrames behavior to your scene graph that wakes + up every frame and in the processStimulus method modify the view + transform with the transform you pull out of Sensor.getRead. + +In a future release, it will be possible to replace steps 2, 3, & 4 with +a single method call to the SimpleUniverse utility. + + +Location for Installation of Device Drivers + +There are two suggested ways to package and distribute drivers. + +If a driver is written entirely in Java and if it is tightly coupled +with a particular application without the expectation of reuse in other +applications, then it should be bundled and distributed with the +application itself. + +If a driver is not associated with any particular application program, +if it contains any native code, or if it is expected to be used by more +than one application program, then it should be installed directly into +the end user's local JRE. It is expected that most drivers for real +devices fall into this category. On the Solaris platform, the Java +portion of the driver should be installed into jre/lib/ext as a +uniquely named jar file and if there is native code it should be +compiled into a shared object and installed into jre/lib/sparc. On the +Win32 platform, the Java portion of the driver should be installed into +jre\lib\ext as a uniquely named jar file and if there is native code it +should be compiled into a standard dynamically linked library (dll) and +installed into jre\bin. + + +Using a Preexistent Native Driver + +It is possible to make a Java 3D driver out of a preexistent native +driver. In order to do this, you need to create an InputDevice +interface that uses JNI to access the associated native driver methods +whenever the corresponding InputDevice interface method is called from +Java 3D. The native portion of the driver must be installed into the +target JRE. + + +Package Naming Conventions + +All device drivers that are installed into the JRE should be part of a +package that follows both standard Java and Java 3D naming +conventions. For instance, an input device driver should be placed +into a package called +com.<company_name>.j3d.drivers.input.<device_name>. The package should +be jarred up into a jar file that has a unique name. + +Any native .so or .dll files installed into the JRE should be uniquely +named. + + +Device Driver Constructor + +The constructor arguments for a device driver must be an array of +strings. So a driver should have a single public constructor that +takes an array of strings. The idea behind this requirement is that +eventually the Java 3D registry will contain an array of string +arguments to be sent to the device constructor at instantiation time. +The SimpleUniverse API will also make a provision for optional String +arguments to be added to the array of String arguments found in the +registry. + + +Driver Scheduling and Blocking Semantics + +When a device is registered with Java 3D via the +PhysicalEnvironment.addInputDevice(InputDevice) method call, +InputDevice.getProcessingMode() is called on the registered device. +This method should return one of the three processing modes defined in +the InputDevice interface: BLOCKING, NON_BLOCKING, and DEMAND_DRIVEN. + + BLOCKING signifies that the driver for a device is a blocking driver + and that it should be scheduled for regular reads by Java 3D. A + blocking driver is defined as a driver that can cause the thread + accessing the driver (the Java 3D implementation thread calling the + pollAndProcessInput method) to block while the data is being accessed + from the driver. + + NON_BLOCKING signifies that the driver for a device is a non-blocking + driver and that it should be scheduled for regular reads by Java 3D. + A non-blocking driver is defined as a driver that does not cause the + calling thread to block while data is being retrieved from the + driver. If no data is available from the device, pollAndProcessInput + should return without updating the sensor read value. + + DEMAND_DRIVEN signifies that the Java 3D implementation should not + schedule regular reads on the sensors of this device; the Java 3D + implementation will only call pollAndProcessInput when one of the + device's sensors' getRead methods is called. A DEMAND_DRIVEN driver + must always provide the current value of the sensor on demand + whenever pollAndProcessInput is called. This means that DEMAND_DRIVEN + drivers are non-blocking by definition. + +It is important that you correctly classify your driver. If it is a +NON_BLOCKING driver, most Java 3D implementations will choose to add +inertia inside the scheduling thread to avoid starvation of the other +Java 3D threads. If it is a BLOCKING driver, most Java 3D +implementations will choose to spawn a separate scheduling thread for +each BLOCKING device. If your driver is a DEMAND_DRIVEN driver, your +driver must always provide the current value upon request along with +the current time stamp. + +When running drivers with the Solaris operating system using the +Solaris reference 1.2 JRE and green threads, you should be aware that +there is a bug that forces all drivers to be BLOCKING. Thus, you +should be careful to always use native threads on the Solaris reference +1.2 JRE in order to get the expected behavior. This is not an issue +with the Solaris 1.2 Performance JRE release, which is native threads +only. + + diff --git a/src/main/java/org/jdesktop/j3d/examples/virtual_input_device/RotationControls.java b/src/main/java/org/jdesktop/j3d/examples/virtual_input_device/RotationControls.java new file mode 100644 index 0000000..ea5b8c9 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/virtual_input_device/RotationControls.java @@ -0,0 +1,71 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.virtual_input_device; + +// Classes that implement this interface must be a subclass +// of java.awt.Component + +public interface RotationControls { + + /** + * Get the angle of Rotation around the X Axis + */ + public abstract float getXAngle(); + + /** + * Get the angle or Rotation around the Y Axis + */ + public abstract float getYAngle(); + + /** + * Get the angle or Rotation around the Z Axis + */ + public abstract float getZAngle(); + + /** + * Reset angles to original angle. + */ + public abstract void reset(); +} diff --git a/src/main/java/org/jdesktop/j3d/examples/virtual_input_device/SensorBehavior.java b/src/main/java/org/jdesktop/j3d/examples/virtual_input_device/SensorBehavior.java new file mode 100644 index 0000000..0cb0ca6 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/virtual_input_device/SensorBehavior.java @@ -0,0 +1,77 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.virtual_input_device; + +import java.util.Enumeration; + +import org.jogamp.java3d.Behavior; +import org.jogamp.java3d.Sensor; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.WakeupOnElapsedFrames; + +public class SensorBehavior extends Behavior { + + private WakeupOnElapsedFrames conditions = new WakeupOnElapsedFrames(0); + private TransformGroup transformGroup; + private Sensor sensor; + private Transform3D transform = new Transform3D(); + + public SensorBehavior( TransformGroup tg, Sensor sensor ) { + transformGroup = tg; + this.sensor = sensor; + } + + public void initialize() { + wakeupOn( conditions ); + } + + public void processStimulus( Enumeration criteria ) { + sensor.getRead( transform ); + transformGroup.setTransform( transform ); + wakeupOn( conditions ); + } + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/virtual_input_device/VirtualInputDevice.java b/src/main/java/org/jdesktop/j3d/examples/virtual_input_device/VirtualInputDevice.java new file mode 100644 index 0000000..380dae9 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/virtual_input_device/VirtualInputDevice.java @@ -0,0 +1,265 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.virtual_input_device; + +import java.awt.BorderLayout; +import java.awt.Frame; +import java.awt.Panel; + +import org.jogamp.java3d.InputDevice; +import org.jogamp.java3d.Sensor; +import org.jogamp.java3d.SensorRead; +import org.jogamp.java3d.Transform3D; +import org.jogamp.vecmath.Vector3f; + +public class VirtualInputDevice implements InputDevice { + + private Vector3f position = new Vector3f(); + private Transform3D newTransform = new Transform3D(); + Sensor sensors[] = new Sensor[1]; + + // The wheel controls control the view platform orientation + private RotationControls rotControls; + + // The button position controls control the view platform position + private PositionControls positionControls; + + private Transform3D rotTransX = new Transform3D(); + private Transform3D rotTransY = new Transform3D(); + private Transform3D rotTransZ = new Transform3D(); + + private Vector3f initPos = new Vector3f(); + + private int processingMode; + private SensorRead sensorRead = new SensorRead(); + + // These are the settable parameters. + private boolean printvalues; + private int xscreeninitloc; + private int yscreeninitloc; + private int xscreensize; + private int yscreensize; + private float xobjinitloc; + private float yobjinitloc; + private float zobjinitloc; + private float xaxisrotinit; + private float yaxisrotinit; + private float zaxisrotinit; + + /* + * Create a device, and use the string arguments in args to construct + * the device with user preferences. + */ + public VirtualInputDevice( String[] args ) { + + // default user-definable values + printvalues = false; + xscreeninitloc = 400; + yscreeninitloc = 0; + xscreensize = 400; + yscreensize = 200; + xobjinitloc = 0.0f; + yobjinitloc = 0.0f; + zobjinitloc = 2.2f; + xaxisrotinit = 0.0f; + yaxisrotinit = 0.0f; + zaxisrotinit = 0.0f; + + + for(int i=0 ; i<args.length ; i+=2) { + if(args[i] == null) + break; + else if(args[i] == "printvalues") + printvalues = (Boolean.valueOf(args[i+1])).booleanValue(); + else if(args[i] == "xscreeninitloc") + xscreeninitloc = (Integer.valueOf(args[i+1])).intValue(); + else if(args[i] == "yscreeninitloc") + yscreeninitloc = (Integer.valueOf(args[i+1])).intValue(); + else if(args[i] == "xscreensize") + xscreensize = (Integer.valueOf(args[i+1])).intValue(); + else if(args[i] == "yscreensize") + yscreensize = (Integer.valueOf(args[i+1])).intValue(); + else if(args[i] == "xobjinitloc") + xobjinitloc = (Float.valueOf(args[i+1])).floatValue(); + else if(args[i] == "yobjinitloc") + yobjinitloc = (Float.valueOf(args[i+1])).floatValue(); + else if(args[i] == "zobjinitloc") + zobjinitloc = (Integer.valueOf(args[i+1])).floatValue(); + } + + if(printvalues == true) { + System.out.println("Initial values for VirtualInputDevice:"); + System.out.println("xscreeninitloc = " + xscreeninitloc); + System.out.println("yscreeninitloc = " + yscreeninitloc); + System.out.println("xscreeninitsize = " + xscreensize); + System.out.println("yscreeninitsize = " + yscreensize); + System.out.println("xobjinitloc = " + xobjinitloc); + System.out.println("yobjinitloc = " + yobjinitloc); + System.out.println("zobjinitloc = " + zobjinitloc); + System.out.println("xaxisrotinit = " + xaxisrotinit); + System.out.println("yaxisrotinit = " + yaxisrotinit); + System.out.println("zaxisrotinit = " + zaxisrotinit); + } + + + // initialize the InputDevice GUI + Frame deviceFrame = new Frame(); + deviceFrame.setSize(xscreensize,yscreensize); + deviceFrame.setLocation(xscreeninitloc, yscreeninitloc); + deviceFrame.setTitle("Virtual Input Device"); + ButtonPositionControls positionControls; + // initialize position with initial x, y, and z position + positionControls = new ButtonPositionControls( xobjinitloc, + yobjinitloc, zobjinitloc); + WheelControls rotControls; + // initialize rotations with initial angles in radians) + rotControls = new WheelControls(xaxisrotinit, yaxisrotinit, + zaxisrotinit); + positionControls.setDevice (this); + Panel devicePanel = new Panel(); + devicePanel.setLayout( new BorderLayout() ); + devicePanel.add("East", positionControls ); + devicePanel.add("West", rotControls ); + deviceFrame.add( devicePanel ); + deviceFrame.pack(); + deviceFrame.setVisible(true); + + initPos.set(xobjinitloc, yobjinitloc, zobjinitloc); + + this.positionControls = positionControls; + this.rotControls = rotControls; + + // default processing mode + processingMode = InputDevice.DEMAND_DRIVEN; + + sensors[0] = new Sensor(this); + } + + public void close() { + } + + public int getProcessingMode() { + return processingMode; + } + + public int getSensorCount() { + return sensors.length; + } + + public Sensor getSensor( int sensorIndex ) { + return sensors[sensorIndex]; + } + + public boolean initialize() { + return true; + } + + public void pollAndProcessInput() { + + sensorRead.setTime( System.currentTimeMillis() ); + + rotTransX.rotX(-rotControls.getXAngle()); + rotTransY.rotY(-rotControls.getYAngle()); + rotTransZ.rotZ(-rotControls.getZAngle()); + + positionControls.getPosition(position); + newTransform.set(position); + newTransform.mul( rotTransX ); + + newTransform.mul(rotTransY); + newTransform.mul(rotTransZ); + + sensorRead.set( newTransform ); + sensors[0].setNextSensorRead( sensorRead ); + } + + + public void processStreamInput() { + } + + + public void setNominalPositionAndOrientation() { + + sensorRead.setTime( System.currentTimeMillis() ); + + rotTransX.rotX(xaxisrotinit); + rotTransY.rotY(yaxisrotinit); + rotTransZ.rotZ(zaxisrotinit); + + position.set(initPos); + + newTransform.set( position ); + + newTransform.mul(rotTransX); + newTransform.mul(rotTransY); + newTransform.mul(rotTransZ); + + sensorRead.set( newTransform ); + sensors[0].setNextSensorRead( sensorRead ); + rotControls.reset(); + positionControls.setPosition(initPos); + } + + + + public void setProcessingMode( int mode ) { + + // A typical driver might implement only one of these modes, and + // throw an exception when there is an attempt to switch modes. + // However, this example allows one to use any processing mode. + + switch(mode) { + case InputDevice.DEMAND_DRIVEN: + case InputDevice.NON_BLOCKING: + case InputDevice.BLOCKING: + processingMode = mode; + break; + default: + throw new IllegalArgumentException("Processing mode must " + + "be one of DEMAND_DRIVEN, NON_BLOCKING, or BLOCKING"); + } + } + +} diff --git a/src/main/java/org/jdesktop/j3d/examples/virtual_input_device/VirtualInputDeviceTest.java b/src/main/java/org/jdesktop/j3d/examples/virtual_input_device/VirtualInputDeviceTest.java new file mode 100644 index 0000000..281bc63 --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/virtual_input_device/VirtualInputDeviceTest.java @@ -0,0 +1,144 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.virtual_input_device; + +import java.applet.Applet; +import java.awt.BorderLayout; +import java.awt.GraphicsConfiguration; + +import org.jogamp.java3d.Alpha; +import org.jogamp.java3d.BoundingSphere; +import org.jogamp.java3d.BranchGroup; +import org.jogamp.java3d.Canvas3D; +import org.jogamp.java3d.InputDevice; +import org.jogamp.java3d.RotationInterpolator; +import org.jogamp.java3d.Transform3D; +import org.jogamp.java3d.TransformGroup; +import org.jogamp.java3d.utils.applet.MainFrame; +import org.jogamp.java3d.utils.geometry.ColorCube; +import org.jogamp.java3d.utils.universe.SimpleUniverse; +import org.jogamp.vecmath.Point3d; + +public class VirtualInputDeviceTest extends Applet { + + private SimpleUniverse u = null; + + public BranchGroup createSceneGraph() { + + BranchGroup objRoot = new BranchGroup(); + TransformGroup objTrans = new TransformGroup(); + objTrans.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE); + objRoot.addChild(objTrans); + objTrans.addChild(new ColorCube(0.2)); + Transform3D yAxis = new Transform3D(); + Alpha rotationAlpha = new Alpha(-1, Alpha.INCREASING_ENABLE, + 0, 0, + 4000, 0, 0, + 0, 0, 0); + RotationInterpolator rotator = + new RotationInterpolator(rotationAlpha, objTrans, yAxis, + 0.0f, (float) Math.PI*2.0f); + BoundingSphere bounds = + new BoundingSphere(new Point3d(0.0,0.0,0.0), 100.0); + rotator.setSchedulingBounds(bounds); + objTrans.addChild(rotator); + return objRoot; + } + + + public VirtualInputDeviceTest() { + + } + + public void init() {System.setProperty("sun.awt.noerasebackground", "true"); + // These are the string arguments given to the VirtualInputDevice + // constructor. These are settable parameters. Look in the + // VirtualInputDevice constructor for a complete list. + String[] args = new String[10]; + args[0] = "printvalues"; + args[1] = "true"; + args[2] = "yscreeninitloc"; + args[3] = "50"; + args[4] = null; + + InputDevice device = new VirtualInputDevice( args ); + + // now create the VirtualInputDeviceTest Canvas + setLayout(new BorderLayout()); + GraphicsConfiguration config = + SimpleUniverse.getPreferredConfiguration(); + + Canvas3D c = new Canvas3D(config); + add("Center", c); + + // Create a simple scene and attach it to the virtual universe + BranchGroup scene = createSceneGraph(); + u = new SimpleUniverse(c); + + // The InputDevice must be initialized before registering it + // with the PhysicalEnvironment object. + device.initialize(); + + // Register the VirtualInputDevice with Java 3D + u.getViewer().getPhysicalEnvironment().addInputDevice( device ); + + TransformGroup viewTrans = + u.getViewingPlatform().getViewPlatformTransform(); + SensorBehavior s = new SensorBehavior( viewTrans, device.getSensor(0) ); + s.setSchedulingBounds( new BoundingSphere + ( new Point3d(0.0,0.0,0.0), Float.MAX_VALUE )); + scene.addChild( s ); + u.addBranchGraph(scene); + } + + public void destroy() { + u.cleanup(); + } + + + public static void main(String[] args) {System.setProperty("sun.awt.noerasebackground", "true"); + new MainFrame(new VirtualInputDeviceTest(), 350, 350); + } +} diff --git a/src/main/java/org/jdesktop/j3d/examples/virtual_input_device/WheelControls.java b/src/main/java/org/jdesktop/j3d/examples/virtual_input_device/WheelControls.java new file mode 100644 index 0000000..60181af --- /dev/null +++ b/src/main/java/org/jdesktop/j3d/examples/virtual_input_device/WheelControls.java @@ -0,0 +1,410 @@ +/* + * $RCSfile$ + * + * Copyright (c) 2007 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: + * + * - Redistribution 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. + * + * Neither the name of Sun Microsystems, Inc. or the names of + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * This software is provided "AS IS," without a warranty of any + * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND + * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY + * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL + * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF + * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS + * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR + * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, + * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND + * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR + * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + * + * You acknowledge that this software is not designed, licensed or + * intended for use in the design, construction, operation or + * maintenance of any nuclear facility. + * + * $Revision$ + * $Date$ + * $State$ + */ + +package org.jdesktop.j3d.examples.virtual_input_device; + +import java.awt.Canvas; +import java.awt.Color; +import java.awt.Dimension; +import java.awt.Graphics; +import java.awt.Graphics2D; +import java.awt.Point; +import java.awt.Polygon; +import java.awt.Rectangle; +import java.awt.event.MouseEvent; +import java.awt.event.MouseListener; +import java.awt.event.MouseMotionListener; +import java.awt.geom.AffineTransform; + +public class WheelControls extends Canvas implements RotationControls, MouseMotionListener, MouseListener { + + private final static int NONE=0; + private final static int SLIDE_Y=1; + private final static int SLIDE_X=2; + private final static int SLIDE_Z=3; + + private int mode = NONE; + + private Dimension size; + private int thickness; + private int diameter; + private int space; + private int pipSize; + private int pipOffset; // Amount pip is below wheel + private int margin; // Margin between edge of Canvas and + // controls + + private Polygon yPip; + private Rectangle yBackClip; + + private Polygon xPip; + private Rectangle xBackClip; + + private Polygon zPip; + + private Rectangle yArea; + private Rectangle xArea; + private Rectangle zArea; + + private Point oldMousePos = new Point(); + + float yAngle = 0.0f; + float xAngle = 0.0f; + float zAngle = 0.0f; + + float yOrigAngle; + float xOrigAngle; + float zOrigAngle; + + float angleStep = (float)Math.PI/30.0f; + + public WheelControls() { + this(0.0f, 0.0f, 0.0f); + } + + public WheelControls( float rotX, float rotY, float rotZ ) { + size = new Dimension( 200, 200 ); + + xAngle = constrainAngle(rotX); + yAngle = constrainAngle(rotY); + zAngle = constrainAngle(rotZ); + + yOrigAngle = yAngle; + xOrigAngle = xAngle; + zOrigAngle = zAngle; + + setSizes(); + + yPip = new Polygon(); + yPip.addPoint( 0, 0 ); + yPip.addPoint( -pipSize/2, pipSize ); + yPip.addPoint( pipSize/2, pipSize ); + + xPip = new Polygon(); + xPip.addPoint(0,0); + xPip.addPoint( pipSize, -pipSize/2 ); + xPip.addPoint( pipSize, pipSize/2 ); + + zPip = new Polygon(); + zPip.addPoint( diameter/2, pipOffset ); + zPip.addPoint( diameter/2-pipSize/2, pipOffset-pipSize ); + zPip.addPoint( diameter/2+pipSize/2, pipOffset-pipSize ); + + addMouseListener( this ); + addMouseMotionListener( this ); + } + + private void setSizes() { + margin = 10; + int width = size.width - margin*2; + thickness = width * 7 / 100; + diameter = width * 70 / 100; + space = width * 10 / 100; + pipSize = width * 7 / 100; + + pipOffset = thickness/2; + + } + + public void paint( Graphics g ) { + Graphics2D g2 = (Graphics2D)g; + + g.drawOval( margin,margin, diameter, diameter ); + zArea = new Rectangle( margin, margin, diameter, diameter ); + drawZPip( g2, zAngle ); + + g.drawRect( margin, margin+diameter+space, + diameter, thickness ); // Y Wheel + yArea = new Rectangle( margin, margin+diameter+space, margin+diameter, + thickness+pipOffset ); + yBackClip = new Rectangle( margin-thickness, + margin+diameter+space+thickness, + margin+diameter+thickness*2, thickness ); + drawYPip( g2, yAngle ); + + g.drawRect( margin+diameter+space, margin, + thickness, diameter ); // X Wheel + xArea = new Rectangle( margin+diameter+space, margin, + thickness+pipOffset, margin+diameter ); + xBackClip = new Rectangle( margin+diameter+space+thickness, + margin-thickness, + thickness, margin+diameter+thickness*2 ); + drawXPip( g2, xAngle ); + + + } + + public float getXAngle() { + return xAngle; + } + + public float getYAngle() { + return yAngle; + } + + public float getZAngle() { + return zAngle; + } + + + public void reset() { + // Overwrite the old pip + drawYPip( (Graphics2D)(this.getGraphics()), + yAngle ); + yAngle = yOrigAngle; + // Draw the new Pip + drawYPip( (Graphics2D)(this.getGraphics()), + yAngle ); + + // Overwrite the old pip + drawXPip( (Graphics2D)(this.getGraphics()), + xAngle ); + xAngle = xOrigAngle; + // Draw the new Pip + drawXPip( (Graphics2D)(this.getGraphics()), + xAngle ); + + drawZPip( (Graphics2D)(this.getGraphics()), + zAngle ); + + zAngle = zOrigAngle; + + drawZPip( (Graphics2D)(this.getGraphics()), + zAngle ); + oldMousePos.setLocation(0,0); + } + + + private void drawXPip( Graphics2D g2, float angle ) { + AffineTransform trans = new AffineTransform(); + int y; + int xOrig = margin+diameter+space; + int yOrig = margin; + Color origColor = g2.getColor(); + + if (angle <= Math.PI) { + y = yOrig + diameter - (int)((Math.abs( angle-Math.PI/2 )/(Math.PI/2)) * diameter/2); + } else + y = yOrig + (int)((Math.abs( (angle-Math.PI*1.5) )/(Math.PI/2)) * diameter/2); + + if (angle<Math.PI/2 || angle > Math.PI*1.5) + g2.setColor( Color.red ); // Infront of wheel + else { + g2.setColor( Color.black ); // Behind Wheel + g2.setClip( xBackClip ); + } + + g2.setXORMode( getBackground() ); + trans.setToTranslation( xOrig+pipOffset, y ); + g2.setTransform( trans ); + g2.fillPolygon( xPip ); + + // Reset graphics context + trans.setToIdentity(); + g2.setTransform( trans ); + g2.setColor(origColor); + g2.setPaintMode(); + } + + private void drawYPip( Graphics2D g2, float angle ) { + AffineTransform trans = new AffineTransform(); + int x; + int xOrig = margin; + int yOrig = margin+diameter+space; + Color origColor = g2.getColor(); + + if (angle <= Math.PI) { + x = xOrig + diameter - (int)((Math.abs( angle-Math.PI/2 )/(Math.PI/2)) * diameter/2); + } else + x = xOrig + (int)((Math.abs( (angle-Math.PI*1.5) )/(Math.PI/2)) * diameter/2); + + if (angle<Math.PI/2 || angle > Math.PI*1.5) + g2.setColor( Color.red ); // Infront on wheel + else { + g2.setColor( Color.black ); // Behind Wheel + g2.setClip( yBackClip ); + } + + g2.setXORMode( getBackground() ); + trans.setToTranslation( x, yOrig+pipOffset ); + g2.setTransform( trans ); + g2.fillPolygon( yPip ); + + // Reset graphics context + trans.setToIdentity(); + g2.setTransform( trans ); + g2.setColor(origColor); + g2.setPaintMode(); + } + + private void drawZPip( Graphics2D g2, float zAngle ) { + AffineTransform trans = new AffineTransform(); + Color origColor = g2.getColor(); + + trans.translate( margin, margin ); + trans.rotate(zAngle, diameter/2, diameter/2 ); + + g2.setXORMode( getBackground() ); + g2.setTransform(trans); + g2.setColor( Color.red ); + g2.fillPolygon( zPip ); + + // Reset graphics context + trans.setToIdentity(); + g2.setTransform( trans ); + g2.setColor( origColor ); + g2.setPaintMode(); + } + + public Dimension getPreferredSize() { + return size; + } + + public void setSize( Dimension d ) { + // Set size to smallest dimension + if (d.width<d.height) + size.width = size.height = d.width; + else + size.width = size.height = d.height; + setSizes(); + } + + public void mouseClicked( MouseEvent e ) { + } + + public void mouseEntered( MouseEvent e ) { + } + + public void mouseExited( MouseEvent e ) { + } + + public void mousePressed( MouseEvent e ) { + if ( yArea.contains( e.getPoint() )) { + mode = SLIDE_Y; + oldMousePos = e.getPoint(); + } else if (xArea.contains( e.getPoint() )) { + mode = SLIDE_X; + oldMousePos = e.getPoint(); + } else if (zArea.contains( e.getPoint() )) { + mode = SLIDE_Z; + oldMousePos = e.getPoint(); + } + } + + public void mouseReleased( MouseEvent e ) { + mode = NONE; + } + + public void mouseDragged( MouseEvent e ) { + Point pos = e.getPoint(); + + int diffX = pos.x - oldMousePos.x; + int diffY = pos.y - oldMousePos.y; + + switch(mode) { + case NONE: + break; + case SLIDE_Y: + // Overwrite the old pip + drawYPip( (Graphics2D)((Canvas)e.getSource()).getGraphics(), + yAngle ); + if (diffX<0) + yAngle -= angleStep; + else if (diffX>0) + yAngle += angleStep; + + yAngle = constrainAngle(yAngle); + + // Draw the new Pip + drawYPip( (Graphics2D)((Canvas)e.getSource()).getGraphics(), + yAngle ); + oldMousePos = pos; + break; + case SLIDE_X: + // Overwrite the old pip + drawXPip( (Graphics2D)((Canvas)e.getSource()).getGraphics(), + xAngle ); + if (diffY<0) + xAngle -= angleStep; + else if (diffY>0) + xAngle += angleStep; + + xAngle = constrainAngle(xAngle); + + // Draw the new Pip + drawXPip( (Graphics2D)((Canvas)e.getSource()).getGraphics(), + xAngle ); + oldMousePos = pos; + break; + case SLIDE_Z: + drawZPip( (Graphics2D)((Canvas)e.getSource()).getGraphics(), + zAngle ); + + if (diffX<0) + zAngle -= angleStep; + else if (diffX>0) + zAngle += angleStep; + + zAngle = constrainAngle( zAngle ); + drawZPip( (Graphics2D)((Canvas)e.getSource()).getGraphics(), + zAngle ); + oldMousePos = pos; + break; + default: + throw( new RuntimeException("Internal Error")); + } + } + + public void mouseMoved( MouseEvent e ) { + } + + /** + * Constrain angle to be 0<angle<2PI + */ + private float constrainAngle( float angle ) { + if ( angle > (float)Math.PI*2 ) return angle-(float)Math.PI*2; + if ( angle < 0.0f) return angle+(float)Math.PI*2; + return angle; + } +} |