Qt-Web混合开发-WebSocket客户端程序Web版本(9)

12 篇文章 20 订阅
本文介绍了使用Qt结合HTML、CSS和JavaScript实现WebSocket客户端程序的Web版本。通过Qt将HTML界面打包,实现了客户端的连接、断开、状态查看和消息收发功能。WebSocket提供了一种在单次TCP连接上进行双向通信的协议,相较于HTTP的单向通信和频繁握手,更加高效。文章提供了关键代码示例,包括HTML、JavaScript和Qt的C++部分。
摘要由CSDN通过智能技术生成

Qt-Web混合开发-WebSocket客户端程序Web版本💚💜🉑🍑

更多精彩内容
👉个人内容分类汇总 👈
👉Qt - Web混合开发👈

1、概述🐛🦆

WebSocket 是 HTML5 开始提供的一种在单个 TCP 连接上进行全双工通讯的协议。

WebSocket 使得客户端和服务器之间的数据交换变得更加简单,允许服务端主动向客户端推送数据。在 WebSocket API 中,浏览器和服务器只需要完成一次握手,两者之间就直接可以创建持久性的连接,并进行双向数据传输。

在 WebSocket API 中,浏览器和服务器只需要做一个握手的动作,然后,浏览器和服务器之间就形成了一条快速通道。两者之间就直接可以数据互相传送。

现在,很多网站为了实现推送技术,所用的技术都是 Ajax 轮询。轮询是在特定的的时间间隔(如每1秒),由浏览器对服务器发出HTTP请求,然后由服务器返回最新的数据给客户端的浏览器。这种传统的模式带来很明显的缺点,即浏览器需要不断的向服务器发出请求,然而HTTP请求可能包含较长的头部,其中真正有效的数据可能只是很小的一部分,显然这样会浪费很多的带宽等资源。

HTML5 定义的 WebSocket 协议,能更好的节省服务器资源和带宽,并且能够更实时地进行通讯。

  • WebSocket和Http的异同点

相同:

  1. 建立在TCP之上,通过TCP协议来传输数据;
  2. 都是可靠性传输协议;
  3. 都是应用层协议。

差异:

  1. WebSocket是HTML5中的协议,支持持久连接,HTTP不支持持久连接;
  2. HTTP是单向协议,只能由客户端发起,做不到服务器主动向客户端推送信息。

2、实现效果😅🙏

在这里插入图片描述

3、实现功能🐮🐴

  1. 使用html编写界面、css设置样式、javascript实现webSocket客户端程序;
  2. 将html、css、js文件分开编写,便于阅读;
  3. 程序编译后自动将html文件夹拷贝到可执行程序当前路径;
  4. 可以直接点击chatClient.html文件运行客户端程序;
  5. 也可以在程序编译运行后使用QDesktopServices自动打开html文件。

4、关键代码💳🛣️🍐

  • pro文件
QT += core  widgets
  • main.cpp
#include <QApplication>
#include <QDesktopServices>
#include <qdir.h>
#include <qurl.h>
#include <QDebug>

int main(int argc, char *argv[])
{
    QApplication a(argc, argv);

    /**
     * 使用合适的程序打开url
     * QDesktopServices需要使用QApplication才可以执行,
     * 否则会报错【QDesktopServices::openUrl: Application is not a GUI application】
     */
    qDebug() << QDesktopServices::openUrl(QDir("./html/chatClient.html").absolutePath());

    return a.exec();
}

  • chatClient.html
<!DOCTYPE html>
<html lang="zh">
<head>
    <meta charset="UTF-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>WebSocket客户端程序</title>

    <script src="./chatClient.js"></script>
    <link rel="stylesheet" type="text/css" href="chatClient.css">
</head>
<body>
    <div>
        <h1>WebSocket客户端程序</h1>
        <p>
            服务端url:<input type="text" id="url" value="ws://localhost:1234">
        </p>
        <p>
            <button id="but_connect" onclick="socketConnectOrDis()">连接</button>
            <button id="but_getState" onclick="getState()">WebSocket状态</button>
        </p>
        <p>
            <textarea name="textShow" id="textShowId" cols="60" rows="10" readonly></textarea>
        </p>
        <p>
            <input type="text" id="nick" value="张三" />
            <input type="text" id="inputText" onkeydown="if(event.keyCode==13)sendMessage();"/>
            <button id="but_send" onclick="sendMessage()" disabled>发送数据</button>
        </p>

    </div>
</body>
</html>
  • chatClient.js
// 关于WebSocket的用法可以看【https://developer.mozilla.org/zh-CN/docs/Web/API/WebSocket】
var g_client = null;     // WebSocket客户端对象

/**
 * 控制WebSocket连接或者断开
 */
function socketConnectOrDis()
{
    var text = document.getElementById("but_connect").innerHTML;
    if(text === "连接")
    {
        connectWebSocket();
    }
    else
    {
        disConnectWebSocket();
    }
}

/**
 * WebSocket连接
 */
function connectWebSocket() 
{
    try
    {
        if(g_client && g_client.readyState === WebSocket.OPEN)  // 如果g_client不为空,并且为连接状态
        {
            g_client.close();  // 关闭连接
        }
        var url = document.getElementById("url").value;
        g_client = new WebSocket(url);      // 创建一个WebSocket客户端,并连接
        /**
         * 连接成功触发事件执行的回调函数
         */
        g_client.onopen = function(evt)   
        {
            showMessage("连接成功!");
            document.getElementById("but_connect").innerHTML = "断开连接";
            document.getElementById("but_send").disabled = false;        // 按键使能
        }
        /**
         * 关闭连接触发事件执行的回调函数
         */
        g_client.onclose = function(evt)
        {
            showMessage("关闭连接");
            document.getElementById("but_connect").innerHTML = "连接";
            document.getElementById("but_send").disabled = true;
        }
        /**
         * 接收到信息的回调函数
         */
        g_client.onmessage = function(evt)
        {
            showMessage("收到:" + evt.data);
        }
        /**
         * 连接失败后的回调函数
         */
        g_client.onerror = function(evt)
        {
            showMessage("Error:" + evt.data);
        }
    }
    catch(exception)   // 捕获异常信息
    {
        showMessage("Error:" + exception);
    }
}

/**
 * 断开连接
 */
function disConnectWebSocket()
{
    if(g_client)
    {
        g_client.close();
    }
}

function getState()
{
    if(g_client)
    {
        var state;
        switch(g_client.readyState)
        {
            case WebSocket.CONNECTING:
            {
                state = "连接中";
                break;
            }
            case WebSocket.OPEN:
            {
                state = "已连接";
                break;
            }
            case WebSocket.CLOSING:
            {
                state = "正在关闭连接";
                break;
            }
            case WebSocket.CLOSED:
            {
                state = "未连接";
                break;
            }
            default:
            {
                state = "未知";
                break;
            }
        }
        showMessage("客户端当前状态:" + state);
    }
    else
    {
        showMessage("客户端未初始化");
    }
}

/**
 * 显示信息
 */
function showMessage(message) 
{
    var textShow = document.getElementById("textShowId");
    textShow.value += message + "\n";              // 追加信息
    textShow.scrollTop = textShow.scrollHeight;    // 滚动条显示最下方
}

/**
 * 发送信息
 */
function sendMessage()
{
    if(g_client != null)
    {
        var nick = document.getElementById("nick").value;       // 获取昵称
        var msg = document.getElementById("inputText").value;   // 获取发送的数据
        var strToSend = nick + ":" + msg;
        g_client.send(strToSend);
        showMessage("发送:" + strToSend);
    }
}

  • chatClient.css
button {
    background-color: #4CAF50; /* Green */
    border: none;
    color: white;
    padding: 15px 32px;
    text-align: center;
    text-decoration: none;
    display: inline-block;
    font-size: 14px;
    margin: 4px 2px;
    cursor: pointer;
    -webkit-transition-duration: 0.4s; /* Safari */
    transition-duration: 0.4s;
    box-shadow: 0 8px 16px 0 rgba(0,0,0,0.2), 0 6px 20px 0 rgba(0,0,0,0.19);
}
button:hover {
    box-shadow: 0 12px 16px 0 rgba(0,0,0,0.24),0 17px 50px 0 rgba(0,0,0,0.19);
}

#textShowId {
     /*去掉右下角的斜杠,不允许文本框缩放*/
     resize: none;
     background: #e6dfdf;
     /*设置字体大小*/
     font-size: 18px;
     /* placeholder位置 提示靠左靠右居中等 */
     text-align: left;
     box-shadow: 0 8px 16px 0 rgba(0,0,0,0.2), 0 6px 20px 0 rgba(0,0,0,0.19);
}

h1 {
    font-size: 40px;
    color:red;
}

div {
    text-align: center;   /* 居中 */
}

input {
        height: 35px;
        background-color: rgb(248, 240, 240);
        font-size: 16px;
        border: 1px solid rgb(27, 26, 26);
        color: black;
        outline: none;  
        padding-left: 15px;  
        box-shadow: 0 8px 16px 0 rgba(0,0,0,0.2), 0 6px 20px 0 rgba(0,0,0,0.19);
}

#nick {
    width: 60px;
}

5、源代码🐍🉐

. ⋆⁺⋆。🦋₊⋆°⋆
 /l、
゙(゚、 。 7
 l、゙ ~ヽ
 じしf_, )ノ

  • 0
    点赞
  • 4
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

mahuifa

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值