Mercurial > hg > ristipolku
view game/SoundElement.java @ 22:afde253ec705
More work.
author | Matti Hamalainen <ccr@tnsp.org> |
---|---|
date | Mon, 31 Jan 2011 21:28:59 +0200 |
parents | |
children | 0741dc117808 |
line wrap: on
line source
/* * Ristipolku Game Engine * (C) Copyright 2011 Matti 'ccr' Hämäläinen <ccr@tnsp.org> */ package game; import java.util.*; import java.io.*; import game.*; import javax.sound.sampled.*; class SoundElement implements Runnable { private final String name; private AudioInputStream stream; private AudioFormat format; private SourceDataLine line; private Thread playThread; private int loopCount; private boolean playing, streaming; private int volume = 100; byte[] buffer; int length; SoundElement(String filename, boolean streaming) throws IOException { this.name = filename; this.streaming = streaming; ResourceLoader res = new ResourceLoader(name); if (res == null || res.getStream() == null) { throw new IOException("Could not load audio resource '"+name+"'.\n"); } try { stream = AudioSystem.getAudioInputStream(res.getStream()); format = stream.getFormat(); } catch (UnsupportedAudioFileException e) { throw new IOException("Unsupported audio file format for '"+name+"'.\n"); } catch (IOException e) { throw new IOException("Could not load audio resource '"+name+"'.\n"); } if (streaming) { System.out.print("Loading '"+name+"' as a clip\n"); try { clip = AudioSystem.getClip(); clip.open(stream); } catch (LineUnavailableException e) { throw new IOException("Line unavailable for '"+name+"'.\n"); } finally { stream.close(); } } else { clip = null; System.out.print("Loading '"+name+"' as stream\n"); try { SourceDataLine.Info info = new DataLine.Info(SourceDataLine.class, format); System.out.print("info: "+stream.getFrameLength() + ", " + format.getFrameSize() + "\n"); line = (SourceDataLine) AudioSystem.getLine(info); line.open(format); } catch (LineUnavailableException e) { throw new IOException("Line unavailable for '"+name+"'.\n"); } } } public void play() { System.out.print("Sound("+name+").play()\n"); if (streaming) { clip.setFramePosition(0); clip.start(); } else { if (playThread == null) { doPlay = true; loopCount = 1; playThread = new Thread(this); playThread.start(); } } } public void loop(int n) { System.out.print("Sound("+name+").loop("+n+")\n"); if (isClip()) { clip.setFramePosition(0); if (n < 0) clip.loop(Clip.LOOP_CONTINUOUSLY); else clip.loop(n); } else { if (playThread == null) { doPlay = true; loopCount = n; playThread = new Thread(this); playThread.start(); } } } public void stop() { if (isClip()) { if (clip.isRunning()) clip.stop(); } else { if (playThread != null) { playThread.interrupt(); doPlay = false; playThread = null; } } } public boolean isPlaying() { if (isClip()) return clip.isRunning(); else return (playThread != null && line.isRunning()); } public void run() { line.start(); byte[] buf = new byte[line.getBufferSize()]; while (doPlay && (loopCount > 0 || loopCount == -1)) { try { int numRead = 0; while ((numRead = stream.read(buf, 0, buf.length)) >= 0 && doPlay) { int offset = 0; while (offset < numRead) { System.out.print("audioThread: offs="+offset+", numread="+numRead+"\n"); offset += line.write(buf, offset, numRead - offset); } } line.drain(); System.out.print("audioThread: stream.reset()\n"); stream.reset(); } catch (IOException e) { } if (loopCount > 0) loopCount--; } line.stop(); doPlay = false; } }