我想从我的麦克风中捕获音频并使用One Server发送给客户端(0或4)...
PD:我正在检查这个问题:Sending audio stream over TCP, UnsupportedAudioFileException但面向的是一台具有One Client解决方案的服务器。 其他问题:Java - Broadcast voice over Java sockets Streaming audio from microphone with Java
我正在考虑使用TCP(服务器/客户端模型),但服务器和4个客户端将接收数据(音频流)并且我不知道是否可以实现此替代方案(I&#39 ; m担心港口管理)....
这是我的初步(它仍然不起作用,因为我怀疑并且我在思考如何解决我的诅咒)
变量:
static boolean bThreadCapture = false;
static boolean bThreadServer = false;
static ByteArrayOutputStream myByteArrayOutStream;
ExecutorService myServerPool = Executors.newFixedThreadPool(4);
static Thread myThreadServer = null;
现在我的头痛
final int iServerPort = 2370;
final AudioFormat myAudioFormat = new AudioFormat(8000,8,1,false, true);
final DataLine.Info myDataLineInfo = new DataLine.Info(TargetDataLine.class, myAudioFormat);
if (!AudioSystem.isLineSupported(myDataLineInfo)) {
System.out.println("Line not supported");
System.exit(0);
}
try {
final TargetDataLine myTargetDataLine = (TargetDataLine) AudioSystem.getLine(myDataLineInfo);
myTargetDataLine.open(myAudioFormat);
myByteArrayOutStream = null;
//BEGIN definition Thread for CAPTURING AUDIO FROM MIC
Runnable runnAudioCapture = new Runnable() {
int bufferSize = (int) myAudioFormat.getSampleRate()* myAudioFormat.getFrameSize();
byte buffer[] = new byte[bufferSize];
public void run() {
myByteArrayOutStream = new ByteArrayOutputStream();
bThreadCapture = true;
while (bThreadCapture) {
try {
int count = myTargetDataLine.read(buffer, 0, buffer.length);
if (count > 0) {
myByteArrayOutStream.write(buffer, 0, count);
// HERE: I need to send the bytes of Sound to all active Threads Client (from 1 until 4)
// But, How to know what (how much and which) are active threads client?
// How to access to each Executor?
}
} catch (IllegalArgumentException | ArrayIndexOutOfBoundsException e) {
System.err.println("TargetDataLine problems: " + e);
}
}
try {
if (myByteArrayOutStream != null) myByteArrayOutStream.close();
} catch (IOException e) { }
}
};
//END definition Thread for CAPTURING AUDIO FROM MIC
//BEGIN definition Thread for ATTENDANT SERVER CLIENT (Still not defined)
myThreadServer = new Thread() {
@Override
public void run() {
try {
SrvrSocketProducer = new ServerSocket(iServerPort);
System.out.println("Server Listening on port number: "+iServerPort);
} catch (IOException e) {
System.out.println("Could not listen on port: "+iServerPort);
}
new Thread(runnAudioCapture).start(); //BEGIN AUDIO CAPTURE
while(bThreadServer) {
Socket clientSocket = null;
try {
clientSocket = SrvrSocketProducer.accept();
} catch (IOException e) {
if(!bThreadServer) {
System.out.println("Server Stopped.") ;
break;
}
throw new RuntimeException("Error accepting client connection", e);
}
myServerPool.execute(new runnWorkerListener(clientSocket,myAudioFormat));
}
myServerPool.shutdown();
bThreadCapture = false; //STOP AUDIO CAPTURE
}
};
//END definition Thread for ATTENDANT SERVER CLIENT (Still not defined)
myThreadServer.start();
} catch (LineUnavailableException ex) {
System.out.println(ex.toString());
}
问题:
(在runnAudioCapture代码中合并以找到帮助)
1. HERE: I need to send the bytes of Sound to all ACTIVE Threads Client (from 1 until 4)
2. But, How to know what (how much and which) are active threads client?
3. How to access to each Executor?
现在工作线程 -
class runnWorkerListener implements Runnable {
Socket innerClientSocket = null;
AudioFormat innerAdfmt = null;
public runnWorkerListener(Socket clientSocket, AudioFormat audioFormat) {
innerClientSocket = clientSocket;
innerAdfmt = audioFormat;
}
public void run() {
try {
InputStream input = innerClientSocket.getInputStream();
OutputStream output = innerClientSocket.getOutputStream();
// Now How Can I to Comunicate with runnAudioCapture?
while (RunningClientAttender /*This variable still is not defined*/) {
// I need to send (thread client here Not defined) EACH bytes from runnAudioCapture
}
output.close();
input.close();
System.out.println("Request processed: ");
} catch (IOException e) {
//report exception somewhere.
e.printStackTrace();
}
}
}
问题:
(在runnWorkerListener代码中合并以查找帮助)
1. Now How Can I to Comunicate with runnAudioCapture?
2. I need to send (thread client here Not defined) EACH bytes from runnAudioCapture
我怀疑与以下事项有关: 一个致力于音频捕获的线程 一个线程专用于使用Pool接收客户端(1,2,3或4)并创建线程工作者(一个线程工作者与#34;远程"客户端进行通信)
我不知道处理器将Capturer线程Capturer与每个工作线程同步...
谢谢...
答案 0 :(得分:0)
不幸的是,在Java中,流只能由一个人一次使用。您有一个流myByteArrayOutStream
,并且您希望在4个TCP连接之间共享它。
我建议您将音频数据写入文件。每次客户端连接时,您都会将文件的所有内容流式传输到该客户端(您可以打开文件,跳到最后,如果需要,只传输新内容)。您需要为每个客户端创建一个新线程。
如果您希望在Java中构建类似Skype音频的东西,那么这比使用TCP要复杂一些。 TCP是一种从A到B,可靠地获取数据的方法。对于音频,您通常希望它从A到B,但实时。如果您在此过程中丢失了一个数据包,则不希望返回并重新传输它,因为这会导致呼叫延迟。 TCP的替代方案,可能更适合您的方案,是UDP。它发送单个数据包,并不保证它们按顺序到达,甚至根本不到。但它并没有停止并等待丢失的数据包。