C# 中利用 EasyModbus 库提升 Modbus 通信效率

2,727 阅读4分钟

前言

Modbus 是一种广泛应用于工业领域的通信协议,用于在电子设备之间传输数据。它简单、可靠,支持串行和以太网通信。

EasyModbus 是一个用于 .NET 平台的开源库,提供了便捷的接口来实现 Modbus 协议的功能。

Modbus 协议简介

Modbus 是一种在工业自动化领域中广泛应用的通信协议,在为电子设备间的通信提供简单而可靠的方法。它支持多种物理层和网络类型,包括串行通信(如 RS-232 和 RS-485)以及以太网通信(如 Modbus TCP),并且由于其开放性和简易性,成为了工业控制系统的标准之一。

EasyModbus 库概述

EasyModbus 是一款专为 .NET 平台设计的开源库,简化了 Modbus 协议的实现。该库提供了易于使用的接口,可以在应用程序中快速集成 Modbus 功能,无论是用于开发客户端还是服务器端应用都十分便捷。

本文将详细介绍如何在 C# 项目中使用 EasyModbus 库,实现 Modbus 通信,包括读取和写入数据的具体示例。

安装 EasyModbus

为了开始使用 EasyModbus 库,首先需要将其添加到您的 C# 项目中。

最简便的方法是通过 NuGet 包管理器进行安装。

请按照以下步骤操作:

1、打开 Visual Studio 中的 "NuGet 包管理器控制台"。可以通过菜单路径 "工具"->"NuGet 包管理器" -> "包管理器控制台" 访问。

2、在控制台窗口中输入并执行以下命令

Install-Package EasyModbus

基本用法

创建 Modbus 客户端

首先,需要创建一个 Modbus 客户端实例,指定目标服务器的 IP 地址和端口号(默认端口为 502)。

static void Main(string[] args)
{
    ModbusClient modbusClient = new ModbusClient("127.0.0.1", 502);
    modbusClient.Connect();
    if (modbusClient.Connected) { 
        Console.WriteLine("Connected to Modbus Server");
    }
}

读取数据

读取线圈(Coils)状态

读取线圈状态通常用于获取开关、继电器等数字量的当前状态。

static void Main(string[] args)
{
    ModbusClient modbusClient = new ModbusClient("127.0.0.1", 502);
    modbusClient.Connect();
    if (modbusClient.Connected) { 
        Console.WriteLine("Connected to Modbus Server");
    }
    // 读取从地址0开始的10个线圈状态
    bool[] coils = modbusClient.ReadCoils(0, 10);

    // 输出结果
    for (int i = 0; i < coils.Length; i++)
    {
        Console.WriteLine($"Coil {i}: {coils[i]}");
    }
}

读取离散输入(Discrete Inputs)

// 读取从地址0开始的5个离散输入状态
bool[] discreteInputs = modbusClient.ReadDiscreteInputs(0, 5);

for (int i = 0; i < discreteInputs.Length; i++)
{
    Console.WriteLine($"Discrete Input {i}: {discreteInputs[i]}");
}

读取保持寄存器(Holding Registers)

保持寄存器用于存储模拟量数据,如传感器读数。

// 读取从地址0开始的5个保持寄存器的值
int[] holdingRegisters = modbusClient.ReadHoldingRegisters(0, 5);

for (int i = 0; i < holdingRegisters.Length; i++)
{
    Console.WriteLine($"Holding Register {i}: {holdingRegisters[i]}");
}

QQ_1736125649962.png

读取输入寄存器(Input Registers)

// 读取从地址0开始的5个输入寄存器的值
int[] inputRegisters = modbusClient.ReadInputRegisters(0, 5);

for (int i = 0; i < inputRegisters.Length; i++)
{
    Console.WriteLine($"Input Register {i}: {inputRegisters[i]}");
}

写入数据

写入单个线圈

// 将地址0的线圈状态设为 true
modbusClient.WriteSingleCoil(0, true);

写入多个线圈

// 将从地址0开始的3个线圈状态设置为 true, false, true
bool[] coilValues = { true, false, true };
modbusClient.WriteMultipleCoils(0, coilValues);

写入单个寄存器

// 将地址0的保持寄存器值设为1234
modbusClient.WriteSingleRegister(01234);

写入多个寄存器

// 将从地址0开始的3个保持寄存器值设置为100, 200, 300
int[] registerValues = { 100200300 };
modbusClient.WriteMultipleRegisters(0, registerValues);

高级用法

使用 Modbus RTU(串行通信)

除了 Modbus TCP,EasyModbus 也支持 Modbus RTU。

// 创建串行通信的 Modbus 客户端
ModbusClient modbusClient = new ModbusClient("COM3");
modbusClient.UnitIdentifier = 1; // 从机地址
modbusClient.Baudrate = 9600;
modbusClient.Parity = System.IO.Ports.Parity.None;
modbusClient.StopBits = System.IO.Ports.StopBits.One;

modbusClient.Connect();

异步通信

使用异步方法可以避免阻塞主线程,提高应用程序的响应速度。

// 异步读取保持寄存器
modbusClient.ConnectionTimeout = 5000; 
// 设定超时时间

Task.Run(() =>
{
    int[] holdingRegisters = modbusClient.ReadHoldingRegisters(0, 5);
    // 处理读取的数据
});

事件处理

EasyModbus 提供了事件机制,可以在数据接收后触发特定操作。

static ModbusClient modbusClient;
static void Main(string[] args)
{
    try
    {
        modbusClient = new ModbusClient("127.0.0.1", 502);

        // 注册事件处理器  
        modbusClient.SendDataChanged += (sender) => {
            Console.WriteLine("发送数据事件触发");
        };

        modbusClient.ReceiveDataChanged += (sender) => {
            Console.WriteLine("接收数据事件触发");

            // 打印接收到的原始数据  
            if (modbusClient.receiveData != null)
            {
                Console.WriteLine("接收数据: " +
                    BitConverter.ToString(modbusClient.receiveData));
            }
        };

        // 连接  
        modbusClient.Connect();

        // 显式写入数据  
        int[] values = new int[] { 123 };
        modbusClient.WriteMultipleRegisters(100, values);

        // 保持连接  
        Console.WriteLine("等待事件触发...");
        Console.ReadKey();
    }
    catch (Exception ex)
    {
        Console.WriteLine($"错误: {ex.Message}");
    }
}

结束通信

在通信完成后,建议关闭连接以释放资源。

modbusClient.Disconnect();

总结

本文全面介绍了如何利用 EasyModbus 库在 C# 项目中实现高效的 Modbus 通信。

从库的安装配置到高级功能的应用,我们提供了详尽的指南和实用示例,帮助大家快速上手并优化其工业自动化解决方案。

最后

如果你觉得这篇文章对你有帮助,不妨点个赞支持一下!你的支持是我继续分享知识的动力。如果有任何疑问或需要进一步的帮助,欢迎随时留言。

也可以加入微信公众号 [DotNet技术匠] 社区,与其他热爱技术的同行一起交流心得,共同成长!

优秀是一种习惯,欢迎大家留言学习!

作者:技术老小子

出处:mp.weixin.qq.com/s/ScHtXBNQziQ5JqdFpw1_UQ

声明:网络内容,仅供学习,尊重版权,侵权速删,歉意致谢!