java 串口工具jSerialComm

由于项目之前用的串口工具RXTX只支持到jdk1.8 然后项目目前用到的jdk是13的 所以在网上找了一下 找到了这个 jSerialComm 目前使用是支持13及1.8的 没做其它jdk版本测试

引入jar包,github地址:http://fazecast.github.io/jSerialComm/

<!--http://fazecast.github.io/jSerialComm/-->
        <!--串口连接工具-->
        <dependency>
            <groupId>com.fazecast</groupId>
            <artifactId>jSerialComm</artifactId>
            <version>[2.0.0,3.0.0)</version>
        </dependency>

连接工具api文档地址:com.fazecast.jSerialComm (jSerialComm 2.9.0 API)

串口操作:

package com.jinfu.core;

import com.fazecast.jSerialComm.SerialPort;
import lombok.extern.slf4j.Slf4j;

import java.util.ArrayList;
import java.util.List;
import java.util.stream.Collectors;

@Slf4j
public class SerialPortManager {
    //查找所有可用端口
    public static List<String> findPorts() {
        // 获得当前所有可用串口
        SerialPort[] serialPorts = SerialPort.getCommPorts();
        List<String> portNameList = new ArrayList<String>();
        // 将可用串口名添加到List并返回该List
        for(SerialPort serialPort:serialPorts) {
            portNameList.add(serialPort.getSystemPortName());
        }
        //去重
        portNameList = portNameList.stream().distinct().collect(Collectors.toList());
        return portNameList;
    }

    /**
     * 打开串口
     *
     * @param portName  端口名称
     * @param baudRate  波特率
     * @return 串口对象
     */
    public static SerialPort openPort(String portName, Integer baudRate) {
        SerialPort serialPort = SerialPort.getCommPort(portName);
        if (baudRate != null) {
            serialPort.setBaudRate(baudRate);
        }
        if (!serialPort.isOpen()) {       //开启串口
           serialPort.openPort(1000);
        }else{
            return serialPort;
        }
        // 设置一下串口的波特率等参数
        // 数据位:8
        // 停止位:1
        // 校验位:None
        serialPort.setFlowControl(SerialPort.FLOW_CONTROL_DISABLED);
        serialPort.setComPortParameters(baudRate, 8, SerialPort.ONE_STOP_BIT, SerialPort.NO_PARITY);
        serialPort.setComPortTimeouts(SerialPort.TIMEOUT_READ_BLOCKING | SerialPort.TIMEOUT_WRITE_BLOCKING, 1000, 1000);
        return serialPort;
    }


    /**
     * 关闭串口
     * @param serialPort    待关闭的串口对象
     */
    public static void closePort(SerialPort serialPort) {
        if (serialPort != null && serialPort.isOpen()){
            serialPort.closePort();
        }
    }

    /**
     * 往串口发送数据
     * @param serialPort    串口对象
     * @param content       待发送数据
     */
    public static void sendToPort(SerialPort serialPort,byte[] content) {
        if (!serialPort.isOpen()) {
            return;
        }
        serialPort.writeBytes(content, content.length);
    }

    /**
     * 从串口读取数据
     * @param serialPort    当前已建立连接的SerialPort对象
     * @return 读取到的数据
     */
    public static byte[] readFromPort(SerialPort serialPort) {
        byte[] reslutData = null;
        try {
            if (!serialPort.isOpen()){return null;};
            int i=0;
            while (serialPort.bytesAvailable() > 0 && i++ < 5) Thread.sleep(20);
            byte[] readBuffer = new byte[serialPort.bytesAvailable()];
            int numRead = serialPort.readBytes(readBuffer, readBuffer.length);
            if (numRead > 0) {
                reslutData = readBuffer;
            }
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
        return reslutData;
    }

    /**
     * 添加监听器
     * @param serialPort    串口对象
     * @param listener  串口存在有效数据监听
     */
    public static void addListener(SerialPort serialPort, DataAvailableListener listener) {
        try {
            // 给串口添加监听器
            serialPort.addDataListener(new SerialPortListener(listener));
        } catch (Exception e) {
            e.printStackTrace();
        }
    }
}

当前串口工具是自带一个监听的方法SerialPortDataListener

目前是写了一个回调来监听串口工具的监听方法 这样做 是为了混淆 混淆后 串口工具自带的监听方法无法被其它地方调用

监听:

import com.fazecast.jSerialComm.SerialPort;
import com.fazecast.jSerialComm.SerialPortDataListener;
import com.fazecast.jSerialComm.SerialPortEvent;
import lombok.extern.slf4j.Slf4j;

/**
 * 串口监听
 */
@Slf4j
public class SerialPortListener implements SerialPortDataListener {

    private DataAvailableListener mDataAvailableListener;

    public SerialPortListener(DataAvailableListener mDataAvailableListener) {
        this.mDataAvailableListener = mDataAvailableListener;
    }

    @Override
    public int getListeningEvents() {     //必须是return这个才会开启串口工具的监听
        return SerialPort.LISTENING_EVENT_DATA_AVAILABLE;
    }

    public void serialEvent(SerialPortEvent serialPortEvent) {
        if (mDataAvailableListener != null) {
            mDataAvailableListener.dataAvailable();
        }
    }
}
  /**
     * 串口存在有效数据监听
     */
    public interface DataAvailableListener {
        /**
         * 串口存在有效数据
         */
        void dataAvailable();
    }

在这里插入图片描述
调用示例:

/** 
     * @throws PortInUseException   串口已经被占用
     */
    public static void main(String[] args) throws PortInUseException {//打开串口,返回一个串口对象 参数:串口号 波特率
        SerialPort serialPort = SerialPortManager.openPort("COM1", 10000);
        //给当前串口对象设置监听器
        SerialPortManager.addListener(serialPort, new DataAvailableListener() {
            @Override
            public void dataAvailable() {
                //当前监听器监听到的串口返回数据 back
                byte[] back = SerialPortManager.readFromPort(serialPort);
            }
        });
        //当前向串口发送的数据(模拟假数据)
        byte[] content = new byte[10];
        //向当前串口发送数据
        SerialPortManager.sendToPort(serialPort,content);
    }

当前项目只针对一个设备 所以监听也是做的针对一个串口对象
目前有个小问题 当串口已经开启后 在去开启串口会提示串口开启失败 同时之前开启的串口无法再次开启除非关闭后才能再次开启 目前做的一个小处理就是在开启的时候先将当前连接上串口关闭 然后再重新开启

  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 2
    评论
Java中使用jSerialComm库可以轻松地实现串口通信。要实现多线程串口监听,您需要创建一个线程来监听串口并在数据到达时执行相应的操作。下面是一个示例代码: ```java import java.io.IOException; import java.io.InputStream; import java.util.Scanner; import com.fazecast.jSerialComm.SerialPort; public class SerialReader implements Runnable { private SerialPort comPort; private InputStream input; public SerialReader(SerialPort comPort) { this.comPort = comPort; this.input = comPort.getInputStream(); } public void run() { try { while (true) { if (input.available() > 0) { byte[] buffer = new byte[input.available()]; int len = input.read(buffer); String data = new String(buffer, 0, len); System.out.print(data); } } } catch (IOException e) { e.printStackTrace(); } } public static void main(String[] args) { SerialPort comPort = SerialPort.getCommPort("COM1"); comPort.setComPortParameters(9600, 8, 1, SerialPort.NO_PARITY); comPort.openPort(); SerialReader reader = new SerialReader(comPort); Thread thread = new Thread(reader); thread.start(); } } ``` 在上面的示例代码中,我们首先通过 `SerialPort.getCommPort` 方法打开串口。然后,我们创建一个名为 `SerialReader` 的类,该类实现了 `Runnable` 接口并在其 `run` 方法中监听串口数据。在 `main` 方法中,我们创建一个 `SerialReader` 对象并将其传递给一个新线程。最后,我们启动该线程并等待数据到达。 您可以根据需要修改此代码,例如添加更多的串口设置或在数据到达时执行其他操作。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值