Files
MassSpectrometer/IOT.Services/PLCDataReader.cs
T
2026-09-09 18:42:38 +08:00

159 lines
4.9 KiB
C#

using JinYuan.DataConvertLib;
using log4net.Core;
using PLCCommunication.PLCType.Omron;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace WindowsService1
{
/// <summary>
/// 定义每个数据读取请求的参数。
/// </summary>
public class PLCDataReadRequest
{
/// <summary>
/// PLC起始地址
/// </summary>
public string StartAddress { get; set; }
/// <summary>
/// 读取长度
/// </summary>
public ushort Length { get; set; }
/// <summary>
/// 读取区域名称
/// </summary>
public string StorageName { get; set; }
/// <summary>
/// 读取数据类型
/// </summary>
public PLCDataType DataType { get; set; }
}
/// <summary>
/// 存储每次读取操作的结果。
/// </summary>
public class PLCDataResult
{
/// <summary>
/// 读取区域名称
/// </summary>
public string StorageName { get; set; }
/// <summary>
/// 读取数据类型
/// </summary>
public PLCDataType DataType { get; set; }
/// <summary>
/// 数据
/// </summary>
public byte[] Data { get; set; }
/// <summary>
/// 是否读取成功
/// </summary>
public bool IsSuccess { get; set; }
/// <summary>
/// 读取失败的错误信息
/// </summary>
public string ErrorMessage { get; set; }
}
public class PLCDataReader
{
private readonly OmronFinsNet _plc;
public PLCDataReader(OmronFinsNet plc)
{
_plc = plc ?? throw new ArgumentNullException(nameof(plc));
}
public async Task<PLCDataResult> ReadDataAsync(PLCDataReadRequest request)
{
try
{
var data = await _plc.ReadAsync(request.StartAddress, request.Length);
if (data.IsSuccess && data.Content.Length > 0)
{
Logger.WriteInfo($"成功读取PLC数据,起始地址:{request.StartAddress},长度:{request.Length},类型:{request.DataType}");
return new PLCDataResult
{
StorageName = request.StorageName,
DataType = request.DataType,
Data = data.Content,
IsSuccess = true
};
}
else
{
Logger.WriteInfo($"读取PLC数据失败,起始地址:{request.StartAddress},长度:{request.Length},类型:{request.DataType}");
return new PLCDataResult
{
StorageName = request.StorageName,
DataType = request.DataType,
IsSuccess = false,
ErrorMessage = "读取PLC数据失败"
};
}
}
catch (Exception ex)
{
Logger.WriteError($"读取PLC数据时发生错误:{ex.Message}");
return new PLCDataResult
{
StorageName = request.StorageName,
DataType = request.DataType,
IsSuccess = false,
ErrorMessage = ex.Message
};
}
}
private object[] ParseData(byte[] content, PLCDataType dataType)
{
switch (dataType)
{
case PLCDataType.Short:
return ParseShortData(content);
case PLCDataType.Float:
return ParseFloatData(content);
default:
throw new ArgumentException($"不支持的数据类型:{dataType}");
}
}
private object[] ParseShortData(byte[] content)
{
int count = content.Length / 2;
return Enumerable.Range(0, count)
.Select(i => (object)ShortLib.GetShortFromByteArray(content, i * 2))
.ToArray();
}
private object[] ParseFloatData(byte[] content)
{
int count = content.Length / 4;
return Enumerable.Range(0, count)
.Select(i => (object)FloatLib.GetFloatFromByteArray(content, i * 4))
.ToArray();
}
}
public static class ConvertHelper
{
/// <summary>
/// 字节数组高低位转换
/// </summary>
/// <param name="Arrbyte"></param>
/// <returns></returns>
public static byte[] ByteReverse(this byte[] Arrbyte)
{
byte[] ArrByte = Arrbyte.Select((x, i) => new { x, i }).GroupBy(x => x.i / 2).SelectMany(x => new byte[] { x.Last().x, x.First().x }).ToArray();
return ArrByte;
}
}
}