一、前言
本聊天室的整体运行逻辑直接参考的本站另一篇文章:手写一个聊天室
只不过本文是用Qt又将其重写了一遍而已,如果你阅读过上面那篇文章,阅读本文可能会更轻松一点。
不得不说,用Qt写代码可比用WTL、MFC方便太多了!
当然,这所谓的容易是建立在你使用过其它不那么容易的框架基础之上的,如果你一来就使用Qt,那可能你很难感受到它的容易。
本文属于C++进阶类型,过于基础的内容不会反复赘述,所以在阅读本文前,我建议你至少需要阅读以下几篇文章:
注意这里的用词:至少,因为该项目大量使用了上面这些文章中提到的知识点,我也不可能每次都挨着赘述一遍。
这里默认你已经了解了C/C++的基本语法。
有了上面几篇文章的基础可以保证你基本能看懂本项目的代码,但如果只看这几篇文章,想要将其完全理解,一般来说肯定还是不够的。
最好的学习方法是尝试自己写一遍,哪里有问题了再来看本文寻找相应的解决方案,这会让你编程能力进步飞快。
二、项目介绍
前面说了,这个项目仅仅只是用Qt来重写了界面而已,其总体功能、使用逻辑其实和用WTL实现的那个聊天室是一模一样的:
当然,可能有的同学对于学习WTL并没有什么兴趣,所以根本就没有看过那篇文章。
我也能理解,毕竟WTL那玩意用起来确实烦人,所以本文尽量还是会从零开始将其介绍一遍的。
该项目文件你可以在文末下载,本文是进阶项目,也不会再从零带着你跟着敲代码了,而是为你理清楚一个现有程序的运行逻辑、以及用到的相应知识点。
三、Qt网络模块
由于我们现在用的是Qt,所以最好就是直接使用Qt为我们封装好的网络库了。
如果你使用的qt creator
,那么你需要在项目文件中添加一句:QT += network
,才能使用网络库。
如果你和我一样习惯于使用vs,那么也很简单,来到创建好的项目属性中:
直接勾选网络模块即可。
同时你也看到了,上面这里还有一个qt的版本号,我目前使用的是6.5.3
,如果你不是这个版本,也可以在这里更换。
添加了网络库后,我们就可以引入以下两个头文件:
#include<qtcpserver.h>
#include<qtcpsocket.h>
这两个文件中就有两个类:QTcpServer
与QTcpSocket
。
其中QTcpServer
就是qt已经为我们封装好的tcp服务器类,而QTcpSocket
则是封装好的客户端类。
现在我们不再需要一步一步按照标准网络编程的步骤去走了,因为人家已经给我们封装好了!
此时一个最简单的服务器代码如下:
QTcpServer server;
server.listen(QHostAddress::Any, 9999);
QObject::connect(&server, &QTcpServer::newConnection, [&]() {})
就三步:
- 创建一个服务器对象。
- 监听地址、端口。
- 将客户端连接信号与一个槽函数进行绑定,这里为了方便,我直接绑定的一个
lambda
表达式。
如果你学过底层TCP编程,那么我相信你是真的能感受到它的便捷的!
也正因为Qt封装的太好了,所以很多时候,它并不适合用来学习知识点,而更适合用来开发应用。
同时它其实也没有那么多知识点需要学习,无非就是找找看它某个类有哪些函数可以用,仅此而已。
所以下面我们就直接开始讲解代码了。
四、网络数据包
网络编程中,首先最重要的一点其实就是确定好客户端、服务器的通信逻辑。
因为在网络通信中,无论你是消息、文件、视频、音乐,在这里都是一堆字节,你只有确定好传输的规则,对方才能够按照规则将其解析、还原。
这种规则也常称为协议,比如tcp协议、udp协议,http协议等等。
而我们这里就相当于要自己规定一个协议。
由于网络数据是流式传输的,所以我们一般会把协议内容放在数据的开头,也常称为数据包头,数据包头结合其后真正要传输的数据,就可以统称为数据包。