001: /*
002: * Licensed to the Apache Software Foundation (ASF) under one or more
003: * contributor license agreements. See the NOTICE file distributed with
004: * this work for additional information regarding copyright ownership.
005: * The ASF licenses this file to You under the Apache License, Version 2.0
006: * (the "License"); you may not use this file except in compliance with
007: * the License. You may obtain a copy of the License at
008: *
009: * http://www.apache.org/licenses/LICENSE-2.0
010: *
011: * Unless required by applicable law or agreed to in writing, software
012: * distributed under the License is distributed on an "AS IS" BASIS,
013: * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
014: * See the License for the specific language governing permissions and
015: * limitations under the License.
016: */
017:
018: package org.apache.harmony.tools.appletviewer;
019:
020: import java.applet.AudioClip;
021: import java.net.URL;
022:
023: import javax.sound.sampled.AudioFormat;
024: import javax.sound.sampled.AudioInputStream;
025: import javax.sound.sampled.AudioSystem;
026: import javax.sound.sampled.DataLine;
027: import javax.sound.sampled.SourceDataLine;
028:
029: class ViewerAudioClip implements AudioClip {
030:
031: private ClipImpl clip;
032:
033: public ViewerAudioClip(URL url) {
034: AudioFormat af = null;
035: AudioInputStream ais = null;
036: SourceDataLine line = null;
037: try {
038: ais = AudioSystem.getAudioInputStream(url);
039: } catch (Exception e) {
040: e.printStackTrace();
041: return;
042: }
043: af = ais.getFormat();
044: DataLine.Info info = new DataLine.Info(SourceDataLine.class, af);
045:
046: boolean isSupported = AudioSystem.isLineSupported(info);
047: if (!isSupported) {
048: AudioFormat tf = new AudioFormat(
049: AudioFormat.Encoding.PCM_SIGNED,
050: af.getSampleRate(), 16, af.getChannels(), af
051: .getChannels() << 1, af.getSampleRate(),
052: false);
053: ais = AudioSystem.getAudioInputStream(tf, ais);
054: af = ais.getFormat();
055: info = new DataLine.Info(SourceDataLine.class, af);
056: }
057: try {
058: line = (SourceDataLine) AudioSystem.getLine(info);
059: } catch (Exception e) {
060: e.printStackTrace();
061: }
062:
063: clip = new ClipImpl(af, ais, line);
064:
065: }
066:
067: public void loop() {
068: if (clip != null)
069: clip.loop();
070: }
071:
072: public void play() {
073: if (clip != null)
074: clip.play();
075: }
076:
077: public void stop() {
078: if (clip != null)
079: clip.stop();
080: }
081:
082: private static class ClipImpl implements AudioClip, Runnable {
083:
084: static final int BufferSize = 1024;
085: static final int UNLIMITED = -1;
086:
087: AudioFormat af;
088: AudioInputStream ais;
089: SourceDataLine line;
090: Thread clip;
091: boolean started;
092: int streamLength;
093: int count;
094:
095: ClipImpl(AudioFormat af, AudioInputStream ais,
096: SourceDataLine line) {
097: this .af = af;
098: this .ais = ais;
099: this .line = line;
100:
101: if (ais.getFrameLength() == AudioSystem.NOT_SPECIFIED
102: || af.getFrameSize() == AudioSystem.NOT_SPECIFIED) {
103:
104: streamLength = -1;
105: }
106:
107: long length = ais.getFrameLength() * af.getFrameSize();
108:
109: if (length > Integer.MAX_VALUE) {
110: streamLength = -1;
111: }
112:
113: streamLength = (int) length;
114: clip = new Thread(this );
115: }
116:
117: public void run() {
118: if (streamLength < 0)
119: return;
120:
121: started = true;
122:
123: int bytesRead = 0;
124: byte[] data = new byte[BufferSize];
125:
126: try {
127: line.open(af);
128: } catch (Exception e) {
129: e.printStackTrace();
130: }
131:
132: // Main cycle
133:
134: while (true) {
135:
136: line.start();
137:
138: do {
139:
140: ais.mark(streamLength);
141: bytesRead = 0;
142: while (bytesRead != -1) {
143: try {
144: bytesRead = ais.read(data, 0, data.length);
145: } catch (Exception e) {
146: e.printStackTrace();
147: }
148:
149: if (bytesRead >= 0) {
150: line.write(data, 0, bytesRead);
151: }
152: }
153:
154: try {
155: ais.reset();
156: } catch (Exception e) {
157: e.printStackTrace();
158: }
159: } while (count < 0 || --count > 0);
160:
161: synchronized (clip) {
162: try {
163: clip.wait();
164: } catch (Exception e) {
165: e.printStackTrace();
166: }
167: }
168:
169: }
170: }
171:
172: public void play() {
173: if (!started)
174: clip.start();
175: synchronized (this ) {
176: count = 1;
177: synchronized (clip) {
178: clip.notify();
179: }
180: }
181: }
182:
183: public void loop() {
184: if (!started)
185: clip.start();
186: synchronized (this ) {
187: count = UNLIMITED;
188: synchronized (clip) {
189: clip.notify();
190: }
191: }
192: }
193:
194: public void stop() {
195: synchronized (this ) {
196: line.stop();
197: count = 1;
198: }
199: }
200:
201: protected void finalize() {
202: if (line != null && line.isOpen()) {
203: line.drain();
204: line.close();
205: }
206: }
207:
208: }
209: }
|