wxWidgets serial Commuication

时间:2018-03-21 10:38:13

标签: port wxwidgets

我完全没有编程串行通信的经验,因为我坚持使用我的代码,我真的很感谢你的帮助!谢谢你!

现在我的问题是:

我有一台发电机,其上有几个不同的传感器,通过CAN与微控制器进行通信。该mc本身通过CAN再次与来自USBTin的设备通信。在USBTin上,一块小板,主要是一个CAN控制器和一个微控制器,它们是由开发人员预编码的。

所以现在我的任务是打开我的COM端口,将正确的消息发送到USBTin(波特率为“S5”,Open CAN为“O”),然后接收数据。

首先是功能和我的问题:

问题是在我的输出文本字段中有类似“PPPPPPPPPP,Râö”的内容。总有这10个P和一些随机字符。我不知道P或这些额外的“Râö”来自哪里。实际的输出字符串应该像“T1E18001F8”。我用hTerm测试了它,这是一个用于串行通信的终端程序。

OPEN:

long Serial::Open()
{
if (IsOpened()) return 0;
#ifdef UNICODE
wstring wtext(port.begin(),port.end());
#else
string wtext = port;
#endif
hComm = CreateFile(wtext.c_str(),
    GENERIC_READ | GENERIC_WRITE,
    0,
    0,
    OPEN_EXISTING,
    FILE_ATTRIBUTE_NORMAL | FILE_FLAG_OVERLAPPED,
    0);
if (hComm == INVALID_HANDLE_VALUE) {return 1;}

if (PurgeComm(hComm, PURGE_TXABORT | PURGE_RXABORT | PURGE_TXCLEAR | 
PURGE_RXCLEAR) == 0) {return 2;}//purge

//get initial state
DCB dcbOri;
bool fSuccess;
fSuccess = GetCommState(hComm, &dcbOri);
if (!fSuccess) {return 3;}

DCB dcb1 = dcbOri;

dcb1.BaudRate = baud;

if (parity == 'E') dcb1.Parity = EVENPARITY;
else if (parity == 'O') dcb1.Parity = ODDPARITY;
else if (parity == 'M') dcb1.Parity = MARKPARITY;
else if (parity == 'S') dcb1.Parity = SPACEPARITY;
else if (parity == 'N') dcb1.Parity = NOPARITY;

dcb1.ByteSize = (BYTE)dsize;

if(stopbits==2) dcb1.StopBits = TWOSTOPBITS;
else if (stopbits == 1.5) dcb1.StopBits = ONE5STOPBITS;
else if (stopbits == 1)   dcb1.StopBits = ONE5STOPBITS;

dcb1.fOutxCtsFlow = false;
dcb1.fOutxDsrFlow = false;
dcb1.fOutX = false;
dcb1.fDtrControl = DTR_CONTROL_DISABLE;
dcb1.fRtsControl = RTS_CONTROL_DISABLE;
fSuccess = SetCommState(hComm, &dcb1);
delay(60);
if (!fSuccess) {return 4;}

fSuccess = GetCommState(hComm, &dcb1);
if (!fSuccess) {return 5;}

osReader = { 0 };// Create the overlapped event. Must be closed before 
exiting to avoid a handle leak.
osReader.hEvent = CreateEvent(NULL, TRUE, FALSE, NULL);

if (osReader.hEvent == NULL) {return 6;}// Error creating overlapped event; 
abort.
fWaitingOnRead = FALSE;

osWrite = { 0 };
osWrite.hEvent = CreateEvent(NULL, TRUE, FALSE, NULL);
if (osWrite.hEvent == NULL) {return 7;}

if (!GetCommTimeouts(hComm, &timeouts_ori)) { return 8; } // Error getting 
time-outs.
COMMTIMEOUTS timeouts;
timeouts.ReadIntervalTimeout = 20;
timeouts.ReadTotalTimeoutMultiplier = 15;
timeouts.ReadTotalTimeoutConstant = 100;
timeouts.WriteTotalTimeoutMultiplier = 15;
timeouts.WriteTotalTimeoutConstant = 100;
if (!SetCommTimeouts(hComm, &timeouts)) { return 9;} // Error setting time-
outs.
return 0;
}

WRITE:

    bool Serial::Write(char *data)
    {
    if (!IsOpened()) {
        return false;
    }
    BOOL fRes;
    DWORD dwWritten;
    long n = strlen(data);
    if (n < 0) n = 0;
    else if(n > 1024) n = 1024;

    // Issue write.
    if (!WriteFile(hComm, data, n, &dwWritten, &osWrite)) {
        if (GetLastError() != ERROR_IO_PENDING) {fRes = FALSE;}// WriteFile 
    failed, but it isn't delayed. Report error and abort.
        else {// Write is pending.
            if (!GetOverlappedResult(hComm, &osWrite, &dwWritten, TRUE)) 
    fRes = FALSE;
            else fRes = TRUE;// Write operation completed successfully.
        }
    }
    else fRes = TRUE;// WriteFile completed immediately.
    return fRes;
    }

READCHAR:

    char Serial::ReadChar(bool& success)
    {
    success = false;
    if (!IsOpened()) {return 0;}

    DWORD dwRead;
    DWORD length=1;
    BYTE* data = (BYTE*)(&rxchar);
    //the creation of the overlapped read operation
    if (!fWaitingOnRead) {
        // Issue read operation.
        if (!ReadFile(hComm, data, length, &dwRead, &osReader)) {
            if (GetLastError() != ERROR_IO_PENDING) { /*Error*/}
            else { fWaitingOnRead = TRUE; /*Waiting*/}
        }
        else {if(dwRead==length) success = true;}//success
    }


    //detection of the completion of an overlapped read operation
    DWORD dwRes;
    if (fWaitingOnRead) {
        dwRes = WaitForSingleObject(osReader.hEvent, READ_TIMEOUT);
        switch (dwRes)
        {
        // Read completed.
        case WAIT_OBJECT_0:
            if (!GetOverlappedResult(hComm, &osReader, &dwRead, FALSE)) 
        {/*Error*/ }
            else {
                if (dwRead == length) success = true;
                fWaitingOnRead = FALSE;// Reset flag so that another 
        opertion 
        can be issued.
            }// Read completed successfully.
            break;

        case WAIT_TIMEOUT:
            // Operation isn't complete yet.
            break;

        default:
            // Error in the WaitForSingleObject;
            break;
        }
    }
    return rxchar;
    }

最后在wxWidgets中显示主要内容以显示收到的数据:

void GUI_1_2Frame::OnConnectButtonClick(wxCommandEvent&  (event))
{
char tempString[10] = {0};
bool ReadChar_success = true;
char temp_Char;
/* Preset Serial Port setting */
Serial com(com_x, 115200, 8, NOPARITY, 1);

char* buffer;
if(connection_flag)
{
    /* Port was connected, Disconnect Button unsed*/
    com.Close();
    wxMessageBox(_("Port closed"),_("Info!"),wxICON_INFORMATION);
    connection_flag = 0;
    ConnectButton->SetLabel("Connect");
    TextCtrl1->SetValue("");
}
else
{
    /* If open() == true -> INVALID HANDLE */
    if(com.Open())
    {
        wxMessageBox(_("Port not available"),_("ERROR!"),wxICON_ERROR);
    }
    else /* Port Opened */
    {
        TextCtrl1->SetValue(com.GetPort());
        ConnectButton->SetLabel("Disconnect");
        connection_flag = 1;
    }
    if(com.Write("S5"))
    {
        TextCtrl1->SetValue("Baudrate sent!\n");
        delay(100);
        if(com.WriteChar('O'))
        {
            TextCtrl1->SetValue("Baudrate & Open Command sent!");

            int i =0;
            while(i<10)
            {
                temp_Char = com.ReadChar(ReadChar_success);
                tempString[i] = temp_Char;
                i++;
            }
            com.WriteChar('C');
            com.Close();
            //com.readSerialPort(data, MAX_DATA_LENGTH);
            TextCtrl2->SetValue(tempString);
            //wxMessageOutput::Get()->Printf("%s", tempString);
        }
        else
        {
            TextCtrl1->SetValue("Open Command Error!");            }
    }
    else
    {
        TextCtrl1->SetValue("Error!");
    }

}
}

因为我不是天生的说英语,所以我对我的语言错误表示抱歉。 非常感谢大家,我非常感谢每一个提示!

问候,

MSOL

0 个答案:

没有答案