< prev index next >

src/java.desktop/share/classes/com/sun/media/sound/DirectAudioDevice.java

Print this page

        

@@ -27,39 +27,39 @@
 
 import java.io.ByteArrayOutputStream;
 import java.io.IOException;
 import java.util.Vector;
 
-import javax.sound.sampled.*;
+import javax.sound.sampled.AudioFormat;
+import javax.sound.sampled.AudioInputStream;
+import javax.sound.sampled.AudioSystem;
+import javax.sound.sampled.BooleanControl;
+import javax.sound.sampled.Clip;
+import javax.sound.sampled.Control;
+import javax.sound.sampled.DataLine;
+import javax.sound.sampled.FloatControl;
+import javax.sound.sampled.Line;
+import javax.sound.sampled.LineUnavailableException;
+import javax.sound.sampled.SourceDataLine;
+import javax.sound.sampled.TargetDataLine;
 
 // IDEA:
 // Use java.util.concurrent.Semaphore,
 // java.util.concurrent.locks.ReentrantLock and other new classes/methods
 // to improve this class's thread safety.
 
-
 /**
- * A Mixer which provides direct access to audio devices
+ * A Mixer which provides direct access to audio devices.
  *
  * @author Florian Bomers
  */
 final class DirectAudioDevice extends AbstractMixer {
 
-    // CONSTANTS
     private static final int CLIP_BUFFER_TIME = 1000; // in milliseconds
 
     private static final int DEFAULT_LINE_BUFFER_TIME = 500; // in milliseconds
 
-    // INSTANCE VARIABLES
-
-    /** number of opened lines */
-    private int deviceCountOpened = 0;
-
-    /** number of started lines */
-    private int deviceCountStarted = 0;
-
-    // CONSTRUCTOR
     DirectAudioDevice(DirectAudioDeviceProvider.DirectAudioDeviceInfo portMixerInfo) {
         // pass in Line.Info, mixer, controls
         super(portMixerInfo,              // Mixer.Info
               null,                       // Control[]
               null,                       // Line.Info[] sourceLineInfo

@@ -166,10 +166,11 @@
         return null;
     }
 
     // ABSTRACT MIXER: ABSTRACT METHOD IMPLEMENTATIONS
 
+    @Override
     public Line getLine(Line.Info info) throws LineUnavailableException {
         Line.Info fullInfo = getLineInfo(info);
         if (fullInfo == null) {
             throw new IllegalArgumentException("Line unsupported: " + info);
         }

@@ -214,11 +215,11 @@
             }
         }
         throw new IllegalArgumentException("Line unsupported: " + info);
     }
 
-
+    @Override
     public int getMaxLines(Line.Info info) {
         Line.Info fullInfo = getLineInfo(info);
 
         // if it's not supported at all, return 0.
         if (fullInfo == null) {

@@ -231,30 +232,30 @@
         }
 
         return 0;
     }
 
-
+    @Override
     protected void implOpen() throws LineUnavailableException {
         if (Printer.trace) Printer.trace("DirectAudioDevice: implOpen - void method");
     }
 
+    @Override
     protected void implClose() {
         if (Printer.trace) Printer.trace("DirectAudioDevice: implClose - void method");
     }
 
+    @Override
     protected void implStart() {
         if (Printer.trace) Printer.trace("DirectAudioDevice: implStart - void method");
     }
 
+    @Override
     protected void implStop() {
         if (Printer.trace) Printer.trace("DirectAudioDevice: implStop - void method");
     }
 
-
-    // IMPLEMENTATION HELPERS
-
     int getMixerIndex() {
         return ((DirectAudioDeviceProvider.DirectAudioDeviceInfo) getMixerInfo()).getIndex();
     }
 
     int getDeviceID() {

@@ -317,16 +318,10 @@
                                    format.getFrameSize(), format.getFrameRate(), format.isBigEndian());
         }
         return null;
     }
 
-
-
-
-    // INNER CLASSES
-
-
     /**
      * Private inner class for the DataLine.Info objects
      * adds a little magic for the isFormatSupported so
      * that the automagic conversion of endianness and sign
      * does not show up in the formats array.

@@ -365,11 +360,11 @@
              return hardwareFormats;
          }
     }
 
     /**
-     * Private inner class as base class for direct lines
+     * Private inner class as base class for direct lines.
      */
     private static class DirectDL extends AbstractDataLine implements EventDispatcher.LineMonitor {
         protected final int mixerIndex;
         protected final int deviceID;
         protected long id;

@@ -395,11 +390,10 @@
         protected volatile boolean noService = false; // do not run the nService method
 
         // Guards all native calls.
         protected final Object lockNative = new Object();
 
-        // CONSTRUCTOR
         protected DirectDL(DataLine.Info info,
                            DirectAudioDevice mixer,
                            AudioFormat format,
                            int bufferSize,
                            int mixerIndex,

@@ -412,15 +406,11 @@
             this.waitTime = 10; // 10 milliseconds default wait time
             this.isSource = isSource;
 
         }
 
-
-        // ABSTRACT METHOD IMPLEMENTATIONS
-
-        // ABSTRACT LINE / DATALINE
-
+        @Override
         void implOpen(AudioFormat format, int bufferSize) throws LineUnavailableException {
             if (Printer.trace) Printer.trace(">> DirectDL: implOpen("+format+", "+bufferSize+" bytes)");
 
             // $$fb part of fix for 4679187: Clip.open() throws unexpected Exceptions
             Toolkit.isFullySpecifiedAudioFormat(format);

@@ -536,11 +526,11 @@
             calcVolume();
 
             if (Printer.trace) Printer.trace("<< DirectDL: implOpen() succeeded");
         }
 
-
+        @Override
         void implStart() {
             if (Printer.trace) Printer.trace(" >> DirectDL: implStart()");
 
             // check for record permission
             if (!isSource) {

@@ -568,10 +558,11 @@
             }
 
             if (Printer.trace) Printer.trace("<< DirectDL: implStart() succeeded");
         }
 
+        @Override
         void implStop() {
             if (Printer.trace) Printer.trace(">> DirectDL: implStop()");
 
             // check for record permission
             if (!isSource) {

@@ -598,10 +589,11 @@
             stoppedWritten = false;
 
             if (Printer.trace) Printer.trace(" << DirectDL: implStop() succeeded");
         }
 
+        @Override
         void implClose() {
             if (Printer.trace) Printer.trace(">> DirectDL: implClose()");
 
             // check for record permission
             if (!isSource) {

@@ -623,12 +615,11 @@
             bytePosition = 0;
             softwareConversionSize = 0;
             if (Printer.trace) Printer.trace("<< DirectDL: implClose() succeeded");
         }
 
-        // METHOD OVERRIDES
-
+        @Override
         public int available() {
             if (id == 0) {
                 return 0;
             }
             int a;

@@ -636,11 +627,11 @@
                 a = nAvailable(id, isSource);
             }
             return a;
         }
 
-
+        @Override
         public void drain() {
             noService = true;
             // additional safeguard against draining forever
             // this occurred on Solaris 8 x86, probably due to a bug
             // in the audio driver

@@ -679,10 +670,11 @@
                 drained = true;
             }
             noService = false;
         }
 
+        @Override
         public void flush() {
             if (id != 0) {
                 // first stop ongoing read/write method
                 flushing = true;
                 synchronized(lock) {

@@ -697,10 +689,11 @@
                 drained = true;
             }
         }
 
         // replacement for getFramePosition (see AbstractDataLine)
+        @Override
         public long getLongFramePosition() {
             long pos;
             synchronized (lockNative) {
                 pos = nGetBytePosition(id, isSource, bytePosition);
             }

@@ -711,11 +704,10 @@
                 pos = 0;
             }
             return (pos / getFormat().getFrameSize());
         }
 
-
         /*
          * write() belongs into SourceDataLine and Clip,
          * so define it here and make it accessible by
          * declaring the respective interfaces with DirectSDL and DirectClip
          */

@@ -784,10 +776,11 @@
         protected boolean requiresServicing() {
             return nRequiresServicing(id, isSource);
         }
 
         // called from event dispatcher for lines that need servicing
+        @Override
         public void checkLine() {
             synchronized (lockNative) {
                 if (monitoring
                         && doIO
                         && id != 0

@@ -824,11 +817,10 @@
                     rightGain = gain;
                 }
             }
         }
 
-
         /////////////////// CONTROLS /////////////////////////////
 
         protected final class Gain extends FloatControl {
 
             private float linearGain = 1.0f;

@@ -842,10 +834,11 @@
                       -1,
                       0.0f,
                       "dB", "Minimum", "", "Maximum");
             }
 
+            @Override
             public void setValue(float newValue) {
                 // adjust value within range ?? spec says IllegalArgumentException
                 //newValue = Math.min(newValue, getMaximum());
                 //newValue = Math.max(newValue, getMinimum());
 

@@ -859,17 +852,17 @@
             float getLinearGain() {
                 return linearGain;
             }
         } // class Gain
 
-
         private final class Mute extends BooleanControl {
 
             private Mute() {
                 super(BooleanControl.Type.MUTE, false, "True", "False");
             }
 
+            @Override
             public void setValue(boolean newValue) {
                 super.setValue(newValue);
                 calcVolume();
             }
         }  // class Mute

@@ -879,10 +872,11 @@
             private Balance() {
                 super(FloatControl.Type.BALANCE, -1.0f, 1.0f, (1.0f / 128.0f), -1, 0.0f,
                       "", "Left", "Center", "Right");
             }
 
+            @Override
             public void setValue(float newValue) {
                 setValueImpl(newValue);
                 panControl.setValueImpl(newValue);
                 calcVolume();
             }

@@ -898,32 +892,28 @@
             private Pan() {
                 super(FloatControl.Type.PAN, -1.0f, 1.0f, (1.0f / 128.0f), -1, 0.0f,
                       "", "Left", "Center", "Right");
             }
 
+            @Override
             public void setValue(float newValue) {
                 setValueImpl(newValue);
                 balanceControl.setValueImpl(newValue);
                 calcVolume();
             }
             void setValueImpl(float newValue) {
                 super.setValue(newValue);
             }
         } // class Pan
-
-
-
     } // class DirectDL
 
-
     /**
-     * Private inner class representing a SourceDataLine
+     * Private inner class representing a SourceDataLine.
      */
     private static final class DirectSDL extends DirectDL
             implements SourceDataLine {
 
-        // CONSTRUCTOR
         private DirectSDL(DataLine.Info info,
                           AudioFormat format,
                           int bufferSize,
                           DirectAudioDevice mixer) {
             super(info, mixer, format, bufferSize, mixer.getMixerIndex(), mixer.getDeviceID(), true);

@@ -931,26 +921,24 @@
         }
 
     }
 
     /**
-     * Private inner class representing a TargetDataLine
+     * Private inner class representing a TargetDataLine.
      */
     private static final class DirectTDL extends DirectDL
             implements TargetDataLine {
 
-        // CONSTRUCTOR
         private DirectTDL(DataLine.Info info,
                           AudioFormat format,
                           int bufferSize,
                           DirectAudioDevice mixer) {
             super(info, mixer, format, bufferSize, mixer.getMixerIndex(), mixer.getDeviceID(), false);
             if (Printer.trace) Printer.trace("DirectTDL CONSTRUCTOR: completed");
         }
 
-        // METHOD OVERRIDES
-
+        @Override
         public int read(byte[] b, int off, int len) {
             flushing = false;
             if (len == 0) {
                 return 0;
             }

@@ -1028,21 +1016,21 @@
         private int loopEndFrame;      // the last sample included in the loop
 
         // auto closing clip support
         private boolean autoclosing = false;
 
-        // CONSTRUCTOR
         private DirectClip(DataLine.Info info,
                            AudioFormat format,
                            int bufferSize,
                            DirectAudioDevice mixer) {
             super(info, mixer, format, bufferSize, mixer.getMixerIndex(), mixer.getDeviceID(), true);
             if (Printer.trace) Printer.trace("DirectClip CONSTRUCTOR: completed");
         }
 
         // CLIP METHODS
 
+        @Override
         public void open(AudioFormat format, byte[] data, int offset, int bufferSize)
             throws LineUnavailableException {
 
             // $$fb part of fix for 4679187: Clip.open() throws unexpected Exceptions
             Toolkit.isFullySpecifiedAudioFormat(format);

@@ -1109,11 +1097,11 @@
                 getEventDispatcher().autoClosingClipOpened(this);
             }
             if (Printer.trace) Printer.trace("< DirectClip.open completed");
         }
 
-
+        @Override
         public void open(AudioInputStream stream) throws LineUnavailableException, IOException {
 
             // $$fb part of fix for 4679187: Clip.open() throws unexpected Exceptions
             Toolkit.isFullySpecifiedAudioFormat(format);
 

@@ -1176,21 +1164,21 @@
 
                 if (Printer.trace) Printer.trace("< DirectClip.open(stream) succeeded");
             } // synchronized
         }
 
-
+        @Override
         public int getFrameLength() {
             return m_lengthInFrames;
         }
 
-
+        @Override
         public long getMicrosecondLength() {
             return Toolkit.frames2micros(getFormat(), getFrameLength());
         }
 
-
+        @Override
         public void setFramePosition(int frames) {
             if (Printer.trace) Printer.trace("> DirectClip: setFramePosition: " + frames);
 
             if (frames < 0) {
                 frames = 0;

@@ -1227,10 +1215,11 @@
                                              +" getLongFramePosition()="+getLongFramePosition());
             if (Printer.trace) Printer.trace("< DirectClip: setFramePosition");
         }
 
         // replacement for getFramePosition (see AbstractDataLine)
+        @Override
         public long getLongFramePosition() {
             /* $$fb
              * this would be intuitive, but the definition of getFramePosition
              * is the number of frames rendered since opening the device...
              * That also means that setFramePosition() means something very

@@ -1241,20 +1230,21 @@
             //return newFramePosition;
             //}
             return super.getLongFramePosition();
         }
 
-
+        @Override
         public synchronized void setMicrosecondPosition(long microseconds) {
             if (Printer.trace) Printer.trace("> DirectClip: setMicrosecondPosition: " + microseconds);
 
             long frames = Toolkit.micros2frames(getFormat(), microseconds);
             setFramePosition((int) frames);
 
             if (Printer.trace) Printer.trace("< DirectClip: setMicrosecondPosition succeeded");
         }
 
+        @Override
         public void setLoopPoints(int start, int end) {
             if (Printer.trace) Printer.trace("> DirectClip: setLoopPoints: start: " + start + " end: " + end);
 
             if (start < 0 || start >= getFrameLength()) {
                 throw new IllegalArgumentException("illegal value for start: "+start);

@@ -1281,31 +1271,29 @@
 
             if (Printer.trace) Printer.trace("  loopStart: " + loopStartFrame + " loopEnd: " + loopEndFrame);
             if (Printer.trace) Printer.trace("< DirectClip: setLoopPoints completed");
         }
 
-
+        @Override
         public void loop(int count) {
             // note: when count reaches 0, it means that the entire clip
             // will be played, i.e. it will play past the loop end point
             loopCount = count;
             start();
         }
 
-        // ABSTRACT METHOD IMPLEMENTATIONS
-
-        // ABSTRACT LINE
-
+        @Override
         void implOpen(AudioFormat format, int bufferSize) throws LineUnavailableException {
             // only if audioData wasn't set in a calling open(format, byte[], frameSize)
             // this call is allowed.
             if (audioData == null) {
                 throw new IllegalArgumentException("illegal call to open() in interface Clip");
             }
             super.implOpen(format, bufferSize);
         }
 
+        @Override
         void implClose() {
             if (Printer.trace) Printer.trace(">> DirectClip: implClose()");
 
             // dispose of thread
             Thread oldThread = thread;

@@ -1331,17 +1319,18 @@
             getEventDispatcher().autoClosingClipClosed(this);
 
             if (Printer.trace) Printer.trace("<< DirectClip: implClose() succeeded");
         }
 
-
+        @Override
         void implStart() {
             if (Printer.trace) Printer.trace("> DirectClip: implStart()");
             super.implStart();
             if (Printer.trace) Printer.trace("< DirectClip: implStart() succeeded");
         }
 
+        @Override
         void implStop() {
             if (Printer.trace) Printer.trace(">> DirectClip: implStop()");
 
             super.implStop();
             // reset loopCount field so that playback will be normal with

@@ -1349,12 +1338,12 @@
             loopCount = 0;
 
             if (Printer.trace) Printer.trace("<< DirectClip: implStop() succeeded");
         }
 
-
         // main playback loop
+        @Override
         public void run() {
             if (Printer.trace) Printer.trace(">>> DirectClip: run() threadID="+Thread.currentThread().getId());
             while (thread != null) {
                 // doIO is volatile, but we could check it, then get
                 // pre-empted while another thread changes doIO and notifies,

@@ -1416,14 +1405,16 @@
         /* $$mp 2003-10-01
            The following two methods are common between this class and
            MixerClip. They should be moved to a base class, together
            with the instance variable 'autoclosing'. */
 
+        @Override
         public boolean isAutoClosing() {
             return autoclosing;
         }
 
+        @Override
         public void setAutoClosing(boolean value) {
             if (value != autoclosing) {
                 if (isOpen()) {
                     if (value) {
                         getEventDispatcher().autoClosingClipOpened(this);

@@ -1433,10 +1424,11 @@
                 }
                 autoclosing = value;
             }
         }
 
+        @Override
         protected boolean requiresServicing() {
             // no need for servicing for Clips
             return false;
         }
 

@@ -1486,7 +1478,6 @@
 
     // returns if the native implementation needs regular calls to nService()
     private static native boolean nRequiresServicing(long id, boolean isSource);
     // called in irregular intervals
     private static native void nService(long id, boolean isSource);
-
 }
< prev index next >