我相信主要问题来自MicrophoneManager中的read方法,但看不到问题出在哪里。我的字节输出控制台输出为0(这在另一个类AudioTransmitter中)。在我看来,它好像没有流音频数据,因为发送的数据没有变化,就像我说读取的字节为0。
public class MicrophoneManager{
// private TargetDataLine targetDataLine;
private float sampleRate = 8000.0F; //8000,11025,16000,22050,44100
private int sampleSizeInBits = 16; //8,16
private int channels = 1; //1,2
private boolean signed = true; //true,false
private boolean bigEndian = false; //true,false
private AudioFormat audioFormat;
// private AudioRecord audioRecord;
// private AudioInputStream ais;
private static MicrophoneManager singletonMicrophoneManager = null;
public AudioRecord audioRecord;
public int mSamplesRead; //how many samples read
public int buffersizebytes;
public int buflen;
public int channelConfiguration = AudioFormat.CHANNEL_CONFIGURATION_MONO;
public int audioEncoding = AudioFormat.ENCODING_PCM_16BIT;
public static byte[] buffer; //+-32767
public static final int SAMPPERSEC = 8000; //samp per sec 8000, 11025, 22050 44100 or 48000
public class MicrophoneManager{
// private TargetDataLine targetDataLine;
private float sampleRate = 8000.0F; //8000,11025,16000,22050,44100
private int sampleSizeInBits = 16; //8,16
private int channels = 1; //1,2
private boolean signed = true; //true,false
private boolean bigEndian = false; //true,false
private AudioFormat audioFormat;
// private AudioRecord audioRecord;
// private AudioInputStream ais;
private static MicrophoneManager singletonMicrophoneManager = null;
public AudioRecord audioRecord;
public int mSamplesRead; //how many samples read
public int buffersizebytes;
public int buflen;
public int channelConfiguration = AudioFormat.CHANNEL_CONFIGURATION_MONO;
public int audioEncoding = AudioFormat.ENCODING_PCM_16BIT;
public static short[] buffer; //+-32767
public static final int SAMPPERSEC = 8000; //samp per sec 8000, 11025, 22050 44100 or 48000
public MicrophoneManager() {
System.out.println("Initializing");
// audioFormat = new AudioFormat(sampleRate,sampleSizeInBits,channels,signed,bigEndian);
// audioRecord = new AudioRecord(MediaRecorder.AudioSource.DEFAULT, (int) sampleRate, channels, AudioFormat.ENCODING_PCM_16BIT, buffersizebytes);
buffersizebytes = AudioRecord.getMinBufferSize(SAMPPERSEC,channelConfiguration,audioEncoding); //4096 on ion
buffer = new short[buffersizebytes];
buflen=buffersizebytes/2;
audioRecord = new AudioRecord(android.media.MediaRecorder.AudioSource.MIC,SAMPPERSEC,
channelConfiguration,audioEncoding,buffersizebytes); //constructor
}
public static MicrophoneManager getMicrophoneManager() throws Exception {
if (singletonMicrophoneManager == null) {
singletonMicrophoneManager = new MicrophoneManager();
singletonMicrophoneManager.initialize();
}
return singletonMicrophoneManager;
}
public void initialize() throws Exception {
}
public void startAudioInput(){
try {
audioRecord.startRecording();
mSamplesRead = audioRecord.read(buffer, 0, buffer.length);
audioRecord.stop();
} catch (Throwable t) {
// Log.e("AudioRecord", "Recording Failed");
System.out.println("Error Starting audio input"+t);
}
}
public void stopAudioInput(){
audioRecord.stop();
System.out.println("Stopping audio input");
}
public void finishAudioInput(){
audioRecord.release();
System.out.println("Finishing audio input");
}
public boolean available() throws Exception {
return true;
}
public int read(byte[] inBuf) throws Exception {
return audioRecord.read(inBuf,0,inBuf.length);
}
}
音频传输器:
public class AudioTransmitter extends Thread{
private MicrophoneManager mm=null;
private boolean transmittingAudio = false;
private String host;
private int port;
private long id=0;
boolean run=true;
public AudioTransmitter(String host, int port, long id) {
this.host = host;
this.port = port;
this.id = id;
this.start();
}
public void run() {
System.out.println("creating audio transmitter host "+host+" port "+port+" id "+id);
TrustManager[] trustAllCerts = new TrustManager[]{
new X509TrustManager() {
public java.security.cert.X509Certificate[] getAcceptedIssuers() {
return null;
}
public void checkClientTrusted(
java.security.cert.X509Certificate[] certs, String authType) {
}
public void checkServerTrusted(
java.security.cert.X509Certificate[] chain, String authType) {
for (int j=0; j<chain.length; j++)
{
System.out.println("Client certificate information:");
System.out.println(" Subject DN: " + chain[j].getSubjectDN());
System.out.println(" Issuer DN: " + chain[j].getIssuerDN());
System.out.println(" Serial number: " + chain[j].getSerialNumber());
System.out.println("");
}
}
}
};
while (run) {
if(transmittingAudio) {
try {
if(mm==null) {
mm = new MicrophoneManager();
// mm.initialize();
}
SSLContext sc = SSLContext.getInstance("SSL");
sc.init(null, trustAllCerts, new java.security.SecureRandom());
SSLSocketFactory sslFact = sc.getSocketFactory();
SSLSocket socket = (SSLSocket)sslFact.createSocket(host, port);
socket.setSoTimeout(10000);
InputStream inputStream = socket.getInputStream();
DataInputStream in = new DataInputStream(new BufferedInputStream(inputStream));
OutputStream outputStream = socket.getOutputStream();
DataOutputStream os = new DataOutputStream(new BufferedOutputStream(outputStream));
PrintWriter socketPrinter = new PrintWriter(os);
BufferedReader br = new BufferedReader(new InputStreamReader(in));
// socketPrinter.println("POST /transmitaudio?patient=1333369798370 HTTP/1.0");
socketPrinter.println("POST /transmitaudio?id="+id+" HTTP/1.0");
socketPrinter.println("Content-Type: audio/basic");
socketPrinter.println("Content-Length: 99999");
socketPrinter.println("Connection: Keep-Alive");
socketPrinter.println("Cache-Control: no-cache");
socketPrinter.println();
socketPrinter.flush();
// in.read();
mm.startAudioInput();
int buffersizebytes = AudioRecord.getMinBufferSize(8000, AudioFormat.CHANNEL_CONFIGURATION_MONO,AudioFormat.ENCODING_PCM_16BIT); //4096 on ion
System.out.println("audio started");
byte[] data = new byte[buffersizebytes];
while(transmittingAudio) {
// byte[] data = new byte[mm.available()];
int bytesRead = mm.read(data);
os.write(data,0,bytesRead);
os.flush();
// ca.transmitAxisAudioPacket(data);
// System.out.println("read "+data);
System.out.println("bytesRead "+bytesRead);
System.out.println("data "+Arrays.toString(data));
}
os.close();
mm.stopAudioInput();
} catch (Exception e) {
System.out.println("excpetion while transmitting audio connection will be closed"+e);
transmittingAudio=false;
}
}
else {
try {
Thread.sleep(1000);
} catch (Exception e){
System.out.println("exception while thread sleeping"+e);}
}
}
}
public void setTransmittingAudio(boolean transmittingAudio) {
this.transmittingAudio = transmittingAudio;
}
public void finished() {
this.transmittingAudio = false;
mm.finishAudioInput();
}
}
最佳答案
你在打电话
mSamplesRead = audioRecord.read(buffer, 0, buffersizebytes);
有一些问题。
audioRecord.read()
想要读取的数组的长度,而不是字节的大小。您已将编码设置为16位。您实际上应该在执行以下操作:new short[] buffer = short[1024]; // or whatever length you like
mSampleRead = audioRecord.read(buffer,0,buffer.length);
您正在打电话阅读
buffersizebytes
,但您设置了buffer = new byte[1024];
。没有特别的理由认为buffersizebytes
是正确的数字吗?您需要一个16位编码的short[]
数组,并且您希望读取的 SAMPLES (而不是字节)的数量小于或等于该short[] buffer
的长度。另外,如果打印出抛出异常时得到的异常,则您的状态会更好。
System.out.println("Error Starting audio input");
至
System.out.println("Error Starting audio input" + t);
而且您至少会暗示为什么android会将您扔进垃圾箱。
关于android - 音频数据有问题,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/10624347/