@jiabaida/tools 1.0.0 → 1.0.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (57) hide show
  1. package/dist/cjs/core/BleApiManager.js +1 -1
  2. package/dist/cjs/core/BleCmdAnalysis/BaseParamProtocol.js +1 -0
  3. package/dist/cjs/core/BleCmdAnalysis/BleCmdAnalysis.js +1 -0
  4. package/dist/cjs/core/BleCmdAnalysis/BleCmdDD.js +1 -0
  5. package/dist/cjs/core/BleCmdAnalysis/BleCmdFFAA.js +1 -0
  6. package/dist/cjs/core/BleCmdAnalysis/BleCmdHVES.js +1 -0
  7. package/dist/cjs/core/BleCmdAnalysis/ESHostProtocol.js +1 -0
  8. package/dist/cjs/core/BleCmdAnalysis/readAndSetParam.js +1 -0
  9. package/dist/cjs/core/BleCmdAnalysis.js +1 -0
  10. package/dist/cjs/core/BleDataProcess.js +1 -0
  11. package/dist/cjs/core/OtaUpgrade.js +1 -0
  12. package/dist/cjs/core/TelinkApi.js +1 -0
  13. package/dist/cjs/core/Transfer.js +1 -0
  14. package/dist/cjs/core/commonfun.js +1 -1
  15. package/dist/cjs/core/dataJson/baseParamsJson.js +1 -0
  16. package/dist/cjs/core/keyAndPwdManager.js +1 -0
  17. package/dist/cjs/index.js +1 -1
  18. package/dist/esm/core/BleApiManager.js +1 -1
  19. package/dist/esm/core/BleCmdAnalysis/BaseParamProtocol.js +1 -0
  20. package/dist/esm/core/BleCmdAnalysis/BleCmdAnalysis.js +1 -0
  21. package/dist/esm/core/BleCmdAnalysis/BleCmdDD.js +1 -0
  22. package/dist/esm/core/BleCmdAnalysis/BleCmdFFAA.js +1 -0
  23. package/dist/esm/core/BleCmdAnalysis/BleCmdHVES.js +1 -0
  24. package/dist/esm/core/BleCmdAnalysis/ESHostProtocol.js +1 -0
  25. package/dist/esm/core/BleCmdAnalysis/readAndSetParam.js +1 -0
  26. package/dist/esm/core/BleCmdAnalysis.js +1 -0
  27. package/dist/esm/core/BleDataProcess.js +1 -0
  28. package/dist/esm/core/OtaUpgrade.js +1 -0
  29. package/dist/esm/core/TelinkApi.js +1 -0
  30. package/dist/esm/core/Transfer.js +1 -0
  31. package/dist/esm/core/commonfun.js +1 -1
  32. package/dist/esm/core/dataJson/baseParamsJson.js +1 -0
  33. package/dist/esm/core/keyAndPwdManager.js +1 -0
  34. package/dist/esm/index.js +1 -1
  35. package/package.json +13 -3
  36. package/src/core/BleApiManager.js +487 -0
  37. package/src/core/BleCmdAnalysis/BaseParamProtocol.js +651 -0
  38. package/src/core/BleCmdAnalysis/BleCmdAnalysis.js +222 -0
  39. package/src/core/BleCmdAnalysis/BleCmdDD.js +1214 -0
  40. package/src/core/BleCmdAnalysis/BleCmdDDA4.js +762 -0
  41. package/src/core/BleCmdAnalysis/BleCmdFFAA.js +407 -0
  42. package/src/core/BleCmdAnalysis/BleCmdHVES.js +1222 -0
  43. package/src/core/BleCmdAnalysis/ESHostProtocol.js +829 -0
  44. package/src/core/BleCmdAnalysis/index.js +7 -0
  45. package/src/core/BleCmdAnalysis/readAndSetParam.js +288 -0
  46. package/src/core/BleDataProcess.js +355 -0
  47. package/src/core/OtaUpgrade.js +338 -0
  48. package/src/core/TelinkApi.js +73 -0
  49. package/src/core/Transfer.js +516 -0
  50. package/src/core/array.js +10 -0
  51. package/src/core/commonfun.js +87 -0
  52. package/src/core/dataJson/baseParamsJson.js +754 -0
  53. package/src/core/dataJson/index.js +1 -0
  54. package/src/core/keyAndPwdManager.js +346 -0
  55. package/src/core/mqttServer.js +296 -0
  56. package/src/core/rsaEncrypt.js +45 -0
  57. package/src/index.js +11 -0
@@ -0,0 +1,829 @@
1
+ import {hexStringToBinary, decimalToHex} from '../BleDataProcess';
2
+ function format(value, n, offset, scope) {
3
+ const v = parseInt(value.join(''), 16) * n + offset;
4
+ if (scope == undefined) return v;
5
+ return v.toFixed(scope);
6
+ }
7
+
8
+ function socFormat(value, n, offset, scope) {
9
+ const v = parseInt(value.join(''), 16) * n + offset;
10
+ return Math.floor(v);
11
+ }
12
+ function kelvinToCelsius(value) {
13
+ return (value - 273.1).toFixed(2);
14
+ }
15
+
16
+ function formatBools(value, n, offset, scope, len) {
17
+ const hexs = value.join('');
18
+ const binary = hexStringToBinary(hexs).split('');
19
+ // 倒叙取值
20
+ binary.reverse();
21
+ const arr = new Array(Math.max(len, binary.length));
22
+ for (let i = 0; i < arr.length; i++) {
23
+ arr[i] = binary[i] == '1' || binary[i] == 1;
24
+ }
25
+ return arr;
26
+ }
27
+
28
+ function hexToAscii(hexString) {
29
+ let asciiString = '';
30
+ for (let i = 0; i < hexString.length; i += 2) {
31
+ const hexPair = hexString.substr(i, 2);
32
+ const decimalValue = parseInt(hexPair, 16);
33
+ asciiString += String.fromCharCode(decimalValue);
34
+ }
35
+ const result = asciiString.replace(/\u0000/g, '');
36
+
37
+ return result;
38
+ }
39
+ function formatP_N(value, n, offset, scope = 2) {
40
+ const el = ['0x', ...value].join('') * 1;
41
+ let negative = (el & 0x8000) !== 0;
42
+ const v = negative ? el - 0x10000 : el;
43
+ return (v * n + offset).toFixed(scope);
44
+ }
45
+ export class HostProtocol {
46
+ readValue;
47
+ receiveLength;
48
+
49
+ constructor() {
50
+ this.readValue = [];
51
+ this.receiveLength = null;
52
+ }
53
+ /**01 50 00 00 00 FF 00 00 => 01 50 00 00 00 FF 00 00 E1 F2
54
+ *
55
+ * @param {*} values
56
+ * @returns
57
+ */
58
+ // console.log(HostProtocol.generateCheck([0x01, 0x50, 0x00, 0x00, 0x00, 0xFF, 0x00, 0x00]), 'E1 F2');
59
+ getBuffer(values) {
60
+ const checks = this.generateCheck(values); // ['0xE1','0xF2']
61
+ const arr = [...values, ...checks];
62
+ if (arr[1] == '0x79') {
63
+ console.log('======下发指令======', arr.join('').replace(/0x/g, ''), arr);
64
+ }
65
+ const buffer = new ArrayBuffer(arr.length);
66
+ const dataView = new DataView(buffer);
67
+ arr.forEach((v, i) => dataView.setUint8(i, v.toString()));
68
+ return buffer;
69
+ }
70
+ /**e.g [0x01, 0x78, 0x10, 0x00, 0x10, 0xA0, 0x00, 0x00] => [0x7F, 0xB2]
71
+ *
72
+ * @param data 地址码 + 功能码 + 起始地址 + 结束地址 + 数据长度
73
+ * @returns 低/高位校验码
74
+ *
75
+ */
76
+ generateCheck(data) {
77
+ const hex = this.crc16modbus(data);
78
+ const hexStr = decimalToHex(hex, 4);
79
+ return [`0x${hexStr.slice(0, 2)}`, `0x${hexStr.slice(2, 4)}`];
80
+ }
81
+ generateCheck2(dataHexString) {
82
+ const dataBytes = [];
83
+ for (let i = 0; i < dataHexString.length; i += 2) {
84
+ dataBytes.push(parseInt(dataHexString.substr(i, 2), 16));
85
+ }
86
+ let crc = 0xffff;
87
+ const polynomial = 0xa001;
88
+ for (const byte of dataBytes) {
89
+ crc ^= byte;
90
+ for (let i = 0; i < 8; i++) {
91
+ if (crc & 0x0001) {
92
+ crc = ((crc >> 1) ^ polynomial) & 0xffff;
93
+ } else {
94
+ crc >>= 1;
95
+ }
96
+ }
97
+ }
98
+ const res = crc.toString(16).toUpperCase();
99
+ return [res.slice(-2), res.slice(-4, -2)];
100
+ }
101
+ crc16modbus(data) {
102
+ let crc = 0xffff;
103
+ for (let i = 0; i < data.length; i++) {
104
+ crc ^= data[i];
105
+ for (let j = 0; j < 8; j++) {
106
+ if (crc & 0x0001) {
107
+ crc = (crc >> 1) ^ 0xa001;
108
+ } else {
109
+ crc = crc >> 1;
110
+ }
111
+ }
112
+ }
113
+ // The result needs to be swapped
114
+ crc = ((crc & 0xff) << 8) | ((crc >> 8) & 0xff);
115
+ return crc & 0xffff;
116
+ }
117
+
118
+ resolveResponse(value, callback) {
119
+ const intArr = Array.prototype.map.call(new Uint8Array(value), (x) => ('00' + x.toString(16)).slice(-2));
120
+
121
+ if (intArr.length > 0) {
122
+ if (this.receiveLength == null) {
123
+ const intArr = Array.prototype.map.call(new Uint8Array(value), (x) => x);
124
+ this.receiveLength = intArr[7] + 10;
125
+ }
126
+ this.readValue = this.readValue.concat(intArr);
127
+ if (this.readValue.length == this.receiveLength) {
128
+ callback([...this.readValue]);
129
+ this.readValue = [];
130
+ this.receiveLength = null;
131
+ }
132
+ } else {
133
+ this.readValue = [];
134
+ this.receiveLength = null;
135
+ }
136
+ }
137
+ // #region 解析pack综合数据
138
+ /**
139
+ * 解析pack综合数据
140
+ * @param {Array} values 回复的指令数组
141
+ * @returns
142
+ */
143
+ // 综合数据(0x01 0x50)
144
+ getHostData(values) {
145
+ if (values[0] != 0x01 || values[1] != 0x50) return null;
146
+ const d_0x01_0x50 = ['01', '50', '00', '00', '00', 'FF', /**数据长度*/ '00', '2E', /*数据内容 46+10=56*/ '14', '64', '00', '00', '00', '30', '00', '64', '0B', 'E7', '0C', 'DB', '0B', 'E0', '0B', 'DB', '0B', 'D9', '00', '03', '02', 'D9', '05', 'DC', '00', '01', '00', '02', '00', '00', '00', '00', '00', '00', '02', '09', '02', '04', '02', '01', '02', '02', '00', '00', '00', '00', /*check*/ 'DD', '32'];
147
+ const data = values.slice(8, values.length - 2).map((x) => ('00' + x.toString(16)).toUpperCase().slice(-2));
148
+
149
+ // 汇总电压-V
150
+ const summarizedVoltage = format([data[0], data[1]], 0.01, 0, 2);
151
+ // 汇总电流-A
152
+ const summarizedElectricity = formatP_N([data[2], data[3]], 0.1, 0, 2);
153
+ // SOC-%
154
+ const soc = socFormat([data[4], data[5]], 1, 0, 0);
155
+ // SOH
156
+ const soh = format([data[6], data[7]], 1, 0, 0);
157
+ // 环境温度 ℃
158
+ const envTemperature = kelvinToCelsius(format([data[8], data[9]], 0.1, 0, 2));
159
+ // 最高单体电压-mV-V
160
+ const maxVoltage = format([data[10], data[11]], 0.001, 0, 3);
161
+ // 最低单体电压-mV-V
162
+ const minVoltage = format([data[12], data[13]], 0.001, 0, 3);
163
+ // 最高温度
164
+ const maxTemperature = kelvinToCelsius(format([data[14], data[15]], 0.1, 0, 2));
165
+ // 最低温度
166
+ const minTemperature = kelvinToCelsius(format([data[16], data[17]], 0.1, 0, 2));
167
+ // MOS状态
168
+ const [dischangeMos, changeMos, dischangeState, changeState] = formatBools([data[18], data[19]], 1, 0, undefined, 4);
169
+ // 剩余容量-AH
170
+ const restCapacity = format([data[20], data[21]], 0.1, 0, 2);
171
+ // 满充容量-AH
172
+ const fullCapacity = format([data[22], data[23]], 0.1, 0, 2);
173
+ // 并机个数
174
+ const PACK_DATA_paralleNum = [data[24], data[25]].join('');
175
+ const PACK_DATA_paralleState = [data[26], data[27]].join('');
176
+ const paralleNum = format([data[24], data[25]], 1, 0, 0);
177
+ // 并机状态
178
+ const paralleState = formatBools([data[26], data[27]], 1, 0, undefined, paralleNum);
179
+
180
+ // console.warn('===并机个数====', PACK_DATA_paralleNum, paralleNum);
181
+ // console.warn('===并机状态====', PACK_DATA_paralleState, paralleState);
182
+
183
+ // 循环次数
184
+ const cycleNum = format([data[28], data[29]], 1, 0, 0);
185
+ // 保护状态
186
+ const protectionInfo = formatBools([data[30], data[31], data[32], data[33]], 1, 0, undefined, 28);
187
+ // 最高单体序号
188
+ const maxMonomerNum = format([data[35]], 1, 0);
189
+ // 最低单体序号
190
+ const minMonomerNum = format([data[37]], 1, 0);
191
+ // 最高温度序号
192
+ const maxTemperatureNum = format([data[39]], 1, 0);
193
+ // 最低温度序号
194
+ const minTemperatureNum = format([data[41]], 1, 0);
195
+ // CAN协议
196
+ const can = format([data[42], data[43]], 1, 0);
197
+ // RS485协议
198
+ const rs485 = format([data[44], data[45]], 1, 0);
199
+
200
+ return { summarizedVoltage, summarizedElectricity, soc, soh, envTemperature, maxVoltage, minVoltage, maxTemperature, minTemperature, dischangeMos, changeMos, dischangeState, changeState, restCapacity, fullCapacity, paralleNum, paralleState, cycleNum, protectionInfo, maxMonomerNum, minMonomerNum, maxTemperatureNum, minTemperatureNum, can, rs485, PACK_DATA_paralleNum, PACK_DATA_paralleState };
201
+ }
202
+ // #region 解析pack基本信息
203
+ /**
204
+ * 解析pack基本信息
205
+ * @param {Array} values 回复的指令数组
206
+ * @returns {Object} 参数
207
+ */
208
+ // 基本信息(0xXX 0x78 10 00 10 A0 00 00 ...)
209
+ getBaseInfo(values) {
210
+ if (values[1] != 0x78 || values[2] != 0x10) return null;
211
+ const d_0x02_0x78 = ['02', '78', '10', '00', '10', 'A0', /**/ '00', '96', /**/ '14', '57', '14', '57', '00', '04', '93', 'E0', '12', 'C0', '1C', '20', '3A', '98', '3A', '98', '03', '29', '03', '34', '00', '00', '00', '64', '00', '00', '00', '00', '00', '00', '00', '00', '00', '00', '00', '00', '00', '00', '00', '09', '0C', 'DA', '00', '04', '0B', '9C', '0C', 'B6', '00', '01', '03', '25', '00', '02', '03', '23', '03', '24', '02', '40', '02', 'EE', '01', 'A4', '05', 'DC', '00', '10', '0C', 'D9', '0C', 'D6', '0C', 'D8', '0B', '9C', '0C', 'D8', '0C', 'D8', '0C', 'D8', '0C', 'D8', '0C', 'DA', '0C', 'D9', '0C', 'D8', '0C', 'DA', '0C', 'DA', '0B', 'FB', '0C', 'D9', '0C', 'D4', '00', '04', '03', '25', '03', '23', '03', '24', '03', '24', '00', '00', '00', '00', '00', '01', '4A', '42', '44', '34', '38', '31', '35', '30', '30', '30', '31', '00', '00', '00', '00', '00', '00', '00', '00', '00', '00', '00', '00', '00', '00', '00', '00', '00', '00', '00', '00', '01', '00', '02', /**/ '87', 'CC'];
212
+ const data = values.slice(8, values.length - 2).map((x) => ('00' + x.toString(16)).toUpperCase().slice(-2));
213
+
214
+ // 总电压-V
215
+ const summarizedVoltage = format([data[0], data[1]], 0.01, 0, 2);
216
+ // 总电流-A
217
+ const summarizedElectricity = format([data[4], data[5], data[6], data[7]], 0.01, -3000, 2);
218
+ // SOC-%
219
+ const soc = socFormat([data[8], data[9]], 0.01, 0, 0);
220
+ // 剩余容量-Ah
221
+ const restCapacity = format([data[10], data[11]], 0.01, 0, 2);
222
+ // 满充容量-Ah
223
+ const fullCapacity = format([data[12], data[13]], 0.01, 0, 2);
224
+ // 标称容量-Ah
225
+ const nominalCapacity = format([data[14], data[15]], 0.01, 0, 2);
226
+ // MOS温度
227
+ const mosTemperature = format([data[16], data[17]], 0.1, -50, 2);
228
+ // 环境温度
229
+ const envTemperature = format([data[18], data[19]], 0.1, -50, 2);
230
+ // 充放电状态
231
+ const state = format([data[20], data[21]], 1, 0);
232
+ // SOH
233
+ const soh = format([data[22], data[23]], 1, 0);
234
+ // 保护信息
235
+ const protectionInfo = formatBools([data[24], data[25], data[26], data[27]], 1, 0, undefined, 28);
236
+ // 告警信息
237
+ const warningInfo = formatBools([data[28], data[29], data[30], data[31]], 1, 0, undefined, 19);
238
+ // MOS状态
239
+ const [dischangeMos, changeMos, preChangeState, hotState, fanState, dryContact1, dryContact2, limitedModule] = formatBools([data[32], data[33]], 1, 0, undefined, 8);
240
+ // 循环次数
241
+ const cycleNum = format([data[36], data[37]], 1, 0, 0);
242
+ // 最高单体序号
243
+ const maxMonomerNum = format([data[38], data[39]], 1, 0);
244
+ // 最高单体电压-mV-V
245
+ const maxVoltage = format([data[40], data[41]], 0.001, 0, 3);
246
+ // 最低单体序号
247
+ const minMonomerNum = format([data[42], data[43]], 1, 0);
248
+ // 最低单体电压-mV-V
249
+ const minVoltage = format([data[44], data[45]], 0.001, 0, 3);
250
+ // 最高温度序号
251
+ const maxTemperatureNum = format([data[48], data[49]], 1, 0);
252
+ // 最高温度
253
+ const maxTemperature = format([data[50], data[51]], 0.1, -50, 2);
254
+ // 最低温度序号
255
+ const minTemperatureNum = format([data[52], data[53]], 1, 0);
256
+ // 最低温度
257
+ const minTemperature = format([data[54], data[55]], 0.1, -50, 2);
258
+ // 单体个数
259
+ const cellNum = format([data[66], data[67]], 1, 0);
260
+ // 电池单体电压-mV-V
261
+ const cellVoltages = [...Array(cellNum)].map((_, i) => format([data[68 + i * 2], data[69 + i * 2]], 0.001, 0, 3));
262
+ // 温度个数
263
+ const n = 68 + 2 * cellNum;
264
+ const temperatureNum = format([data[n], data[n + 1]], 1, 0);
265
+ // 电池单体温度
266
+ const m = n + 2;
267
+ const temperatures = [...Array(temperatureNum)].map((_, i) => format([data[m + i * 2], data[m + 1 + i * 2]], 0.1, -50, 2));
268
+ // 均衡状态
269
+ const q = m + 2 * temperatureNum;
270
+ const cellEquilibriumInfo = formatBools([data[q], data[q + 1], data[q + 2], data[q + 3]], 1, 0, undefined, cellNum);
271
+
272
+ return { summarizedVoltage, summarizedElectricity, soc, restCapacity, fullCapacity, nominalCapacity, mosTemperature, envTemperature, state, soh, protectionInfo, warningInfo, dischangeMos, changeMos, preChangeState, hotState, fanState, dryContact1, dryContact2, limitedModule, cycleNum, maxMonomerNum, maxVoltage, minMonomerNum, minVoltage, maxTemperatureNum, maxTemperature, minTemperatureNum, minTemperature, cellNum, cellVoltages, temperatureNum, temperatures, cellEquilibriumInfo };
273
+ }
274
+ // #region 解析pack告警与保护参数
275
+ /**
276
+ * 解析pack告警与保护参数
277
+ * @param {Array}values 回复的指令数组
278
+ * @returns
279
+ */
280
+ // 告警与保护参数(0xXX 0x78 18 00 19 00 00 00 ...)
281
+ getProtectionParams(values) {
282
+ if (values[1] != 0x78 || values[2] != 0x18) return null;
283
+ const d_0x02_0x78_0x1800 = `['01','78','18','00','19','A0',/**/'00','D0',/**/'0E','10','0D','48','0B','B8','0E','42','0D','48','0B','B8','0A','8C','0B','54','0B','B8','09','C4','0B','B8','0B','B8','16','80','15','40','0B','B8','16','D0','15','40','0B','B8','10','68','12','C0','03','E8','0F','A0','12','C0','0B','B8','06','40','05','78','07','D0','06','A4','07','D0','02','58','FF','FF','07','08','01','F4','02','58','06','40','05','78','07','D0','06','A4','07','D0','00','3C','00','03','07','08','00','C8','00','3C','04','1A','03','E8','0B','B8','04','7E','03','E8','0B','B8','02','26','02','58','0B','B8','01','F4','02','26','0B','B8','04','1A','03','E8','0B','B8','04','7E','03','E8','0B','B8','01','5E','01','90','0B','B8','01','2C','01','5E','0B','B8','05','AA','05','14','0B','B8','06','0E','05','46','0B','B8','04','4C','03','E8','0B','B8','04','7E','04','4C','0B','B8','04','7E','01','90','0B','B8','01','2C','01','5E','0B','B8','00','50','00','50','0B','B8','00','50','00','50','0B','B8','02','58','01','F4','07','D0','03','20','01','F4','07','D0','00','0A','00','0F','07','D0','00','03','00','05','07','D0',/**/ '31','9D']`;
284
+ const data = values.slice(8, values.length - 2).map((x) => ('00' + x.toString(16)).toUpperCase().slice(-2));
285
+
286
+ /* ********** 单体过压 ********** */
287
+ // 单体过压告警值-mV
288
+ const monomerOverVoltageWarning = format([data[0], data[1]], 1, 0, 0);
289
+ // 单体过压告警恢复值-mV
290
+ const monomerOverVoltageRecovery = format([data[2], data[3]], 1, 0, 0);
291
+ // 单体过压告警延迟-mS
292
+ const monomerOverVoltageDelay = format([data[4], data[5]], 1, 0, 0);
293
+ // 单体过压保护值-mV
294
+ const monomerOverVoltageProtection = format([data[6], data[7]], 1, 0, 0);
295
+ // 单体过压保护恢复值-mV
296
+ const monomerOverVoltageProtectionRecovery = format([data[8], data[9]], 1, 0, 0);
297
+ // 单体过压保护延时-mS
298
+ const monomerOverVoltageProtectionDelay = format([data[10], data[11]], 1, 0, 0);
299
+
300
+ /* ********** 单体欠压 ********** */
301
+ // 单体欠压告警值-mV
302
+ const monomerUnderVoltageWarning = format([data[12], data[13]], 1, 0, 0);
303
+ // 单体欠压告警恢复值-mV
304
+ const monomerUnderVoltageRecovery = format([data[14], data[15]], 1, 0, 0);
305
+ // 单体欠压告警延迟-mS
306
+ const monomerUnderVoltageDelay = format([data[16], data[17]], 1, 0, 0);
307
+ // 单体欠压保护值-mV
308
+ const monomerUnderVoltageProtection = format([data[18], data[19]], 1, 0, 0);
309
+ // 单体欠压保护恢复值-mV
310
+ const monomerUnderVoltageProtectionRecovery = format([data[20], data[21]], 1, 0, 0);
311
+ // 单体欠压保护延时-mS
312
+ const monomerUnderVoltageProtectionDelay = format([data[22], data[23]], 1, 0, 0);
313
+
314
+ /* ********** 总体过压********** */
315
+ // 总体过压告警值-V
316
+ const collectivityOverVoltageWarning = format([data[24], data[25]], 0.01, 0, 1);
317
+ // 总体过压告警恢复值-V
318
+ const collectivityOverVoltageRecovery = format([data[26], data[27]], 0.01, 0, 1);
319
+ // 总体过压告警延迟-mS
320
+ const collectivityOverVoltageDelay = format([data[28], data[29]], 1, 0, 0);
321
+ // 总体过压保护值-V
322
+ const collectivityOverVoltageProtection = format([data[30], data[31]], 0.01, 0, 1);
323
+ // 总体过压保护恢复值-V
324
+ const collectivityOverVoltageProtectionRecovery = format([data[32], data[33]], 0.01, 0, 1);
325
+ // 总体过压保护延时-mS
326
+ const collectivityOverVoltageProtectionDelay = format([data[34], data[35]], 1, 0, 0);
327
+
328
+ /* ********** 总体欠压 ********** */
329
+ // 总体欠压告警值-V
330
+ const collectivityUnderVoltageWarning = format([data[36], data[37]], 0.01, 0, 1);
331
+ // 总体欠压告警恢复值-V
332
+ const collectivityUnderVoltageRecovery = format([data[38], data[39]], 0.01, 0, 1);
333
+ // 总体欠压告警延迟-mS
334
+ const collectivityUnderVoltageDelay = format([data[40], data[41]], 1, 0, 0);
335
+ // 总体欠压保护值-V
336
+ const collectivityUnderVoltageProtection = format([data[42], data[43]], 0.01, 0, 1);
337
+ // 总体欠压保护恢复值-V
338
+ const collectivityUnderVoltageProtectionRecovery = format([data[44], data[45]], 0.01, 0, 1);
339
+ // 总体欠压保护延时-mS
340
+ const collectivityUnderVoltageProtectionDelay = format([data[46], data[47]], 1, 0, 0);
341
+
342
+ /* ********** 充电过流 ********** */
343
+ // 充电过流告警值-A
344
+ const chargeOverElectricityWarning = format([data[48], data[49]], 0.1, 0, 2);
345
+ // 充电过流告警恢复值-A
346
+ const chargeOverElectricityRecovery = format([data[50], data[51]], 0.1, 0, 2);
347
+ // 充电过流告警延迟-mS
348
+ const chargeOverElectricityDelay = format([data[52], data[53]], 1, 0, 2);
349
+ // 充电过流保护值-A
350
+ const chargeOverElectricityProtection = format([data[54], data[55]], 0.1, 0, 2);
351
+ // 充电过流保护延时-mS
352
+ const chargeOverElectricityProtectionDelay = format([data[56], data[57]], 1, 0, 0);
353
+ // 充电过流恢复延迟-S
354
+ const chargeOverElectricityRecoveryDelay = format([data[58], data[59]], 1, 0, 0);
355
+ // 充电过流锁定次数
356
+ const chargeOverElectricityLockNum = format([data[60], data[61]], 1, 0, 0);
357
+ // 充电过流2保护值-A
358
+ const chargeOverElectricity2Protection = format([data[62], data[63]], 0.1, 0, 2);
359
+ // 充电过流2保护延时-mS
360
+ const chargeOverElectricity2ProtectionDelay = format([data[64], data[65]], 1, 0, 0);
361
+ // 充电过流2恢复延迟-S
362
+ const chargeOverElectricity2RecoveryDelay = format([data[66], data[67]], 1, 0, 0);
363
+
364
+ /* ********** 放电过流 ********** */
365
+ // 放电过流告警值-A
366
+ const dischargeOverElectricityWarning = format([data[68], data[69]], 0.1, 0, 2);
367
+ // 放电过流告警恢复值-A
368
+ const dischargeOverElectricityRecovery = format([data[70], data[71]], 0.1, 0, 2);
369
+ // 放电过流告警延迟-mS
370
+ const dischargeOverElectricityDelay = format([data[72], data[73]], 1, 0, 0);
371
+ // 放电过流保护值-A
372
+ const dischargeOverElectricityProtection = format([data[74], data[75]], 0.1, 0, 2);
373
+ // 放电过流保护延时-mS
374
+ const dischargeOverElectricityProtectionDelay = format([data[76], data[77]], 1, 0, 0);
375
+ // 放电过流恢复延迟-S
376
+ const dischargeOverElectricityRecoveryDelay = format([data[78], data[79]], 1, 0, 0);
377
+ // 放电过流锁定次数
378
+ const dischargeOverElectricityLockNum = format([data[80], data[81]], 1, 0, 0);
379
+ // 放电过流2保护值-A
380
+ const dischargeOverElectricity2Protection = format([data[82], data[83]], 0.1, 0, 2);
381
+ // 放电过流2保护延时-mS
382
+ const dischargeOverElectricity2ProtectionDelay = format([data[84], data[85]], 1, 0, 0);
383
+ // 放电过流2恢复延迟-S
384
+ const dischargeOverElectricity2RecoveryDelay = format([data[86], data[87]], 1, 0, 0);
385
+
386
+ /* ********** 充电高温 ********** */
387
+ // 充电高温告警值-℃
388
+ const chargeHighTemperatureWarning = format([data[88], data[89]], 0.1, -50, 2);
389
+ // 充电高温告警恢复值-℃
390
+ const chargeHighTemperatureRecovery = format([data[90], data[91]], 0.1, -50, 2);
391
+ // 充电高温告警延迟-mS
392
+ const chargeHighTemperatureDelay = format([data[92], data[93]], 1, 0, 0);
393
+ // 充电高温保护值-℃
394
+ const chargeHighTemperatureProtection = format([data[94], data[95]], 0.1, -50, 2);
395
+ // 充电高温保护恢复值-℃
396
+ const chargeHighTemperatureProtectionRecovery = format([data[96], data[97]], 0.1, -50, 2);
397
+ // 充电高温保护延时-mS
398
+ const chargeHighTemperatureProtectionDelay = format([data[98], data[99]], 1, 0, 0);
399
+
400
+ /* ********** 充电低温 ********** */
401
+ // 充电低温告警值-℃
402
+ const chargeLowTemperatureWarning = format([data[100], data[101]], 0.1, -50, 2);
403
+ // 充电低温告警恢复值-℃
404
+ const chargeLowTemperatureRecovery = format([data[102], data[103]], 0.1, -50, 2);
405
+ // 充电低温告警延迟-mS
406
+ const chargeLowTemperatureDelay = format([data[104], data[105]], 1, 0, 0);
407
+ // 充电低温保护值-℃
408
+ const chargeLowTemperatureProtection = format([data[106], data[107]], 0.1, -50, 2);
409
+ // 充电低温保护恢复值-℃
410
+ const chargeLowTemperatureProtectionRecovery = format([data[108], data[109]], 0.1, -50, 2);
411
+ // 充电低温保护延时-mS
412
+ const chargeLowTemperatureProtectionDelay = format([data[110], data[111]], 1, 0, 0);
413
+
414
+ /* ********** 放电高温 ********** */
415
+ // 放电高温告警值-℃
416
+ const dischargeHighTemperatureWarning = format([data[112], data[113]], 0.1, -50, 2);
417
+ // 放电高温告警恢复值-℃
418
+ const dischargeHighTemperatureRecovery = format([data[114], data[115]], 0.1, -50, 2);
419
+ // 放电高温告警延迟-mS
420
+ const dischargeHighTemperatureDelay = format([data[116], data[117]], 1, 0, 0);
421
+ // 放电高温保护值-℃
422
+ const dischargeHighTemperatureProtection = format([data[118], data[119]], 0.1, -50, 2);
423
+ // 放电高温保护恢复值-℃
424
+ const dischargeHighTemperatureProtectionRecovery = format([data[120], data[121]], 0.1, -50, 2);
425
+ // 放电高温保护延时-mS
426
+ const dischargeHighTemperatureProtectionDelay = format([data[122], data[123]], 1, 0, 0);
427
+
428
+ /* ********** 放电低温 ********** */
429
+ // 放电低温告警值-℃
430
+ const dischargeLowTemperatureWarning = format([data[124], data[125]], 0.1, -50, 2);
431
+ // 放电低温告警恢复值-℃
432
+ const dischargeLowTemperatureRecovery = format([data[126], data[127]], 0.1, -50, 2);
433
+ // 放电低温告警延迟-mS
434
+ const dischargeLowTemperatureDelay = format([data[128], data[129]], 1, 0, 0);
435
+ // 放电低温保护值-℃
436
+ const dischargeLowTemperatureProtection = format([data[130], data[131]], 0.1, -50, 2);
437
+ // 放电低温保护恢复值-℃
438
+ const dischargeLowTemperatureProtectionRecovery = format([data[132], data[133]], 0.1, -50, 2);
439
+ // 放电低温保护延时-mS
440
+ const dischargeLowTemperatureProtectionDelay = format([data[134], data[135]], 1, 0, 0);
441
+
442
+ /* ********** MOS高温 ********** */
443
+ // MOS高温告警值-℃
444
+ const mosHighTemperatureWarning = format([data[136], data[137]], 0.1, -50, 2);
445
+ // MOS高温告警恢复值-℃
446
+ const mosHighTemperatureRecovery = format([data[138], data[139]], 0.1, -50, 2);
447
+ // MOS高温告警延迟-mS
448
+ const mosHighTemperatureDelay = format([data[140], data[141]], 1, 0, 0);
449
+ // MOS高温保护值-℃
450
+ const mosHighTemperatureProtection = format([data[142], data[143]], 0.1, -50, 2);
451
+ // MOS高温保护恢复值-℃
452
+ const mosHighTemperatureProtectionRecovery = format([data[144], data[145]], 0.1, -50, 2);
453
+ // MOS高温保护延时-mS
454
+ const mosHighTemperatureProtectionDelay = format([data[146], data[147]], 1, 0, 0);
455
+
456
+ /* ********** 环境高温 ********** */
457
+ const n = 148;
458
+ // 环境高温告警值-℃
459
+ const envHighTemperatureWarning = format([data[n], data[n + 1]], 0.1, -50, 2);
460
+ // 环境高温告警恢复值-℃
461
+ const envHighTemperatureRecovery = format([data[n + 2], data[n + 3]], 0.1, -50, 2);
462
+ // 环境高温告警延迟-mS
463
+ const envHighTemperatureDelay = format([data[n + 4], data[n + 5]], 1, 0, 0);
464
+ // 环境高温保护值-℃
465
+ const envHighTemperatureProtection = format([data[n + 6], data[n + 7]], 0.1, -50, 2);
466
+ // 环境高温保护恢复值-℃
467
+ const envHighTemperatureProtectionRecovery = format([data[n + 8], data[n + 9]], 0.1, -50, 2);
468
+ // 环境高温保护延时-mS
469
+ const envHighTemperatureProtectionDelay = format([data[n + 10], data[n + 11]], 1, 0, 0);
470
+
471
+ /* ********** 环境低温 ********** */
472
+ const m = 160;
473
+ // 环境低温告警值-℃
474
+ const envLowTemperatureWarning = format([data[m], data[m + 1]], 0.1, -50, 2);
475
+ // 环境低温告警恢复值-℃
476
+ const envLowTemperatureRecovery = format([data[m + 2], data[m + 3]], 0.1, -50, 2);
477
+ // 环境低温告警延迟-mS
478
+ const envLowTemperatureDelay = format([data[m + 4], data[m + 5]], 1, 0, 0);
479
+ // 环境低温保护值-℃
480
+ const envLowTemperatureProtection = format([data[m + 6], data[m + 7]], 0.1, -50, 2);
481
+ // 环境低温保护恢复值-℃
482
+ const envLowTemperatureProtectionRecovery = format([data[m + 8], data[m + 9]], 0.1, -50, 2);
483
+ // 环境低温保护延时-mS
484
+ const envLowTemperatureProtectionDelay = format([data[m + 10], data[m + 11]], 1, 0, 0);
485
+
486
+ /* ********** 温差过大 ********** */
487
+ const q = 172;
488
+ // 温差过大告警值-℃
489
+ const overTemperatureRangeWarning = format([data[q], data[q + 1]], 0.1, 0, 2);
490
+ // 温差过大告警恢复值-℃
491
+ const overTemperatureRangeRecovery = format([data[q + 2], data[q + 3]], 0.1, 0, 2);
492
+ // 温差过大告警延迟-mS
493
+ const overTemperatureRangeDelay = format([data[q + 4], data[q + 5]], 1, 0, 0);
494
+ // 温差过大保护值-℃
495
+ const overTemperatureRangeProtection = format([data[q + 6], data[q + 7]], 0.1, 0, 2);
496
+ // 温差过大保护恢复值-℃
497
+ const overTemperatureRangeProtectionRecovery = format([data[q + 8], data[q + 9]], 0.1, 0, 2);
498
+ // 温差过大保护延时-mS
499
+ const overTemperatureRangeProtectionDelay = format([data[q + 10], data[q + 11]], 1, 0, 0);
500
+
501
+ /* ********** 压差过大 ********** */
502
+ const o = 184;
503
+ // 压差过大告警值-mV
504
+ const overVoltageRangeWarning = format([data[o], data[o + 1]], 1, 0, 0);
505
+ // 压差过大告警恢复值-mV
506
+ const overVoltageRangeRecovery = format([data[o + 2], data[o + 3]], 1, 0, 0);
507
+ // 压差过大告警延迟-mS
508
+ const overVoltageRangeDelay = format([data[o + 4], data[o + 5]], 1, 0, 0);
509
+ // 压差过大保护值-mV
510
+ const overVoltageRangeProtection = format([data[o + 6], data[o + 7]], 1, 0, 0);
511
+ // 压差过大保护恢复值-mV
512
+ const overVoltageRangeProtectionRecovery = format([data[o + 8], data[o + 9]], 1, 0, 0);
513
+ // 压差过大保护延时-mS
514
+ const overVoltageRangeProtectionDelay = format([data[o + 10], data[o + 11]], 1, 0, 0);
515
+
516
+ /* ********** SOC过低 ********** */
517
+ const p = 196;
518
+ // SOC过低告警值-%
519
+ const underSOCRangeWarning = format([data[p], data[p + 1]], 1, 0);
520
+ // SOC过低告警恢复值-%
521
+ const underSOCRangeRecovery = format([data[p + 2], data[p + 3]], 1, 0);
522
+ // SOC过低告警延迟-mS
523
+ const underSOCRangeDelay = format([data[p + 4], data[p + 5]], 1, 0);
524
+ // SOC过低保护值-%
525
+ const underSOCRangeProtection = format([data[p + 6], data[p + 7]], 1, 0);
526
+ // SOC过低保护恢复值-%
527
+ const underSOCRangeProtectionRecovery = format([data[p + 8], data[p + 9]], 1, 0);
528
+ // SOC过低保护延时-mS
529
+ const underSOCRangeProtectionDelay = format([data[p + 10], data[p + 11]], 1, 0);
530
+
531
+ return {
532
+ monomerOverVoltageWarning,
533
+ monomerOverVoltageRecovery,
534
+ monomerOverVoltageDelay,
535
+ monomerOverVoltageProtection,
536
+ monomerOverVoltageProtectionRecovery,
537
+ monomerOverVoltageProtectionDelay,
538
+ monomerUnderVoltageWarning,
539
+ monomerUnderVoltageRecovery,
540
+ monomerUnderVoltageDelay,
541
+ monomerUnderVoltageProtection,
542
+ monomerUnderVoltageProtectionRecovery,
543
+ monomerUnderVoltageProtectionDelay,
544
+ collectivityOverVoltageWarning,
545
+ collectivityOverVoltageRecovery,
546
+ collectivityOverVoltageDelay,
547
+ collectivityOverVoltageProtection,
548
+ collectivityOverVoltageProtectionRecovery,
549
+ collectivityOverVoltageProtectionDelay,
550
+ collectivityUnderVoltageWarning,
551
+ collectivityUnderVoltageRecovery,
552
+ collectivityUnderVoltageDelay,
553
+ collectivityUnderVoltageProtection,
554
+ collectivityUnderVoltageProtectionRecovery,
555
+ collectivityUnderVoltageProtectionDelay,
556
+ chargeOverElectricityWarning,
557
+ chargeOverElectricityRecovery,
558
+ chargeOverElectricityDelay,
559
+ chargeOverElectricityProtection,
560
+ chargeOverElectricityProtectionDelay,
561
+ chargeOverElectricityRecoveryDelay,
562
+ chargeOverElectricityLockNum,
563
+ chargeOverElectricity2Protection,
564
+ chargeOverElectricity2ProtectionDelay,
565
+ chargeOverElectricity2RecoveryDelay,
566
+ dischargeOverElectricityWarning,
567
+ dischargeOverElectricityRecovery,
568
+ dischargeOverElectricityDelay,
569
+ dischargeOverElectricityProtection,
570
+ dischargeOverElectricityProtectionDelay,
571
+ dischargeOverElectricityRecoveryDelay,
572
+ dischargeOverElectricityLockNum,
573
+ dischargeOverElectricity2Protection,
574
+ dischargeOverElectricity2ProtectionDelay,
575
+ dischargeOverElectricity2RecoveryDelay,
576
+ chargeHighTemperatureWarning,
577
+ chargeHighTemperatureRecovery,
578
+ chargeHighTemperatureDelay,
579
+ chargeHighTemperatureProtection,
580
+ chargeHighTemperatureProtectionRecovery,
581
+ chargeHighTemperatureProtectionDelay,
582
+ chargeLowTemperatureWarning,
583
+ chargeLowTemperatureRecovery,
584
+ chargeLowTemperatureDelay,
585
+ chargeLowTemperatureProtection,
586
+ chargeLowTemperatureProtectionRecovery,
587
+ chargeLowTemperatureProtectionDelay,
588
+ dischargeHighTemperatureWarning,
589
+ dischargeHighTemperatureRecovery,
590
+ dischargeHighTemperatureDelay,
591
+ dischargeHighTemperatureProtection,
592
+ dischargeHighTemperatureProtectionRecovery,
593
+ dischargeHighTemperatureProtectionDelay,
594
+ dischargeLowTemperatureWarning,
595
+ dischargeLowTemperatureRecovery,
596
+ dischargeLowTemperatureDelay,
597
+ dischargeLowTemperatureProtection,
598
+ dischargeLowTemperatureProtectionRecovery,
599
+ dischargeLowTemperatureProtectionDelay,
600
+ mosHighTemperatureWarning,
601
+ mosHighTemperatureRecovery,
602
+ mosHighTemperatureDelay,
603
+ mosHighTemperatureProtection,
604
+ mosHighTemperatureProtectionRecovery,
605
+ mosHighTemperatureProtectionDelay,
606
+ envHighTemperatureWarning,
607
+ envHighTemperatureRecovery,
608
+ envHighTemperatureDelay,
609
+ envHighTemperatureProtection,
610
+ envHighTemperatureProtectionRecovery,
611
+ envHighTemperatureProtectionDelay,
612
+ envLowTemperatureWarning,
613
+ envLowTemperatureRecovery,
614
+ envLowTemperatureDelay,
615
+ envLowTemperatureProtection,
616
+ envLowTemperatureProtectionRecovery,
617
+ envLowTemperatureProtectionDelay,
618
+ overTemperatureRangeWarning,
619
+ overTemperatureRangeRecovery,
620
+ overTemperatureRangeDelay,
621
+ overTemperatureRangeProtection,
622
+ overTemperatureRangeProtectionRecovery,
623
+ overTemperatureRangeProtectionDelay,
624
+ overVoltageRangeWarning,
625
+ overVoltageRangeRecovery,
626
+ overVoltageRangeDelay,
627
+ overVoltageRangeProtection,
628
+ overVoltageRangeProtectionRecovery,
629
+ overVoltageRangeProtectionDelay,
630
+ underSOCRangeWarning,
631
+ underSOCRangeRecovery,
632
+ underSOCRangeDelay,
633
+ underSOCRangeProtection,
634
+ underSOCRangeProtectionRecovery,
635
+ underSOCRangeProtectionDelay,
636
+ };
637
+ }
638
+ // #region 解析储能pack基本参数
639
+ /**
640
+ * 解析pack基本参数
641
+ * @param {Array} values 数据
642
+ * @returns {Object} 参数
643
+ */
644
+ // 参数(0xXX 0x78 1C 00 1C 86 00 00 ...)
645
+ getParams(values) {
646
+ if (values[1] != 0x78 || values[2] != 0x1c) return null;
647
+ const d_0x02_0x78_0x1C00 = ['01', '78', '1C', '00', '1C', '86', /**/ '00', '86', /**/ '00', '00', '00', '00', '0D', '48', '00', '1E', '01', 'F4', '02', '58', '16', '30', '05', 'DC', '55', '50', '31', '36', '53', '30', '31', '35', '30', '30', '30', '31', '33', '30', '37', '32', '34', '30', '35', '30', '35', '30', '30', '38', '36', '31', '00', '00', '00', '00', '07', 'E8', '00', '06', '00', '01', '4A', '42', '44', '34', '38', '31', '35', '30', '30', '30', '31', '00', '00', '00', '00', '00', '00', '00', '00', '00', '00', '00', '00', '00', '00', '00', '00', '00', '00', '00', '07', 'E8', '00', '02', '00', '12', '4A', '42', '44', '00', '00', '00', '00', '00', '00', '00', '00', '00', '00', '00', '00', '00', '00', '00', '00', '00', '00', '00', '00', '00', '00', '00', '00', '00', '00', '00', '00', '01', '0B', 'B8', '0B', '40', '00', '00', '00', '00', '00', '00', '00', '00', '00', '0A', /**/ '9A', '6C'];
648
+ const data = values.slice(8, values.length - 2).map((x) => ('00' + x.toString(16)).toUpperCase().slice(-2));
649
+ let i = 0;
650
+ // 电池类型
651
+ const batteryType = format(data.slice(i, (i += 2)), 1, 0);
652
+ const batteryTypeName = batteryType == 0 ? '铁锂' : batteryType == 1 ? '三元' : '';
653
+ // 电池厂家
654
+ const batteryFactory = format(data.slice(i, (i += 2)), 1, 0);
655
+ // 均衡开启电压
656
+ const equilibriumOpenedVoltage = format(data.slice(i, (i += 2)), 1, 0);
657
+ // 均衡开启压差
658
+ const equilibriumOpenedVoltageDeviation = format(data.slice(i, (i += 2)), 1, 0);
659
+ // 加热开启温度-℃
660
+ const hotOpenedTemperature = format(data.slice(i, (i += 2)), 0.1, -50, 2);
661
+ // 加热关闭温度-℃
662
+ const hotClosedTemperature = format(data.slice(i, (i += 2)), 0.1, -50, 2);
663
+ // 满充校准电压-V
664
+ const fullyChargedCalibrationVoltage = format(data.slice(i, (i += 2)), 0.01, 0);
665
+ // 满充校准电流-mA
666
+ // FIXME:
667
+ const fullyChargedCalibrationElectricity = format(data.slice(i, (i += 2)), 1, 0);
668
+ // BMS条码
669
+ const bmsBarcode = hexToAscii(data.slice(i, (i += 30)).join(''));
670
+ // BMS生产日期
671
+ const bmsProductionDate_Year = format(data.slice(i, (i += 2)), 1, 0);
672
+ const bmsProductionDate_Month = format(data.slice(i, (i += 2)), 1, 0);
673
+ const bmsProductionDate_Day = format(data.slice(i, (i += 2)), 1, 0);
674
+ const bmsProductionDate = [bmsProductionDate_Year, bmsProductionDate_Month, bmsProductionDate_Day].join('-');
675
+ // SN码
676
+ const snBarcode = hexToAscii(data.slice(i, (i += 30)).join(''));
677
+
678
+ // PACK生产日期
679
+ const packProductionData_Year = format(data.slice(i, (i += 2)), 1, 0);
680
+ const packProductionData_Month = format(data.slice(i, (i += 2)), 1, 0);
681
+ const packProductionData_Day = format(data.slice(i, (i += 2)), 1, 0);
682
+ // 厂家代号
683
+ const factoryCode = hexToAscii(data.slice(i, (i += 30)).join(''));
684
+ // CAN协议
685
+ const can = format(data.slice(i, (i += 2)), 1, 0);
686
+ // 待机休眠电压-mV
687
+ const standbySleepVoltage = format(data.slice(i, (i += 2)), 1, 0);
688
+ // 待机休眠延时
689
+ const standbySleepDelay = format(data.slice(i, (i += 2)), 1, 0);
690
+ // 均衡模式
691
+ const equilibriumMode = format(data.slice(i, (i += 2)), 1, 0);
692
+ const equilibriumModeName = equilibriumMode == 0 ? '充电均衡' : batteryType == 1 ? '静态与充电均衡' : '';
693
+ // RS485协议
694
+ const rs485 = format(data.slice(i, (i += 2)), 1, 0);
695
+ // CAN特波特设置
696
+ const canTeport = format(data.slice(i, (i += 2)), 1, 0);
697
+ // RS485特波特设置
698
+ const rs385Teport = format(data.slice(i, (i += 2)), 1, 0);
699
+ // 待机休眠电流-A
700
+ const standbySleepElectricity = format(data.slice(i, (i += 2)), 0.1, 0);
701
+ return {
702
+ batteryType,
703
+ batteryTypeName,
704
+ batteryFactory,
705
+ equilibriumOpenedVoltage,
706
+ equilibriumOpenedVoltageDeviation,
707
+ hotOpenedTemperature,
708
+ hotClosedTemperature,
709
+ fullyChargedCalibrationVoltage,
710
+ fullyChargedCalibrationElectricity,
711
+ bmsBarcode,
712
+ bmsProductionDate_Year,
713
+ bmsProductionDate_Month,
714
+ bmsProductionDate_Day,
715
+ bmsProductionDate,
716
+ snBarcode,
717
+ packProductionData_Year,
718
+ packProductionData_Month,
719
+ packProductionData_Day,
720
+ factoryCode,
721
+ can,
722
+ standbySleepVoltage,
723
+ standbySleepDelay,
724
+ equilibriumMode,
725
+ equilibriumModeName,
726
+ rs485,
727
+ canTeport,
728
+ rs385Teport,
729
+ standbySleepElectricity,
730
+ };
731
+ }
732
+ // #region 解析pack校准参数
733
+ /**
734
+ * 解析pack校准参数
735
+ * @param {*} values
736
+ * @returns
737
+ */
738
+ // 校准信息(0xXX 0x78 20 00 20 36 00 00 ...)
739
+ getCalibrationInfo(values) {
740
+ if (values[1] != 0x78 || values[2] != 0x20) return null;
741
+ const d_0x02_0x78_0x2000 = ['01', '78', '20', '00', '20', '36', /**/ '00', '40', /**/ '3A', '98', '3A', '98', '14', '96', '0D', 'B9', '00', '64', '00', '00', '00', '96', '00', '50', '00', '00', '00', '00', '00', '00', '00', '12', '00', '14', '0C', '1C', '00', '14', '0C', '80', '00', '1E', '0D', '7A', '00', '50', '0D', 'DE', '00', '5A', '02', '40', '02', 'EE', '01', 'A4', '05', 'DC', '00', '10', '00', 'D2', '00', '04', '00', '04', '00', '04', '00', '00', '00', '00', /**/ 'A2', 'B5'];
742
+ const data = values.slice(8, values.length - 2).map((x) => ('00' + x.toString(16)).toUpperCase().slice(-2));
743
+ let i = 0;
744
+
745
+ // 标称容量-Ah
746
+ const nominalCapacity = format(data.slice(i, (i += 2)), 0.01, 0, 2);
747
+ // 满充容量-Ah
748
+ const fullCapacity = format(data.slice(i, (i += 2)), 0.01, 0, 2);
749
+ // 剩余容量-Ah
750
+ const restCapacity = format(data.slice(i, (i += 2)), 0.01, 0, 2);
751
+ // SOC-%
752
+ const soc = socFormat(data.slice(i, (i += 2)), 0.01, 0, 0);
753
+ // SOH
754
+ const soh = format(data.slice(i, (i += 2)), 1, 0, 0);
755
+ // 循环次数
756
+ const cycleNum = format(data.slice(i, (i += 2)), 1, 0, 0);
757
+ // 循环衰减系数-衰减1%循环次数
758
+ const cycleAttenuationFactor = format(data.slice(i, (i += 2)), 1, 0, 0);
759
+ // 循环系数-%
760
+ const cycleFactor = format(data.slice(i, (i += 2)), 1, 0);
761
+ // 累计充电-Ah
762
+ const cumulativeCharge = format(data.slice(i, (i += 4)), 0.1, 0);
763
+ // 累计放电-Ah
764
+ const cumulativeDisharge = format(data.slice(i, (i += 4)), 0.1, 0);
765
+ // 电池自功耗系数-多少天1%
766
+ const batterySelfConsumptionFactor = format(data.slice(i, (i += 2)), 1, 0);
767
+ // OCV校准电压1
768
+ const ocvCalibrationVoltage1 = format(data.slice(i, (i += 2)), 1, 0);
769
+ // OCV校准SOC1-%
770
+ const ocvCalibrationSOC1 = format(data.slice(i, (i += 2)), 1, 0);
771
+ // OCV校准电压2
772
+ const ocvCalibrationVoltage2 = format(data.slice(i, (i += 2)), 1, 0);
773
+ // OCV校准SOC2-%
774
+ const ocvCalibrationSOC2 = format(data.slice(i, (i += 2)), 1, 0);
775
+ // OCV校准电压3
776
+ const ocvCalibrationVoltage3 = format(data.slice(i, (i += 2)), 1, 0);
777
+ // OCV校准SOC3-%
778
+ const ocvCalibrationSOC3 = format(data.slice(i, (i += 2)), 1, 0);
779
+ // OCV校准电压4
780
+ const ocvCalibrationVoltage4 = format(data.slice(i, (i += 2)), 1, 0);
781
+ // OCV校准SOC4-%
782
+ const ocvCalibrationSOC4 = format(data.slice(i, (i += 2)), 1, 0);
783
+ // 充电需求电压-V
784
+ const chargeDemandVoltage = format(data.slice(i, (i += 2)), 0.1, 0, 2);
785
+ // 充电需求电流-A
786
+ const chargeDemandElectricity = format(data.slice(i, (i += 2)), 0.1, 0, 2);
787
+ // 放电需求电压-V
788
+ const dischargeDemandVoltage = format(data.slice(i, (i += 2)), 0.1, 0, 2);
789
+ // 放电需求电流-A
790
+ const dischargeDemandElectricity = format(data.slice(i, (i += 2)), 0.1, 0, 2);
791
+ // 电池串数
792
+ const batterySerial = format(data.slice(i, (i += 1)), 1, 0);
793
+
794
+ return { nominalCapacity, fullCapacity, restCapacity, soc, soh, cycleNum, cycleAttenuationFactor, cycleFactor, cumulativeCharge, cumulativeDisharge, batterySelfConsumptionFactor, ocvCalibrationVoltage1, ocvCalibrationSOC1, ocvCalibrationVoltage2, ocvCalibrationSOC2, ocvCalibrationVoltage3, ocvCalibrationSOC3, ocvCalibrationVoltage4, ocvCalibrationSOC4, chargeDemandVoltage, chargeDemandElectricity, dischargeDemandVoltage, dischargeDemandElectricity, batterySerial };
795
+ }
796
+ // #region 解析pack版本参数
797
+ /**
798
+ * 解析pack版本参数
799
+ * @param {*} values
800
+ * @returns
801
+ */
802
+ // 版本信息(0xXX 0x78 28 10 28 40 00 00 ...)
803
+ getVersionInfo(values) {
804
+ if (values[1] != 0x78 || values[2] != 0x28) return null;
805
+ const d_0x02_0x78_0x2810 = ['01', '78', '28', '10', '28', '40', /**/ '00', '2C', /**/ '00', '0E', '00', '03', '00', '0A', '00', '01', '00', '05', '00', '24', '55', '50', '31', '36', '53', '30', '31', '35', '00', '00', '00', '00', '00', '00', '00', '00', '4A', '42', '44', '2D', '4C', '31', '36', '53', '31', '30', '30', '41', '00', '00', '00', '00', /**/ 'D2', '3C'];
806
+ const data = values.slice(8, values.length - 2).map((x) => ('00' + x.toString(16)).toUpperCase().slice(-2));
807
+ let i = 0;
808
+
809
+ // BOOT版本
810
+ const bootVersion = format(data.slice(i, (i += 2)), 1, 0);
811
+ // 硬件版本
812
+ const hardwareVersion = format(data.slice(i, (i += 2)), 1, 0);
813
+ // APP版本
814
+ const appMajorVersion = format(data.slice(i, (i += 2)), 1, 0);
815
+ const appMinorVersion = format(data.slice(i, (i += 2)), 1, 0);
816
+ const appBetaVersion = format(data.slice(i, (i += 2)), 1, 0);
817
+
818
+ // 协议版本
819
+ const protocolVersion = format(data.slice(i, (i += 2)), 1, 0);
820
+ // 硬件名称
821
+ const hardwareName = hexToAscii(data.slice(i, (i += 16)).join(''));
822
+ // 项目名称
823
+ const projectName = hexToAscii(data.slice(i, (i += 16)).join(''));
824
+
825
+ const appVersion = [projectName, appMajorVersion, appMinorVersion, appBetaVersion].join('.');
826
+ const firmwaeVersion = appVersion;
827
+ return { bootVersion, hardwareVersion, appBetaVersion, appVersion, protocolVersion, hardwareName, projectName, firmwaeVersion };
828
+ }
829
+ }