![VC++網(wǎng)絡(luò)聊天軟件課程設(shè)計_第1頁](http://file2.renrendoc.com/fileroot_temp3/2021-4/17/f8e3e98f-c225-4ca5-8724-113822385274/f8e3e98f-c225-4ca5-8724-1138223852741.gif)
![VC++網(wǎng)絡(luò)聊天軟件課程設(shè)計_第2頁](http://file2.renrendoc.com/fileroot_temp3/2021-4/17/f8e3e98f-c225-4ca5-8724-113822385274/f8e3e98f-c225-4ca5-8724-1138223852742.gif)
![VC++網(wǎng)絡(luò)聊天軟件課程設(shè)計_第3頁](http://file2.renrendoc.com/fileroot_temp3/2021-4/17/f8e3e98f-c225-4ca5-8724-113822385274/f8e3e98f-c225-4ca5-8724-1138223852743.gif)
![VC++網(wǎng)絡(luò)聊天軟件課程設(shè)計_第4頁](http://file2.renrendoc.com/fileroot_temp3/2021-4/17/f8e3e98f-c225-4ca5-8724-113822385274/f8e3e98f-c225-4ca5-8724-1138223852744.gif)
![VC++網(wǎng)絡(luò)聊天軟件課程設(shè)計_第5頁](http://file2.renrendoc.com/fileroot_temp3/2021-4/17/f8e3e98f-c225-4ca5-8724-113822385274/f8e3e98f-c225-4ca5-8724-1138223852745.gif)
版權(quán)說明:本文檔由用戶提供并上傳,收益歸屬內(nèi)容提供方,若內(nèi)容存在侵權(quán),請進行舉報或認領(lǐng)
文檔簡介
1、摘摘 要要 網(wǎng)絡(luò)聊天室,其實質(zhì)就是基于 internet 的一種網(wǎng)絡(luò)聊天軟件。它可以在網(wǎng) 絡(luò)環(huán)境下進行實時的一對多或多對多的匿名交談。網(wǎng)絡(luò)聊天室軟件的制作方法 有很多種,比如用 mfc 和 java 等語言設(shè)計的就有很多,本次課程設(shè)計主要是 利用 mfc 所提供的各種控件尤其是 winsock 控件,基于 c/s 模式,設(shè)計了一個 網(wǎng)絡(luò)聊天室,圓滿地實現(xiàn)在網(wǎng)絡(luò)上實時聊天及多種人性化的輔助功能。 關(guān)鍵詞:winsockwinsock;c/sc/s ;visualvisual c+c+ 6.06.0;聊天室聊天室 目錄目錄 .查找資料.4 1.1 網(wǎng)絡(luò)聊天程序的開發(fā)背景 .4 1.2 網(wǎng)絡(luò)聊天程序
2、的設(shè)計目標 .4 .相關(guān)知識.5 2.1 winsock介紹 .5 2.2 mfc 的 casyncsocket類和 csocket類 .6 2.3 利用 csocket進行有連接的通信 8 2.4 方案比較與選 擇 9 .詳細設(shè) 計 .14 .1 聊天程序 現(xiàn) .15 .程序流程圖.62 4.1 建立連接的流程圖 .62 4.2 客戶關(guān)閉或者注銷時的程序流程圖 .63 .程序運行結(jié)果.64 5.1 客戶端 .64 5.2 服務(wù)端 .64 、討論及進一步研究建 議 65 、課程設(shè)計心得 66 、參考文 獻 67 1.查找資料 當(dāng)前是數(shù)字信息時代,網(wǎng)絡(luò)時代,獲得信息的渠道做種多樣。而最為快速 的
3、當(dāng)然就是網(wǎng)絡(luò)了。所以在課程設(shè)計動員之后,我們就馬不停蹄的通過互聯(lián)網(wǎng) 收縮有關(guān)網(wǎng)絡(luò)編程和 mfc 編程的有關(guān)資料。找到大量資料之后,我們還有根據(jù) 課程設(shè)計的要求進行篩選資料,最后選定方案和確定實現(xiàn)方法。這也是我們第 一階段的工作。 1.1 網(wǎng)絡(luò)聊天程序的開發(fā)背景 近年來,互連網(wǎng)發(fā)展日新月異,網(wǎng)絡(luò)使空間的距離不再成為人們溝通的障 礙,世界各個角落的人們可以通過 internet 收發(fā)郵件、實時聊天、獲取最新的 資訊。所以網(wǎng)絡(luò)聊天的程序早已被前人所實現(xiàn),而且實現(xiàn)的方法多種多樣。因 此,本次課程設(shè)計,我們主要借鑒前人創(chuàng)立的方法和編程經(jīng)驗來制作一個 c/s 聊天室程序,通過制作該程序達到的學(xué)習(xí)網(wǎng)絡(luò) so
4、cket 編程和使用 mfc 編程的相 關(guān)知識。 1.2 網(wǎng)絡(luò)聊天程序的設(shè)計目標 本課題是設(shè)計一個網(wǎng)絡(luò)聊天的程序,包括服務(wù)器端和客戶端,主要功能為: 客戶端部分: 、輸入服務(wù)器端 ip 地址和端口號進行連接 、發(fā)送消息給服務(wù)器端并顯示服務(wù)器端回傳的消息 、在客戶端增加歷史聊天記錄和當(dāng)天聊天記錄 、可以設(shè)置個性昵稱、增添快捷表情、更換個性圖像和背景設(shè)計 服務(wù)器端部分: 、立服務(wù)器端與客戶端的連接請求 、接收所有用戶發(fā)送的消息 、向所有在線用戶群發(fā)消息 、在客戶端增加歷史聊天記錄和當(dāng)天聊天記錄 、可以設(shè)置個性昵稱、增添快捷表情、更換個性圖像和背景設(shè)計 通過這次課程設(shè)計,可以比較深入的了解和掌握 w
5、insock 控件基本屬性、 方法和事件,熟悉 vc+的開發(fā)環(huán)境。理解網(wǎng)絡(luò)聊天通信的概念,輸控制協(xié)議 (tcp)進行數(shù)據(jù)交流,初步掌握網(wǎng)絡(luò)聊天通信程序的設(shè)計方法,以及 windows 編程的一些方法。并能鞏固和擴展之前學(xué)過的知識,進行項目的設(shè)計開發(fā)訓(xùn)練, 更好的適應(yīng)社會的需求。 2.相關(guān)知識 2.1 winsock 介紹 windows sockets 規(guī)范以 u.c. berkeley 大學(xué) bsd unix 中流行的 socket 接口為范例定義了一套 micosoft windows 下網(wǎng)絡(luò)編程接口。它不僅包含了人們 所熟悉的 berkeley socket 風(fēng)格的庫函數(shù);也包含了一組針
6、對 windows 的擴展 庫函數(shù),以使程序員能充分地利用 windows 消息驅(qū)動機制進行編程。 windows sockets 規(guī)范本意在于提供給應(yīng)用程序開發(fā)者一套簡單的 api,并 讓各家網(wǎng)絡(luò)軟件供應(yīng)商共同遵守。此外,在一個特定版本 windows 的基礎(chǔ)上, windows sockets 也定義了一個二進制接口(abi) ,以此來保證應(yīng)用 windows sockets api 的應(yīng)用程序能夠在任何網(wǎng)絡(luò)軟件供應(yīng)商的符合 windows sockets 協(xié)議的實現(xiàn)上工作。因此這份規(guī)范定義了應(yīng)用程序開發(fā)者能夠使用,并且網(wǎng)絡(luò) 軟件供應(yīng)商能夠?qū)崿F(xiàn)的一套庫函數(shù)調(diào)用和相關(guān)語義。 遵守這套 win
7、dows sockets 規(guī)范的網(wǎng)絡(luò)軟件,我們稱之為 windows sockets 兼容的,而 windows sockets 兼容實現(xiàn)的提供者,我們稱之為 windows sockets 提供者。一個網(wǎng)絡(luò)軟件供應(yīng)商必須百分之百地實現(xiàn) windows sockets 規(guī)范才能做到現(xiàn) windows sockets 兼容。 任何能夠與 windows sockets 兼容實現(xiàn)協(xié)同工作的應(yīng)用程序就被認為是具 有 windows sockets 接口。我們稱這種應(yīng)用程序為 windows sockets 應(yīng)用程序。 windows sockets 規(guī)范定義并記錄了如何使用 api 與 intern
8、et 協(xié)議族 (ips,通常我們指的是 tcp/ip)連接,尤其要指出的是所有的 windows sockets 實現(xiàn)都支持流套接口和數(shù)據(jù)報套接口. 應(yīng)用程序調(diào)用 windows sockets 的 api 實現(xiàn)相互之間的通訊。windows sockets 又利用下層的網(wǎng)絡(luò)通訊協(xié)議功能和操作系統(tǒng)調(diào)用實現(xiàn)實際的通訊工作。 2.22.2 mfcmfc 的的 casyncsocketcasyncsocket 類和類和 csocketcsocket 類類 構(gòu)造一個 casyncsocket 對象并使用該對象創(chuàng)建基礎(chǔ) socket 句柄。 套接字的創(chuàng)建:遵循兩階段構(gòu)造的 mfc 模式。 例如: cas
9、yncsocket sock;sock.create( ); / use the default parameters - 或 - casyncsocket* psocket = new casyncsocket;int nport = 27; psocket- create( nport, sock_dgram ); 上面的第一個構(gòu)造函數(shù)在堆棧上創(chuàng)建一個 casyncsocket 對象,第二個構(gòu) 造函數(shù)在堆上創(chuàng)建 casyncsocket 。上面的第一個 create 調(diào)用使用默認參數(shù) 創(chuàng)建流式套接字,第二個 create 調(diào)用創(chuàng)建具有指定端口和地址的數(shù)據(jù)文報套 接字。 (任一個 creat
10、e 版本都可以和任一種構(gòu)造方法一起使用。 ) create 的參數(shù)有: “端口”:短整型。 對于服務(wù)器套接字,必須指定端口。對于客戶端套接字,通常接受此參數(shù) 的默認值,該值允許 windows sockets 選擇端口。 套接字類型: sock_stream (默認值)或 sock_dgram 。 套接字“地址” ,如“”或“128.56.22.8” 。 該地址為 網(wǎng)絡(luò)上的網(wǎng)際協(xié)議 (ip) 地址。很可能要始終依賴此參數(shù)的默認值。 如果套接字是客戶端,則使用 casyncsocket:connect 將此套接字對 象連接到服務(wù)器套接字。 如果套接字是服務(wù)器,則將套接字設(shè)置為開始偵聽 (使用 c
11、asyncsocket:listen)來自客戶端的連接嘗試。接收到連接請求時, 用 casyncsocket:accept 接受該請求。 接受連接后,可以執(zhí)行驗證密碼等任務(wù)。 注意 accept 成員函數(shù)采用對新的空 csocket 對象的引用作為它的參數(shù)。 在調(diào)用 accept 之前,必須構(gòu)造該對象。如果此套接字對象超出范圍,則連接 關(guān)閉。不要對這個新套接字對象調(diào)用 create 。 通過調(diào)用 casyncsocket 對象的封裝 windows sockets api 函數(shù)的成員 函數(shù),與其他套接字進行通信。 如果在堆棧上創(chuàng)建了套接字對象,當(dāng)包含函數(shù)超出范圍時將調(diào)用此對象 的析構(gòu)函數(shù)。如果
12、使用 new 運算符在堆上創(chuàng)建了套接字對象,則您必須負責(zé)使 用 delete 運算符銷毀此對象。 析構(gòu)函數(shù)在銷毀對象之前調(diào)用對象的 close 成員函數(shù)。 2.3 利用 csocket 進行有連接的通信 微軟的 mfc 把復(fù)雜的 winsock api 函數(shù)封裝到類里,這使得編寫網(wǎng)絡(luò)應(yīng)用 程序更容易。casyncsocket 類逐個封裝了 winsock api,為高級網(wǎng)絡(luò)程序員 提 供了更加有力而靈活的方法。這個類基于程序員了解網(wǎng)絡(luò)通訊的假設(shè),目的是 為了在 mfc 中使用 winsock,程序員有責(zé)任處理諸如阻塞、字節(jié)順序和在 unicode 與 mbcs 間轉(zhuǎn)換字符的任務(wù)。 為了給程序員
13、提供更方便的接口以自動處理這些任務(wù),mfc 給出 了 csocket 類,這個類是由 casyncsocket 類繼承下來的,它提供了比 casyncsocket 更高層的 winsock api 接口。csocket 類和 csocketfile 類可以 與 carchive 類一起合作來管理發(fā)送和接收的數(shù)據(jù),這使管理數(shù)據(jù)收發(fā)更加便利。 csocket 對象提供阻塞模式,這對于 carchive 的同步操作是至關(guān)重要的。阻塞 函數(shù)(如 receive()、send()、receivefrom()、sendto() 和 accept())直到 操作完成后才返回控制權(quán)。 因此如果需要低層控制和高
14、效率,就使用 casyncsock 類;如果需要方便, 則可使用 csocket 類。 由于我們對網(wǎng)絡(luò)底層的了解比較淺薄,所以這次課程設(shè)計我們選擇了采用 csocket 類來編程實現(xiàn)。下面主要針對這種方法進行講述。 使用 csocket 對象涉及 carchive 和 csocketfile 類對象。以下介紹的針 對字節(jié)流型(即基于 tcp/ip 協(xié)議)套接字的操作步驟中,只有第 3 和第 4 步對于 客戶端和服務(wù)端操作是不同的,其他步驟都相同。 構(gòu)造一個 csocket 對象。 使用這個對象的 create()成員函數(shù)產(chǎn)生一個 socket 對象。在客戶端 程序中,除非需要數(shù)據(jù)報套接字,cr
15、eate()函數(shù)一般情況下應(yīng)該使用默認參 數(shù)。而對于服務(wù)端程序,必須在調(diào)用 create 時指定一個端口。需要注意的是, carchive 類對象不能與數(shù)據(jù)報(udp)套接字一起工作,因此對于數(shù)據(jù)報套接 字,casyncsocket 和 csocket 的使用方法是一樣的。 如果是客戶端套接字,則調(diào)用 casyncsocket connect()函數(shù)與服 務(wù)端套接字連接;如果是服務(wù)端套接字,則調(diào)用 casyncsocketlisten()開 始監(jiān)聽來自客戶端的連接請求,收到連接請求后,調(diào)用 casyncsocketaccept()函數(shù)接受請求,建立連接。請注意 accept()成員 函數(shù)需要一
16、個新的并且為空的 csocket 對象作為它的參數(shù)。 重載 csocket 類的部分函數(shù)??蛻舳诵枰剌d onreceive(int i) 和 onclose(int i);服務(wù)器端需要重載 onaccept(int i) 、onclose(int i) 和 onreceive(int i); 調(diào)用 send()的方法來發(fā)送數(shù)據(jù),調(diào)用 receive()的方法來接受數(shù)據(jù)。 調(diào)用 close()方法來關(guān)閉套接字以終止通信。 通訊完畢后,銷毀 csocket 對象。 2.42.4 方案比較與選擇方案比較與選擇 系統(tǒng)分析與設(shè)計系統(tǒng)分析與設(shè)計 1、系統(tǒng)構(gòu)架方式如下圖所示: 設(shè)計出一個完整的網(wǎng)絡(luò)聊天程序
17、,使之實現(xiàn)以上基本要求。 1、 服務(wù)端需要完成的三件事 1) 在特定端口等待連接請求,并需要維護一個客戶連接表,已記錄所 有成功連接。 2) 及時接受消息,然后轉(zhuǎn)發(fā)到客戶連接。 3) 監(jiān)控連接狀態(tài),客戶離開或故障時從列表中刪除相應(yīng)表項,并及時 更新連接表。 2、 客戶端需要完成的三件事 1) 建立與維護服務(wù)器的連接,并隨時監(jiān)測連接狀態(tài)。 2) 把用戶輸入的信息及時發(fā)送到服務(wù)端,同時準備好接受,并顯示信 息。 3) 在用戶退出時關(guān)閉連接。 程序方案程序方案比較:比較: 方案一:基于方案一:基于 tcptcp 的的 socketsocket 編程編程 tcp(transmission contro
18、l protocol,傳輸控制協(xié)議)是基于連接的協(xié) 議,也就是說,在正式收發(fā)數(shù)據(jù)前,必須和對方建立可靠的連接。 服務(wù)器端程序流程如下: 1) 創(chuàng)建套接字(socket) ; 2) 將套接字綁定到一個本地地址和端口上(bind) ; 3) 將套接字設(shè)為監(jiān)聽模式,準備接受客戶請求(listen) ; 4) 等待客戶請求到來;當(dāng)請求到來后,接受連接請求,返回一個新的對應(yīng) 于此次連接的套接字(accept) ; 5) 用返回的套接字和客戶端進行通信(send/recv) ; 6) 返回,等待另一客戶請求; 7) 關(guān)閉套接字; 客戶端程序流程如下: 1) 創(chuàng)建套接字(socket) ; 2) 向服務(wù)器發(fā)
19、出連接請求(connect) ; 3) 和服務(wù)器端進行通信(send/recv) ; 4) 關(guān)閉套接字。 在服務(wù)器端,當(dāng)調(diào)用 accept 函數(shù)時,程序就會等待,等待客戶調(diào)用 connect 函數(shù)發(fā)出連接請求,然后服務(wù)器端接受該請求,于是雙方就建立了連 接。之后,服務(wù)器端和客戶端就可以利用 send 和 recv 函數(shù)進行通信了。因為 服務(wù)器需要接受客戶端的請求,所以必須告訴本地主機它打算在哪個 ip 地址和 哪個端口上等待客戶要求,因此必須調(diào)用 bind 函數(shù)來實現(xiàn)這一功能。而對客戶 端來說,當(dāng)它發(fā)起連接請求,服務(wù)器端接受請求后,在服務(wù)端就保存了改客戶 端的 ip 地址和端口的信息。這樣,對
20、服務(wù)器端來說,一旦建立連接之后,實際 上它已經(jīng)保存了客戶端的 ip 地址和端口號的信息,就可以利用所返回的套接字 調(diào)用 send/recv 函數(shù)與客戶端進行通信。 程序流程圖如下: 方案二:基于方案二:基于 udpudp(面向無連接)的(面向無連接)的 socketsocket 程序程序 udp(user data protocol,用戶數(shù)據(jù)報協(xié)議)是與 tcp 相對應(yīng)的協(xié)議。它 是面向非連接的協(xié)議,它不與對方建立連接,而是直接就把數(shù)據(jù)包發(fā)送過去。 udp 適用于一次只傳送少量數(shù)據(jù)、對可靠性要求不高的應(yīng)用環(huán)境 服務(wù)器端也叫接收端,對于基于 udp(面向無連接)的套接字編程來說, 它的服務(wù)器端和
21、客戶端這種概念不是很強化,我們也可以把服務(wù)器端,即先啟 動的一端稱為接收端,發(fā)送數(shù)據(jù)的一端稱為發(fā)送端,也稱為客戶端。 服務(wù)端程序編寫流程如下: 1) 創(chuàng)建套接字(socket) ; 2) 將套接字綁定到一個本地地址和端口上(bind) ; 3) 等待接受數(shù)據(jù)(recvfrom) ; 4) 關(guān)閉套接字。 雖然面向無連接的 socket 編程無須建立連接,但是為了完成這次通信,對 于接受端來說,它必須先啟動以接受客戶端發(fā)送的數(shù)據(jù),因此接收端必須告訴 主機它是在哪個地址和端口上等待數(shù)據(jù)的到來,接收端(服務(wù)器端)必須調(diào)用 bind 函數(shù)將套接字綁定到一個本地地址和端口上。 客戶端程序編寫流程如下: 1
22、) 創(chuàng)建套接字(socket) ; 2) 向服務(wù)器發(fā)送數(shù)據(jù)(sengto) ; 3) 關(guān)閉套接字。 在 udp 的套接字編程時,利用的是 sendto 和 recvfrom 這兩個函數(shù)實現(xiàn)數(shù) 據(jù)的發(fā)送和接收,而基于 tcp 的套接字編程時,發(fā)送數(shù)據(jù)是調(diào)用 send 函數(shù),接 受數(shù)據(jù)調(diào)用 recv 函數(shù)。 程序流程圖如下: 方案比較結(jié)果方案比較結(jié)果 tcp 與 udp 最基本的區(qū)別在于基于連接與無連接,相比之下,第一種方案 對系統(tǒng)的要求以及數(shù)據(jù)量都比較大,但是保證數(shù)據(jù)的正確性與數(shù)據(jù)順序,在傳 輸大量數(shù)據(jù)的時候具有更高的可靠性。至于第二種方案的優(yōu)點在于傳輸?shù)乃俣?快,程序結(jié)構(gòu)精簡。 總的來說,我認
23、為 tcp 協(xié)議更能滿足目前各行業(yè)對遠程數(shù)據(jù)傳輸?shù)囊?,它?供更穩(wěn)定更便利的傳輸通道,滿足了對安全性的要求以及遠程數(shù)據(jù)傳輸?shù)囊蟆?所以我們小組選擇方案一。 3.3.詳細設(shè)計詳細設(shè)計 我們利用 mfc 提供的 csocket 類來編程實現(xiàn)一個網(wǎng)絡(luò)聊天室。那么就需要一個聊天的 服務(wù)器(即是服務(wù)端) ,它可以和很多客戶端進行通信,從而把來自不同的客戶的聊天信息 轉(zhuǎn)交到所有其他的客戶端。當(dāng)然也需要用戶界面(客戶端) 。這樣就形成了一個采用 client/server 結(jié)構(gòu)的并可以多人同時在線的聊天室。同時,服務(wù)器端應(yīng)該有一定的管理 功能,如手動/自動響應(yīng)申請、設(shè)置服務(wù)器名稱和服務(wù)器端口、在線名單統(tǒng)
24、計、單獨斷開某 人連接以及保持聊天記錄等功能。對于客戶端,因為是面向用戶,所以外觀和功能都應(yīng)有 更高的要求。實現(xiàn)諸如:手動輸入 ip 和用戶名、頭像切換、心情書寫、表情輸入、軟件 皮膚切換、注銷登錄、保存聊天記錄以及伸縮界面等功能。下面詳細介紹各項功能是如何 實現(xiàn)的。 3.13.1 聊天程序的實現(xiàn)聊天程序的實現(xiàn) (1)首先啟動 visual c+ 6.0,利用 mfc appwizardexe建立一個新的 mfc 工程,工程名為 chat,在 mfc appwizard step1 的時候選擇 dialog based 即基于對話框,在 step4 時勾選 windows sockets 選項
25、(如圖表 0-2) ,其他默 認值下一步。 圖表 0-1 圖表 0-2 (2)客戶端的界面如圖圖表 0-3 所示。其中包含文檔編輯框、按鍵控件、靜 態(tài)文本控件組成。左半邊由上自下分別是:頭像、昵稱、當(dāng)天聊天信息顯示、 12 個表情按鈕、消息輸入框和發(fā)送按鈕。右半邊有歷史記錄顯示框、歷史記錄 顯示按鈕。 圖表 0-3 軟件界面 圖表 0-4 控件類型及各自 id 標題控件類型控件 id 昵稱: staticidc_static 服務(wù)器 ip: staticidc_static 端口號(默認 5000): staticidc_static 頭像 buttonidc_touxiang 表情 1 bu
26、ttonidc_bq1 表情 2 button idc_bq2 表情 3 button idc_bq3 表情 4 button idc_bq4 表情 5 button idc_bq5 表情 6 button idc_bq6 表情 7 button idc_bq7 表情 8 button idc_bq8 表情 9 button idc_bq9 表情 10 button idc_bq10 表情 11 button idc_bq11 表情 12 button idc_bq12 發(fā)送 button idc_send 連接 button idc_connect 建立 button idc_setserv
27、er 聊天紀錄 button idc_liaotianjilu 聊天信息顯示 editidc_showtext 信息輸入 edit idc_inputtext 昵稱輸入 edit idc_name 服務(wù)器 ip 輸入 edit idc_serverip 端口輸入 edit idc_port 聊天記錄顯示 edit idc_showhistory 聊天程序總共有 6 個類。其中,cchatapp 和 caboutdlg 由 appwizard 實現(xiàn);另 外,cserversocket 和 cclientsocket 分別負責(zé)服務(wù)端和客戶端的網(wǎng)絡(luò)通信功 能;cchatdlg 為程序的主控類,主界面
28、、通信方式及程序邏輯均由該類實現(xiàn), 它繼承自 cdialog 類;cmessgage 是對消息的封裝。 cclientsocketcclientsocket 通過相應(yīng)的 onreceive 消息來接收數(shù)據(jù),響應(yīng) onclose 消息來斷開對話的 處理,實現(xiàn)以 carchive 對數(shù)據(jù)進行的串行化。 類定義代碼如下: #includemessg.h /命令目標 class cchatdlg; class cclientsocket:public csocket public: carchive *m_asessionin; carchive *m_asessionout; csocketfile
29、 *m_sfsocketfile; cchatdlg *m_dlg; bool m_binit; /是否進行了初始化 bool m_bclose; /連接是否關(guān)閉 public: void init(cchatdlg *dlg); bool sendmessage(cmessg *msg); void closesocket(); public: static int getlocalhostname(cstring /獲得本地 計算機名稱 static int getipaddress(const cstring /獲得本地 ip static int getipaddress(const
30、cstring /獲得 本地 ip static cstring errorreason(int tag); public: virtual void onreceive(int nerrorcode); virtual void onclose(int nerrorcode); public: cclientsocket(); virtual cclientsocket(); protected: ; cclientsocket.cppcclientsocket.cpp 中的代碼:中的代碼: #include stdafx.h #include chat.h #include clients
31、ocket.h #includechatdlg.h / cclientsocket cclientsocket:cclientsocket() m_asessionin=null; m_asessionout=null; m_sfsocketfile=null; m_binit=false; m_bclose=false; cclientsocket:cclientsocket() if(m_asessionin) delete m_asessionin; if(m_asessionout) delete m_asessionout; if(m_sfsocketfile) delete m_s
32、fsocketfile; /clientsocket 成員函數(shù) void cclientsocket:onreceive(int nerrorcode) csocket:onreceive(nerrorcode); /onreceive()函數(shù)的實現(xiàn) do cmessg temp; temp.serialize(*m_asessionin); m_dlg-m_smsglist+=temp.m_strtext+rn; m_dlg-m_tmpmsglist=temp.m_strtext+rn; m_dlg-setdlgitemtext(idc_showtext,m_dlg-m_smsglist);
33、 file* fp; fp = fopen(chatnote.txt,a+); fputs(m_dlg-m_tmpmsglist,fp); fclose(fp); m_dlg-setdlgitemtext(idc_showtext,m_dlg-m_smsglist); int linenum=(cedit*) (m_dlg-getdlgitem(idc_showtext)-getlinecount(); (cedit*) (m_dlg-getdlgitem(idc_showtext)- linescroll(linenum); if(!m_dlg-m_bclient) for(position
34、 pos=m_dlg- m_connectionlist.getheadposition(); pos!=null;) cclientsocket *t=(cclientsocket*) m_dlg- m_connectionlist.getnext(pos); if(t-m_hsocket!=this-m_hsocket) t-sendmessage( while(!m_asessionin-isbufferempty(); void cclientsocket:init(cchatdlg *dlg) m_sfsocketfile=new csocketfile(this); m_asess
35、ionin=new carchive(m_sfsocketfile,carchive:load); m_asessionout=new carchive(m_sfsocketfile,carchive:store); m_bclose=false; this-m_dlg=dlg; /* *sendmessage()函數(shù)的實現(xiàn) *主要功能: *將信息串行化 */ bool cclientsocket:sendmessage(cmessg *msg) if(m_asessionout!=null) msg-serialize(*m_asessionout); m_asessionout-flush
36、(); return true; else m_bclose=true; /對方關(guān)閉了連接 closesocket(); m_dlg-closesessionsocket(); return false; /* *closesocket()函數(shù)的實現(xiàn) *主要功能: *關(guān)閉套接字的連接 */ void cclientsocket:closesocket() if(m_asessionin) delete m_asessionin; m_asessionin=null; if(m_asessionout) delete m_asessionout; m_asessionout=null; if(m
37、_sfsocketfile) delete m_sfsocketfile; m_sfsocketfile=null; close(); m_binit=false; m_bclose=true; /* *onclose()函數(shù)的實現(xiàn) *主要功能: *關(guān)閉套接字的連接 */ void cclientsocket:onclose(int nerrorcode) m_bclose=true; closesocket(); m_dlg-closesessionsocket(); csocket:onclose(nerrorcode); /* *getlocalhostname()函數(shù)的實現(xiàn) *主要功能
38、: *獲得本地計算機的名稱 */ int cclientsocket:getlocalhostname(cstring int nretcode; nretcode=gethostname(szhostname,sizeof(szhostname); if(nretcode!=0) /產(chǎn)生錯誤 shostname=_t(沒有取得); return getlasterror(); shostname=szhostname; return 0; /* *getipaddress()函數(shù)的實現(xiàn) *主要功能: *取得本地 ip 地址 */ int cclientsocket:getipaddress(
39、const cstring if(lphostent=null) /產(chǎn)生錯誤 sipaddress=_t(); return getlasterror(); lpstr lpaddr=lphostent-h_addr_list0; if(lpaddr) struct in_addr inaddr; memmove( sipaddress=inet_ntoa(inaddr); /轉(zhuǎn)換為標準格式 if(sipaddress.isempty() sipaddress=_t(沒有取得); return 0; /* * getipaddress ()函數(shù)的實現(xiàn) *主要功能: *獲得本地 ip 地址 */
40、 int cclientsocket:getipaddress(const cstring if(lphostent=null) /產(chǎn)生錯誤 f0=f1=f2=f3=0; return getlasterror(); lpstr lpaddr=lphostent-h_addr_list0; /獲取 ip if(lpaddr) struct in_addr inaddr; memmove( f0=inaddr.s_un.s_un_b.s_b1; f1=inaddr.s_un.s_un_b.s_b2; f2=inaddr.s_un.s_un_b.s_b3; f3=inaddr.s_un.s_un_
41、b.s_b4; return 0; cstring cclientsocket:errorreason(int tag) /錯誤信息的宏定義 cstring result; switch(tag) case wsanotinitialised: result=a successful afxsocketinit must occur before using this api.; break; case wsaenetdown: result=the network subsystem failed; break; case wsaeaddrinuse: result=the specifie
42、d address is already in use; break; case wsaeinprogress: result=a blocking windows socket call is in progress; break; case wsaeaddrnotavail: result=the specified address is not available from the local machine; break; case wsaeafnosupport: result=address in the specified family cannot be used with t
43、his socket; break; case wsaeconnrefused: result=the attempt to connect eas rejected; break; case wsaedestaddrreq: result=a destination address is requireed; break; case wsaefault: result=the nsockaddrlen arguement is incorrect; break; case wsaeinval: result=invalid host address; break; case wsaeisco
44、nn: result=the socket is already connected; break; case wsaemfile: result=no more file descriptions are available; break; case wsaenetunreach: result=the network cannot be reached from this host at this time; break; case wsaenobufs: result=no buffer space is available.the socket cannot be connected;
45、 break; case wsaenotsock: result=the descriptor is not a socket; break; case wsaetimedout: result=attempt to connect timed out without establishing a connection; break; case wsaewouldblock: result=the socket is marked as nonblocking and the connnection cannot be completed immediately; break; default
46、: result=unknown error; return result; cserversocketcserversocket cserversocket 主要功能是實現(xiàn) onaccept()消息,負責(zé)監(jiān)聽服務(wù)窗口,是 一個服務(wù) socket。 cserversocket.h 的代碼如下: / cserversocket command target class cchatdlg; class cserversocket: public csocket public: cserversocket(); virtual cserversocket(); cchatdlg *m_dlg; ui
47、nt m_uport; bool init(uint port,cchatdlg *dlg); public: virtual void onaccept(int nerrorcode); /用于響應(yīng) onaccept 消 息的函數(shù) ; cserversocket.cppcserversocket.cpp 的代碼如下:的代碼如下: #include stdafx.h #include chat.h #include serversocket.h #include chatdlg.h / cserversocket cserversocket:cserversocket() cserversoc
48、ket:cserversocket() /cserversocket 成員函數(shù) bool cserversocket:init(uint port,cchatdlg *dlg) m_uport=port; m_dlg=dlg; if(create(m_uport)=false) afxmessagebox(_t(server socket create error); return false; if(this-listen()=false) afxmessagebox(server listen error); return false; m_dlg-setdlgitemtext(idc_s
49、howtext,serverr has been set ok!); return true; void cserversocket:onaccept(int nerrorcode) m_dlg-processpendingaccept(); csocket:onaccept(nerrorcode); cmessgcmessg cmessg 類主要作用是實現(xiàn)信息的串行化,方便信息的傳輸。 cmessg.h 代碼如下: #pragma once class cmessg:public cobject /命令目標 protected: declare_dyncreate(cmessg) publi
50、c: cmessg(); public: cstring m_strtext; public: void init(); public: virtual cmessg(); virtual void serialize(carchive /實行串行化 #if def_debug virtual void assertvalid() const; virtual void dump(cdumpcontext #endif ; cmessg.cppcmessg.cpp 代碼如下:代碼如下: #include stdafx.h #include chat.h #include messg.h / c
51、onstruction/destruction implement_dyncreate(cmessg,cobject) cmessg:cmessg() init(); cmessg:cmessg() /cmessg 成員函數(shù) void cmessg:init() m_strtext = _t(); /cmsg serialization void cmessg:serialize(carchive /cmsg diagnostics #if def_debug void cmessg:assertvalid() const cobject:assertvalid(); void cmessg:
52、dump(cdumpcontext #endif cchatdlgcchatdlg cchatdlg 類負責(zé)調(diào)度整個工程,實現(xiàn)界面消息的添加與響應(yīng),組織整個工 程的運行。 1) 程序開始運行,進行對話框的初始化是在 oninitdialog()函數(shù)中實現(xiàn) 的,在開始的時候自動獲得本地機器的 ip 地址并顯示在 ip address control 控件中。 2) 連接服務(wù)器按鈕消息的響應(yīng)函數(shù)。完成服務(wù)器的連接,調(diào)用 cclientsocket 類的 connect 函數(shù)來實現(xiàn),同時對連接返回的信息進行 處理。 3) 建立服務(wù)器按鈕信息的響應(yīng)函數(shù)。 4) 發(fā)送按鈕消息的響應(yīng)函數(shù)。讀取文本框中的信
53、息,調(diào)用 cmessg 類的函 數(shù)以實現(xiàn)信息的串行化,然后再調(diào)用 cclientsocket 類的 sendmessage()函數(shù)將信息發(fā)送給建立連接的對方。 chatdlg.h 代碼如下: / cchatdlg dialog #include clientsocket.h #include serversocket.h /cchatdlg 對話框 class cchatdlg : public cdialog /構(gòu)造 public: cchatdlg(cwnd* pparent = null); /標準構(gòu)造函數(shù) /對話框數(shù)據(jù) enumidd=idd_chat_dialog; protecte
54、d: virtual void dodataexchange(cdataexchange *pdx); protected: hicon m_hicon; /生成的消息映射函數(shù) virtual bool oninitdialog(); afx_msg void onsyscommand(uint nid,lparam lparam); afx_msg void onpaint(); /afx_msg void oninputtext(); afx_msg hcursor onquerydragicon(); declare_message_map() public: cstring m_sin
55、puttext; public: cstring name; public: cstring m_sshowstring; public: uint m_uport; /添加的變量 public: bool m_binit; bool m_bclient; cclientsocket m_clientsocket; cserversocket m_plistensocket; cptrlist m_connectionlist; cstring m_smsglist; cstring m_tmpmsglist; public: void processpendingaccept(); void
56、 closesessionsocket(); void clearcontent(); void onclearconnection(); public: afx_msg void onbnclickedconnect(); public: afx_msg void onbnclickedsetserver(); public: afx_msg void onbnclickedbutton1(); ; cchatdlg.cppcchatdlg.cpp 代碼如下:代碼如下: #include stdafx.h #include chat.h #include chatdlg.h #ifdef _
57、debug #define new debug_new #undef this_file static char this_file = _file_; #endif / / / caboutdlg dialog used for app about int touxiangnum=0; cstring liaotianjilu; class caboutdlg:public cdialog public: caboutdlg(); enumidd=idd_aboutbox; protected: virtual void dodataexchange(cdataexchange *pdx);
58、 protected: declare_message_map() ; caboutdlg:caboutdlg():cdialog(caboutdlg:idd) void caboutdlg:dodataexchange(cdataexchange *pdx) cdialog:dodataexchange(pdx); begin_message_map(caboutdlg,cdialog) end_message_map() cchatdlg:cchatdlg(cwnd *pparent /*=null*/) :cdialog(cchatdlg:idd,pparent) m_sinputtex
59、t=_t(); name=_t(); m_hicon = afxgetapp()-loadicon(idr_mainframe); /加載圖 標 m_sshowstring=_t(); m_uport=5000; m_hicon=afxgetapp()-loadicon(idr_mainframe); void cchatdlg:dodataexchange(cdataexchange *pdx) cdialog:dodataexchange(pdx); ddx_text(pdx,idc_inputtext,m_sinputtext); ddx_text(pdx,idc_name,name);
60、 ddx_text(pdx,idc_showtext,m_sshowstring); ddx_text(pdx,idc_port,m_uport); /ddv_minmaxuint(pdx,m_uport,1024,100000); begin_message_map(cchatdlg,cdialog) on_wm_syscommand() on_wm_paint() on_wm_querydragicon() /on_en_update(idc_inputtext,oninputtext) /afx_msg_map on_bn_clicked(idc_connect, onbnclicked
溫馨提示
- 1. 本站所有資源如無特殊說明,都需要本地電腦安裝OFFICE2007和PDF閱讀器。圖紙軟件為CAD,CAXA,PROE,UG,SolidWorks等.壓縮文件請下載最新的WinRAR軟件解壓。
- 2. 本站的文檔不包含任何第三方提供的附件圖紙等,如果需要附件,請聯(lián)系上傳者。文件的所有權(quán)益歸上傳用戶所有。
- 3. 本站RAR壓縮包中若帶圖紙,網(wǎng)頁內(nèi)容里面會有圖紙預(yù)覽,若沒有圖紙預(yù)覽就沒有圖紙。
- 4. 未經(jīng)權(quán)益所有人同意不得將文件中的內(nèi)容挪作商業(yè)或盈利用途。
- 5. 人人文庫網(wǎng)僅提供信息存儲空間,僅對用戶上傳內(nèi)容的表現(xiàn)方式做保護處理,對用戶上傳分享的文檔內(nèi)容本身不做任何修改或編輯,并不能對任何下載內(nèi)容負責(zé)。
- 6. 下載文件中如有侵權(quán)或不適當(dāng)內(nèi)容,請與我們聯(lián)系,我們立即糾正。
- 7. 本站不保證下載資源的準確性、安全性和完整性, 同時也不承擔(dān)用戶因使用這些下載資源對自己和他人造成任何形式的傷害或損失。
最新文檔
- 2025年紅磷阻燃母粒項目可行性研究報告
- 2025年電動車減震項目可行性研究報告
- 2025年泡泡紗布項目可行性研究報告
- 2025至2031年中國柜臺鏡行業(yè)投資前景及策略咨詢研究報告
- 2025年懸壁梁式傳感器項目可行性研究報告
- 2025至2031年中國可調(diào)腹肌訓(xùn)練器行業(yè)投資前景及策略咨詢研究報告
- 2025年三乙二醇雙異辛酸酯項目可行性研究報告
- 2025至2030年中國雪松苗木數(shù)據(jù)監(jiān)測研究報告
- 2025至2030年中國銅沖片接觸腳數(shù)據(jù)監(jiān)測研究報告
- 2025至2030年紅外線自動門項目投資價值分析報告
- (更新版)HCIA安全H12-711筆試考試題庫導(dǎo)出版-下(判斷、填空、簡答題)
- 糖尿病運動指導(dǎo)課件
- 蛋白表達及純化課件
- 完整版金屬學(xué)與熱處理課件
- T∕CSTM 00640-2022 烤爐用耐高溫粉末涂料
- 304不銹鋼管材質(zhì)證明書
- 民用機場不停航施工安全管理措施
- 港口集裝箱物流系統(tǒng)建模與仿真技術(shù)研究-教學(xué)平臺課件
- 新教科版2022年五年級科學(xué)下冊第2單元《船的研究》全部PPT課件(共7節(jié))
- QTD01鋼質(zhì)焊接氣瓶檢驗工藝指導(dǎo)書
- 人教版七年級英語下冊全冊英語單詞默寫直接打印
評論
0/150
提交評論