?? pc2pcview.cpp
字號:
}
dwFileLen=arrRcvData[1]+arrRcvData[2]*256+arrRcvData[3]*65536+arrRcvData[4]*16777216;
myFile.SetLength(dwFileLen);
uintStxCurNo=1;
bytRcvStatus=1;
bytResendCount=0;
arrSendData[0]=6;
Write(arrSendData,1);
break;
}
case 100://超時錯誤
{
//接收0態時,對超時不作處理
break;
}
}
break;
}
case 1:
{
switch(lParam)
{
case EV_RXCHAR://收到字符
{
switch(Detect(1))
{
case 0://收到指定數量的字符
{
break;
}
case 4://超時錯誤
{
DisRcv(4);
return -1;
break;
}
case 8://無效,輸入緩沖區中字符數量為0
{
return 0;
break;
}
}
switch(Read(myByte,1))
{
case 0:
{
break;
}
case 4:
{
DisRcv(4);
return -1;
break;
}
case 16:
{
DisRcv(16);
return -1;
break;
}
}
switch(myByte[0])//判斷是STX還是ETX
{
case 2://首字符是STX
{
//讀取數據
arrRcvData[0]=myByte[0];
uintRcvLen=1028;
switch(Detect(1027))
{
case 0://收到指定數量的字符
{
//跳出switch,繼續下面的操作
break;
}
case 4://超時錯誤
{
DisRcv(4);
return -1;
break;
}
case 8://無效,輸入緩沖區中字符數量為0
{
return 0;
break;
}
}///
switch(Read(myByte,1027))
{
case 0:
{
break;
}
case 4:
{
DisRcv(4);
return -1;
break;
}
case 16:
{
DisRcv(16);
return -1;
break;
}
}
for(i=0;i<=1026;i++)
{
arrRcvData[i+1]=myByte[i];//保存數據至arrRcvData[]數組中
}
uintStxCurNo=arrRcvData[1]+arrRcvData[2]*256;
if(uintStxCurNo==1)
{
myEdit.SetSel(1000000,1000000);
myEdit.ReplaceSel("正在接收數據……\15\12");
}
strDis.Format("已接收(%.0f%%)",(float)((uintStxCurNo+1)*1024)/dwFileLen*100);
m_pStatus->SetPaneText(0,strDis); //將傳輸進度顯示在狀態條上
myFile.Seek((uintStxCurNo-1)*1024,CFile::begin);
myFile.Write(&arrRcvData[3],1024);
bytResendCount=0;
arrSendData[0]=6;
Write(arrSendData,1);
break;
}
case 3://首字符是ETX
{
//讀取數據
arrRcvData[0]=myByte[0];
switch(Read(myByte,2))
{
case 0:
{
break;
}
case 4:
{
DisRcv(4);
return -1;
break;
}
case 16:
{
DisRcv(16);
return -1;
break;
}
}
arrRcvData[1]=myByte[0];
arrRcvData[2]=myByte[1];
uintRcvLen=1+2+2+(arrRcvData[1]+arrRcvData[2]*256)+1;//數據總長度
switch(Read(myByte,uintRcvLen-3))
{
case 0:
{
break;
}
case 4:
{
DisRcv(4);
return -1;
break;
}
case 16:
{
DisRcv(16);
return -1;
break;
}
}
for(i=0;(UINT)i<=uintRcvLen-2;i++)
{
arrRcvData[i+3]=myByte[i];
}
//至此,完整數據已經讀入arrRcvData[]中。
uintStxCurNo=arrRcvData[3]+arrRcvData[4]*256;
if(uintStxCurNo==1)
{
myEdit.SetSel(1000000,1000000);
myEdit.ReplaceSel("正在接收數據……\15\12");
}
myFile.Seek((uintStxCurNo-1)*1024,CFile::begin);
myFile.Write(&arrRcvData[5],arrRcvData[1]+arrRcvData[2]*256);
myEdit.SetSel(1000000,1000000);
myEdit.ReplaceSel("接收完畢!\15\12\15\12");
strDis="已接收完畢";
m_pStatus->SetPaneText(0,strDis); //將傳輸進度顯示在狀態欄上
bytRcvStatus=0;
bytActStatus=10;
bytSendStatus=0;
bytResendCount=0;
arrSendData[0]=6;
Write(arrSendData,1);
if(myFile.m_pStream!=NULL)
{
myFile.Close();//關閉打開的文件
}
break;
}
}
break;
}
case 100://超時錯誤
{
break;
}
}
break;
}
}
break;
}
}
return 0;
}
void CPC2PCView::OnUpdateSendfile(CCmdUI* pCmdUI)
{
// TODO: Add your command update UI handler code here
if (blnOpened)//根據串口是否打開,決定是否允許“發送文件”命令
{
if(!((bytSendStatus+bytRcvStatus)>0))//當前既沒開始發送,也沒開始接收
{
pCmdUI->Enable(true);
}
else
{
pCmdUI->Enable(false);
}
}
else
{
pCmdUI->Enable(false);
}
}
void CPC2PCView::OnUpdateSetupcom(CCmdUI* pCmdUI)
{
// TODO: Add your command update UI handler code here
if (!blnOpened)//根據串口是否打開,決定是否允許“設置”命令
{
pCmdUI->Enable(true);
}
else
{
pCmdUI->Enable(false);
}
}
void CPC2PCView::OnUpdateOpencom(CCmdUI* pCmdUI)
{
// TODO: Add your command update UI handler code here
if (!blnOpened && blnSeted)//根據串口是否打開,決定是否允許“打開”命令
{
pCmdUI->Enable(true);
}
else
{
pCmdUI->Enable(false);
}
}
void CPC2PCView::OnUpdateClosecom(CCmdUI* pCmdUI)
{
// TODO: Add your command update UI handler code here
if (blnOpened)//根據串口是否打開,決定是否允許“關閉”命令
{
if(!((bytSendStatus+bytRcvStatus)>0))//當前既沒開始發送文件,也沒開始接收文件
{
pCmdUI->Enable(true);
}
else
{
pCmdUI->Enable(false);
}
}
else
{
pCmdUI->Enable(false);
}
}
int CPC2PCView::OnCreate(LPCREATESTRUCT lpCreateStruct)
{
if (CEditView::OnCreate(lpCreateStruct) == -1)
return -1;
// TODO: Add your specialized creation code here
CEdit& myEdit=this->GetEditCtrl( );
myEdit.SetReadOnly (true); //將顯示區域設為只讀
hWnd=GetSafeHwnd(); //獲取當前窗口的句柄
blnOpened=false; //串口已經打開標志
blnSeted=false; //已經設置過通信參數
bytRcvStatus=0; //初始化時,接收狀態為等待ENQ
dwTimeoutValue=1500; //初始化事件線程超時時間
bytActStatus=10; //初始化為接收態
blnNoTimeout=true;
uintStxCurNo=0;
bytTimeoutCounter=0;
return 0;
}
bool CPC2PCView::DisSend(BYTE bytType)//發送態顯示信息函數,bytType決定顯示信息的內容
{
CString strDis;
CEdit& myEdit=this->GetEditCtrl();
myEdit.SetReadOnly(true);
myEdit.SetSel(1000000,1000000);
switch(bytType)
{
case 1:
{
strDis="取消操作!\15\12";
break;
}
case 2:
{
strDis="收到無效的命令!\15\12";
break;
}
case 4:
{
strDis="對方無響應,超時錯誤!\15\12";
break;
}
case 8:
{
strDis="重試次數多于3次!\15\12";
break;
}
}
myEdit.ReplaceSel(strDis);
bytSendStatus=0;//恢復發送0態
bytActStatus=10;//恢復為接收態
bytRcvStatus=0;
bytResendCount=0;//重試次數初始化為0
if(myFile.m_pStream!=NULL)
{
myFile.Close();//關閉打開的文件
}
Beep(1000,50);
return true;
}
bool CPC2PCView::DisRcv(BYTE bytType)//接收態顯示信息函數,bytType決定顯示信息的內容
{
CString strDis;
CEdit& myEdit=this->GetEditCtrl();
myEdit.SetReadOnly(true);
myEdit.SetSel(1000000,1000000);
switch(bytType)
{
case 1:
{
strDis="取消操作!\15\12";
break;
}
case 2:
{
strDis="收到無效的命令!\15\12";
break;
}
case 4:
{
strDis="對方無響應,超時錯誤!\15\12";
break;
}
case 8:
{
strDis="重試次數多于3次!\15\12";
break;
}
}
myEdit.ReplaceSel(strDis);
bytRcvStatus=0; //恢復接收0態
bytActStatus=10; //恢復為接收態
bytSendStatus=0; //發送態恢復為0態
bytResendCount=0; //重試次數初始化為0
if(myFile.m_pStream!=NULL)
{
myFile.Close(); //關閉打開的文件
}
return true;
}
BYTE CPC2PCView::Read(BYTE arrBin[],int count)//讀數據函數,arrBin[]存放數據,count是讀的個數
{ //成功返回0,讀失敗返回16,超時錯誤返回4
DWORD dwRes;
DWORD dwRead;
Rol.hEvent=CreateEvent(NULL, //創建Rol.hEvent為無信號狀態
TRUE,
FALSE,
NULL);
if (ReadFile(hCom,
arrBin,
count, //讀取count個字節
NULL,
&Rol))
{
//串口接收的數據已經成功讀出,并存放在arrBin[]數組中
return 0;
}
else
{
dwRes = WaitForSingleObject(Rol.hEvent,
2000); //設置2秒的讀超時
switch(dwRes)
{
case WAIT_OBJECT_0:
{
if (!GetOverlappedResult(hCom,
&Rol,
&dwRead, //實際讀取字節數存放在dwRead中
TRUE))
{
//讀操作失敗。使用GetLastError()函數可以獲取錯誤消息
return 16;
}
else
{
//串口接收的數據已經成功讀出,并存放在arrBin[]數組中
return 0;
}
break;
}
case WAIT_TIMEOUT:
{
//讀操作出現超時錯誤。
return 4;
}
}
}
return 0;
}
//發送數據函數,arrBin[]存放數據,count是發送個數
//發送態時,發送數據調用這個函數
//接收態時,響應時調用這個函數發送響應代碼ACK、NAK或CAN
bool CPC2PCView::Write(BYTE arrBin[],int count)
{
DWORD dwWrite;
Wol.hEvent=CreateEvent(NULL, //創建Wol.hEvent事件句柄,并設置為無信號狀態
TRUE,
FALSE,
NULL);
WriteFile(hCom, //寫數據,通過Wol結構獲取操作結果
arrBin,
count,
NULL,
&Wol);
if(GetOverlappedResult(hCom,&Wol,&dwWrite,true))
{
return true;
}
return false;
}
//檢測串口輸入緩沖區中是否有指定個數的數據
//返回0-有,4-超時錯誤,8-無效
BYTE CPC2PCView::Detect(int count)
{
DWORD dwErrors;
COMSTAT Rcs;
CString strDis,strDis1;
BYTE bytTimeCount;
ClearCommError(hCom, //串口句柄
&dwErrors, //存放出錯信息的掩碼組合
&Rcs); //COMSTAT類型結構變量
if(Rcs.cbInQue==0)
return 8;
bytTimeCount=0;
while(bytTimeCount<4)
{
ClearCommError(hCom, //串口句柄
&dwErrors, //存放出錯信息的掩碼組合
&Rcs); //COMSTAT類型結構變量
if(Rcs.cbInQue>=(UINT)count)
{
return 0;//在輸入緩沖區中找到指定數量的字符
}
Sleep(500);
bytTimeCount++;
}
if((bytTimeCount>=4)&&(Rcs.cbInQue>0))//超時錯誤
{
return 4;//未找到
}
return 8;//無效狀態,輸入緩沖區中為0個字符
}
void CPC2PCView::OnDestroy()
{
CEditView::OnDestroy();
// TODO: Add your message handler code here
}
void CPC2PCView::OnUpdateAppExit(CCmdUI* pCmdUI)
{
// TODO: Add your command update UI handler code here
if (!blnOpened) //根據串口是否打開,決定是否允許“退出”命令
{
pCmdUI->Enable(true);
}
else
{
pCmdUI->Enable(false);
}
}
?? 快捷鍵說明
復制代碼
Ctrl + C
搜索代碼
Ctrl + F
全屏模式
F11
切換主題
Ctrl + Shift + D
顯示快捷鍵
?
增大字號
Ctrl + =
減小字號
Ctrl + -