https://blog.csdn.net/trustguan/article/details/50598840
https://blog.csdn.net/qing666888/article/details/78435715?locationNum=1&fps=1
這倆位博主發的博文很有參考意義但是存在很多錯誤
0. 筆者電腦環境
win10+VS2015+CnComm v1.51 多線程串口通訊庫
1. 安裝usb轉串口驅動:PL2303_Prolific_DriverInstaller_v1.11.0
留下郵箱,筆者可以發給你
2. 下載串口助手:USR-TCP232-Test-V1.3(串口以太網調試助手)
留下郵箱,筆者可以發給你
打開之後的樣子
參數設置操作
3. 下載“CnComm.h”頭文件,引入項目
可以在開頭兩個博主那裏下載,也可以私信筆者
4. 新建win32項目SerialThread
5. 構建繼承CnComm類的子類:SerialThread類(要分別編寫“SerialThread.h”、"SerialThread.cpp")
首先編寫“SerialThread.h”頭文件,定義繼承自CnComm類的子類:SerialThread類
//SRIALTHREAD_H 頭文件標識,避免重複定義,
//和頭文件無直接關係,可以隨便定義,但一般是文件名的大寫
#ifndef SRIALTHREAD_H
#define SRIALTHREAD_H
#include"CnComm.h"
class SerialThread : public CnComm
{
public:
SerialThread();//構建函數,可以爲空
virtual ~SerialThread();//解析函數,可以爲空
void ThreadInit();//打開串口
void CloseSerialPort(); //關閉串口
void SendDatas(char *msg);//發送數據
void OnReceive(); //接收數據
private:
CnComm Com;//實例化CnComm類
//備用函數,不是必須的
int Ascii2Hex(char* ascii, char* hex); //ascii轉十六進制
int Hex2Ascii(char* hex, char* ascii); //十六進制轉ascii
};
#endif
然後編寫“SerialThread.cpp”具體定義SerialThread類中的方法
#include "SerialThread.h"
#include <iostream>
using namespace std;
SerialThread::SerialThread()
{
}
SerialThread::~SerialThread()
{
}
void SerialThread::ThreadInit()
{
if (!Com.IsOpen())
{
//CnComm::Open函數就是用來打開串口
//bool Open(DWORD dwPort, LPCTSTR szPortName, DWORD dwBaudRate, BYTE btParity = NOPARITY, BYTE btByteSize = 8, BYTE btStopBits = ONESTOPBIT)
//dwPort,szPortName可以在“計算機管理->設備管理器->端口(COM和LPT)->雙擊設備名:位置”
if (!Com.Open(7, _T("COM5"), 115200))//
{
cout << "open fail" << endl;
}
}
else {
cout << "already open" << endl;
}
}
void SerialThread::CloseSerialPort()
{
Com.Close();//關閉串口
cout << "Close Successfully!" << endl;
}
void SerialThread::SendDatas(char *msg)
{
if (Com.IsOpen())
{
Com.Write(msg);//寫入字符串,實現控制
}
}
void SerialThread::OnReceive()
{
do {
char buffer[1024];
int len = Com.Read(buffer, 1023);//接受字符串
buffer[len] = _T('\0');
cout << buffer << endl;
} while (Com.IsRxBufferMode() && Com.Input().SafeSize());
}
int SerialThread::Ascii2Hex(char* ascii, char* hex)
{
int i, len = strlen(ascii);
char chHex[] = "0123456789ABCDEF";
for (i = 0; i < len; i++)
{
hex[i * 3] = chHex[((BYTE)ascii[i]) >> 4];
hex[i * 3 + 1] = chHex[((BYTE)ascii[i]) & 0xf];
hex[i * 3 + 2] = ' ';
}
hex[len * 3] = '\0';
return len * 3;
}
int SerialThread::Hex2Ascii(char* hex, char* ascii)
{
int len = strlen(hex), tlen, i, cnt;
for (i = 0, cnt = 0, tlen = 0; i < len; i++)
{
char c = toupper(hex[i]);
if ((c >= '0'&& c <= '9') || (c >= 'A'&& c <= 'F'))
{
BYTE t = (c >= 'A') ? c - 'A' + 10 : c - '0';
if (cnt)
ascii[tlen++] += t, cnt = 0;
else
ascii[tlen] = t << 4, cnt = 1;
}
}
return tlen;
}
這裏要想用CnComm::Open打開串口,就要找對端口號(port number)和端口名稱(port name)
找尋方法:
計算機管理->設備管理器->端口(COM和LPT)->雙擊設備名:位置
6. 編寫“main.cpp”,實例開發
release x86 編譯通過!
記得關閉 串口助手,避免它佔用端口
#include"SerialThread.h"
#include<iostream>
using namespace std;
void main() {
SerialThread st;
st.ThreadInit();
char msg[] = {"(send2:0)"};//這是筆者自己的通訊字符格式
st.SendDatas(msg);//發送控制字符
st.OnReceive();//接受回覆字符
//st.CloseSerialPort();//關閉串口
system("pause");
}
【1】error C3688: 文本後綴“L”無效;未找到文文本運算符或文本運算符模板“operator “”“”L”
解決方法:
詳情參見:https://blog.csdn.net/qq_29350001/article/details/79994524
解決方法:在字符串里加引號用\
原來宏定義爲:
#define CN_ASSERT(E) ((E) ? true : CnComm::Assert(_T(“CN_ASSERT(“)_T(#E)_T(“) failed; CnComm(“)CN_LINE(LINE)_T(“); “)))
修改爲:
#define CN_ASSERT(E) ((E) ? true : CnComm::Assert(_T(“CN_ASSERT(\”)_T(#E)_T(\”) failed; CnComm(\”)CN_LINE(LINE)_T(\”); “)))
【2】warning C4996: '_vsnprintf': This function or variable may be unsafe. ......(VS2013)
解決方法:
詳情參見:https://blog.csdn.net/hw_henry2008/article/details/6436451
在“CnComm.h”頭文件最開始處添加如下代碼
#pragma warning(disable:4996)
不容易啊!