網路聊天室

來源:互聯網
上載者:User

標籤:mfc   socket   tcp協議   

1網路聊天室項目描述1.1功能描述

MyQQv1採用C/S模式,構建網路聊天室,具體實現功能:

A.能顯示線上使用者列表

B.能在聊天室裡進行群聊天

C.能指定使用者進行私聊

D.某使用者下線,其他使用者能接到提示

1.2所需技術

MFC,Socket通訊端,TCP/IP協議,動態數組,CString字串拼接與拆分

2網路聊天室運行流程圖2.1伺服器運行流程圖


2.2用戶端運行流程圖


3網路聊天室詳細3.1通訊格式

每次用戶端與伺服器之間的通訊都是發送“START&命令&自己名字&訊息&私密者&END”(為標準格式字串)的字串,然後接受方會進行分割和按照“&”進行分段解析。

3.1.1訊息分割

當某次(在接受全部線上使用者列表時)次接受不止一條格式字串時,把整個字串切割成若干個標準格式字串。程式清單如下所示。

/********************************************************************函數名稱:MsgCut函數功能:把資料流按通訊格式分割處理傳入參數:CString strText傳回值:  無********************************************************************/void CClientSocket::MsgCut(CString strText){UINT nfirst , nlast;CString strTmp;while(strText.GetLength() > 9){nfirst = strText.Find("START");nlast  = strText.Find("END");strTmp = strText.Mid(nfirst, nlast+3);//每次截取從START到END的字串char * sTran = strTmp.GetBuffer(0);//CString轉化為char *型MsgDeal(sTran);strText = strText.Mid(nlast+3,strText.GetLength()-nlast-3);}}

nfirst得到“START”子串的起始位置,nlast得到“END”子串的起始位置,strTmp為“START”開始到“END”(包括末尾D)的一個標準格式字串。再把原始長串切掉剛形成的strTmp,strText使用Mid(上一個EDN位置+3,總長度-上一個EDN位置-3)函數得到切割完的字串,直到strText滿足最小標準長度。

3.1.2按“&”分段解析

每個標準格式字串中包含命令,發來使用者名稱,訊息,私密者4個資訊。它們按照“&”串連在一起,接收端要按“&”分段解析,程式清單如下。

/***********************************************************************函數名稱:MsgExplain函數功能:對訊息的拆解,訊息傳來的格式是 k&1&使用者名稱&說的話&私密的人傳入參數:char sMsgDeal[5][BUFMAX],char * sMsgInit傳回值:  無***********************************************************************/void CClientSocket::MsgExplain(char sMsgDeal[6][BUFMAX],char * sMsgInit){char *p;bool bFlg = FALSE;int iRow = -1;int iCol = 0;char c = 0;p=sMsgInit;while (*p != '\0'){c = *p;if ( c != '&'){if (bFlg == FALSE)//如果碰到新的單詞列{bFlg = TRUE;iRow++;iCol = 0;}sMsgDeal[iRow][iCol] = c;iCol++;} else{if (bFlg == TRUE){sMsgDeal[iRow][iCol]='\0';}bFlg = FALSE;}p++;sMsgDeal[iRow][iCol] = '\0';}}

其中最後一句是當解析到最後一個單詞的時候沒有&,但是還是要在字串的末尾加’\0’的字串結束符,避免最後一個sMsgDeal[6]串出錯。

3.2伺服器類3.2.1重載OnAccept函數

伺服器使用Create(PORT)開啟成功後,使用Listen()進行監聽,當有用戶端進行串連請求後,發生OnAccept訊息響應,此時重載OnAccept函數。

/***********************************************************************函數名稱:OnAccept函數功能:接受串連傳入參數:int nErrorCode傳回值:  無***********************************************************************/void CServerSocket::OnAccept(int nErrorCode) {// TODO: Add your specialized code here and/or call the base classCClientSocket *_pNewClient = new CClientSocket();_pNewClient->GetServerPointer(this);//!!這句話至關重要,把伺服器的通訊端綁定到此Accept(*_pNewClient);m_ClientArr.Add(_pNewClient);//接受一個串連把它加入到動態數組中CSocket::OnAccept(nErrorCode);}

建立一個CClientSocket通訊端,把用戶端的串連綁定到此通訊端上,並把此通訊端增加到動態數組中。相當於伺服器端自從接受新的串連後就不再管理,後面的發送與接受都使用自己剛剛建立的CClientSocket通訊端來完成。

3.2.2發送給指定使用者

伺服器負責所有訊息的轉寄,當有私密訊息發來時,進行分類處理。有私密訊息時,掃描動態數字,把私密者的名字與動態數組每個通訊端的名字進行比較,相同則進行轉寄。

3.3用戶端類3.3.1初次串連

用戶端串連成功,發送包含自己名字的標註格式字串。如下程式清單所示。

/***********************************************************************函數名稱:OnButLink函數功能:用戶端串連伺服器傳入參數:無傳回值:  無***********************************************************************/void CSetDlg::OnButLink() {// TODO: Add your control notification handler code hereCMyQQDlg *pParent = (CMyQQDlg*)this->GetParent(); pParent->m_Client.Create();//pParent->m_Client.SetDialog(pParent);  //設定通訊端成員變數UpdateData(TRUE);pParent->m_Client.m_strUserName = m_sName;if(pParent->m_Client.Connect(m_sServerIP,PORT)){MessageBox("串連伺服器成功");CString str;pParent->m_Client.m_strUserName = m_sName;str.Format("START&0&%s&0&0&END",m_sName);pParent->m_Client.Send(str,str.GetLength());pParent->m_cChoseFlg = 2;pParent->SetWindowText("用戶端——"+m_sName);}else{MessageBox("串連失敗","警告");}EndDialog(0);}

伺服器端接受到新上線的使用者名稱,把它賦給建立CClientSocket的m_strUserName,使動態數組裡每個通訊端都有一個m_strUserName與之對應,為私密資訊做好準備。

3.3.2重載OnReceive函數

用戶端接收到訊息,產生OnReceive訊息,這裡進行重寫,進行字串的拆分與解析。程式清單如下。

/***********************************************************************函數名稱:OnReceive函數功能:用戶端的接受訊息的響應函數傳入參數:int nErrorCode傳回值:  無***********************************************************************/void CClientSocket::OnReceive(int nErrorCode) {// TODO: Add your specialized code here and/or call the base classchar strText[512] = {0};Receive(strText, 512);MsgCut(strText);CSocket::OnReceive(nErrorCode);}

用戶端接收到訊息後,是產生了OnReceive訊息。重載OnReceive函數,把每次得到字串進行拆分解析。

4網路聊天室運行情況





著作權聲明:本文為博主原創文章,未經博主允許不得轉載。

網路聊天室

相關文章

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.