好得很程序员自学网

<tfoot draggable='sEl'></tfoot>

java使用Rxtx实现串口通信调试工具

本文实例为大家分享了 java 使用rxtx实现 串口通信 调试工具的具体代码,供大家参考,具体内容如下

最终效果如下图:

1、把rxtxparallel.dll、rxtxserial.dll拷贝到:c:\windows\system32下。
2、rxtxcomm.jar 添加到项目类库中。

代码:

?

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

19

20

21

22

23

24

25

26

27

28

29

30

31

32

33

34

35

36

37

38

39

40

41

42

43

44

45

46

47

48

49

50

51

52

53

54

55

56

57

58

59

60

61

62

63

64

65

66

67

68

69

70

71

72

73

74

75

76

77

78

79

80

81

82

83

84

85

86

87

88

89

90

91

92

93

94

95

96

97

98

99

100

101

102

103

104

105

106

107

108

109

110

111

112

113

114

115

116

117

118

119

120

121

122

123

124

125

126

127

128

129

130

131

132

133

134

135

136

137

138

139

140

141

142

143

144

145

146

147

148

149

150

151

152

153

package serialport;

 

import java.io.ioexception;

import java.io.inputstream;

import java.io.outputstream;

import java.util.arraylist;

import java.util.enumeration;

import java.util.list;

import java.util.toomanylistenersexception;

 

import gnu.io测试数据mport;

import gnu.io测试数据mportidentifier;

import gnu.io.nosuchportexception;

import gnu.io.portinuseexception;

import gnu.io.serialport;

import gnu.io.serialporteventlistener;

import gnu.io.unsupportedcommoperationexception;

 

/**串口服务类,提供打开、关闭串口,读取、发送串口数据等服务

  */

public class serialtool {

 

  private static serialtool serialtool = null ;

 

  static {

   //在该类被classloader加载时就初始化一个serialtool对象

   if (serialtool == null ) {

    serialtool = new serialtool();

   }

  }

 

  //私有化serialtool类的构造方法,不允许其他类生成serialtool对象

  private serialtool() {}

  /**

   * 获取提供服务的serialtool对象

   * @return serialtool

   */

  public static serialtool getserialtool() {

 

   if (serialtool == null ) {

    serialtool = new serialtool();

   }

   return serialtool;

  }

  /**

   * 查找所有可用端口

   * @return 可用端口名称列表

   */

  public static final list<string> findport() {

 

   //获得当前所有可用串口

   @suppresswarnings ( "unchecked" )

   enumeration<commportidentifier> portlist = commportidentifier.getportidentifiers();

   list<string> portnamelist = new arraylist<>();

   //将可用串口名添加到list并返回该list

   while (portlist.hasmoreelements()) {

    string portname = portlist.nextelement().getname();

    portnamelist.add(portname);

   }

   return portnamelist;

  }

  /**

   * 打开串口

   * @param portname 端口名称

   * @param baudrate 波特率

   * @return 串口对象

   * @throws unsupportedcommoperationexception

   * @throws portinuseexception

   * @throws nosuchportexception

   */

  public static final serialport openport(string portname, int baudrate) throws unsupportedcommoperationexception, portinuseexception, nosuchportexception {

 

   //通过端口名识别端口

   commportidentifier portidentifier = commportidentifier.getportidentifier(portname);

   //打开端口,并给端口名字和一个timeout(打开操作的超时时间)

   commport commport = portidentifier.open(portname, 2000 );

   //判断是不是串口

   if (commport instanceof serialport) {

    serialport serialport = (serialport) commport;

    //设置一下串口的波特率等参数

    serialport.setserialportparams(baudrate, serialport.databits_8, serialport.stopbits_1, serialport.parity_none);       

    return serialport;

   }

   return null ;

  }

  /**

   * 关闭串口

   * @param serialport 待关闭的串口对象

   */

  public static void closeport(serialport serialport) {

 

   if (serialport != null ) {

    serialport.close();

    serialport = null ;

   }

  }

  /**

   * 往串口发送数据

   * @param serialport 串口对象

   * @param order 待发送数据

   * @throws ioexception

   */

  public static void sendtoport(serialport serialport, byte [] order) throws ioexception {

 

   outputstream out = null ;

   out = serialport.getoutputstream();

   out.write(order);

   out.flush();

   out.close();

  }

  /**

   * 从串口读取数据

   * @param serialport 当前已建立连接的serialport对象

   * @return 读取到的数据

   * @throws ioexception

   */

  public static byte [] readfromport(serialport serialport) throws ioexception {

 

   inputstream in = null ;

   byte [] bytes = null ;

   try {

    in = serialport.getinputstream();

    int bufflenth = in.available(); //获取buffer里的数据长度

    while (bufflenth != 0 ) {       

     bytes = new byte [bufflenth]; //初始化byte数组为buffer中数据的长度

     in.read(bytes);

     bufflenth = in.available();

    }

   } catch (ioexception e) {

    throw e;

   } finally {

    if (in != null ) {

     in.close();

     in = null ;

    }

   }

   return bytes;

  }

  /**添加监听器

   * @param port  串口对象

   * @param listener 串口监听器

   * @throws toomanylistenersexception

   */

  public static void addlistener(serialport port, serialporteventlistener listener) throws toomanylistenersexception {

 

   //给串口添加监听器

   port.addeventlistener(listener);

   //设置当有数据到达时唤醒监听接收线程

   port.notifyondataavailable( true );

   //设置当通信中断时唤醒中断线程

   port.notifyonbreakinterrupt( true );

  }

}

?

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

19

20

21

22

23

24

25

26

27

28

29

30

31

32

33

34

35

36

37

38

39

40

41

42

43

44

45

46

47

48

49

50

51

52

53

54

55

56

57

58

59

60

61

62

63

64

65

66

67

68

69

70

71

72

73

74

75

76

77

78

79

80

81

82

83

84

85

86

87

88

89

90

91

92

93

94

95

96

97

98

99

100

101

102

103

104

105

106

107

108

109

110

111

112

113

114

115

116

117

118

119

120

121

122

123

124

125

126

127

128

129

130

131

132

133

134

135

136

137

138

139

140

141

142

143

144

145

146

147

148

149

150

151

152

153

154

155

156

157

158

159

160

161

162

163

164

165

166

167

168

169

170

171

172

173

174

175

176

177

178

179

180

181

182

183

184

185

186

187

188

189

190

191

192

193

194

195

196

197

198

199

200

201

202

203

204

205

206

207

208

209

210

211

212

213

214

215

216

217

218

219

220

221

222

223

224

225

226

227

228

229

230

231

232

233

234

235

236

237

238

239

240

241

242

243

244

245

246

247

248

249

250

251

252

253

254

255

256

257

258

259

260

261

262

263

264

265

266

267

268

269

270

271

272

273

274

275

276

277

278

279

280

281

282

283

284

285

286

287

288

289

290

291

292

293

294

295

296

297

298

299

300

301

302

303

304

305

306

307

308

309

310

311

312

313

314

315

316

317

318

319

320

321

322

323

324

325

326

327

328

329

330

331

332

package serialport;

 

import java.awt.color;

import java.awt.font;

import java.awt.image;

import java.awt.toolkit;

import java.awt.event.actionevent;

import java.awt.event.actionlistener;

import java.awt.event.mouseadapter;

import java.awt.event.mouseevent;

import java.io.ioexception;

import java.time.instant;

import java.time.localdatetime;

import java.time.zoneid;

import java.time.format.datetimeformatter;

import java.util.list;

import java.util.timer;

import java.util.timertask;

import java.util.toomanylistenersexception;

 

import javax.swing.jbutton;

import javax.swing.jcombobox;

import javax.swing.jframe;

import javax.swing.jlabel;

import javax.swing.joptionpane;

import javax.swing.jscrollpane;

import javax.swing.jtextarea;

import javax.swing.border.titledborder;

 

import gnu.io.nosuchportexception;

import gnu.io.portinuseexception;

import gnu.io.serialport;

import gnu.io.serialportevent;

import gnu.io.serialporteventlistener;

import gnu.io.unsupportedcommoperationexception;

 

/**

  * 监测数据显示类

  * @author zhong

  *

  */

public class serialview extends jframe {

 

  /**

   */

  private static final long serialversionuid = 1l;

 

  //设置window的icon

  toolkit toolkit = gettoolkit();

  image icon = toolkit.getimage(serialview. class .getresource( "computer.png" ));

  datetimeformatter df= datetimeformatter.ofpattern( "yyyy-mm-dd hh:mm:ss.sss" );

 

  private jcombobox<string> commchoice;

  private jcombobox<string> bpschoice;

  private jbutton openserialbutton;

  private jbutton sendbutton;

  private jtextarea sendarea;

  private jtextarea receivearea;

  private jbutton closeserialbutton;

 

  private list<string> commlist = null ; //保存可用端口号

  private serialport serialport = null ; //保存串口对象

 

  /**类的构造方法

   * @param client

   */

  public serialview() {

 

   init();

   timertask task = new timertask() {

    @override

    public void run() {

     commlist = serialtool.findport(); //程序初始化时就扫描一次有效串口

     //检查是否有可用串口,有则加入选项中

     if (commlist == null || commlist.size()< 1 ) {

      joptionpane.showmessagedialog( null , "没有搜索到有效串口!" , "错误" , joptionpane.information_message);

     } else {

      commchoice.removeallitems();

      for (string s : commlist) {

       commchoice.additem(s);

      }

     }

    }

   };

   timer timer = new timer();

   timer.scheduleatfixedrate(task, 0 , 10000 );

   listen();

 

  }

  /**

   */

  private void listen(){

 

   //打开串口连接

   openserialbutton.addactionlistener( new actionlistener() {

 

    public void actionperformed(actionevent e) {

     //获取串口名称

     string commname = (string) commchoice.getselecteditem();  

     //获取波特率

     string bpsstr = (string) bpschoice.getselecteditem();

     //检查串口名称是否获取正确

     if (commname == null || commname.equals( "" )) {

      joptionpane.showmessagedialog( null , "没有搜索到有效串口!" , "错误" , joptionpane.information_message);  

     } else {

      //检查波特率是否获取正确

      if (bpsstr == null || bpsstr.equals( "" )) {

       joptionpane.showmessagedialog( null , "波特率获取错误!" , "错误" , joptionpane.information_message);

      } else {

       //串口名、波特率均获取正确时

       int bps = integer.parseint(bpsstr);

       try {

        //获取指定端口名及波特率的串口对象

        serialport = serialtool.openport(commname, bps);

        serialtool.addlistener(serialport, new seriallistener());

        if (serialport== null ) return ;

        //在该串口对象上添加监听器

        closeserialbutton.setenabled( true );

        sendbutton.setenabled( true );

        openserialbutton.setenabled( false );

        string time=df.format(localdatetime.ofinstant(instant.ofepochmilli(system.currenttimemillis()),zoneid.of( "asia/shanghai" )));

        receivearea.append(time+ " [" +serialport.getname().split( "/" )[ 3 ]+ "] : " + " 连接成功..." + "\r\n" );

        receivearea.setcaretposition(receivearea.gettext().length());

       } catch (unsupportedcommoperationexception | portinuseexception | nosuchportexception | toomanylistenersexception e1) {

        e1.printstacktrace();

       }

      }

     }

    }

   });

   //发送数据

   sendbutton.addmouselistener( new mouseadapter() {

    @override

    public void mouseclicked(mouseevent e) {

     if (!sendbutton.isenabled()) return ;

     string message= sendarea.gettext();

     //"fe0400030001d5c5"

     try {

      serialtool.sendtoport(serialport, hex2byte(message));

     } catch (ioexception e1) {

      e1.printstacktrace();

     }

    }

   });

   //关闭串口连接

   closeserialbutton.addmouselistener( new mouseadapter() {

    @override

    public void mouseclicked(mouseevent e) {

     if (!closeserialbutton.isenabled()) return ;

     serialtool.closeport(serialport);

     string time=df.format(localdatetime.ofinstant(instant.ofepochmilli(system.currenttimemillis()),zoneid.of( "asia/shanghai" )));

     receivearea.append(time+ " [" +serialport.getname().split( "/" )[ 3 ]+ "] : " + " 断开连接" + "\r\n" );

     receivearea.setcaretposition(receivearea.gettext().length());

     openserialbutton.setenabled( true );

     closeserialbutton.setenabled( false );

     sendbutton.setenabled( false );

    }

   });

  }

  /**

   * 主菜单窗口显示;

   * 添加jlabel、按钮、下拉条及相关事件监听;

   */

  private void init() {

 

   this .setbounds(wellcomview.loc_x, wellcomview.loc_y, wellcomview.width, wellcomview.height);

   this .settitle( "串口调试" );

   this .seticonimage(icon);

   this .setbackground(color.gray);

   this .setlayout( null );

 

   font font = new font( "微软雅黑" , font.bold, 16 );

 

   receivearea= new jtextarea( 18 , 30 );

   receivearea.seteditable( false );

   jscrollpane receivescroll = new jscrollpane(receivearea);

   receivescroll.setborder( new titledborder( "接收区" ));

   //滚动条自动出现 fe0400030001d5c5

   receivescroll.sethorizontalscrollbarpolicy(

     jscrollpane.horizontal_scrollbar_as_needed);

   receivescroll.setverticalscrollbarpolicy(

     jscrollpane.vertical_scrollbar_as_needed);

   receivescroll.setbounds( 52 , 20 , 680 , 340 );

   this .add(receivescroll);

 

   jlabel chuankou= new jlabel( " 串口选择: " );

   chuankou.setfont(font);

   chuankou.setbounds( 50 , 380 , 100 , 50 );

   this .add(chuankou);

 

   jlabel botelv= new jlabel( " 波 特 率: " );

   botelv.setfont(font);

   botelv.setbounds( 290 , 380 , 100 , 50 );

   this .add(botelv);

 

   //添加串口选择选项

   commchoice = new jcombobox<string>(); //串口选择(下拉框)

   commchoice.setbounds( 145 , 390 , 100 , 30 );

   this .add(commchoice);

 

   //添加波特率选项

   bpschoice = new jcombobox<string>(); //波特率选择

   bpschoice.setbounds( 380 , 390 , 100 , 30 );

   bpschoice.additem( "1500" );

   bpschoice.additem( "2400" );

   bpschoice.additem( "4800" );

   bpschoice.additem( "9600" );

   bpschoice.additem( "14400" );

   bpschoice.additem( "19500" );

   bpschoice.additem( "115500" );

   this .add(bpschoice);

 

   //添加打开串口按钮

   openserialbutton = new jbutton( "连接" );

   openserialbutton.setbounds( 540 , 390 , 80 , 30 );

   openserialbutton.setfont(font);

   openserialbutton.setforeground(color.darkgray);

   this .add(openserialbutton);

 

   //添加关闭串口按钮

   closeserialbutton = new jbutton( "关闭" );

   closeserialbutton.setenabled( false );

   closeserialbutton.setbounds( 650 , 390 , 80 , 30 );

   closeserialbutton.setfont(font);

   closeserialbutton.setforeground(color.darkgray);

   this .add(closeserialbutton);

 

   sendarea= new jtextarea( 30 , 20 );

   jscrollpane sendscroll = new jscrollpane(sendarea);

   sendscroll.setborder( new titledborder( "发送区" ));

   //滚动条自动出现

   sendscroll.sethorizontalscrollbarpolicy(

     jscrollpane.horizontal_scrollbar_always);

   sendscroll.setverticalscrollbarpolicy(

     jscrollpane.vertical_scrollbar_always);

   sendscroll.setbounds( 52 , 450 , 500 , 100 );

   this .add(sendscroll);

 

   sendbutton = new jbutton( "发 送" );

   sendbutton.setbounds( 610 , 520 , 120 , 30 );

   sendbutton.setfont(font);

   sendbutton.setforeground(color.darkgray);

   sendbutton.setenabled( false );

   this .add(sendbutton);

 

   this .setresizable( false ); //窗口大小不可更改

   this .setdefaultcloseoperation(jframe.exit_on_close);

   this .setvisible( true );

  }

 

  /**字符串转16进制

   * @param hex

   * @return

   */

  private byte [] hex2byte(string hex) {

 

   string digital = "0123456789abcdef" ;

   string hex1 = hex.replace( " " , "" );

   char [] hex2char = hex1.tochararray();

   byte [] bytes = new byte [hex1.length() / 2 ];

   byte temp;

   for ( int p = 0 ; p < bytes.length; p++) {

    temp = ( byte ) (digital.indexof(hex2char[ 2 * p]) * 16 );

    temp += digital.indexof(hex2char[ 2 * p + 1 ]);

    bytes[p] = ( byte ) (temp & 0xff );

   }

   return bytes;

  }

  /**字节数组转16进制

   * @param b

   * @return

   */

  private string printhexstring( byte [] b) {

 

   stringbuffer sbf= new stringbuffer();

   for ( int i = 0 ; i < b.length; i++) {

    string hex = integer.tohexstring(b[i] & 0xff );

    if (hex.length() == 1 ) {

     hex = '0' + hex;

    }

    sbf.append(hex.touppercase()+ " " );

   }

   return sbf.tostring().trim();

  }

  /**

   * 以内部类形式创建一个串口监听类

   * @author zhong

   */

  class seriallistener implements serialporteventlistener {

 

   /**

    * 处理监控到的串口事件

    */

   public void serialevent(serialportevent serialportevent) {

 

    switch (serialportevent.geteventtype()) {

    case serialportevent.bi: // 10 通讯中断

     joptionpane.showmessagedialog( null , "与串口设备通讯中断" , "错误" , joptionpane.information_message);

     break ;

    case serialportevent.oe: // 7 溢位(溢出)错误

     break ;

    case serialportevent.fe: // 9 帧错误

     break ;

    case serialportevent.pe: // 8 奇偶校验错误

     break ;

    case serialportevent.cd: // 6 载波检测

     break ;

    case serialportevent.cts: // 3 清除待发送数据

     break ;

    case serialportevent.dsr: // 4 待发送数据准备好了

     break ;

    case serialportevent.ri: // 5 振铃指示

     break ;

    case serialportevent.output_buffer_empty: // 2 输出缓冲区已清空

     break ;

    case serialportevent.data_available: // 1 串口存在可用数据

     string time=df.format(localdatetime.ofinstant(instant.ofepochmilli(system.currenttimemillis()),zoneid.of( "asia/shanghai" )));

     byte [] data; //fe0400030001d5c5

     try {

      data = serialtool.readfromport(serialport);

      receivearea.append(time+ " [" +serialport.getname().split( "/" )[ 3 ]+ "] : " + printhexstring(data)+ "\r\n" );

      receivearea.setcaretposition(receivearea.gettext().length());

     } catch (ioexception e) {

      e.printstacktrace();

     }

     break ;

    default :

     break ;

    }

   }

  }

}

?

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

19

20

21

22

23

24

25

26

27

28

29

30

31

32

33

34

35

36

37

38

39

40

41

42

43

44

45

46

47

48

49

50

51

52

53

54

55

56

57

58

59

60

61

62

63

64

65

66

67

68

69

70

71

72

73

74

75

76

77

78

79

80

81

82

83

84

85

86

87

88

89

90

91

92

package serialport;

 

import java.awt.color;

import java.awt.font;

import java.awt.image;

import java.awt.toolkit;

import java.awt.event.keyadapter;

import java.awt.event.keyevent;

 

import javax.swing.jframe;

import javax.swing.jlabel;

 

 

/**

  * @author bh

  * 如果运行过程中抛出 java.lang.unsatisfiedlinkerror 错误,

  * 请将rxtx解压包中的 rxtxparallel.dll,rxtxserial.dll 这两个文件复制到 c:\windows\system32 目录下即可解决该错误。

  */

public class wellcomview {

 

  /** 程序界面宽度*/

  public static final int width = 800 ;

  /** 程序界面高度*/

  public static final int height = 620 ;

  /** 程序界面出现位置(横坐标) */

  public static final int loc_x = 200 ;

  /** 程序界面出现位置(纵坐标)*/

  public static final int loc_y = 70 ;

 

  private jframe jframe;

 

  /**主方法

   * @param args //

   */

  public static void main(string[] args) {

 

   new wellcomview();

  }

  public wellcomview() {

 

   init();

   listen();

  }

  /**

   */

  private void listen() {

 

   //添加键盘监听器

   jframe.addkeylistener( new keyadapter() {

    public void keyreleased(keyevent e) {

     int keycode = e.getkeycode();

     if (keycode == keyevent.vk_enter) { //当监听到用户敲击键盘enter键后执行下面的操作

      jframe.setvisible( false ); //隐去欢迎界面

      new serialview(); //主界面类(显示监控数据主面板)

     }

    }

   });

  }

  /**

   * 显示主界面

   */

  private void init() {

 

   jframe= new jframe( "串口调试" );

   jframe.setbounds(loc_x, loc_y, width, height); //设定程序在桌面出现的位置

   jframe.setlayout( null );

   //设置window的icon(这里我自定义了一下windows窗口的icon图标,因为实在觉得哪个小咖啡图标不好看 = =)

   toolkit toolkit = jframe.gettoolkit();

   image icon = toolkit.getimage(wellcomview. class .getresource( "computer.png" ));

   jframe.seticonimage(icon);

   jframe.setbackground(color.white); //设置背景色

 

   jlabel huanyin= new jlabel( "欢迎使用串口调试工具" );

   huanyin.setbounds( 170 , 80 , 600 , 50 );

   huanyin.setfont( new font( "微软雅黑" , font.bold, 40 ));

   jframe.add(huanyin);

 

   jlabel banben= new jlabel( "version:1.0 powered by:cyq" );

   banben.setbounds( 180 , 390 , 500 , 50 );

   banben.setfont( new font( "微软雅黑" , font.italic, 26 ));

   jframe.add(banben);

 

   jlabel enter= new jlabel( "————点击enter键进入主界面————" );

   enter.setbounds( 100 , 480 , 600 , 50 );

   enter.setfont( new font( "微软雅黑" , font.bold, 30 ));

   jframe.add(enter);

 

   jframe.setresizable( false ); //窗口大小不可更改

   jframe.setdefaultcloseoperation(jframe.exit_on_close);

   jframe.setvisible( true ); //显示窗口

  }

}

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持。

原文链接:https://blog.csdn.net/cuiyaoqiang/article/details/54928627

查看更多关于java使用Rxtx实现串口通信调试工具的详细内容...

  阅读:29次