For the audio format, you will need to determine the number of channels and sample size in bits. I expect you can get that from whatever is returned in “format”. If it indicates things like mono8, mono16, stereo8, and stereo16, then:
mono8: sampleSize 8, channels 1
mono16: sampleSize 16, channels 1
stereo8: sampleSize 8, channels 2
stereo16: sampleSize 16, channels 2
In which case you could create your AudioFormat instance like so:
AudioFormat audioFormat = new AudioFormat( (float) rate, sampleSize, channels, true, false );
I haven’t used OggInputStream before, so I’ll leave that question for someone else with the experience.
If you can get the length of the file from that OggInputStream there may be an easier way, but if not, you could just read the file in by chunks and append them together. The following is thrown together quickly from some source code I had sitting around, so check for typos. It should at least give you the basic idea:
public static final int BUFSIZE = 1024;
byte[] inputBuffer = new byte[BUFSIZE];
byte[] fullBuffer = null;
int readSize = readBuffer( input, inputBuffer );
if( readSize > 0 )
{
if( readSize < BUFSIZE )
fullBuffer = trimArray( inputBuffer, readSize );
else
{
while( readSize > 0 )
{
readSize = readBuffer( input, inputBuffer );
if( readSize > 0 )
fullBuffer = appendByteArrays( fullBuffer, inputBuffer, readSize );
}
}
}
else
; //TODO: Handle no data situation
Clip clip = loadClip( fullBuffer, audioFormat );
I almost forgot; here are the methods I referenced in the above code:
/**
* Attempts to read one buffer full of data, and returns
* the number of bytes read in.
* @param in Stream to read from.
* @param buf Buffer to put the data into.
* @return Bytes read, or 0 if error or end of stream.
*/
private int readBuffer( InputStream in, byte[] buf )
{
try
{
int readSize = 0;
while( ( readSize = in.read( buf, 0, BUFSIZE ) ) > -1 )
{
ogg.read( in, 0, readSize );
}
}
catch( IOException e )
{
e.printStackTrace();
}
return readSize;
}
/**
* Trims down the size of the array if it is larger than the specified
* maximum length.
* @param array Array containing audio data.
* @param maxLength Maximum size this array may be.
* @return New array.
*/
private static byte[] trimArray( byte[] array, int maxLength )
{
byte[] trimmedArray = null;
if( array != null && array.length > maxLength )
{
trimmedArray = new byte[maxLength];
System.arraycopy( array, 0, trimmedArray, 0, maxLength );
}
return trimmedArray;
}
/**
* Creates a new array with the second array appended to the end of the first
* array.
* @param arrayOne The first array.
* @param arrayTwo The second array.
* @param arrayTwoBytes The number of bytes to append from the second array.
* @return Byte array containing information from both arrays.
*/
private static byte[] appendByteArrays( byte[] arrayOne, byte[] arrayTwo,
int arrayTwoBytes )
{
byte[] newArray;
int bytes = arrayTwoBytes;
// Make sure we aren't trying to append more than is there:
if( arrayTwo == null || arrayTwo.length == 0 )
bytes = 0;
else if( arrayTwo.length < arrayTwoBytes )
bytes = arrayTwo.length;
if( arrayOne == null && (arrayTwo == null || bytes <= 0) )
{
// no data, just return
return null;
}
else if( arrayOne == null )
{
// create the new array, same length as arrayTwo:
newArray = new byte[ bytes ];
// fill the new array with the contents of arrayTwo:
System.arraycopy( arrayTwo, 0, newArray, 0, bytes );
arrayTwo = null;
}
else if( arrayTwo == null || bytes <= 0 )
{
// create the new array, same length as arrayOne:
newArray = new byte[ arrayOne.length ];
// fill the new array with the contents of arrayOne:
System.arraycopy( arrayOne, 0, newArray, 0, arrayOne.length );
arrayOne = null;
}
else
{
// create the new array large enough to hold both arrays:
newArray = new byte[ arrayOne.length + bytes ];
System.arraycopy( arrayOne, 0, newArray, 0, arrayOne.length );
// fill the new array with the contents of both arrays:
System.arraycopy( arrayTwo, 0, newArray, arrayOne.length,
bytes );
arrayOne = null;
arrayTwo = null;
}
return newArray;
}