171 lines
6.0 KiB
C
171 lines
6.0 KiB
C
|
#include "HLW8032.h"
|
||
|
#include "math.h"
|
||
|
/* Private defines -----------------------------------------------------------*/
|
||
|
|
||
|
/* Private variables ---------------------------------------------------------*/
|
||
|
uint8_t first_run = 1; // 添加这行代码
|
||
|
float E_total = 0; // 累计电量
|
||
|
uint8_t UART4_RX_BUF[UART4_MAX_RECV_LEN]; // 改为UART4
|
||
|
uint8_t UART4_TX_BUF[UART4_MAX_SEND_LEN]; // 改为UART4
|
||
|
__IO uint16_t UART4_RX_STA; // 改为UART4
|
||
|
float g_energy = 0; // 初始化为0
|
||
|
uint8_t link = 0;
|
||
|
volatile float analog_status[3] = {0}; // 定义并初始化数组
|
||
|
uint8_t k = 0;
|
||
|
uint16_t old_reg = 0, len = 0;
|
||
|
double V = 0, C = 0, P = 0, E_con = 0;
|
||
|
double base_energy = 0; // EEPROM中的基准值
|
||
|
float last_minute_energy = 0; // 上一分钟的电量值
|
||
|
float current_minute_energy = 0; // 当前分钟的电量值
|
||
|
void Apphl8032_Init(void)
|
||
|
{
|
||
|
/* 初始化串口4 */
|
||
|
MX_UART4_Init();
|
||
|
|
||
|
// 使用HAL库的单字节接收中断
|
||
|
HAL_UART_Receive_IT(&huart4, &aRxBuffer, 1);
|
||
|
|
||
|
// 初始化变量
|
||
|
base_energy = 0.0;
|
||
|
analog_status[1] = 0.0;
|
||
|
}
|
||
|
|
||
|
void Data_Processing(void)
|
||
|
{
|
||
|
static uint32_t lastProcessTime = 0;
|
||
|
uint32_t currentTime = HAL_GetTick();
|
||
|
|
||
|
// 至少1秒处理一次
|
||
|
if(currentTime - lastProcessTime < 1000)
|
||
|
{
|
||
|
// printf("Data processing skipped: less than 1 second since last processing.\r\n");
|
||
|
UART4_RX_STA = 0;
|
||
|
return;
|
||
|
}
|
||
|
|
||
|
if (UART4_RX_STA & 0x8000) // 接收完成
|
||
|
{
|
||
|
// printf("Data reception complete. Processing data...\r\n");
|
||
|
|
||
|
uint32_t VP_REG = 0, V_REG = 0; // 电压相关寄存器
|
||
|
uint32_t CP_REG = 0, C_REG = 0; // 电流相关寄存器
|
||
|
uint32_t PP_REG = 0, P_REG = 0; // 功率相关寄存器
|
||
|
uint32_t PF = 0, PF_COUNT = 0; // 电量相关寄存器
|
||
|
uint32_t dat_sum = 0; // 校验和
|
||
|
|
||
|
// 计算校验和
|
||
|
for (uint8_t i = 2; i < 23; i++)
|
||
|
{
|
||
|
dat_sum += UART4_RX_BUF[i];
|
||
|
}
|
||
|
|
||
|
// printf("Calculated checksum: %lu, Received checksum: %02X\r\n", dat_sum % 256, UART4_RX_BUF[23]);
|
||
|
|
||
|
if (dat_sum % 256 == UART4_RX_BUF[23]) // 校验和正确
|
||
|
{
|
||
|
// printf("Checksum is valid.\r\n");
|
||
|
|
||
|
// 1. 计算电压
|
||
|
VP_REG = UART4_RX_BUF[2] * 65536 + UART4_RX_BUF[3] * 256 + UART4_RX_BUF[4];
|
||
|
V_REG = UART4_RX_BUF[5] * 65536 + UART4_RX_BUF[6] * 256 + UART4_RX_BUF[7];
|
||
|
if (V_REG != 0)
|
||
|
{
|
||
|
V = (VP_REG / V_REG) * 1.88;
|
||
|
// printf("Voltage calculated: V=%.2fV\r\n", V);
|
||
|
}
|
||
|
else
|
||
|
{
|
||
|
// printf("V_REG is zero, voltage calculation skipped.\r\n");
|
||
|
}
|
||
|
|
||
|
// 2. 计算电流
|
||
|
CP_REG = UART4_RX_BUF[8] * 65536 + UART4_RX_BUF[9] * 256 + UART4_RX_BUF[10];
|
||
|
C_REG = UART4_RX_BUF[11] * 65536 + UART4_RX_BUF[12] * 256 + UART4_RX_BUF[13];
|
||
|
if (C_REG != 0)
|
||
|
{
|
||
|
C = ((CP_REG * 100.0) / C_REG) / 100.0;
|
||
|
// printf("Current calculated: I=%.3fA\r\n", C);
|
||
|
}
|
||
|
else
|
||
|
{
|
||
|
// printf("C_REG is zero, current calculation skipped.\r\n");
|
||
|
}
|
||
|
|
||
|
// 3. 计算功率
|
||
|
PP_REG = UART4_RX_BUF[14] * 65536 + UART4_RX_BUF[15] * 256 + UART4_RX_BUF[16];
|
||
|
P_REG = UART4_RX_BUF[17] * 65536 + UART4_RX_BUF[18] * 256 + UART4_RX_BUF[19];
|
||
|
if (P_REG != 0)
|
||
|
{
|
||
|
P = (PP_REG / P_REG) * 1.88;
|
||
|
// printf("Power calculated: P=%.3fW\r\n", P);
|
||
|
}
|
||
|
else
|
||
|
{
|
||
|
// printf("P_REG is zero, power calculation skipped.\r\n");
|
||
|
}
|
||
|
|
||
|
// 4. 计算电量
|
||
|
if ((UART4_RX_BUF[20] & 0x80) != old_reg)
|
||
|
{
|
||
|
k++;
|
||
|
old_reg = UART4_RX_BUF[20] & 0x80;
|
||
|
}
|
||
|
|
||
|
PF = (k * 65536) + (UART4_RX_BUF[21] * 256) + UART4_RX_BUF[22];
|
||
|
// printf("Power factor calculated: PF=%lu\r\n", PF);
|
||
|
|
||
|
if (P >= 0.0 && PP_REG != 0)
|
||
|
{
|
||
|
PF_COUNT = ((100000 * 3600) / (PP_REG * 1.88)) * 10000;
|
||
|
current_minute_energy = ((PF * 10000.0) / PF_COUNT) / 10000.0;
|
||
|
|
||
|
static uint32_t last_save_time = 0;
|
||
|
uint32_t current_time = HAL_GetTick();
|
||
|
|
||
|
// 每10秒打印一次当前状态
|
||
|
if(current_time - last_save_time >= 10000) // 每10秒
|
||
|
{
|
||
|
// printf("Current Status:\r\n");
|
||
|
// printf("V=%.2fV, I=%.3fA, P=%.3fW\r\n", V, C, P);
|
||
|
// printf("Current Energy=%.6f, Last Energy=%.6f\r\n",
|
||
|
// current_minute_energy, last_minute_energy);
|
||
|
}
|
||
|
|
||
|
// 每分钟计算一次增量
|
||
|
if (current_time - last_save_time >= 60000) // 60秒
|
||
|
{
|
||
|
float minute_increase = current_minute_energy - last_minute_energy;
|
||
|
// printf("Minute increase: %.6f KWH\r\n", minute_increase);
|
||
|
|
||
|
// 添加保护,防止异常值
|
||
|
if (minute_increase > 0.0f && minute_increase < 1.0f)
|
||
|
{
|
||
|
base_energy += minute_increase;
|
||
|
analog_status[1] = base_energy;
|
||
|
// printf("Energy Update: %.6f KWH\r\n", base_energy);
|
||
|
}
|
||
|
else
|
||
|
{
|
||
|
// printf("Invalid energy increase: %.6f KWH\r\n", minute_increase);
|
||
|
}
|
||
|
|
||
|
last_minute_energy = current_minute_energy;
|
||
|
last_save_time = current_time;
|
||
|
}
|
||
|
}
|
||
|
else
|
||
|
{
|
||
|
// printf("Power or PP_REG is zero. P=%.3f, PP_REG=%lu\r\n", P, PP_REG);
|
||
|
}
|
||
|
}
|
||
|
else
|
||
|
{
|
||
|
// printf("Checksum is invalid.\r\n");
|
||
|
}
|
||
|
}
|
||
|
|
||
|
lastProcessTime = currentTime;
|
||
|
UART4_RX_STA = 0; // 这里可能需要调整
|
||
|
}
|
||
|
|