36package com.jogamp.openal.util;
39import java.io.FileInputStream;
40import java.io.IOException;
41import java.io.InputStream;
42import java.nio.ByteOrder;
44import com.jogamp.common.util.Bitstream;
45import com.jogamp.openal.ALException;
65 final File soundFile =
new File(filename);
66 final InputStream is =
new FileInputStream(soundFile);
67 return loadFromStreamImpl(is);
82 return loadFromStreamImpl(stream);
85 private static final int RIFF = 0x52494646;
86 private static final int RIFX = 0x52494658;
87 private static final int WAVE = 0x57415645;
88 private static final int FACT = 0x66616374;
89 private static final int FMT = 0x666D7420;
90 private static final int DATA = 0x64617461;
92 private static WAVData loadFromStreamImpl(
final InputStream aIn)
throws ALException, IOException {
100 final Bitstream.ByteInputStream bis =
new Bitstream.ByteInputStream(aIn);
101 final Bitstream<InputStream> bs =
new Bitstream<InputStream>(bis,
false);
102 bs.setThrowIOExceptionOnEOF(
true);
104 final boolean bigEndian;
106 final long riffMarker = bs.readUInt32(
true );
107 if ( RIFF == riffMarker ) {
109 }
else if( RIFX == riffMarker ) {
112 throw new ALException(
"Invalid RIF header: 0x"+Integer.toHexString((
int)riffMarker)+
", "+bs);
114 final long riffLenL = bs.readUInt32(bigEndian);
115 final int riffLenI = Bitstream.uint32LongToInt(riffLenL);
116 final long wavMarker = bs.readUInt32(
true );
117 if ( WAVE != wavMarker ) {
118 throw new ALException(
"Invalid WAV header: 0x"+Integer.toHexString((
int)wavMarker)+
", "+bs);
120 boolean foundFmt =
false;
121 boolean foundData =
false;
123 short sChannels = 0, sSampleSizeInBits = 0;
125 long chunkLength = 0;
129 final int chunkId = (int)bs.readUInt32(
true );
130 chunkLength = bs.readUInt32(bigEndian);
134 @SuppressWarnings(
"unused")
135 final
int compressionCode = bs.readUInt16(bigEndian);
136 sChannels = (
short)bs.readUInt16(bigEndian);
137 sampleRate = bs.readUInt32(bigEndian);
138 @SuppressWarnings("unused")
139 final
long bytesPerSeconds = bs.readUInt32(bigEndian);
140 @SuppressWarnings("unused")
141 final
short blockAlignment = (
short) bs.readUInt16(bigEndian);
142 sSampleSizeInBits = (
short) bs.readUInt16(bigEndian);
143 bs.skip( 8 * ( chunkLength - 16 ) );
147 bs.skip( 8 * chunkLength );
151 throw new ALException(
"WAV fmt chunks must be before data chunks: "+bs);
154 dataLength = Bitstream.uint32LongToInt(chunkLength);
158 bs.skip( 8 * chunkLength );
162 final int channels = sChannels;
163 final int sampleSizeInBits = sSampleSizeInBits;
164 final float fSampleRate = sampleRate;
165 return WAVData.loadFromStream(bs.getSubStream(), dataLength, channels, sampleSizeInBits,
166 Math.round(fSampleRate), bigEndian ? ByteOrder.BIG_ENDIAN : ByteOrder.LITTLE_ENDIAN,
false);
A generic exception for OpenAL errors used throughout the binding as a substitute for RuntimeExceptio...
This class is a holder for WAV (.wav ) file Data returned from the WavLoader, or directly via loadFro...
A Loader utility for (.wav) files.
static WAVData loadFromStream(final InputStream stream)
This method loads a (.wav) file into a WAVData object.
static WAVData loadFromFile(final String filename)
This method loads a (.wav) file into a WAVData object.