QT TCP服务器
创始人
2025-01-17 07:02:36
0

客户端:

功能:

连接:获取ip地址和端口号,并连接   取消:关闭窗口

工程文件加上

QT=+=core gui network

相关类与函数

QTcpSocket类:(需要被包含)

connectToHost()  连接。参数:QHostAdress地址对象(可用QString初始化),端口号(16位短整型)(QString自带进制转换,如ip.toshort)

连接成功后会发出一个信号:&QTcpSocket::connected

连接异常也会发出一个信号:&QTcpSocket::disconnected

peerAddress();获取客户端地址

peerAddress的子函数toString():将其转化位字符串

peerPort():获取客户端端口号(并非服务器端口)

write():参数:QByteArray ,可用append拼接,发送后会出现&QTcpSocket::readyread信号

QHostAddress类:(需要被包含)

其他函数:

(QTcpSocket * )sender();获取信号的发送者并强制转为QTcpSocket指针

服务器:

相关类与函数:

QTcpServer类:

listen():监听网卡,参数QHostAdress::AnyIPv4,端口号

如果有信号,会发出QTcpServer::newConnection信号

nextPendingConnection() 建立TCP连接,返回QTcpSocket类型

实现服务器与客户端连接

在widget构造函数中监听网卡ip,等待请求,收到信号后与客户端建立连接

注意,必须使用127开头的地址

127.0.0.1 地址称为本地回环地址,是一种特殊的网络地址,用于让单独的计算机进行自我回路测试和通信。 这个地址在 IP 协议中被定义为环回地址。 在网络设备中,网络接口上的 127.0.0.1 地址本质上是本机对自己的网络地址。

通信

打开其他窗口:新建qt->设计师...,在客户端创建新的窗口类chat

this->hide()隐藏窗口

创建新窗口对象时要用堆空间创建,也即是指针形式,这样申请的内存不会被销毁,

widget在连接成功后隐藏当前窗口,并打开新窗口chat,与打开widget窗口类似

         chat *k=new chat(SOCKET);          k->show();

要将socket信息传到新窗口中,所以类chat中要有参数,并在chat构造函数中初始化

QTcpSocket *s

在新窗口中,使用socket中的write发送信息,参数是QByteArray类型

在服务器中连接后再connect一个新的信号与曹:

&QTcpSocket::readyRead &Widget::data_resslot

在槽函数中要注意变量的范围,如果QTcpSocket指针是内部变量,则需要使用

(QTcpSocket*)sender();

将其转化为QTcpSocket类型指针,再用readAll读取所有发送的数据。

服务器代码:

chat.h

#ifndef CHAT_H #define CHAT_H  #include  #include    namespace Ui { class chat; }  class chat : public QWidget {     Q_OBJECT  public:     explicit chat(QTcpSocket *s,QWidget *parent = nullptr);     ~chat();  private slots:     void on_clearButton_clicked();      void on_sendButton_2_clicked();  private:     Ui::chat *ui;     QTcpSocket *SOCKET; };  #endif // CHAT_H 

widget.h

#ifndef WIDGET_H #define WIDGET_H  #include  #include  #include  #include  #include  #include   QT_BEGIN_NAMESPACE namespace Ui { class Widget; } QT_END_NAMESPACE  class Widget : public QWidget {     Q_OBJECT  public:     Widget(QWidget *parent = nullptr);     ~Widget();   private slots:     void on_cancelButton_2_clicked();      void on_connectButton_clicked();      void on_pushButton_clicked();  private:     Ui::Widget *ui;     QTcpSocket *SOCKET; }; #endif // WIDGET_H 

chat.cpp

#include "chat.h" #include "ui_chat.h"  chat::chat(QTcpSocket *s,QWidget *parent) :     QWidget(parent),     ui(new Ui::chat) {     ui->setupUi(this);     SOCKET=s; }  chat::~chat() {     delete ui; }  void chat::on_clearButton_clicked() {     ui->lineEdit->clear(); }  void chat::on_sendButton_2_clicked() {     QString text1=ui->lineEdit->text();     QByteArray ba;     ba.append(text1);     //write只能发送QByteArray类型数据     SOCKET->write(ba); } 

widget.cpp

#include "widget.h" #include "ui_widget.h"  Widget::Widget(QWidget *parent)     : QWidget(parent)     , ui(new Ui::Widget) {     ui->setupUi(this);     SOCKET=new QTcpSocket;     //成功/异常警告     connect(SOCKET,&QTcpSocket::connected,[this]()     {          QMessageBox::information(this,"提示","连接成功");          this->hide();          chat *k=new chat(SOCKET);          k->show();     });     connect(SOCKET,&QTcpSocket::disconnected,[this]()     {          QMessageBox::warning(this,"警告","连接异常");     });  }  Widget::~Widget() {     delete ui; }   void Widget::on_cancelButton_2_clicked() {     this->close(); }  void Widget::on_connectButton_clicked() {     //获取ip与端口号     QString com1=ui->COMlineEdit_2->text();     QString ip1=ui->IPlineEdit->text();     if(com1.isEmpty()||ip1.isEmpty())     {         QMessageBox::warning(this,"警告","请输入ip地址和端口号");     }     //开始连接     SOCKET->abort();     SOCKET->connectToHost(QHostAddress(ip1),com1.toShort()); }  void Widget::on_pushButton_clicked() {     qDebug()<<"disconnect";     SOCKET->disconnectFromHost(); } 

服务器代码:

widget.h

#ifndef WIDGET_H #define WIDGET_H  #include  #include  #include  #include  #include  #include    QT_BEGIN_NAMESPACE namespace Ui { class Widget; } QT_END_NAMESPACE #define TCPCOM 8000    class Widget : public QWidget {     Q_OBJECT  public:     Widget(QWidget *parent = nullptr);     ~Widget();  private slots:     void serverslot();     void on_check_clicked();     void data_resslot(); private:     Ui::Widget *ui;     QTcpServer *SERVER; }; #endif // WIDGET_H 

widget.cpp

#include "widget.h" #include "ui_widget.h"  Widget::Widget(QWidget *parent)     : QWidget(parent)     , ui(new Ui::Widget) {     ui->setupUi(this);     SERVER=new QTcpServer;     SERVER->listen(QHostAddress::Any,TCPCOM);     qDebug()<nextPendingConnection();     QHostAddress ip1=SOCKET1->peerAddress();     quint16 com1=SOCKET1->peerPort();     ui->comlineEdit->setText(QString::number(com1));     ui->iplineEdit_2->setText(ip1.toString());     QMessageBox::information(this,"提示","连接成功");     connect(SOCKET1,&QTcpSocket::readyRead,this,&Widget::data_resslot); }     void Widget::on_check_clicked() {     if(SERVER->isListening())     {             qDebug()<<"IS LISTENING";     }  } void Widget::data_resslot() {     QTcpSocket *Socket=(QTcpSocket*)sender();     ui->datalineEdit->setText(Socket->readAll());  } 

结果:

多线程

在服务器中启用多线程,即可接收多个客户端的连接。

相关类与函数

在文件中添加c++类,在继承中继承QThread,添加后多了.h和.cpp文件

QThread类,需要包含

start()打开线程

虚函数run():在run里连接信号与槽,线程处理函数

自定义信号

在类中定义,和private同级,在信号传递时可以附加参数

signals:  void sendtowidget(QByteArray ba);

在需要发出信号的地方加上即可,最后在widget中连接信号与槽

QByteArray ba=socket->readall(); emit sendtowidget(ba); 

相关内容

热门资讯

攻略辅助!德州私人局怎么透视,... 攻略辅助!德州私人局怎么透视,wejoker辅助软件视频,解迷教程(竟然有挂)该软件可以轻松地帮助玩...
必知教程!微乐小程序黑科技,7... 必知教程!微乐小程序黑科技,789大菠萝可以控制吗,积累教程(真的有挂)1、上手简单,内置详细流程视...
步骤辅助!竞技联盟破解版最新版... 步骤辅助!竞技联盟破解版最新版,hhpoker免费透视脚本,推荐教程(发现有挂)1、让任何用户在无需...
分享给玩家!创思维激k辅助工具... 分享给玩家!创思维激k辅助工具,约局吧辅助器,讲义教程(有挂总结)该软件可以轻松地帮助玩家将创思维激...
妙招辅助!德扑之心免费透视,w... 妙招辅助!德扑之心免费透视,wepoker怎么开辅助,辅助教程(有挂工具)1、玩家可以在德扑之心免费...
玩家必备教程!皮皮游戏辅助平台... 玩家必备教程!皮皮游戏辅助平台,朱雀开心罗松怎么开挂,资料教程(有挂透视)1、皮皮游戏辅助平台脚本辅...
总结辅助!hhpoker是正品... 总结辅助!hhpoker是正品吗,aapoker透视怎么用,解谜教程(有挂实锤)1)aapoker透...
今日重大通报!微信广东雀神挂件... 今日重大通报!微信广东雀神挂件辅助,随意玩辅助器,指南教程(有挂教学)1.微信广东雀神挂件辅助 选牌...
资料辅助!wepoker有辅助... 资料辅助!wepoker有辅助工具吗,wepoker软件安装包,教你教程(竟然有挂)小薇(辅助器软件...
实测分享!广西友乐免费辅助,新... 实测分享!广西友乐免费辅助,新荣耀辅助软件,指南书教程(有挂规律)1、玩家可以在广西友乐免费辅助透视...