001: /*
002: * $RCSfile: TickTockPicking.java,v $
003: *
004: * Copyright (c) 2007 Sun Microsystems, Inc. All rights reserved.
005: *
006: * Redistribution and use in source and binary forms, with or without
007: * modification, are permitted provided that the following conditions
008: * are met:
009: *
010: * - Redistribution of source code must retain the above copyright
011: * notice, this list of conditions and the following disclaimer.
012: *
013: * - Redistribution in binary form must reproduce the above copyright
014: * notice, this list of conditions and the following disclaimer in
015: * the documentation and/or other materials provided with the
016: * distribution.
017: *
018: * Neither the name of Sun Microsystems, Inc. or the names of
019: * contributors may be used to endorse or promote products derived
020: * from this software without specific prior written permission.
021: *
022: * This software is provided "AS IS," without a warranty of any
023: * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND
024: * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY,
025: * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY
026: * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL
027: * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF
028: * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS
029: * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR
030: * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL,
031: * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND
032: * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR
033: * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE
034: * POSSIBILITY OF SUCH DAMAGES.
035: *
036: * You acknowledge that this software is not designed, licensed or
037: * intended for use in the design, construction, operation or
038: * maintenance of any nuclear facility.
039: *
040: * $Revision: 1.3 $
041: * $Date: 2007/02/09 17:21:49 $
042: * $State: Exp $
043: */
044:
045: package org.jdesktop.j3d.examples.picking;
046:
047: import com.sun.j3d.utils.universe.*;
048: import javax.media.j3d.*;
049: import javax.vecmath.*;
050: import com.sun.j3d.utils.image.TextureLoader;
051: import java.awt.GraphicsConfiguration;
052: import org.jdesktop.j3d.examples.Resources;
053:
054: public class TickTockPicking extends javax.swing.JFrame {
055:
056: private SimpleUniverse univ = null;
057: private BranchGroup scene = null;
058: // path the the texture map image
059: private java.net.URL texImage = null;
060:
061: public BranchGroup createSceneGraph(Canvas3D c) {
062: // Create the root of the branch graph
063: BranchGroup objRoot = new BranchGroup();
064:
065: // Create a Transformgroup to scale all objects so they
066: // appear in the scene.
067: TransformGroup objScale = new TransformGroup();
068: Transform3D t3d = new Transform3D();
069: t3d.setScale(0.4);
070: objScale.setTransform(t3d);
071: objRoot.addChild(objScale);
072:
073: // Create a bounds for the background and behaviors
074: BoundingSphere bounds = new BoundingSphere(new Point3d(0.0,
075: 0.0, 0.0), 100.0);
076:
077: // Set up the background
078: Color3f bgColor = new Color3f(0.05f, 0.05f, 0.2f);
079: Background bg = new Background(bgColor);
080: bg.setApplicationBounds(bounds);
081: objScale.addChild(bg);
082:
083: // Set up the global lights
084: Color3f lColor1 = new Color3f(0.7f, 0.7f, 0.7f);
085: Vector3f lDir1 = new Vector3f(-1.0f, -1.0f, -1.0f);
086: Color3f alColor = new Color3f(0.2f, 0.2f, 0.2f);
087:
088: AmbientLight aLgt = new AmbientLight(alColor);
089: aLgt.setInfluencingBounds(bounds);
090: DirectionalLight lgt1 = new DirectionalLight(lColor1, lDir1);
091: lgt1.setInfluencingBounds(bounds);
092: objScale.addChild(aLgt);
093: objScale.addChild(lgt1);
094:
095: // Create a pair of transform group nodes and initialize them to
096: // identity. Enable the TRANSFORM_WRITE capability so that
097: // our behaviors can modify them at runtime. Add them to the
098: // root of the subgraph.
099: TransformGroup objTrans1 = new TransformGroup();
100: objTrans1.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE);
101: objScale.addChild(objTrans1);
102:
103: TransformGroup objTrans2 = new TransformGroup();
104: objTrans2.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE);
105: objTrans1.addChild(objTrans2);
106:
107: // Create the positioning and scaling transform group node.
108: Transform3D t = new Transform3D();
109: t.set(0.3, new Vector3d(0.0, -1.5, 0.0));
110: TransformGroup objTrans3 = new TransformGroup(t);
111: objTrans2.addChild(objTrans3);
112:
113: // Create a simple shape leaf node, set it's appearance, and
114: // add it to the scene graph.
115: Shape3D shape = new Cube();
116: Appearance a = new Appearance();
117: Color3f black = new Color3f(0.0f, 0.0f, 0.0f);
118: Color3f white = new Color3f(1.0f, 1.0f, 1.0f);
119: Color3f objColor = new Color3f(0.8f, 0.0f, 0.0f);
120: a.setMaterial(new Material(objColor, black, objColor, white,
121: 80.0f));
122: shape.setAppearance(a);
123: shape.setCapability(shape.ALLOW_APPEARANCE_READ);
124: shape.setCapability(shape.ALLOW_APPEARANCE_WRITE);
125: objTrans3.addChild(shape);
126:
127: // Create a new Behavior object that will perform the desired
128: // rotation on the specified transform object and add it into
129: // the scene graph.
130: Transform3D yAxis1 = new Transform3D();
131: yAxis1.rotX(Math.PI / 2.0);
132: Alpha tickTockAlpha = new Alpha(-1, Alpha.INCREASING_ENABLE
133: | Alpha.DECREASING_ENABLE, 0, 0, 5000, 2500, 200, 5000,
134: 2500, 200);
135:
136: RotationInterpolator tickTock = new RotationInterpolator(
137: tickTockAlpha, objTrans1, yAxis1,
138: -(float) Math.PI / 2.0f, (float) Math.PI / 2.0f);
139: tickTock.setSchedulingBounds(bounds);
140: objTrans2.addChild(tickTock);
141:
142: // Create a new Behavior object that will perform the desired
143: // rotation on the specified transform object and add it into
144: // the scene graph.
145: Transform3D yAxis2 = new Transform3D();
146: Alpha rotationAlpha = new Alpha(-1, Alpha.INCREASING_ENABLE, 0,
147: 0, 4000, 0, 0, 0, 0, 0);
148:
149: RotationInterpolator rotator = new RotationInterpolator(
150: rotationAlpha, objTrans2, yAxis2, 0.0f,
151: (float) Math.PI * 2.0f);
152: rotator.setSchedulingBounds(bounds);
153: objTrans2.addChild(rotator);
154:
155: // Now create the simple picking behavior
156: PickHighlightBehavior pickBeh = new PickHighlightBehavior(c,
157: objRoot, bounds);
158:
159: // Create a bunch of objects with a behavior and add them
160: // into the scene graph.
161:
162: int row, col;
163: Appearance[][] app = new Appearance[3][3];
164:
165: for (row = 0; row < 3; row++)
166: for (col = 0; col < 3; col++)
167: app[row][col] = createAppearance(row * 3 + col);
168:
169: for (int i = 0; i < 3; i++) {
170: double ypos = (double) (i - 1) * 1.5;
171: for (int j = 0; j < 3; j++) {
172: double xpos = (double) (j - 1) * 1.5;
173: objScale.addChild(createObject(app[i][j], 0.3, xpos,
174: ypos));
175: }
176: }
177:
178: // Have Java 3D perform optimizations on this scene graph.
179: objRoot.compile();
180:
181: return objRoot;
182: }
183:
184: private Appearance createAppearance(int idx) {
185: Appearance app = new Appearance();
186:
187: // Globally used colors
188: Color3f black = new Color3f(0.0f, 0.0f, 0.0f);
189: Color3f white = new Color3f(1.0f, 1.0f, 1.0f);
190:
191: switch (idx) {
192: // Unlit solid
193: case 0: {
194: // Set up the coloring properties
195: Color3f objColor = new Color3f(1.0f, 0.2f, 0.4f);
196: ColoringAttributes ca = new ColoringAttributes();
197: ca.setColor(objColor);
198: app.setColoringAttributes(ca);
199: break;
200: }
201:
202: // Unlit wire frame
203: case 1: {
204: // Set up the coloring properties
205: Color3f objColor = new Color3f(1.0f, 0.4f, 0.0f);
206: ColoringAttributes ca = new ColoringAttributes();
207: ca.setColor(objColor);
208: app.setColoringAttributes(ca);
209:
210: // Set up the polygon attributes
211: PolygonAttributes pa = new PolygonAttributes();
212: pa.setPolygonMode(pa.POLYGON_LINE);
213: pa.setCullFace(pa.CULL_NONE);
214: app.setPolygonAttributes(pa);
215: break;
216: }
217:
218: // Unlit points
219: case 2: {
220: // Set up the coloring properties
221: Color3f objColor = new Color3f(1.0f, 1.0f, 0.0f);
222: ColoringAttributes ca = new ColoringAttributes();
223: ca.setColor(objColor);
224: app.setColoringAttributes(ca);
225:
226: // Set up the polygon attributes
227: PolygonAttributes pa = new PolygonAttributes();
228: pa.setPolygonMode(pa.POLYGON_POINT);
229: pa.setCullFace(pa.CULL_NONE);
230: app.setPolygonAttributes(pa);
231:
232: // Set up point attributes
233: PointAttributes pta = new PointAttributes();
234: pta.setPointSize(5.0f);
235: app.setPointAttributes(pta);
236: break;
237: }
238:
239: // Lit solid
240: case 3: {
241: // Set up the material properties
242: Color3f objColor = new Color3f(0.8f, 0.0f, 0.0f);
243: app.setMaterial(new Material(objColor, black, objColor,
244: white, 80.0f));
245: break;
246: }
247:
248: // Texture mapped, lit solid
249: case 4: {
250: // Set up the texture map
251: TextureLoader tex = new TextureLoader(texImage, this );
252: app.setTexture(tex.getTexture());
253:
254: TextureAttributes texAttr = new TextureAttributes();
255: texAttr.setTextureMode(TextureAttributes.MODULATE);
256: app.setTextureAttributes(texAttr);
257:
258: // Set up the material properties
259: app.setMaterial(new Material(white, black, white, black,
260: 1.0f));
261: break;
262: }
263:
264: // Transparent, lit solid
265: case 5: {
266: // Set up the transparency properties
267: TransparencyAttributes ta = new TransparencyAttributes();
268: ta.setTransparencyMode(ta.BLENDED);
269: ta.setTransparency(0.6f);
270: app.setTransparencyAttributes(ta);
271:
272: // Set up the polygon attributes
273: PolygonAttributes pa = new PolygonAttributes();
274: pa.setCullFace(pa.CULL_NONE);
275: app.setPolygonAttributes(pa);
276:
277: // Set up the material properties
278: Color3f objColor = new Color3f(0.7f, 0.8f, 1.0f);
279: app.setMaterial(new Material(objColor, black, objColor,
280: black, 1.0f));
281: break;
282: }
283:
284: // Lit solid, no specular
285: case 6: {
286: // Set up the material properties
287: Color3f objColor = new Color3f(0.8f, 0.0f, 0.0f);
288: app.setMaterial(new Material(objColor, black, objColor,
289: black, 80.0f));
290: break;
291: }
292:
293: // Lit solid, specular only
294: case 7: {
295: // Set up the material properties
296: Color3f objColor = new Color3f(0.8f, 0.0f, 0.0f);
297: app.setMaterial(new Material(black, black, black, white,
298: 80.0f));
299: break;
300: }
301:
302: // Another lit solid with a different color
303: case 8: {
304: // Set up the material properties
305: Color3f objColor = new Color3f(0.8f, 0.8f, 0.0f);
306: app.setMaterial(new Material(objColor, black, objColor,
307: white, 80.0f));
308: break;
309: }
310:
311: default: {
312: ColoringAttributes ca = new ColoringAttributes();
313: ca.setColor(new Color3f(0.0f, 1.0f, 0.0f));
314: app.setColoringAttributes(ca);
315: }
316: }
317:
318: return app;
319: }
320:
321: private Group createObject(Appearance app, double scale,
322: double xpos, double ypos) {
323:
324: // Create a transform group node to scale and position the object.
325: Transform3D t = new Transform3D();
326: t.set(scale, new Vector3d(xpos, ypos, 0.0));
327: TransformGroup objTrans = new TransformGroup(t);
328:
329: // Create a second transform group node and initialize it to the
330: // identity. Enable the TRANSFORM_WRITE capability so that
331: // our behavior code can modify it at runtime.
332: TransformGroup spinTg = new TransformGroup();
333: spinTg.setCapability(TransformGroup.ALLOW_TRANSFORM_WRITE);
334: spinTg.setCapability(TransformGroup.ALLOW_TRANSFORM_READ);
335:
336: // Create a simple shape leaf node and set the appearance
337: Shape3D shape = new Tetrahedron();
338: shape.setAppearance(app);
339: shape.setCapability(shape.ALLOW_APPEARANCE_READ);
340: shape.setCapability(shape.ALLOW_APPEARANCE_WRITE);
341:
342: // add it to the scene graph.
343: spinTg.addChild(shape);
344:
345: // Create a new Behavior object that will perform the desired
346: // operation on the specified transform object and add it into
347: // the scene graph.
348: Transform3D yAxis = new Transform3D();
349: Alpha rotationAlpha = new Alpha(-1, Alpha.INCREASING_ENABLE, 0,
350: 0, 5000, 0, 0, 0, 0, 0);
351:
352: RotationInterpolator rotator = new RotationInterpolator(
353: rotationAlpha, spinTg, yAxis, 0.0f,
354: (float) Math.PI * 2.0f);
355:
356: BoundingSphere bounds = new BoundingSphere(new Point3d(0.0,
357: 0.0, 0.0), 100.0);
358:
359: rotator.setSchedulingBounds(bounds);
360:
361: // Add the behavior and the transform group to the object
362: objTrans.addChild(rotator);
363: objTrans.addChild(spinTg);
364:
365: return objTrans;
366: }
367:
368: private Canvas3D createUniverse() {
369: // Get the preferred graphics configuration for the default screen
370: GraphicsConfiguration config = SimpleUniverse
371: .getPreferredConfiguration();
372:
373: // Create a Canvas3D using the preferred configuration
374: Canvas3D c = new Canvas3D(config);
375:
376: // Create simple universe with view branch
377: univ = new SimpleUniverse(c);
378:
379: // This will move the ViewPlatform back a bit so the
380: // objects in the scene can be viewed.
381: univ.getViewingPlatform().setNominalViewingTransform();
382:
383: // Ensure at least 5 msec per frame (i.e., < 200Hz)
384: univ.getViewer().getView().setMinimumFrameCycleTime(5);
385:
386: return c;
387: }
388:
389: /**
390: * Creates new form HelloUniverse
391: */
392: public TickTockPicking() {
393:
394: // the path to the image for an applet
395: texImage = Resources.getResource("resources/images/stone.jpg");
396: if (texImage == null) {
397: System.err.println("resources/images/stone.jpg not found");
398: System.exit(1);
399: }
400: // Initialize the GUI components
401: initComponents();
402:
403: // Create Canvas3D and SimpleUniverse; add canvas to drawing panel
404: Canvas3D c = createUniverse();
405: drawingPanel.add(c, java.awt.BorderLayout.CENTER);
406:
407: // Create the content branch and add it to the universe
408: scene = createSceneGraph(c);
409: univ.addBranchGraph(scene);
410: }
411:
412: // ----------------------------------------------------------------
413:
414: /** This method is called from within the constructor to
415: * initialize the form.
416: * WARNING: Do NOT modify this code. The content of this method is
417: * always regenerated by the Form Editor.
418: */
419: // <editor-fold defaultstate="collapsed" desc=" Generated Code ">//GEN-BEGIN:initComponents
420: private void initComponents() {
421: drawingPanel = new javax.swing.JPanel();
422:
423: setDefaultCloseOperation(javax.swing.WindowConstants.EXIT_ON_CLOSE);
424: setTitle("TickTockPicking");
425: drawingPanel.setLayout(new java.awt.BorderLayout());
426:
427: drawingPanel.setPreferredSize(new java.awt.Dimension(700, 700));
428: getContentPane()
429: .add(drawingPanel, java.awt.BorderLayout.CENTER);
430:
431: pack();
432: }// </editor-fold>//GEN-END:initComponents
433:
434: /**
435: * @param args the command line arguments
436: */
437: public static void main(String args[]) {
438: java.awt.EventQueue.invokeLater(new Runnable() {
439: public void run() {
440: new TickTockPicking().setVisible(true);
441: }
442: });
443: }
444:
445: // Variables declaration - do not modify//GEN-BEGIN:variables
446: private javax.swing.JPanel drawingPanel;
447: // End of variables declaration//GEN-END:variables
448:
449: }
|