IT数码 购物 网址 头条 软件 日历 阅读 图书馆
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
图片批量下载器
↓批量下载图片,美女图库↓
图片自动播放器
↓图片自动播放器↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁
 
   -> 网络协议 -> QT7联合Modbus(TCP)读写PLC数据——全网最完整 -> 正文阅读

[网络协议]QT7联合Modbus(TCP)读写PLC数据——全网最完整

前言:

B站视频、CSDN“找宝贝”、度娘、博客园、Github找了好久关于QT联合Modbus(TCP)读写PLC数据的知识真就没有一个能从头到尾讲下来这个知识的,可能有也是我能力有限疏忽了,但是我能力范围内真就没有能把这个事儿说明白的,我自己通过学习CSDN前人的QT5里面读写PLC的知识和B站大佬讲解两个PLC之间TCP通讯,举一反三,硬把他们联系到一起,费话不多少,直接分享我的经验。

一、PLC配置连接环境和通讯模块引脚设置

不知道为啥首先添加新设备(我这个PLC只能用4.2版本的,其他版本不好用,有懂哥可以留言告诉弟弟,感谢)

其次设置IP地址

?访问和连接打开

?在主函数中找到Modbus(TCP)通讯模块并拖到主函数中

?配置通讯块:这里很重要

第一个是是否通讯flase就是通讯、true就是不通讯

第二个是服务器数据存储区:我上图的参数意思就是从M10.0开始的4个区域,也就是M10.0、M12.0、M14.0、M16.0(对应地址就是0、1、2、3)

第三个参数是配置通讯的IP之类的我们接下来展开说:

首先创建一个DB块,他的数据类型是箭头所指(自己手打别无他法)

interfaceid就是64别动(除非你的是极少数的电脑,相信我你就是64)

id随便设置,和QT配对用的,我这里写1

其他的不用动

LocaIPort是端口号,和那个64一样固定502(别给自己找麻烦就用大家都用的就行)

设置完这些,把DB块的变量A放到刚才的通讯块第三个参数中,如上上个图所示

接下来设置监控的地址变量

添加新监控表->地址写上如上所示两个地址

这样一来,PLC这边配置完毕

二、QT配置Modbus编写程序

新建一个QT7(pro)项目

在Pro文件中添加如下代码

QT += serialbus serialport widgets//添加库

在头文件内容如下

#ifndef MAINWINDOW_H
#define MAINWINDOW_H
#include <QModbusDataUnit> //存储接收和发送数据的类,数据类型为1bit和16bit
#include <QModbusReply> //客户端访问服务器后得到的回复(如客户端读服务器数据时包含数据信息)
#include <QMainWindow>

QT_BEGIN_NAMESPACE
namespace Ui { class MainWindow; }
QT_END_NAMESPACE
class QModbusClient;
class QModbusReply;

class MainWindow : public QMainWindow
{
    Q_OBJECT

public:
    MainWindow(QWidget *parent = nullptr);
    ~MainWindow();
    QModbusClient *modbusDevice = nullptr;
    void readDevice();
    void toReadReady();
    void on_writeTor();

private slots:
    void on_pushButton_clicked();

    void on_pushButton_2_clicked();

    void on_pushButton_3_clicked();

private:
    Ui::MainWindow *ui;
};
#endif // MAINWINDOW_H

Cpp文件如下

#include "mainwindow.h"
#include "ui_mainwindow.h"
#include <QModbusTcpClient>
#include <QDebug>
#include <QThread>

MainWindow::MainWindow(QWidget *parent)
    : QMainWindow(parent)
    , ui(new Ui::MainWindow)
{
    ui->setupUi(this);
    modbusDevice = new QModbusTcpClient();
}

MainWindow::~MainWindow()
{
    delete ui;
}


void MainWindow::on_pushButton_clicked()
{
    if (!modbusDevice)
        return;
    if (modbusDevice->state() != QModbusDevice::ConnectedState) {
        //处于非连接状态,进行连接
        //TCP连接,端口502,地址192.168.0.1
        modbusDevice->setConnectionParameter(QModbusDevice::NetworkPortParameter, 502);
        modbusDevice->setConnectionParameter(QModbusDevice::NetworkAddressParameter, "192.168.0.1");
        //连接超时设置,2000ms
        modbusDevice->setTimeout(2000);
        //连接失败重试连接,3次
        modbusDevice->setNumberOfRetries(3);
        //调试窗口显示连接状态
        if (modbusDevice->connectDevice()) {
            qDebug()<< "Connected!";
        }
     }
        else {
        //处在连接状态进行断开连接的操作
        modbusDevice->disconnectDevice();
    }
}

void MainWindow::readDevice()
{
    if (!modbusDevice)
    {
        return;
    }

    qDebug()<<"read device";
    
    QModbusDataUnit readUnit = QModbusDataUnit(QModbusDataUnit::HoldingRegisters, 0, 1);

    if (auto *reply = modbusDevice->sendReadRequest(readUnit, 1))   //1->modbus设备地址
    {
        if (!reply->isFinished())
        {
            connect(reply, &QModbusReply::finished, this, &MainWindow::toReadReady);
        }
        else
        {
            delete reply; // broadcast replies return immediately
        }
    }
    else
    {
        //emit statusBar(tr("Read error: ") + modbusDevice->errorString());
    }
     QThread::msleep(1);

}

void MainWindow::toReadReady()
{
//QModbusReply这个类存储了来自client的数据,sender()返回发送信号的对象的指针
    auto reply = qobject_cast<QModbusReply *>(sender());
    if (!reply)
    {
        return;
    }

    if (reply->error() == QModbusDevice::NoError)
    {
        //处理成功返回的数据
       const QModbusDataUnit unit = reply->result();
        //quint16 stat = unit.value(1);  //状态(位与关系)
       int a = unit.value(0);
       qDebug()<<a;
    }
}

void MainWindow::on_pushButton_2_clicked()
{
    readDevice();
}


void MainWindow::on_pushButton_3_clicked()
{
    on_writeTor();
}

void MainWindow::on_writeTor()
{
    QModbusDataUnit writeUnit(QModbusDataUnit::HoldingRegisters, 0, 1); // write 1 value in address 40003
    writeUnit.setValue(0, 0x00C);
    //这里先建好QModbusDataUnit

    if (auto *reply = modbusDevice->sendWriteRequest(writeUnit, 1))
    //发送写请求
    {
        if (!reply->isFinished())
        {
            connect(reply, &QModbusReply::finished, this, [this, reply]()
            {
                if (reply->error() != QModbusDevice::NoError)
                        // error in reply

                    reply->deleteLater();
                });
        }
        else
        {
            if (reply->error() != QModbusDevice::NoError)
                // error in reply

            // broadcast replies return immediately
            reply->deleteLater();
        }
    }
    else
    {
        // error in request
    }


}

写入和读取我挑一个说里面值得注意的地方

?第一行的参数0代表第一个地址,上文PLC有介绍

第一行的参数1代表读一个

第二行的0代表要往0中写入数据

第二行的0x00C表示往0地址中写入16进制(十进制就是12)

UI界面就三个按钮

三、测试

首先打开PLC转至在线,监视STATUS,7002就是没有通讯?

运行QT程序点击连接PLC变为7006就是通讯连接?

监视监控表,这里的12是我测试的时候写进去的,你们的刚开始肯定是0

?点击QT界面写入,检测到PLCM10.0出现数据12,如上图所示?

?点击QT界面读取,qDebug出来数据可以看到确实是读到了

至此QT7联合Modbus(TCP)读写PLC数据全部完成。

但是还有个问题就是只能读写int类型的数据,十进制转16进制的时候写不进PLC,PLC读入Real类型进QT的时候也只能是整数,这个问题还没有解决,不知道有没有大佬或者懂哥指点一下,谢谢了,实在是不太想再在CSDN里面“遨游”了(狗头)

感谢大家支持,希望对你们有帮助!!!

  网络协议 最新文章
使用Easyswoole 搭建简单的Websoket服务
常见的数据通信方式有哪些?
Openssl 1024bit RSA算法---公私钥获取和处
HTTPS协议的密钥交换流程
《小白WEB安全入门》03. 漏洞篇
HttpRunner4.x 安装与使用
2021-07-04
手写RPC学习笔记
K8S高可用版本部署
mySQL计算IP地址范围
上一篇文章      下一篇文章      查看所有文章
加:2022-06-16 21:52:38  更:2022-06-16 21:52:46 
 
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁

360图书馆 购物 三丰科技 阅读网 日历 万年历 2024年5日历 -2024/5/19 15:34:31-

图片自动播放器
↓图片自动播放器↓
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
图片批量下载器
↓批量下载图片,美女图库↓
  网站联系: qq:121756557 email:121756557@qq.com  IT数码