You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

305 lines
8.4 KiB

This file contains ambiguous Unicode characters!

This file contains ambiguous Unicode characters that may be confused with others in your current locale. If your use case is intentional and legitimate, you can safely ignore this warning. Use the Escape button to highlight these characters.

package Adl200Impl
import (
"fmt"
"tgk-touch/internal/global"
"tgk-touch/internal/library/ADL200"
"time"
)
// ===== 时间读取 =====
// ReadYear 读取电表年份
func (a *Adl200Impl) ReadYear(commUid string, addr byte) (int, error) {
read, err := ADL200.H0012.Read(commUid, addr)
if err != nil {
return 0, err
}
value := read[0]
// 高字节=年 (如 0x07 表示 2007)
year := int(byte(value >> 8))
return year, nil
}
// ReadMonth 读取电表月份
func (a *Adl200Impl) ReadMonth(commUid string, addr byte) (int, error) {
read, err := ADL200.H0012.Read(commUid, addr)
if err != nil {
return 0, err
}
value := read[0]
// 低字节=月
month := int(byte(value))
return month, nil
}
// ReadDay 读取电表日期
func (a *Adl200Impl) ReadDay(commUid string, addr byte) (int, error) {
read, err := ADL200.H0013.Read(commUid, addr)
if err != nil {
return 0, err
}
value := read[0]
// 低字节=日
day := int(byte(value))
return day, nil
}
// ReadHour 读取电表小时
func (a *Adl200Impl) ReadHour(commUid string, addr byte) (int, error) {
read, err := ADL200.H0013.Read(commUid, addr)
if err != nil {
return 0, err
}
value := read[0]
// 高字节=时
hour := int(byte(value >> 8))
return hour, nil
}
// ReadMinute 读取电表分钟
func (a *Adl200Impl) ReadMinute(commUid string, addr byte) (int, error) {
read, err := ADL200.H0014.Read(commUid, addr)
if err != nil {
return 0, err
}
value := read[0]
// 低字节=分
minute := int(byte(value))
return minute, nil
}
// ReadSecond 读取电表秒数
func (a *Adl200Impl) ReadSecond(commUid string, addr byte) (int, error) {
read, err := ADL200.H0014.Read(commUid, addr)
if err != nil {
return 0, err
}
value := read[0]
// 高字节=秒
second := int(byte(value >> 8))
return second, nil
}
// ReadTime 读取电表完整时间
func (a *Adl200Impl) ReadTime(commUid string, addr byte) (time.Time, error) {
// 读取各个时间组件
year, err := a.ReadYear(commUid, addr)
if err != nil {
return time.Time{}, fmt.Errorf("读取年份失败: %v", err)
}
month, err := a.ReadMonth(commUid, addr)
if err != nil {
return time.Time{}, fmt.Errorf("读取月份失败: %v", err)
}
day, err := a.ReadDay(commUid, addr)
if err != nil {
return time.Time{}, fmt.Errorf("读取日期失败: %v", err)
}
hour, err := a.ReadHour(commUid, addr)
if err != nil {
return time.Time{}, fmt.Errorf("读取小时失败: %v", err)
}
minute, err := a.ReadMinute(commUid, addr)
if err != nil {
return time.Time{}, fmt.Errorf("读取分钟失败: %v", err)
}
second, err := a.ReadSecond(commUid, addr)
if err != nil {
return time.Time{}, fmt.Errorf("读取秒数失败: %v", err)
}
// 构建时间对象 (年份为 2 位数字,加 2000)
loc, _ := time.LoadLocation("Local")
t := time.Date(
year+2000,
time.Month(month),
day,
hour,
minute,
second,
0,
loc,
)
return t, nil
}
// ===== 电气参数读取 =====
// ReadVoltage 读取电压 (单相电表只有单相电压)
func (a *Adl200Impl) ReadVoltage(commUid string, addr byte) (totalVoltage, aVoltage, bVoltage, cVoltage float64, err error) {
read, err := ADL200.H000B.Read(commUid, addr)
if err != nil {
return
}
// 单位: 0.1V
aVoltage = float64(read[0]) * 0.1
// ADL200 是单相电表,总电压即为 A 相电压
totalVoltage = aVoltage
return totalVoltage, aVoltage, bVoltage, cVoltage, err
}
// ReadElectricCurrent 读取电流 (单相电表只有单相电流)
func (a *Adl200Impl) ReadElectricCurrent(commUid string, addr byte) (totalElectricCurrent, aElectricCurrent, bElectricCurrent, cElectricCurrent float64, err error) {
read, err := ADL200.H000C.Read(commUid, addr)
if err != nil {
return
}
// 单位: 0.01A
aElectricCurrent = float64(read[0]) * 0.01
totalElectricCurrent = aElectricCurrent
return totalElectricCurrent, aElectricCurrent, bElectricCurrent, cElectricCurrent, err
}
// ReadPower 读取功率 (单相电表只有总有功功率)
func (a *Adl200Impl) ReadPower(commUid string, addr byte) (totalPower, aPower, bPower, cPower float64, err error) {
read, err := ADL200.H000D.Read(commUid, addr)
if err != nil {
return
}
// 单位: 0.001kW
totalPower = float64(read[0]) * 0.001
aPower = totalPower
return totalPower, aPower, bPower, cPower, err
}
// ReadTotalPower 读取总有功功率
func (a *Adl200Impl) ReadTotalPower(commUid string, addr byte) (totalPower float64, err error) {
read, err := ADL200.H000D.Read(commUid, addr)
if err != nil {
return 0, err
}
// 单位: 0.001kW
totalPower = float64(read[0]) * 0.001
return totalPower, err
}
// ReadEnergy 读取电能 (4 字节数据,需要两个寄存器)
func (a *Adl200Impl) ReadEnergy(commUid string, addr byte) (totalEnergy, aEnergy, bEnergy, cEnergy float64, err error) {
read, err := ADL200.H0068.Read(commUid, addr)
if err != nil {
return
}
// 高16位在前低16位在后 (大端序)
high := uint32(read[0]) // 高16位
low := uint32(read[1]) // 低16位
value := (high << 16) | low // 组合为32位整数
// 单位: 0.01kWh
totalEnergy = float64(value) * 0.01
aEnergy = totalEnergy // 单相电表A相电能即为总电能
return totalEnergy, aEnergy, bEnergy, cEnergy, err
}
// ReadPowerFactor 读取功率因数 (单相电表)
func (a *Adl200Impl) ReadPowerFactor(commUid string, addr byte) (totalPf, aPf, bPf, cPf float64, err error) {
read, err := ADL200.H0010.Read(commUid, addr)
if err != nil {
return
}
// 单位: 0.001
aPf = float64(read[0]) * 0.001
totalPf = aPf
return totalPf, aPf, bPf, cPf, err
}
// ===== 其他读取 =====
// ReadMsgAddr 读取通信地址
func (a *Adl200Impl) ReadMsgAddr(commUid string, addr byte) (msgAddr byte, err error) {
read, err := ADL200.H0015.Read(commUid, addr)
if err != nil {
return 0, err
}
value := read[0]
// 高8位=通信地址 (0~254)
msgAddr = byte(value >> 8)
g.Log().Infof("ADL200 ReadMsgAddr raw: 0x%X, msgAddr: 0x%X (%d)", value, msgAddr, msgAddr)
return msgAddr, nil
}
// ReadMainAddr 读取主控地址 (DL/T645 表号,暂不支持)
func (a *Adl200Impl) ReadMainAddr(commUid string, addr byte) (byte, error) {
// ADL200 使用表号代替主控地址,此处返回通信地址作为占位
return a.ReadMsgAddr(commUid, addr)
}
// ReadDailyFreezingTime 读取日冻结时间 (ADL200 不支持日冻结,返回默认)
func (a *Adl200Impl) ReadDailyFreezingTime(commUid string, addr byte) (dailyFreezingTime string, err error) {
// ADL200 单相电表不支持日冻结时间设置
return "00:00", nil
}
// ReadMonthlyFreezingTime 读取月冻结时间 (ADL200 不支持月冻结,返回默认)
func (a *Adl200Impl) ReadMonthlyFreezingTime(commUid string, addr byte) (day, hour string, err error) {
// ADL200 单相电表不支持月冻结时间设置
return "01", "00", nil
}
// ===== 额外的数据读取方法 =====
// ReadFrequency 读取电网频率
func (a *Adl200Impl) ReadFrequency(commUid string, addr byte) (frequency float64, err error) {
read, err := ADL200.H0011.Read(commUid, addr)
if err != nil {
return 0, err
}
// 单位: 0.01Hz
frequency = float64(read[0]) * 0.01
return frequency, nil
}
// ReadReactivePower 读取无功功率
func (a *Adl200Impl) ReadReactivePower(commUid string, addr byte) (reactivePower float64, err error) {
read, err := ADL200.H000E.Read(commUid, addr)
if err != nil {
return 0, err
}
// 单位: 0.001kvar
reactivePower = float64(read[0]) * 0.001
return reactivePower, nil
}
// ReadApparentPower 读取视在功率
func (a *Adl200Impl) ReadApparentPower(commUid string, addr byte) (apparentPower float64, err error) {
read, err := ADL200.H000F.Read(commUid, addr)
if err != nil {
return 0, err
}
// 单位: 0.001kVA
apparentPower = float64(read[0]) * 0.001
return apparentPower, nil
}
// ReadCombinedEnergy 读取组合有功总电能
func (a *Adl200Impl) ReadCombinedEnergy(commUid string, addr byte) (energy float64, err error) {
read, err := ADL200.H0000.Read(commUid, addr)
if err != nil {
return 0, err
}
high := uint32(read[0])
low := uint32(read[1])
value := (high << 16) | low
// 单位: 0.01kWh
energy = float64(value) * 0.01
return energy, nil
}
// ReadReactiveEnergy 读取总无功电能
func (a *Adl200Impl) ReadReactiveEnergy(commUid string, addr byte) (energy float64, err error) {
read, err := ADL200.H00B0.Read(commUid, addr)
if err != nil {
return 0, err
}
high := uint32(read[0])
low := uint32(read[1])
value := (high << 16) | low
// 单位: 0.01kVarh
energy = float64(value) * 0.01
return energy, nil
}