10 *
11 * This code is distributed in the hope that it will be useful, but WITHOUT
12 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
13 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
14 * version 2 for more details (a copy is included in the LICENSE file that
15 * accompanied this code).
16 *
17 * You should have received a copy of the GNU General Public License version
18 * 2 along with this work; if not, write to the Free Software Foundation,
19 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
20 *
21 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
22 * or visit www.oracle.com if you need additional information or have any
23 * questions.
24 */
25
26 package com.sun.media.sound;
27
28 import java.util.Arrays;
29
30 import javax.sound.sampled.*;
31
32 /**
33 * Class to write an AudioInputStream to a SourceDataLine.
34 * Was previously an inner class in various classes like JavaSoundAudioClip
35 * and sun.audio.AudioDevice.
36 * It auto-opens and closes the SourceDataLine.
37 *
38 * @author Kara Kytle
39 * @author Florian Bomers
40 */
41
42 public final class DataPusher implements Runnable {
43
44 private static final int AUTO_CLOSE_TIME = 5000;
45 private static final boolean DEBUG = false;
46
47 private final SourceDataLine source;
48 private final AudioFormat format;
49
50 // stream as source data
108 }
109 if (DEBUG || Printer.trace)Printer.trace("DataPusher: source.flush()");
110 source.flush();
111 if (DEBUG || Printer.trace)Printer.trace("DataPusher: source.start()");
112 source.start();
113 if (pushThread == null) {
114 if (DEBUG || Printer.debug) Printer.debug("DataPusher.start(): Starting push");
115 pushThread = JSSecurityManager.createThread(this,
116 null, // name
117 false, // daemon
118 -1, // priority
119 true); // doStart
120 }
121 notifyAll();
122 } catch (Exception e) {
123 if (DEBUG || Printer.err) e.printStackTrace();
124 }
125 if (DEBUG || Printer.debug) Printer.debug("< DataPusher.start(loop="+loop+")");
126 }
127
128
129 public synchronized void stop() {
130 if (DEBUG || Printer.debug) Printer.debug("> DataPusher.stop()");
131 if (threadState == STATE_STOPPING
132 || threadState == STATE_STOPPED
133 || pushThread == null) {
134 if (DEBUG || Printer.debug) Printer.debug("DataPusher.stop(): nothing to do");
135 return;
136 }
137 if (DEBUG || Printer.debug) Printer.debug("DataPusher.stop(): Stopping push");
138
139 wantedState = STATE_WAITING;
140 if (source != null) {
141 if (DEBUG || Printer.trace)Printer.trace("DataPusher: source.flush()");
142 source.flush();
143 }
144 notifyAll();
145 int maxWaitCount = 50; // 5 seconds
146 while ((maxWaitCount-- >= 0) && (threadState == STATE_PLAYING)) {
147 try {
148 wait(100);
149 } catch (InterruptedException e) { }
150 }
151 if (DEBUG || Printer.debug) Printer.debug("< DataPusher.stop()");
152 }
153
154 synchronized void close() {
155 if (source != null) {
156 if (DEBUG || Printer.trace)Printer.trace("DataPusher.close(): source.close()");
157 source.close();
158 }
159 }
160
161 /**
162 * Write data to the source data line.
163 */
164 public void run() {
165 byte[] buffer = null;
166 boolean useStream = (ais != null);
167 if (useStream) {
168 buffer = new byte[BUFFER_SIZE];
169 } else {
170 buffer = audioData;
171 }
172 while (wantedState != STATE_STOPPING) {
173 //try {
174 if (wantedState == STATE_WAITING) {
175 // wait for 5 seconds - maybe the clip is to be played again
176 if (DEBUG || Printer.debug)Printer.debug("DataPusher.run(): waiting 5 seconds");
177 try {
178 synchronized(this) {
179 threadState = STATE_WAITING;
180 wantedState = STATE_STOPPING;
181 wait(AUTO_CLOSE_TIME);
182 }
183 } catch (InterruptedException ie) {}
225 pos += bytesWritten;
226 if (DEBUG || Printer.debug) Printer.debug("< DataPusher.run(): Wrote " + bytesWritten + " bytes");
227 }
228 threadState = STATE_STOPPING;
229 if (DEBUG || Printer.debug)Printer.debug("DataPusher: closing device");
230 if (Printer.trace)Printer.trace("DataPusher: source.flush()");
231 source.flush();
232 if (DEBUG || Printer.trace)Printer.trace("DataPusher: source.stop()");
233 source.stop();
234 if (DEBUG || Printer.trace)Printer.trace("DataPusher: source.flush()");
235 source.flush();
236 if (DEBUG || Printer.trace)Printer.trace("DataPusher: source.close()");
237 source.close();
238 threadState = STATE_STOPPED;
239 synchronized (this) {
240 pushThread = null;
241 notifyAll();
242 }
243 if (DEBUG || Printer.debug)Printer.debug("DataPusher:end of thread");
244 }
245
246 } // class DataPusher
|
10 *
11 * This code is distributed in the hope that it will be useful, but WITHOUT
12 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
13 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
14 * version 2 for more details (a copy is included in the LICENSE file that
15 * accompanied this code).
16 *
17 * You should have received a copy of the GNU General Public License version
18 * 2 along with this work; if not, write to the Free Software Foundation,
19 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
20 *
21 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
22 * or visit www.oracle.com if you need additional information or have any
23 * questions.
24 */
25
26 package com.sun.media.sound;
27
28 import java.util.Arrays;
29
30 import javax.sound.sampled.AudioFormat;
31 import javax.sound.sampled.AudioInputStream;
32 import javax.sound.sampled.SourceDataLine;
33
34 /**
35 * Class to write an AudioInputStream to a SourceDataLine.
36 * Was previously an inner class in various classes like JavaSoundAudioClip
37 * and sun.audio.AudioDevice.
38 * It auto-opens and closes the SourceDataLine.
39 *
40 * @author Kara Kytle
41 * @author Florian Bomers
42 */
43
44 public final class DataPusher implements Runnable {
45
46 private static final int AUTO_CLOSE_TIME = 5000;
47 private static final boolean DEBUG = false;
48
49 private final SourceDataLine source;
50 private final AudioFormat format;
51
52 // stream as source data
110 }
111 if (DEBUG || Printer.trace)Printer.trace("DataPusher: source.flush()");
112 source.flush();
113 if (DEBUG || Printer.trace)Printer.trace("DataPusher: source.start()");
114 source.start();
115 if (pushThread == null) {
116 if (DEBUG || Printer.debug) Printer.debug("DataPusher.start(): Starting push");
117 pushThread = JSSecurityManager.createThread(this,
118 null, // name
119 false, // daemon
120 -1, // priority
121 true); // doStart
122 }
123 notifyAll();
124 } catch (Exception e) {
125 if (DEBUG || Printer.err) e.printStackTrace();
126 }
127 if (DEBUG || Printer.debug) Printer.debug("< DataPusher.start(loop="+loop+")");
128 }
129
130 public synchronized void stop() {
131 if (DEBUG || Printer.debug) Printer.debug("> DataPusher.stop()");
132 if (threadState == STATE_STOPPING
133 || threadState == STATE_STOPPED
134 || pushThread == null) {
135 if (DEBUG || Printer.debug) Printer.debug("DataPusher.stop(): nothing to do");
136 return;
137 }
138 if (DEBUG || Printer.debug) Printer.debug("DataPusher.stop(): Stopping push");
139
140 wantedState = STATE_WAITING;
141 if (source != null) {
142 if (DEBUG || Printer.trace)Printer.trace("DataPusher: source.flush()");
143 source.flush();
144 }
145 notifyAll();
146 int maxWaitCount = 50; // 5 seconds
147 while ((maxWaitCount-- >= 0) && (threadState == STATE_PLAYING)) {
148 try {
149 wait(100);
150 } catch (InterruptedException e) { }
151 }
152 if (DEBUG || Printer.debug) Printer.debug("< DataPusher.stop()");
153 }
154
155 synchronized void close() {
156 if (source != null) {
157 if (DEBUG || Printer.trace)Printer.trace("DataPusher.close(): source.close()");
158 source.close();
159 }
160 }
161
162 /**
163 * Write data to the source data line.
164 */
165 @Override
166 public void run() {
167 byte[] buffer = null;
168 boolean useStream = (ais != null);
169 if (useStream) {
170 buffer = new byte[BUFFER_SIZE];
171 } else {
172 buffer = audioData;
173 }
174 while (wantedState != STATE_STOPPING) {
175 //try {
176 if (wantedState == STATE_WAITING) {
177 // wait for 5 seconds - maybe the clip is to be played again
178 if (DEBUG || Printer.debug)Printer.debug("DataPusher.run(): waiting 5 seconds");
179 try {
180 synchronized(this) {
181 threadState = STATE_WAITING;
182 wantedState = STATE_STOPPING;
183 wait(AUTO_CLOSE_TIME);
184 }
185 } catch (InterruptedException ie) {}
227 pos += bytesWritten;
228 if (DEBUG || Printer.debug) Printer.debug("< DataPusher.run(): Wrote " + bytesWritten + " bytes");
229 }
230 threadState = STATE_STOPPING;
231 if (DEBUG || Printer.debug)Printer.debug("DataPusher: closing device");
232 if (Printer.trace)Printer.trace("DataPusher: source.flush()");
233 source.flush();
234 if (DEBUG || Printer.trace)Printer.trace("DataPusher: source.stop()");
235 source.stop();
236 if (DEBUG || Printer.trace)Printer.trace("DataPusher: source.flush()");
237 source.flush();
238 if (DEBUG || Printer.trace)Printer.trace("DataPusher: source.close()");
239 source.close();
240 threadState = STATE_STOPPED;
241 synchronized (this) {
242 pushThread = null;
243 notifyAll();
244 }
245 if (DEBUG || Printer.debug)Printer.debug("DataPusher:end of thread");
246 }
247 } // class DataPusher
|