欢迎使用CSDN-markdown编辑器
来源:互联网 发布:澳洲绵羊油 知乎 编辑:程序博客网 时间:2024/06/16 16:07
串口通信1(单向传输)
发送端
代码块
代码块语法遵循标准markdown代码,例如:
#ifndef SERIAL_H_#define SERIAL_H_class CSerial{public: CSerial(void); ~CSerial(void); //打开串口 BOOL OpenSerialPort(TCHAR* port, UINT baud_rate, BYTE date_bits, BYTE stop_bit, BYTE parity = NOPARITY); //发送数据 BOOL SendData(unsigned char* data); unsigned char* modbusFormat_pre(SLocaVecTime hitPoint);//击球点,水平角,垂直角度 unsigned char* modbusFormat_realtime(SLocaVecTime hitPoint);public: HANDLE m_hComm;private: UINT crc; unsigned char modbusDataBuf_pre[26]; unsigned char modbusDataBuf_realtime[14]; int m_dataLength;private: void calccrc(BYTE crcbuf); unsigned char highByte(int data); unsigned char lowByte(int data);};#endifCSerial.h
#pragma warning(disable:4996)typedef unsigned(__stdcall *PTHREAD_START) (void *);typedef int8_t;CSerial::CSerial(void){ m_hComm = INVALID_HANDLE_VALUE;}CSerial::~CSerial(void){ if (m_hComm != INVALID_HANDLE_VALUE){ CloseHandle(m_hComm); }}/********************************************************************************************** 功能 : 读串口线程回调函数* 描述 : 收到数据后,简单的显示出来********************************************************************************************/DWORD WINAPI CommProc(LPVOID lpParam){ CSerial* pSerial = (CSerial*)lpParam; // //清空串口 PurgeComm(pSerial->m_hComm, PURGE_RXCLEAR | PURGE_TXCLEAR); unsigned char buf[26]; DWORD dwRead; while (pSerial->m_hComm != INVALID_HANDLE_VALUE){ BOOL bReadOK = ReadFile(pSerial->m_hComm, buf, 26, &dwRead, NULL); if (bReadOK && (dwRead > 0)){ buf[dwRead] = '\0'; /*MessageBoxA(NULL, buf, "串口收到数据", MB_OK);*/ } } return 0;}/******************************************************************************************** 功能 : 打开串口* port : 串口号, 如_T("COM1:")* baud_rate: 波特率* date_bits: 数据位(有效范围4~8)* stop_bit : 停止位* parity : 奇偶校验。默认为无校验。NOPARITY 0; ODDPARITY 1;EVENPARITY 2;MARKPARITY 3;SPACEPARITY 4********************************************************************************************/BOOL CSerial::OpenSerialPort(TCHAR* port, UINT baud_rate, BYTE date_bits, BYTE stop_bit, BYTE parity){ //打开串口 m_hComm = CreateFile(port, GENERIC_READ | GENERIC_WRITE, 0, NULL, OPEN_EXISTING, 0, NULL);//独占方式打开串口 TCHAR err[512]; if (m_hComm == INVALID_HANDLE_VALUE){ _stprintf(err, _T("打开串口%s 失败,请查看该串口是否已被占用"), port); MessageBox(NULL, err, _T("提示"), MB_OK); return FALSE; } //MessageBox(NULL,_T("打开成功"),_T("提示"),MB_OK); //获取串口默认配置 DCB dcb; if (!GetCommState(m_hComm, &dcb)){ MessageBox(NULL, _T("获取串口当前属性参数失败"), _T("提示"), MB_OK); } //配置串口参数 dcb.BaudRate = baud_rate; //波特率 dcb.fBinary = TRUE; //二进制模式。必须为TRUE dcb.ByteSize = date_bits; //数据位。范围4-8 dcb.StopBits = ONESTOPBIT; //停止位 if (parity == NOPARITY){ dcb.fParity = FALSE; //奇偶校验。无奇偶校验 dcb.Parity = parity; //校验模式。无奇偶校验 } else{ dcb.fParity = TRUE; //奇偶校验。 dcb.Parity = parity; //校验模式。无奇偶校验 } dcb.fOutxCtsFlow = FALSE; //CTS线上的硬件握手 dcb.fOutxDsrFlow = FALSE; //DST线上的硬件握手 dcb.fDtrControl = DTR_CONTROL_ENABLE; //DTR控制 dcb.fDsrSensitivity = FALSE; dcb.fTXContinueOnXoff = FALSE;// dcb.fOutX = FALSE; //是否使用XON/XOFF协议 dcb.fInX = FALSE; //是否使用XON/XOFF协议 dcb.fErrorChar = FALSE; //是否使用发送错误协议 dcb.fNull = FALSE; //停用null stripping dcb.fRtsControl = RTS_CONTROL_ENABLE;// dcb.fAbortOnError = FALSE; //串口发送错误,并不终止串口读写 //设置串口参数 if (!SetCommState(m_hComm, &dcb)){ MessageBox(NULL, _T("设置串口参数失败"), _T("提示"), MB_OK); return FALSE; } //设置串口事件 SetCommMask(m_hComm, EV_RXCHAR); //在缓存中有字符时产生事件 SetupComm(m_hComm, 16384, 16384); //设置串口读写时间 COMMTIMEOUTS CommTimeOuts; GetCommTimeouts(m_hComm, &CommTimeOuts); CommTimeOuts.ReadIntervalTimeout = MAXDWORD; CommTimeOuts.ReadTotalTimeoutMultiplier = 0; CommTimeOuts.ReadTotalTimeoutConstant = 0; CommTimeOuts.WriteTotalTimeoutMultiplier = 10; CommTimeOuts.WriteTotalTimeoutConstant = 1000; if (!SetCommTimeouts(m_hComm, &CommTimeOuts)){ MessageBox(NULL, _T("设置串口时间失败"), _T("提示"), MB_OK); return FALSE; } //创建线程,读取数据 HANDLE hReadCommThread = (HANDLE)_beginthreadex(NULL, 0, (PTHREAD_START)CommProc, (LPVOID) this, 0, NULL); return TRUE;}/********************************************************************************************* 功能 : 通过串口发送一条数据********************************************************************************************/BOOL CSerial::SendData(unsigned char* data){ if (m_hComm == INVALID_HANDLE_VALUE){ MessageBox(NULL, _T("串口未打开"), _T("提示"), MB_OK); return FALSE; } //清空串口 PurgeComm(m_hComm, PURGE_RXCLEAR | PURGE_TXCLEAR); //写串口 DWORD dwWrite = 0; DWORD dwRet = WriteFile(m_hComm, data, m_dataLength, &dwWrite, NULL); //清空串口 PurgeComm(m_hComm, PURGE_RXCLEAR | PURGE_TXCLEAR); if (!dwRet){ MessageBox(NULL, _T("发送数据失败"), _T("提示"), MB_OK); return FALSE; } //HANDLE hReadCommThread = (HANDLE)_beginthreadex(NULL, 0, (PTHREAD_START)CommProc, (LPVOID) this, 0, NULL); return TRUE;}/********************************************************************************************* 功能 : CRC校验码计算********************************************************************************************/void CSerial::calccrc(BYTE crcbuf){ crc = crc^crcbuf; for (BYTE i = 0; i < 8; i++){ BYTE TT; TT = crc & 1; crc = crc & 0x7fff; if (TT == 1){ crc = crc ^ 0xa001; crc = crc & 0xffff; } }}/********************************************************************************************* 功能 : 数据格式转换********************************************************************************************/unsigned char* CSerial::modbusFormat_pre(SLocaVecTime hitPoint){ unsigned char startCharacter = 0x02;//起始 unsigned char stopCharacter = 0x03;//结束 unsigned char funcCode = 0x06;//命令 unsigned char sizeOfData = 0x14;//数据个数 crc = 0xffff; int time = int(hitPoint.Time * 1000);//单位:秒*1000 int coordX = int(hitPoint.Location.x * 1000);//单位:毫米 int coordY = int(hitPoint.Location.y * 1000); int coordZ = int(hitPoint.Location.z * 1000); int vectorX = int(hitPoint.Vec.x * 1000);//单位:毫米每秒 int vectorY = int(hitPoint.Vec.y * 1000); int vectorZ = int(hitPoint.Vec.z * 1000); int angleN = int(hitPoint.Yangle * 10);//水平角,单位:度*10 int angleO = int(hitPoint.Pangle * 10);//垂直角 modbusDataBuf_pre[0] = startCharacter; modbusDataBuf_pre[1] = funcCode; modbusDataBuf_pre[2] = sizeOfData; modbusDataBuf_pre[3] = highByte(time); modbusDataBuf_pre[4] = lowByte(time); modbusDataBuf_pre[5] = highByte(coordX); modbusDataBuf_pre[6] = lowByte(coordX); modbusDataBuf_pre[7] = highByte(coordY); modbusDataBuf_pre[8] = lowByte(coordY); modbusDataBuf_pre[9] = highByte(coordZ); modbusDataBuf_pre[10] = lowByte(coordZ); modbusDataBuf_pre[11] = highByte(angleN); modbusDataBuf_pre[12] = lowByte(angleN); modbusDataBuf_pre[13] = highByte(angleO); modbusDataBuf_pre[14] = lowByte(angleO); modbusDataBuf_pre[15] = highByte(vectorX); modbusDataBuf_pre[16] = lowByte(vectorX); modbusDataBuf_pre[17] = highByte(vectorY); modbusDataBuf_pre[18] = lowByte(vectorY); modbusDataBuf_pre[19] = highByte(vectorZ); modbusDataBuf_pre[20] = lowByte(vectorZ); modbusDataBuf_pre[21] = 0x00; modbusDataBuf_pre[22] = 0x00; for (int i = 3; i <= 22; i++){ calccrc(modbusDataBuf_pre[i]); } modbusDataBuf_pre[23] = crc & 0xff; modbusDataBuf_pre[24] = crc / 0x100; modbusDataBuf_pre[25] = stopCharacter; m_dataLength = 26; return modbusDataBuf_pre;}unsigned char* CSerial::modbusFormat_realtime(SLocaVecTime hitPoint){ unsigned char startCharacter = 0x02;//起始 unsigned char stopCharacter = 0x03;//结束 unsigned char funcCode = 0x08;//命令 unsigned char sizeOfData = 0x08;//数据个数 crc = 0xffff; int time = int(hitPoint.Time * 1000);//单位:秒*1000 int coordX = int(hitPoint.Location.x * 1000);//单位:毫米 int coordY = int(hitPoint.Location.y * 1000); int coordZ = int(hitPoint.Location.z * 1000); modbusDataBuf_realtime[0] = startCharacter; modbusDataBuf_realtime[1] = funcCode; modbusDataBuf_realtime[2] = sizeOfData; modbusDataBuf_realtime[3] = highByte(time); modbusDataBuf_realtime[4] = lowByte(time); modbusDataBuf_realtime[5] = highByte(coordX); modbusDataBuf_realtime[6] = lowByte(coordX); modbusDataBuf_realtime[7] = highByte(coordY); modbusDataBuf_realtime[8] = lowByte(coordY); modbusDataBuf_realtime[9] = highByte(coordZ); modbusDataBuf_realtime[10] = lowByte(coordZ); for (int i = 3; i <= 10; i++){ calccrc(modbusDataBuf_realtime[i]); } modbusDataBuf_realtime[11] = crc & 0xff; modbusDataBuf_realtime[12] = crc / 0x100; modbusDataBuf_realtime[13] = stopCharacter; m_dataLength = 14; return modbusDataBuf_realtime;}/********************************************************************************************* 功能 : 数据高低位计算********************************************************************************************/unsigned char CSerial::highByte(int data){ unsigned char HighByte; if (data >= 0){ HighByte = data / 256; } else{ data = abs(data); HighByte = data / 256 + 0x80; } return HighByte & 0xFF;}unsigned char CSerial::lowByte(int data){ data = abs(data); unsigned char LowByte; LowByte = data % 256; return LowByte & 0xFF;}... CSerial.cpp'''
#include <fstream>#include <tchar.h>#include "Global.h"#include "CSerial.h"using namespace std;ifstream fin("result.txt");int main(){ CSerial* pSerial = new CSerial(); if(!pSerial->OpenSerialPort(_T("COM7:"), 115200, 8, 1, 1)){ cout << "OpenSerialPort Error" << endl; return -1; } SLocaVecTime data; float HorAngle = 0.0; float VerAngle = 0.0; int line = 0; while (!fin.eof()){ fin >> data.Location.x; fin >> data.Location.y; fin >> data.Location.z; fin >> data.Vec.x; fin >> data.Vec.y; fin >> data.Vec.z; fin >> data.Yangle; fin >> data.Pangle; fin >> data.Time; pSerial->SendData(pSerial->modbusFormat_pre(data)); line++; cout << line << endl; Sleep(10); }}
阅读全文
0 0
- 欢迎使用CSDN-markdown编辑器
- 欢迎使用CSDN-markdown编辑器
- 欢迎使用CSDN-markdown编辑器
- 欢迎使用CSDN-markdown编辑器
- 欢迎使用CSDN-markdown编辑器
- 欢迎使用CSDN-markdown编辑器
- 欢迎使用CSDN-markdown编辑器
- 欢迎使用CSDN-markdown编辑器
- 欢迎使用CSDN-markdown编辑器
- 欢迎使用CSDN-markdown编辑器
- 欢迎使用CSDN-markdown编辑器
- 欢迎使用CSDN-markdown编辑器
- 欢迎使用CSDN-markdown编辑器
- 欢迎使用CSDN-markdown编辑器
- 欢迎使用CSDN-markdown编辑器
- 欢迎使用CSDN-markdown编辑器
- 欢迎使用CSDN-markdown编辑器
- 欢迎使用CSDN-markdown编辑器
- (学习java)哈夫曼树的简单实现
- pandas常见的时间处理函数
- SQL中的Case when
- c++常见问题
- MySQL 学习教程(十一)【整理】-子查询
- 欢迎使用CSDN-markdown编辑器
- Java HashMap工作原理及实现
- 测试
- 链表,顺序表的逆置
- JSP 四大作用域:
- 输出数字方阵
- Leetcode 213
- python类的重写、私有变量
- HTC View 手柄操作简介