最近在做一个项目,采用 Android 的工控屏通过 485 协议读取硬件数据,经过一顿折腾,终于可以正常的读取到数据了,不过还有点问题,希望大神指点。
首先加载andoird 串口库
dependencies {
implementation 'io.github.xmaihh:serialport:2.1.1'
}
获取设备数据
import android.util.Log;
import java.io.File;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.util.ArrayList;
import java.util.List;
import android_serialport_api.SerialPort;
public class SerialComm {
private SerialPort serialPort;
private InputStream inputStream;
private OutputStream outputStream;
private ReadThread mReadThread;
private List<Byte> receivedDataBuffer = new ArrayList<>();
private static final int PACKET_LENGTH = 5; // 假设数据包长度为16字节
public void open() {
try {
serialPort = new SerialPort(new File("/dev/ttyS2"), 9600, 1, 8, 0, 0, 0);
inputStream = serialPort.getInputStream();
outputStream = serialPort.getOutputStream();
mReadThread = new ReadThread();
mReadThread.start();
} catch (IOException e) {
e.printStackTrace();
}
}
public void close() {
if (serialPort != null) {
serialPort.close();
}
}
public void write(byte[] data) {
try {
outputStream.write(data);
outputStream.flush();
} catch (IOException e) {
e.printStackTrace();
}
}
public void sendHexString(String hexString) throws IOException {
byte[] bytes = hexStringToByteArray(hexString);
outputStream.write(bytes);
}
private byte[] hexStringToByteArray(String hexString) {
int len = hexString.length();
byte[] data = new byte[len / 2];
for (int i = 0; i < len; i += 2) {
data[i / 2] = (byte) ((Character.digit(hexString.charAt(i), 16) << 4)
+ Character.digit(hexString.charAt(i + 1), 16));
}
return data;
}
//在子线程里面完成获取数据
private class ReadThread extends Thread {
@Override
public void run() {
while (true) {
try {
if (inputStream == null) return;
//这里获取到有效的数据长度,不知道为什么 485 会把一条数据,分多次返回
int available = inputStream.available();
if (available > 0) {
Log.e("有效长度",available + "");
byte[] buffer = new byte[available];
int bytesRead = inputStream.read(buffer);
if (bytesRead > 0) {
for (int i = 0; i < bytesRead; i++) {
receivedDataBuffer.add(buffer[i]);
}
processReceivedData();
}
}
Thread.sleep(10);
} catch (Throwable e) {
Log.e("SerialComm", "读取数据异常", e);
return;
}
}
}
}
/**
* 将获取到的数据,进行长度比较,如果小于预设长度,存放到 ArrayList 里面
*/
private void processReceivedData() {
while (receivedDataBuffer.size() >= PACKET_LENGTH) {
byte[] completePacket = new byte[PACKET_LENGTH];
for (int i = 0; i < PACKET_LENGTH; i++) {
completePacket[i] = receivedDataBuffer.get(i);
}
handleCompletePacket(completePacket);
for (int i = 0; i < PACKET_LENGTH; i++) {
receivedDataBuffer.remove(0);
}
}
}
//将完成的数据转换成十六进制的数据
private void handleCompletePacket(byte[] packet) {
String hexString = Utils.bytesToHex(packet);
Log.d("SerialComm", "Received Packet: " + hexString);
// 在这里添加对完整数据包的处理逻辑
}
}