Files
StandardSence/StandardScene.Core/Docs/Charge/充电桩报文自动更新说明.md
2026-06-14 11:19:15 +08:00

310 lines
8.8 KiB
Markdown
Raw Permalink Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
# 充电桩报文自动更新功能说明
## 功能概述
系统现已支持发送和接收充电桩UDP报文,**分别解析后合并更新**充电桩管理列表中的实时数据。
## 工作流程
```
发送方向: 应用程序 → 发送报文 → CommunicationMessageService(存储+解析发送数据) → 更新设定值
接收方向: 充电桩设备 → UDP报文(40001端口) → ChargeUdpService → CommunicationMessageService(存储+解析接收数据) → 更新实时数据
合并结果: 发送数据 + 接收数据 → 数据服务 → 管理界面自动刷新
```
## 核心组件
### 1. CommunicationMessageService(通讯报文服务)
**文件位置**: `Charge/CommunicationMessageService.cs`
**主要功能**:
- 存储所有发送和接收的报文(最多保留100条)
- **分开解析发送和接收的报文数据**
- 根据IP地址匹配对应的充电桩并更新数据
- 提供报文查询和筛选功能
**发送报文解析的数据**:
- ✅ 充电指令(启动/停止)
- ✅ 设定电压(V
- ✅ 设定电流(A
- ✅ 发送时间
**接收报文解析的数据**:
- ✅ 通讯状态(正常/错误)
- ✅ 充电指令状态(启动/停止)
- ✅ 机构状态(伸出/缩回/伸出中/缩回中/故障)
- ✅ 实时电压(V
- ✅ 实时电流(A
- ✅ 电量百分比(%
- ✅ 报警状态和级别
- ✅ 充电桩状态(空闲/充电中/故障/离线)
- ✅ 当前充电车辆编号
- ✅ 接收时间
### 2. ChargeUdpServiceUDP监听服务)
**文件位置**: `Charge/ChargeUdpService.cs`
**监听端口**: 40001
**工作流程**:
1. 接收UDP报文
2. 调用 `CommunicationMessageService.AddReceiveMessage()` 记录报文
3. `CommunicationMessageService` 自动解析接收报文并更新充电桩数据
4. 保持原有任务处理逻辑的兼容性
### 3. 发送报文处理
**发送位置**:
- `ChargeStationType/MuXingChargeStation.cs`
- `ChargeStationType/FLChargeStation.cs`
- `ChargeStationType/PCBChargeStation.cs`
**工作流程**:
1. 发送UDP报文到充电桩
2. 调用 `CommunicationMessageService.AddSendMessage()` 记录报文
3. `CommunicationMessageService` 自动解析发送报文并更新充电桩设定值
### 4. ChargeStationDataService(数据服务)
**新增方法**: `GetStationByIp(string ipAddress)`
**功能**: 根据IP地址快速查找对应的充电桩记录
### 5. ChargeStationManagementForm(管理界面)
**新增功能**: 自动刷新
**刷新间隔**: 2秒
**特点**:
- 自动更新列表显示
- 不影响用户的编辑操作
- 窗体关闭时自动停止刷新
## 报文格式说明
### 当前支持的报文格式
报文采用逗号分隔的字节数组格式,例如:
```
1,2,3,4,5,...,28,29,30
```
### 发送报文字节位置定义(示例)
| 字节位置 | 数据内容 | 说明 |
|---------|---------|------|
| 5 | 充电指令 | 0=停止, 1=启动 |
| 6-7 | 设定电压 | 高低字节,单位0.1V |
| 8-9 | 设定电流 | 高低字节,单位0.1A |
### 接收报文字节位置定义(示例)
| 字节位置 | 数据内容 | 说明 |
|---------|---------|------|
| 10 | 充电指令状态 | 0=停止, 1=启动 |
| 11 | 机构状态 | 0=未知, 1=伸出, 2=缩回, 3=伸出中, 4=缩回中, 5=故障 |
| 12-13 | 实时电压 | 高低字节,单位0.1V |
| 14-15 | 实时电流 | 高低字节,单位0.1A |
| 16 | 电量百分比 | 0-100 |
| 20 | 报警级别 | 0=无, 1-2=低, 3-5=中, 6-8=高, 9+=严重 |
| 25 | 充电桩状态 | 0=空闲, 1=充电中, 2=故障, 3=离线 |
| 26-29 | 车辆编号 | 4字节整数 |
| 28 | 通讯状态 | 1=正常, 其他=错误 |
**⚠️ 注意**: 以上字节位置为示例,需要根据实际通讯协议进行调整。
## 如何调整报文解析规则
打开 `CommunicationMessageService.cs` 文件,分别修改发送和接收报文的解析方法:
### 调整发送报文解析
修改 `ParseSendRawData` 方法中的字节位置:
```csharp
private ParsedSendData ParseSendRawData(string rawData)
{
// ... 字节数组转换代码 ...
var parsed = new ParsedSendData
{
// 根据实际协议修改字节位置
ChargeCommand = bytes.Length > 5 ? bytes[5] : (byte)0,
SetVoltage = bytes.Length > 7 ? (bytes[6] << 8 | bytes[7]) / 10.0 : 0,
SetCurrent = bytes.Length > 9 ? (bytes[8] << 8 | bytes[9]) / 10.0 : 0,
SendTime = DateTime.Now
};
return parsed;
}
```
### 调整接收报文解析
修改 `ParseReceiveRawData` 方法中的字节位置:
```csharp
private ParsedReceiveData ParseReceiveRawData(string rawData)
{
// ... 字节数组转换代码 ...
var parsed = new ParsedReceiveData
{
// 根据实际协议修改字节位置
CommStatus = bytes[28] == 1 ? CommunicationStatus.Normal : CommunicationStatus.Error,
ChargeCommandStatus = bytes[10] == 1 ? ChargeCommandStatus.Started : ChargeCommandStatus.Stopped,
// ... 其他字段 ...
ReceiveTime = DateTime.Now
};
return parsed;
}
```
## 使用示例
### 1. 启动UDP监听
```csharp
// 在程序启动时创建UDP服务
var udpService = new ChargeUdpService();
```
### 2. 添加充电桩
在充电桩管理界面中添加充电桩,确保IP地址与实际设备一致:
```
充电桩编号: 1
名称: 1号充电桩
IP地址: 192.168.1.101 ← 必须与设备IP一致
端口: 502
```
### 3. 自动更新
**发送报文时**
1. 应用程序发送充电指令到充电桩
2. 系统记录发送报文
3. 解析发送报文数据(设定电压、电流等)
4. 根据IP地址匹配充电桩
5. 更新充电桩的设定值
**接收报文时**
1. 系统自动接收UDP报文(端口40001)
2. 记录接收报文
3. 解析接收报文数据(实时状态、电压、电流等)
4. 根据IP地址匹配充电桩
5. 更新充电桩的实时数据
**界面显示**
- 管理界面每2秒自动刷新显示
- 同时显示设定值(来自发送报文)和实时值(来自接收报文)
## 调试信息
系统会在日志中输出以下信息:
```
[UDP返回报文信息] ChargeStation ADD:[1,2,3,4,...]
[ChargeStation] 更新充电桩成功: [1] 1号充电桩 (192.168.1.101:502) - Charging
```
**查看报文记录**
- 打开通讯监控界面可以查看所有发送和接收的报文
- 报文按时间倒序排列(最新的在最前面)
- 最多保留100条报文记录
## 常见问题
### Q1: 报文接收了但数据没更新?
**检查项**:
1. 充电桩的IP地址是否在管理列表中
2. 报文格式是否正确(至少30字节)
3. 查看日志中是否有解析错误信息
### Q2: 如何修改刷新间隔?
`ChargeStationManagementForm.cs``InitializeAutoRefresh` 方法中修改:
```csharp
autoRefreshTimer.Interval = 2000; // 改为你需要的毫秒数
```
### Q3: 如何关闭自动刷新?
```csharp
// 在InitializeAutoRefresh方法中注释掉这行
// autoRefreshTimer.Start();
```
## 扩展功能
### 添加新的解析字段
**发送报文新字段**
1.`ParsedSendData` 类中添加新属性
2.`ParseSendRawData` 方法中解析新字段
3.`UpdateStationFromSendData` 方法中更新到充电桩对象
**接收报文新字段**
1.`ParsedReceiveData` 类中添加新属性
2.`ParseReceiveRawData` 方法中解析新字段
3.`UpdateStationFromReceiveData` 方法中更新到充电桩对象
### 支持其他通讯协议
`CommunicationMessageService.cs` 中可以根据端口号或其他特征判断协议类型:
```csharp
public void AddReceiveMessage(string ipAddress, int port, string rawData, string stationId = null)
{
// ... 添加报文记录 ...
// 根据端口判断协议类型
if (port == 40001)
{
ParseReceiveDataAndUpdateStation(ipAddress, rawData); // UDP协议
}
else if (port == 502)
{
ParseModbusReceiveAndUpdate(ipAddress, rawData); // Modbus协议
}
}
public void AddSendMessage(string ipAddress, int port, string rawData, string stationId = null)
{
// ... 添加报文记录 ...
// 根据端口判断协议类型
if (port == 40001)
{
ParseSendDataAndUpdateStation(ipAddress, rawData); // UDP协议
}
else if (port == 502)
{
ParseModbusSendAndUpdate(ipAddress, rawData); // Modbus协议
}
}
```
## 技术特点
**实时性**: UDP报文接收后立即解析更新
**自动化**: 无需手动刷新,数据自动同步
**分离解析**: 发送和接收报文分开解析,数据更准确
**合并更新**: 自动合并发送和接收数据到充电桩管理界面
**可扩展**: 支持自定义报文格式和解析规则
**兼容性**: 保留原有任务处理逻辑
**稳定性**: 异常处理完善,不影响系统运行
## 版本历史
- **v1.1** (2026-01-18): 发送和接收报文分开解析,合并更新到充电桩管理界面
- **v1.0** (2026-01-18): 初始版本,支持UDP报文自动解析和更新