The Sound of ShootingJava 3D has three kinds of sound node classes. All three are subclasses of the Sound class.
Before sound nodes can be added to a scene, an audio device must be created and linked to the Viewer object. This is simple if the SimpleUniverse utility class is being used (as in this example): AudioDevice audioDev = su.getViewer( ).createAudioDevice( );
SimpleUniverse was introduced in Chapter 14; it builds the view branch part of the scene graph, which specifies how the user's viewpoint is positioned in the world and includes the Viewer object. WrapShooter3D uses initSound( ) to load a WAV sound file and create a PointSound object: private PointSound initSound(String filename) { MediaContainer soundMC = null; try { soundMC = new MediaContainer("file:sounds/" + filename); soundMC.setCacheEnable(true); // load sound into container } catch (Exception ex) { System.out.println(ex); } // create a point sound PointSound ps = new PointSound( ); ps.setSchedulingBounds( bounds ); ps.setSoundData( soundMC ); ps.setInitialGain(1.0f); // full on sound from the start // allow sound to be switched on/off & its position to be moved ps.setCapability(PointSound.ALLOW_ENABLE_WRITE); ps.setCapability(PointSound.ALLOW_POSITION_WRITE); System.out.println("PointSound created from sounds/" + filename); return ps; } // end of initSound( ) A Sound node needs a sound source, which is loaded with a MediaContainer object. Loading can be done from a URL, local file, or input stream; the try/catch block handles invalid filenames, as well as problems with opening files. initSound( ) loads its sound from a local file in the subdirectory sounds/. All Sound nodes must be given a bounding region and assigned a sound source: PointSound ps = new PointSound( ); ps.setSchedulingBounds( bounds ); ps.setSoundData( soundMC ); To play, the sound node must be enabled with setEnable( ). initSound( ) doesn't call setEnable( ) since the sound isn't played when first loaded. Instead, the node's capability bits are set to allow it to be enabled and disabled during execution: ps.setCapability(PointSound.ALLOW_ENABLE_WRITE); The explosion sound will be positioned at runtime, requiring another capability bit: ps.setCapability(PointSound.ALLOW_POSITION_WRITE); Other sound elements include setting the volume and saying whether the sound should loop (and if so, then how many times). The relevant methods are: void setInitialGain(float volume); void setLoop(int loopTimes); initSound( ) sets the volume to 1.0f (full-on) and uses the default looping behavior (play once, finish). PointSound nodes have a location in space, given by setPosition( ). They emit sound in all directions, so attenuation factors can be specified in a similar way to Java 3D PointLight nodes.
|