一 任务描述
1.界面要求 :
一个 网址输入框,一个端口输入框,一个发送信息输入框
一个连接按钮,一个断开连接按钮(或者和连接做成一个按钮),一个发送按钮
2.功能要求:实现tcp链接
(1)连接指定的服务器地址及端口
(2)能发送+接收信息并显示
二 实现过程
前提: 使用QT的网络套接字 需要.pro文件中加入一句: QT += network
Ⅰ.客户端不需要监测,比服务器端简单 ,5大步
(1)创建QTcpSocket套接字对象 socket = new QTcpSocket();
(2)使用这个对象连接服务器 socket->connectToHost(IP, port);
(3)使用write函数向服务器发送数据 socket->write(data);
(4)当socket接收缓冲区有新数据到来时,会发出readRead()信号,因此为该信号添加槽函数以读取数据
QObject::connect(socket, &QTcpSocket::readyRead, this, &MainWindow::socket_Read_Data);
void MainWindow::socket_Read_Data()
{
QByteArray buffer;
//读取缓冲区数据
buffer = socket->readAll();
}
(5)断开与服务器的连接(关于close()和disconnectFromHost()的区别,可以按F1看帮助)
socket->disconnectFromHost();
Ⅱ 代码实现
1..pro文件
+ _network库
QT += network # 实现TCP连接
2.UI界面 绘制
PS1:注意写功能前 就改名字!!巧妙使用布局
PS2:先操作 按钮的go to slot (建立一个框架)
3..h文件书写
+ _读数据,断开连接 2个函数
+ _套接字socket 的定义
#ifndef MAINWINDOW_H
#define MAINWINDOW_H
#include <QMainWindow>
#include<QTcpSocket>
#include<QtNetwork>
namespace Ui {
class MainWindow;
}
class MainWindow : public QMainWindow
{
Q_OBJECT
public:
explicit MainWindow(QWidget *parent = 0);
~MainWindow();
private slots:
void on_pushButton_Connect_clicked();
void on_pushButton_Send_clicked();
void socket_Read_Data(); //自己写 读数据
void socket_Disconnected();//自己写 断开连接
private:
Ui::MainWindow *ui;
QTcpSocket *socket;//定义 套接字对象 PS:还没实例化
};
#endif // MAINWINDOW_H
4.mainwindow.cpp文件
(1) + _头文件 #include<QDebug> #include<QtNetwork>
(2)构造函数
+ _套接字实例化
+ _socket 信号与 槽连接
+ _界面默认IP 和 端口
+ _发送按钮 未连接不可操作
(3)+ _删除时 释放socket
(4) 连接按钮 槽函数
+ _判断按钮文字是”连接“ -> 获取IP和Port
+ _abort取消现有连接后,连接服务器connectToHost
+ _判断是否连接,通过 waitForConnected()
PS:只有用waitForConnected()后,QTcpSocket才真正尝试连接服务器,并返回是否连接的结果。
+_连接成败结果打印出来,通过qDebug()打印
+_判断按钮文字不是连接(也就是”断开连接“)
+_socket断开连接,并更新按钮文字为“连接”
+_发送按钮 可以使能
(5)发送按钮的槽函数
+_ 获取文本内容
+_ 以ASCII码发送,通过write() 文本的.toLatin1(),
+_ flush从缓存区 写到 网络套接字
(6)读取缓存区数据 函数基于 QByteArray类字节数组类
+_ 定义QByteArray类,并readAll
+_ 读取的内容 添加到 文本
+_ 文本区 setText () 进行刷新显示
(7)断开连接函数
+_ 发送按钮不可用
+_ 更新按钮的文字为“连接”
+_ 打印提示信息
#include "mainwindow.h"
#include "ui_mainwindow.h"
#include<QDebug>
#include<QtNetwork>
MainWindow::MainWindow(QWidget *parent) :
QMainWindow(parent),
ui(new Ui::MainWindow)
{
ui->setupUi(this);
socket = new QTcpSocket(this);//勿忘实例化,在connect之前 所有对象要存在
//连接信号与槽
//connect(socket,&QTcpSocket::readyRead,this,&MainWindow::socket_Read_Data);
//connect(socket,&QTcpSocket::disconnected,this,&MainWindow::socket_Disconnected);
connect(socket,SIGNAL(readyRead()),this,SLOT(socket_Read_Data()));
connect(socket,SIGNAL(disconnected()),this,SLOT(socket_Disconnected()));
ui->lineEdit_IP->setText("127.0.0.1");
ui->lineEdit_Port->setText("6000");
ui->pushButton_Send->setEnabled(false);//发送按钮先禁止操作
}
MainWindow::~MainWindow()
{
//增加释放
delete this->socket;
delete ui;
}
void MainWindow::on_pushButton_Connect_clicked()//建立TCP 连接
{
if(ui->pushButton_Connect->text() == tr("连接"))
{
QString IP;
int port;
IP = ui->lineEdit_IP->text(); //获取IP地址
port = ui->lineEdit_Port->text().toInt();//获取端口号
socket->abort();//取消已经有的连接
socket->connectToHost(IP,port);//连接服务器
if(!socket->waitForConnected(30000))
{
qDebug() << "connection failed!";
return;
}
qDebug() <<"connection successfully!";
ui->pushButton_Send->setEnabled(true);//发送按钮 使能
ui->pushButton_Connect->setText("断开连接");//智能检测 变化
}
else
{
socket->disconnectFromHost();//断开 连接 区别close() abort()
ui->pushButton_Connect->setText("连接");
ui->pushButton_Send->setEnabled(false);//
}
}
void MainWindow::on_pushButton_Send_clicked()
{
qDebug() <<"Send: " <<ui->textEdit_3->toPlainText();//获得文本内容
socket->write(ui->textEdit_3->toPlainText().toLatin1());//内容已ASCII码发送
socket->flush();//将数据从内部写缓冲区写到底层的网络套接字,而不会造成阻塞。
}
void MainWindow::socket_Read_Data()
{
QByteArray buffer;
//读取缓冲区数据
buffer = socket->readAll();
if(!buffer.isEmpty())
{
QString str = ui->textEdit_Recv->toPlainText();
str+=tr(buffer);
//刷新显示
ui->textEdit_Recv->setText(str);
}
}
void MainWindow::socket_Disconnected()
{
//发送按键失能
ui->pushButton_Send->setEnabled(false);
//修改按键文字
ui->pushButton_Connect->setText("连接");
qDebug() << "Disconnected!";
}
TCP通信原理参考https://blog.csdn.net/u014695839/article/details/70041771
socket 的介绍 https://blog.csdn.net/qq_37002901/article/details/86636813