Nodejs 串口通信 : websocket , serialport

最近在学习如何实现web页面和串口间通信,网页请求使用websocket,实现的基本功能如下:

1、基本需求:硬件:有两个信号灯(TLA-505-1T),一个485继电器(开关),电压转换器,工业触屏一体机。

2、原理图:

                Nodejs 串口通信 : websocket , serialport_第1张图片

3工作原理:

首先一体机中采用node开发服务器,网页请求采用websocket协议,直接放代码了:

var express = require('express');
var SerialPort = require('serialport');
var app = express();
var expressWs = require('express-ws')(app);
var util = require('util');
/*
var com =require('./com.js');
var logger = require('./log.js').logger;
*/


app.use(express.static('public'));
//ejs
app.set('view engine','ejs');

app.get('/',function(req,res){
    res.render('control');
})

app.ws('/ws', function(ws, req) {
    util.inspect(ws);

    ws.on("message",function(str){
        console.log('1234');
        //hander(str,ws);

    });
    ws.on("close",function(code,reason){
        console.log('connection closed');
    })
    //处理错误事件信息
    ws.on('error',function(err){
        console.log('throw err',err);
    })


})
function hander(str,ws) {
    //发送数据到客户端
    //console.log(str);
    var arr = str.split('');
    if(arr[2]==1){//close
        arr[2]=0;
    }else{
        arr[2]=1;
    }
    //console.log(arr.join(''));
    ws.send(arr.join(''));
}


app.listen(3004);

这样一个server服务写好,然后在写html界面:

html>
<html lang="en">
<head>

<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1">
<link rel="stylesheet" href="js/jquery.mobile-1.4.5.min.css">
<script src="js/jquery-1.11.3.min.js">script>
<script src="js/jquery.mobile-1.4.5.min.js">script>
    <title>Titletitle>
    <style>
        form{
            margin: 30px auto;
            width: 35%;
        }
    style>
 


head>
<body>
<br>
<form class="form">
    <fieldset>
        <legend>websocket 控制legend>
        <br>
        <br>
        <div>  
    <button type="button" style="background: #EEF9F3" id="deng1" value="100">灯1关闭状态button>
    <button type="button" style="background: #EEF9F3" id="deng2" value="110">灯2关闭状态button>
        div>
        <br>
         
        <span id='content'>客户端未连接span>br>

        <input type="button" value="连接" id="connect" class="connect"/>
    fieldset>
form>
<script>
    var oUl=document.getElementById('content');
    var oConnect=document.getElementById('connect');
    var oSend=document.getElementById('send');
    var oInput=document.getElementById('message');
    var ws=null;
    oConnect.onclick=function(){
        ws = new WebSocket('ws://localhost:3004/ws');
        ws.onopen=function(){
             
            document.getElementById('content').innerHTML = "客户端已连接";
        }
        ws.onmessage=function(evt){ 
            
            //document.getElementById('states').innerHTML = "deng : "+evt.data
            var arr = evt.data.split('');
            if(arr[1]==0){//deng1
                var deng = "deng1";
                changeState(deng,'states1');
            }else if(arr[1]==1){//deng2
                var deng = "deng2";
                changeState(deng,'states2');
            } 
            function changeState(deng,state){

                $('#'+deng).val(evt.data);
                if(arr[2]==1){//open 
                   // document.getElementById(state).innerHTML = deng+" open:"+evt.data;
                    document.getElementById(deng).innerHTML = (deng =='deng1'?'灯1':'灯2')+"关闭状态";
                    $('#'+deng).css("background-color","#B3B4A6");
                }else if(arr[2]==0){
                   // document.getElementById(state).innerHTML = deng+" close:"+evt.data;
                    document.getElementById(deng).innerHTML = (deng =='deng1'?'灯1':'灯2')+"打开状态";
                    $('#'+deng).css("background-color","#EEF9F3");
                }
            }   

        }
        ws.onclose=function(){
            document.getElementById('content').innerHTML = "客户端已断开连接";
        };
        ws.onerror=function(evt){
            oUl.innerHTML+="
  • "+evt.data+"
  • "
    ; }; }; //$(document).on("pagecreate","#pageone",function(){ $("#deng1").on("tap",function(){ ws.send($("#deng1").val()); }); //}); $("#deng2").on("tap",function(){ ws.send($("#deng2").val()); }); /*function clickDend(val){ console.log(val) if(ws){ ws.send(val); } }*/ script> body> html>

    这样一个完整的websocket协议完成,最后在socket协议中加入串口通信:

    var express = require('express');
    var SerialPort = require('serialport');
    var app = express();
    var expressWs = require('express-ws')(app);
    var util = require('util');
    var com =require('./com.js');
    /*
    var com =require('./com.js');
    var logger = require('./log.js').logger;
    */
    
    
    app.use(express.static('public'));
    //ejs
    app.set('view engine','ejs');
    
    app.get('/',function(req,res){
        res.render('control');
    })
    
    app.ws('/ws', function(ws, req) {
        util.inspect(ws);
        var sendDelay = 2000;
        ws.on("message",function(str){
            console.log('1234');
    
            var arr = str.split('');
            if(arr[2]==1){//close
                arr[2]=0;
            }else{
                arr[2]=1;
            }
            sendData(arr,ws);
            //setInterval(sendData,sendDelay);
    
        });
        ws.on("close",function(code,reason){
            console.log('connection closed');
        })
        //处理错误事件信息
        ws.on('error',function(err){
            console.log('throw err',err);
        })
    
    
    })
    
    var defaults = {
        //reportVersionTimeout: 5000,
        receiveInterval: 100,
        sendInterval: 500,
        repeatSendTimes: 30,  // ??????
        SerialName:'/dev/ttyAMA0',
        SerialPort: {
            baudRate: 9600,
            autoOpen: false,
            parity: 'none',
            xon: false,
            xoff: false,
            xany: false,
            rtscts: false,
            hupcl: true,
            dataBits: 8,
            stopBits: 1,
            bufferSize: 11
        }
    };
    
    
    var SerialPort = com.SerialPort;
    //logger.info('List all serialport');
    SerialPort.list(function (err, ports) {
        ports.forEach(function(port) {
            console.log(port.comName);
            console.log(port.pnpId);
            console.log(port.manufacturer);
        });
    });
    
    
    var test = new com.SerialPort(defaults.SerialName, defaults.SerialPort);
    
    
    var count=0;
    var sendTime = Date.now();
    test.on('data', function (data) {
        console.log("receive:"+util.inspect(data));
        count++;
        var elapsed = Date.now() - sendTime;
        console.log("count:"+count+",elapsed:"+elapsed+" ms");
    });
    
    test.on('error',function (err){
        console.log("error:"+err);
    });
    
    
    test.on('close',function (){
        console.log("close occured");
    });
    
    
    
    test.open(function (error) {
        console.log(error);
        console.log('com port opened');
    
    
    });
    
    var cmd1 = Buffer.from([0xaa,0x07,0xde,0x03,0x03,0x01,0x27,0x34,0x10,0x08,0x09]);
    var cmd2 = Buffer.from([0xaa,0x07,0xde,0x03,0x03,0x01,0x27,0x34,0x10,0x02,0x03]);
    var cmd3 = Buffer.from([0xFE,0x05,0x00,0x00,0xFF,0x00,0x98,0x35]);
    var cmd4 = Buffer.from([0xFE,0x05,0x00,0x00,0x00,0x00,0xD9,0xC5]);
    
    var cmd5 = Buffer.from([0xFE,0x05,0x00,0x01,0xFF,0x00,0xc9,0xf5]);
    var cmd6 = Buffer.from([0xFE,0x05,0x00,0x01,0x00,0x00,0x88,0x05]);
    
    var sendCount = 0;
    function sendData(arr,ws){
        console.log("send count:"+arr[1]);
        if(arr[1]==0){
            if(arr[2]==0){
                test.write(cmd3); //灯1 打开
                arr[2]==1;
            }else if(arr[2]==1){
                test.write(cmd4);  //灯1 关闭
                arr[2]==0;
            }
        }
        else if(arr[1]==1){
            if(arr[2]==0){
                test.write(cmd5); //灯1 打开
                arr[2]==1;
            }else if(arr[2]==1){
                test.write(cmd6);  //灯1 关闭
                arr[2]==0;
            }
        }
        ws.send(arr.join(''));
    }
    
    
    app.listen(3004);
    ok,就可以在一体机上单机按钮,控制灯的开关啦。






    你可能感兴趣的:(nodejs,基础)