1、配置樹莓派:
(1)sudo raspi-config
(2)選擇 Interfacing Options,然後選擇Serial,關閉串口shell終端,使能串口。
(3)修改配置文件
sudo nano /boot/config.txt
追加如下內容
dtoverlay=pi3-miniuart-bt
enable_uart=1
2、配置Java串口環境
(1)獲取系統版本信息
uname -r
(2)將獲取到的系統版本信息寫入配置文件/usr/include/linux/version.h
#define UTS_RELEASE "4.14.34-v7+" //引號內容根據實際情概況修改
(3)下載相關程序包【網頁鏈接:http://rxtx.qbang.org/wiki/index.php/Download】
wget http://rxtx.qbang.org/pub/rxtx/rxtx-2.2pre2.zip
unzip rxtx-2.2pre2.zip
cd rxtx-2.2pre2
(4)JDK1.6及以上的運行環境下,需要對configure文件進行修改。
在configure文件中找到所有的 1.2*|1.3*|1.4*|1.5* , 將現有的JDK版本加入進去即可.如:改成 1.2*|1.3*|1.4*|1.5*|1.6*|1.7*|1.8*
sh ./configure
make
make install
(5)安裝成功後,會顯示如下信息
Libraries have been installed in:
/cloud/jdk/jre/lib/arm
...................
/usr/bin/install -c RXTXcomm.jar /cloud/jdk/jre/lib/ext/
3、編寫java代碼
示例代碼如下
/**
* 串口通訊
*/
public class SerialPortManager
{
private static final SerialPortManager SERIAL_PORT_MANAGER = new SerialPortManager();
private SerialPort serialPort;
private InputStream inputStream;
private OutputStream outputStream;
public static SerialPortManager getInstance()
{
return SERIAL_PORT_MANAGER;
}
public void init()
{
if (openPort())//打開串口
{
addListener();//添加監聽器
return;
}
Device.isConnect = false;
try
{
Thread.sleep(2000);
}
catch (InterruptedException e)
{
e.printStackTrace();
}
//刷新參數
new ParameterManager(false).run();
}
/**
* 從串口讀取數據
*/
private void readPortData(DataLinkParserUtil parserUtil)
{
if (!Device.isConnect)
{
return;
}
try
{
if (serialPort == null)
{
System.out.println("Serial-串口對象爲空,監聽失敗!");
init();
return;
}
}
catch (Exception e)
{
e.printStackTrace();
init();
return;
}
byte[] readBuffer = new byte[4096];
try
{
parserUtil.unpackData(inputStream.read(readBuffer), readBuffer);
}
catch (IOException ignored)
{
System.out.println("inputStream.read(readBuffer):ERROR!");
init();
}
}
/**
* 給串口添加監聽器
*/
private void addListener()
{
try
{
inputStream = serialPort.getInputStream();
outputStream = serialPort.getOutputStream();
Device.isConnect = true;
final DataLinkParserUtil parserUtil = new DataLinkParserUtil();
serialPort.addEventListener(new SerialPortListener(() -> readPortData(parserUtil)));
// 設置當有數據到達時喚醒監聽接收線程
serialPort.notifyOnDataAvailable(true);
// 設置當通信中斷時喚醒中斷線程
serialPort.notifyOnBreakInterrupt(true);
new Thread(this::sendPortData).start();//發送串口數據
new Thread(this::getSn).start();//發送獲取飛控編號請求
}
catch (TooManyListenersException | IOException e)
{
e.printStackTrace();
Device.isConnect = false;
init();
}
}
/**
* 發送串口數據
*/
private void sendPortData()
{
while (Device.isConnect && outputStream != null)
{
if (Device.sendCommandQueue.isEmpty())
{
continue;
}
Packet packet = null;
try
{
packet = Device.sendCommandQueue.take();
}
catch (InterruptedException e)
{
e.printStackTrace();
}
if (packet == null)
{
continue;
}
try
{
outputStream.write(packet.encodePacket());
outputStream.flush();
}
catch (IOException e)
{
e.printStackTrace();
}
}
}
/**
* 打開串口
*/
private boolean openPort()
{
closePort();
try
{
if (Parameter.isLinux)
{ //RXTX只支持ttyS開頭的設備,而我們要跟串口通訊用的是 ttyAMA0,所以在此之前還要做一下映射
Util.exeShellCommand("sudo ln -s /dev/ttyAMA0 /dev/ttyS4502");
}
System.out.println("打開串口:PORT=" + Parameter.PORT + ",RATE=" + Parameter.RATE);
serialPort = openPort(Parameter.PORT, Parameter.RATE);
if (serialPort != null)
{
System.out.println("Serial-串口已打開!");
return true;
}
}
catch (PortInUseException e)
{
System.out.println("Serial-串口已被佔用!");
e.printStackTrace();
return false;
}
return false;
}
/**
* 打開串口
*
* @param portName 端口名稱
* @param rate 波特率
* @return 串口對象
* @throws PortInUseException 串口已被佔用
*/
private SerialPort openPort(String portName, int rate) throws PortInUseException
{
try
{
// 通過端口名識別端口
CommPortIdentifier portIdentifier = CommPortIdentifier.getPortIdentifier(portName);
// 打開端口,並給端口名字和一個timeout(打開操作的超時時間)
CommPort commPort = portIdentifier.open(portName, 2000);
// 判斷是不是串口
if (!(commPort instanceof SerialPort))
{
System.out.println("Serial-" + portName + "不是串口");
return null;
}
SerialPort serialPort = (SerialPort) commPort;
try
{
// 設置一下串口的波特率等參數
// 數據位:8
// 停止位:1
// 校驗位:None
serialPort.setSerialPortParams(rate, SerialPort.DATABITS_8, SerialPort.STOPBITS_1, SerialPort.PARITY_NONE);
return serialPort;
}
catch (UnsupportedCommOperationException e)
{
e.printStackTrace();
return null;
}
}
catch (NoSuchPortException e1)
{
e1.printStackTrace();
System.out.println("Serial-沒有這個端口");
return null;
}
}
/**
* 關閉串口
*/
public void closePort()
{
System.out.println("Serial-關閉串口中...");
Device.isConnect = false;
if (serialPort != null)
{
serialPort.removeEventListener();
serialPort.close();
serialPort = null;
}
if (inputStream != null)
{
try
{
inputStream.close();
inputStream = null;
}
catch (IOException e)
{
e.printStackTrace();
}
}
if (outputStream != null)
{
try
{
outputStream.close();
outputStream = null;
}
catch (IOException e)
{
e.printStackTrace();
}
}
System.out.println("Serial-串口已關閉");
}
}