學習C++和QT剛剛兩個月出頭削葱,所以剛聽到要做一個類似飛秋,并且可以推送SVN消息的客戶端有些擔心淳梦。但是前輩給了很多幫助析砸,在設(shè)計的思路,用什么方法完成功能爆袍,到具體的協(xié)議解析時的類型轉(zhuǎn)換首繁,都給了很多幫助,所以暫時把登陸端和SVN消息的解析做了出來陨囊,下面就說下這部分的收獲吧蛮瞄。
PS:可能有些地方我說的有問題,希望了解的朋友可以提出來谆扎。
1.做到登陸和注冊消息的時候挂捅,因為要向服務器發(fā)消息,而qt通過套接字(QTcpSocket)中轉(zhuǎn)堂湖,需要將消息發(fā)送到套接字闲先。后面發(fā)送文本消息的時候也需要這樣做,所以抽象了一個類專門處理向套接字發(fā)消息和從服務器收消息无蜂。這樣分層結(jié)構(gòu)使得修改代碼更簡潔伺糠,代碼重用性也更高。
2.在使用信號與槽的時候斥季,最好在聲明槽函數(shù)的同時就把信號與槽綁定起來训桶,不然在運行程序的時候會發(fā)現(xiàn)槽函數(shù)沒有運行。
3.在寫一個函數(shù)的定義酣倾,其中有很多判斷語句的時候舵揭,最好一層一層的寫,每一個判斷語句的括號一定要記得成對使用躁锡,我寫的時候沒有注意到午绳,最后一個判斷少了一個括號,報了莫名其妙的錯誤映之。首先拦焚,這個函數(shù)接著的下一個函數(shù)報錯“該函數(shù)不能重復聲明”蜡坊,其次是后面會有一些變量會報錯為“未定義標識符”。
4.登陸界面有個注冊按鈕和groupbox用信號與槽連接赎败。想實現(xiàn)的功能是:最開始打開登陸界面這個groupbox不顯示秕衙,在點擊按鈕后,這個groupbox會顯示出來僵刮。
要實現(xiàn)這個功能据忘,在構(gòu)造函數(shù)的時候用hide() 將其隱藏,再寫一個槽函數(shù)妓笙,用判斷語句isHidden() 和show()來實現(xiàn)若河。
5.在解析協(xié)議的時候能岩,我們規(guī)定了一個結(jié)構(gòu)體類型的協(xié)議頭
enum ReceiverType
{
TO_SOMEONE?=?1,
BROADCAST,
};
enum ContentType
{
REGISTER?=?1,
ACK_RESULT,
LOGIN,
TEXT,
SVN_LOG,
};
typedef struct tagMessageHeader
{
unsigned int messageLen;
unsigned char sender?[64];
ReceiverType?receiverType;
unsigned char receiver?[64];
ContentType?contentType;
}?MessageHeader;
或不同情況下在其后的內(nèi)存空間存放unsigned?char[64]或unsigned?char?*類型的內(nèi)容寞宫。
這里有兩點:
一是根據(jù)我們的要求,unsigned?char?*和unsigned?char[64]在這里表示著這個變量所占的內(nèi)存空間拉鹃,而前者代表不定空間大小辈赋,后者固定占64字節(jié)的空間。這個與正常的語法不同膏燕,遇到這種情況時要根據(jù)文檔規(guī)定的協(xié)議要求理解其含義钥屈。
二是為了解析協(xié)議,需要將每段不同類型的變量分別解析坝辫,而整個協(xié)議是存放在一個連續(xù)的內(nèi)存空間中篷就。所以要用一個指針來控制具體解析協(xié)議的哪一部分。這里需要注意的是要計算每一部分的長度近忙,然后利用長度控制指針的偏移量使其指向下一部分竭业。
6.發(fā)送和解析協(xié)議的時候我用到了一些類型轉(zhuǎn)換的函數(shù),這里簡單介紹一下
data():將QByteArray轉(zhuǎn)換成char*
toLocal8Bit()將QString轉(zhuǎn)化成QByteArray
還有就是需要一些強制類型轉(zhuǎn)換來使得函數(shù)的參數(shù)匹配及舍。
還有一些學習到的東西可能沒有完全列出來未辆,我會在之后繼續(xù)更新。