When I run the following code I have no sound as output instead it gives me noise.
I have two audio files in my resource folder and using 1 inputstream these are converted to bytearray.If I add mp3 then the app closes unfortunately.
private void mixSound() throws IOException {
AudioTrack audioTrack =new AudioTrack(AudioManager.STREAM_MUSIC,44100,AudioFormat.CHANNEL_OUT_STEREO, AudioFormat.ENCODING_PCM_16BIT, 44100, AudioTrack.MODE_STREAM);
Log.i(tag,"inside mixSound");
InputStream in1=getResources().openRawResource(R.raw.cut1); s
InputStream in2=getResources().openRawResource(R.raw.cut2);
byte[] music1 = null;
music1= new byte[in1.available()];
Log.i(tag,"in1");
music1=convertStreamToByteArray(in1);
in1.close();
byte[] music2 = null;
music2= new byte[in2.available()];
music2=convertStreamToByteArray(in2);
in2.close();
byte[] output = new byte[music1.length];
audioTrack.play();
for(int i=0; i < output.length; i++){
float samplef1 = music1[i] / 128.0f; // 2^7=128
float samplef2 = music2[i] / 128.0f;
float mixed = samplef1 + samplef2;
// reduce the volume a bit:
mixed *= 0.8;
// hard clipping
if (mixed > 1.0f) mixed = 1.0f;
if (mixed < -1.0f) mixed = -1.0f;
byte outputSample = (byte)(mixed * 128.0f);
output[i] = outputSample;
} //for loop
audioTrack.write(output, 0, output.length);
}
public static byte[] convertStreamToByteArray(InputStream is) throws IOException {
ByteArrayOutputStream baos = new ByteArrayOutputStream();
byte[] buff = new byte[10240];
int i = Integer.MAX_VALUE;
Log.i(tag,"in csb");
while ((i = is.read(buff, 0, buff.length)) > 0) {
baos.write(buff, 0, i);
}
return baos.toByteArray();
}
Thank you for help in advance.
A few issues here...
If you are working with 16-bit PCM audio (which by your initialization of
AudioTrack
it appears you are), then you should access your source audio and write to yourAudioTrack
inshort
s (which are 16 bits) rather thanbyte
s (8 bits). If you must readbyte
s from your source, you'll need to read two of them at a time in your loop and do something likeand then write the result to your stored buffer. This is assuming you have 16-bit shorts stored in the files you're reading from, which you should. Better to just read those as what they are, though.
Using
AudioTrack.MODE_STREAM
implies you will write continuously to the buffer while audio is playing. The way you've done it here fills the entire buffer and then writes it to theAudioTrack
. If this is a one-off playback, you should probably useAudioTrack.MODE_STATIC
.This is a corner case, but consider what happens if
mixed == 1.0f
. If you multiply that by 128.0f and truncate tobyte
, you'll get 128, which is actually beyond the range of a signedbyte
(because of 0, the range is [-128, 127]).I believe problem #1 is the source of your noise. You need to keep your 16-bit PCM data intact rather than splitting it up.