mppt/App/src/mppt_control.c

372 lines
9.0 KiB
C
Raw Normal View History

2024-07-11 06:58:55 +00:00
/*
* mppt_control.c
*
* Created on: 2024<EFBFBD><EFBFBD>6<EFBFBD><EFBFBD>29<EFBFBD><EFBFBD>
* Author: psx
*/
#include "mppt_control.h"
#include "collect_Conversion.h"
#include "pwm.h"
#include "inflash.h"
2024-07-22 06:20:24 +00:00
#include "gpio.h"
2024-08-29 02:50:22 +00:00
#include "sl_protocol.h"
#include "task.h"
#include "uart_dev.h"
#include "parameter.h"
static void ConstantCurrentCharge(void);
static void ConstantVoltageCharge(void);
static void FloatingCharge(void);
/**
* @brief <EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ѹ
* @param
* @retval
*
*/
void mppt_constantVoltage(float InVoltage)
{
static float_t kp = 0.005;
static float_t ki = 0.00001;
2024-10-26 01:07:30 +00:00
float_t pv1Volt = g_otherParameter.Solar_In_Circuit_Voltage;
float_t error = pv1Volt - InVoltage;
float_t stepPwm = kp * error + ki * pv1Volt;
2024-11-18 02:48:07 +00:00
g_controlParameter.dutyRatio += stepPwm;
Set_duty_ratio(&g_controlParameter.dutyRatio);
}
/**
* @brief <EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ѹ(<EFBFBD><EFBFBD><EFBFBD><EFBFBD>)
* @param
* @retval
*
*/
void mppt_constantVoltageB(float OutVoltage)
{
static float_t kp = 0.005;
static float_t ki = 0.00001;
float_t outVolt = g_otherParameter.Battery_Voltage;
float_t error = OutVoltage - outVolt;
float_t stepPwm = kp * error + ki * outVolt;
g_controlParameter.dutyRatio += stepPwm;
Set_duty_ratio(&g_controlParameter.dutyRatio);
}
/**
2024-11-18 02:48:07 +00:00
* @brief <EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ѹ<EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>,û<EFBFBD>е<EFBFBD><EFBFBD><EFBFBD>ʱ<EFBFBD><EFBFBD>
* @param
* @retval
*
*/
2024-11-18 02:48:07 +00:00
void mppt_constantVoltageNoBatteryO(float OutVoltage)
{
static float_t kp = 0.005;
static float_t ki = 0.00001;
float_t outVolt = g_otherParameter.Output_Voltage;
float_t error = OutVoltage - outVolt;
float_t stepPwm = kp * error + ki * outVolt;
g_controlParameter.dutyRatio += stepPwm;
Set_duty_ratio(&g_controlParameter.dutyRatio);
}
2024-11-18 02:48:07 +00:00
/**
* @brief <EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ѹ<EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ˣ<EFBFBD>
* @param
* @retval
*
*/
float_t lastVolt = 0;
float_t lastStepPwm = 0;
float_t lastDutyRatio = 0;
void mppt_constantVoltageO(float OutVoltage)
{
static float_t kp = 0.005;
static float_t ki = 0.00001;
// static uint8_t flag = 0;
float_t outVolt = g_otherParameter.Output_Voltage;
float_t error = OutVoltage - outVolt;
float_t StepPwm = kp * error + ki * outVolt;
/* <20><><EFBFBD>е<EFBFBD><D0B5><EFBFBD>ʱ<EFBFBD><CAB1><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ѹ<EFBFBD><D1B9><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>½<EFBFBD> */
if (lastDutyRatio >= g_controlParameter.dutyRatio) {
// if (lastVolt >= outVolt) {
g_controlParameter.dutyRatio += StepPwm;
// } else {
// g_controlParameter.dutyRatio -= StepPwm;
// }
} else {
// if (lastVolt >= outVolt) {
// g_controlParameter.dutyRatio -= StepPwm;
// } else {
// g_controlParameter.dutyRatio += StepPwm;
// }
g_controlParameter.dutyRatio -= StepPwm;
}
if (g_otherParameter.overTemperature == 0) {
} else if (g_otherParameter.overTemperature == 1) {
g_controlParameter.dutyRatio -= 0.1;
} else if (g_otherParameter.overTemperature == 2) {
g_controlParameter.dutyRatio -= 0.2;
} else if (g_otherParameter.overTemperature == 3) {
g_controlParameter.dutyRatio -= 0.3;
}
lastVolt = outVolt;
lastStepPwm = StepPwm;
lastDutyRatio = g_controlParameter.dutyRatio;
Set_duty_ratio(&g_controlParameter.dutyRatio);
}
/**
* @brief ͨ<EFBFBD><EFBFBD><EFBFBD>Ŷ<EFBFBD><EFBFBD><EFBFBD><EFBFBD>ŷ<EFBFBD>׷<EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ʵ<EFBFBD>
* @param
* @retval
*
*/
float_t lastPower = 0;
float_t lastSolarInCircuitVoltage = 0;
void mppt_readJust(void)
{
static float_t step1 = 0.01;
static float_t step2 = 0.005;
static float_t tempV = 0.1;
static uint16_t flag = 0;
flag++;
if (flag < 600) {
return;
}
flag = 0;
float_t SolarInCircuitVoltage = get_PV1_VOLT_IN();
float_t power = g_otherParameter.Output_Voltage * g_otherParameter.Charg_Current;
float_t voltageDifference = SolarInCircuitVoltage - lastSolarInCircuitVoltage;
/* <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ѹ<EFBFBD><D1B9>ռ<EFBFBD>ձ<EFBFBD><D5B1><EFBFBD><EFBFBD>ӵ<EFBFBD>ѹ<EFBFBD><D1B9>С */
if (power <= lastPower) {
if (lastSolarInCircuitVoltage <= SolarInCircuitVoltage) {
if (voltageDifference > tempV) {
g_controlParameter.dutyRatio += step2;
} else {
g_controlParameter.dutyRatio += step1;
}
} else {
if (voltageDifference > tempV) {
g_controlParameter.dutyRatio -= step2;
} else {
g_controlParameter.dutyRatio -= step1;
}
}
} else {
if (lastSolarInCircuitVoltage <= SolarInCircuitVoltage) {
if (voltageDifference > tempV) {
g_controlParameter.dutyRatio -= step2;
} else {
g_controlParameter.dutyRatio -= step1;
}
} else {
if (voltageDifference > tempV) {
g_controlParameter.dutyRatio += step2;
} else {
g_controlParameter.dutyRatio += step1;
}
}
}
lastPower = power;
lastSolarInCircuitVoltage = SolarInCircuitVoltage;
/* <20><><EFBFBD>±<EFBFBD><C2B1><EFBFBD> */
if (g_otherParameter.overTemperature == 0) {
} else if (g_otherParameter.overTemperature == 1) {
g_controlParameter.dutyRatio -= 0.1;
} else if (g_otherParameter.overTemperature == 2) {
g_controlParameter.dutyRatio -= 0.2;
} else if (g_otherParameter.overTemperature == 3) {
g_controlParameter.dutyRatio -= 0.3;
}
Set_duty_ratio(&g_controlParameter.dutyRatio);
}
/**
* @brief <EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>mppt<EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ʳ<EFBFBD><EFBFBD><EFBFBD>
* @param
* @retval
*
*/
void ConstantCurrentCharge(void)
{
2024-11-18 02:48:07 +00:00
// mppt_constantVoltage(18);
mppt_readJust();
}
/**
* @brief <EFBFBD><EFBFBD>ѹ<EFBFBD><EFBFBD><EFBFBD><EFBFBD>
* @param
* @retval
*
*/
void ConstantVoltageCharge(void)
{
mppt_constantVoltageO(g_controlParameter.constantVoltageChargeV);
}
/**
* @brief <EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>
* @param
* @retval
*
*/
void FloatingCharge(void)
{
mppt_constantVoltageO(g_controlParameter.FloatV);
}
/**
* @brief mppt<EFBFBD><EFBFBD><EFBFBD><EFBFBD>ģʽ<EFBFBD><EFBFBD>ȷ<EFBFBD><EFBFBD>
* @param
* @retval
*
*/
void MpptContorlChoice(void)
{
switch(g_otherParameter.MPPT_Mode) {
case CONSTANTCURRENT:
ConstantCurrentCharge();
break;
case CONSTANTVOLTAGE:
ConstantVoltageCharge();
break;
case FLOAT:
FloatingCharge();
break;
default:
break;
}
}
/**
* @brief mpptģʽ<EFBFBD><EFBFBD>ȷ<EFBFBD><EFBFBD>
* @param
* @retval
*
*/
void MpptModeChoice(void)
{
/* ̫<><CCAB><EFBFBD>ܰ<EFBFBD><DCB0><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ѹС<D1B9><D0A1>һ<EFBFBD><D2BB>ֵ<EFBFBD>ҳ<EFBFBD><D2B3><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ҲС<D2B2><D0A1>һ<EFBFBD><D2BB>ֵʱmpptֹͣ<CDA3><D6B9><EFBFBD><EFBFBD> */
if ((g_otherParameter.Input_Voltage < g_controlParameter.stopSolarOpenCircuitV
2024-11-18 02:48:07 +00:00
&& g_otherParameter.Charg_Current < 0.1) ){
// && g_otherParameter.MPPT_Mode != NoWork) {
g_otherParameter.MPPT_Mode = NoWork;
TIM_Cmd(TIM3, DISABLE);
TIM_SetCompare4(TIM4, 0);
g_controlParameter.dutyRatio = 0;
TimeSliceOffset_Register(&g_startMpptControl, Task_startMpptControl
, startMpptControl_reloadVal, startMpptControl_offset);
TimeSliceOffset_Unregister(&g_collectOpenCircuitVoltage);
return;
}
/* <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>صĵ<D8B5><C4B5><EFBFBD>С<EFBFBD><D0A1>һ<EFBFBD><D2BB>ֵ<EFBFBD><D6B5><EFBFBD>ߵ<EFBFBD>ѹ<EFBFBD><D1B9><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>߹<EFBFBD>С<EFBFBD><D0A1><EFBFBD>ø<EFBFBD><C3B8><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> */
if ((g_otherParameter.Charg_BatteryCurrent < 0.05 && g_otherParameter.Charg_BatteryCurrent > -0.05)
|| g_otherParameter.Battery_Voltage > 16 || g_otherParameter.Battery_Voltage < 8) {
g_otherParameter.MPPT_Mode = FLOAT;
g_otherParameter.batteryState = 0;
return;
}
/* */
if ((g_controlParameter.constantVoltageV - 0.2) >= g_otherParameter.Battery_Voltage
&& g_otherParameter.Charg_Current > 0.1) {
g_otherParameter.MPPT_Mode = CONSTANTCURRENT;
return;
}
2024-10-26 01:07:30 +00:00
if ((g_controlParameter.constantVoltageV < g_otherParameter.Battery_Voltage)
// && (g_controlParameter.floatI + 0.1 <= g_otherParameter.Charg_Current)) {
&& ((g_controlParameter.floatI + 0.1 <= g_otherParameter.Charg_BatteryCurrent) || (g_controlParameter.floatI + 0.1 <= -g_otherParameter.Charg_Current))) {
g_otherParameter.MPPT_Mode = CONSTANTVOLTAGE;
return;
}
if ((((g_controlParameter.constantVoltageV < g_otherParameter.Battery_Voltage)
&& (g_controlParameter.floatI > g_otherParameter.Charg_Current))
&& (g_controlParameter.floatI > g_otherParameter.Discharg_Current))) {
g_otherParameter.MPPT_Mode = FLOAT;
return;
}
}
/**
* @brief mppt<EFBFBD>Ŀ<EFBFBD><EFBFBD><EFBFBD>
* @param
* @retval
*
*/
void MpptContorl(void)
{
g_otherParameter.Output_Voltage = get_PV_VOLT_OUT();
2024-10-26 01:07:30 +00:00
g_otherParameter.Solar_In_Circuit_Voltage = get_PV1_VOLT_IN();
2024-10-26 01:07:30 +00:00
// /* <20><><EFBFBD><EFBFBD>adc<64>ɼ<EFBFBD><C9BC><EFBFBD><EFBFBD><EFBFBD>ȫΪ0,<2C>˳<EFBFBD><CBB3><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ж<EFBFBD> */
// if (g_otherParameter.Discharg_Current == 0 && g_otherParameter.Charg_Current == 0) {
// return;
// }
g_otherParameter.Charg_BatteryCurrent = g_otherParameter.Charg_Current - g_otherParameter.Discharg_Current;
2024-11-18 02:48:07 +00:00
MpptModeChoice();
/* <20>޵<EFBFBD><DEB5><EFBFBD>ʱ<EFBFBD><CAB1><EFBFBD><EFBFBD>ѹ<EFBFBD><D1B9><EFBFBD><EFBFBD> */
if (!g_otherParameter.batteryState) {
if (!g_otherParameter.overTemperature) {
// mppt_constantVoltageNoBatteryO(g_controlParameter.FloatV);
2024-11-18 02:48:07 +00:00
mppt_constantVoltageO(g_controlParameter.FloatV);
}
return;
}
2024-11-18 02:48:07 +00:00
// /* <20>е<EFBFBD><D0B5><EFBFBD>ʱ */
// if (!g_otherParameter.overTemperature) {
// MpptModeChoice();
// MpptContorlChoice();
// }
MpptContorlChoice();
}