我想从串口读取数据,为此我需要一个单独的线程,它将在后台运行并不断检查数据是否可以读取,进一步的串口是双向(rx-tx)。一种方法是添加一个串行事件监听器,但我没有得到如何使后台线程做同样的事情,请帮助我!
我做了一个类读取,它接受来自其他类的输入流,我正在创建这个读类的一个线程,以便它在后台运行,看看是否有任何接收事件被触发,但接收是不是&# 39;发生了什么,问题是什么,有人吗?
import java.io.IOException;
import java.io.InputStream;
import java.util.TooManyListenersException;
import javax.comm.SerialPort;
import javax.comm.SerialPortEvent;
import javax.comm.SerialPortEventListener;
public class read implements SerialPortEventListener, Runnable {
InputStream inputStream;
SerialPort sp;
public read(SerialPort sp, InputStream input){
inputStream = input;
this.sp = sp;
try {
sp.addEventListener(this);
} catch (TooManyListenersException e) {System.out.println(e);}
sp.notifyOnDataAvailable(true);
/* try{
sp.setSerialPortParams(9600, SerialPort.DATABITS_8, SerialPort.STOPBITS_1, SerialPort.PARITY_NONE);
}
catch(Exception e){}*/
new Thread(this).start();
}
@Override
public void run() {
try {
Thread.sleep(20000);
} catch (InterruptedException e) {System.out.println(e);}
}
@Override
public void serialEvent(SerialPortEvent event) {
switch(event.getEventType()) {
case SerialPortEvent.BI:
case SerialPortEvent.OE:
case SerialPortEvent.FE:
case SerialPortEvent.PE:
case SerialPortEvent.CD:
case SerialPortEvent.CTS:
case SerialPortEvent.DSR:
case SerialPortEvent.RI:
case SerialPortEvent.OUTPUT_BUFFER_EMPTY:
break;
case SerialPortEvent.DATA_AVAILABLE:
byte[] readBuffer = new byte[1000];
try {
while (true) {
int numBytes;
if(inputStream.available() > 0){
numBytes = inputStream.read(readBuffer);
}
else
break;
}
System.out.print(new String(readBuffer));
try{
inputStream.close();
sp.close();
}
catch(Exception e){}
} catch (IOException e) {System.out.println(e);}
break;
}
}
}
答案 0 :(得分:1)
我想从串口读取数据,为此我需要一个单独的线程,它将在后台运行并不断检查数据是否可以读取'
不,你没有。你需要一个倾听者。你已经有了一个倾听者。您已将其添加到串行端口。你不需要任何其他东西。您不需要将侦听器作为线程启动。它是JavaComm将自动调用的回调对象。
此外串口是双向的(rx-tx)。一种方法是添加一个串行事件监听器,但我没有得到如何使后台线程做同样的事情...
那是因为你不必这样做。你误解了听众的工作方式。当侦听器触发时,执行适当的回调方法中的代码。就是这样。您无需线程。
我做了一个类读取,它从一些其他类
获取输入流
正确。
我正在制作这个读类的一个线程,以便它在后台运行以查看是否有任何接收事件被触发
不必要且毫无意义,见上文。
但接收没有发生,问题是什么,有人吗?
你做错了。删除线程,删除run()
方法,删除start()
,然后等待事件传递给回调方法。
重新编写代码:
case SerialPortEvent.DATA_AVAILABLE:
byte[] readBuffer = new byte[1000];
try {
while (true) {
删除循环。
int numBytes;
if(inputStream.available() > 0){
删除测试。这已经成为现实,case SerialPortEvent.DATA_AVAILABLE
意味着什么。
numBytes = inputStream.read(readBuffer);
}
else
break;
删除此else
和break
。
System.out.print(new String(readBuffer));
更改为
System.out.print(new String(readBuffer, 0, numBytes));
您忽略了read()
返回的长度,因此您需要在缓冲区末尾构建一个String
垃圾,而不是读取的内容。
try{
inputStream.close();
sp.close();
}
删除所有这些。您不应该因为目前没有可读取的数据而关闭输入流。保持开放。目前,您正在关闭流,因此在第一个数据到达后禁用侦听器。