Skip to content

Commit

Permalink
Feature: add SoC & voltage thresholds for battery current limit
Browse files Browse the repository at this point in the history
This changes the custom current limit so the custom limit is only
applied when any of:

- SoC is valid and not ignored and SoC < threshold
- Voltage is valid and Voltage < threshold
- Voltage is invalid

Independently, if "Use Battery-Reported limit" is enabled and valid, it
is applied (unless a lower custom limit already was applied).
  • Loading branch information
ranma authored and schlimmchen committed Oct 24, 2024
1 parent d36b30a commit 2e85b42
Show file tree
Hide file tree
Showing 8 changed files with 56 additions and 4 deletions.
2 changes: 2 additions & 0 deletions include/Configuration.h
Original file line number Diff line number Diff line change
Expand Up @@ -145,6 +145,8 @@ struct BATTERY_CONFIG_T {
BatteryVoltageUnit MqttVoltageUnit;
bool EnableDischargeCurrentLimit;
float DischargeCurrentLimit;
float DischargeCurrentLimitBelowSoc;
float DischargeCurrentLimitBelowVoltage;
bool UseBatteryReportedDischargeCurrentLimit;
char MqttDischargeCurrentTopic[MQTT_MAX_TOPIC_STRLEN + 1];
char MqttDischargeCurrentJsonPath[BATTERY_JSON_MAX_PATH_STRLEN + 1];
Expand Down
2 changes: 2 additions & 0 deletions include/defaults.h
Original file line number Diff line number Diff line change
Expand Up @@ -156,6 +156,8 @@
#define BATTERY_JKBMS_POLLING_INTERVAL 5
#define BATTERY_ENABLE_DISCHARGE_CURRENT_LIMIT false
#define BATTERY_DISCHARGE_CURRENT_LIMIT 0.0
#define BATTERY_DISCHARGE_CURRENT_LIMIT_BELOW_SOC 100.0
#define BATTERY_DISCHARGE_CURRENT_LIMIT_BELOW_VOLTAGE 60.0
#define BATTERY_USE_BATTERY_REPORTED_DISCHARGE_CURRENT_LIMIT false

#define HUAWEI_ENABLED false
Expand Down
20 changes: 16 additions & 4 deletions src/Battery.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -91,14 +91,26 @@ float BatteryClass::getDischargeCurrentLimit()
if (!config.Battery.EnableDischargeCurrentLimit) { return FLT_MAX; }

auto dischargeCurrentLimit = config.Battery.DischargeCurrentLimit;
auto dischargeCurrentValid = dischargeCurrentLimit > 0.0f;

auto dischargeCurrentLimitValid = dischargeCurrentLimit > 0.0f;
auto dischargeCurrentLimitBelowSoc = config.Battery.DischargeCurrentLimitBelowSoc;
auto dischargeCurrentLimitBelowVoltage = config.Battery.DischargeCurrentLimitBelowVoltage;
auto statsSoCValid = getStats()->getSoCAgeSeconds() <= 60 && !config.PowerLimiter.IgnoreSoc;
auto statsSoC = statsSoCValid ? getStats()->getSoC() : 100.0; // fail open so we use voltage instead
auto statsVoltageValid = getStats()->getVoltageAgeSeconds() <= 60;
auto statsVoltage = statsVoltageValid ? getStats()->getVoltage() : 0.0; // fail closed
auto statsCurrentLimit = getStats()->getDischargeCurrentLimit();
auto statsLimitValid = config.Battery.UseBatteryReportedDischargeCurrentLimit
&& statsCurrentLimit >= 0.0f
&& getStats()->getDischargeCurrentLimitAgeSeconds() <= 60;

if (statsLimitValid && dischargeCurrentValid) {

if (statsSoC > dischargeCurrentLimitBelowSoc && statsVoltage > dischargeCurrentLimitBelowVoltage) {
// Above SoC and Voltage thresholds, ignore custom limit.
// Battery-provided limit will still be applied.
dischargeCurrentLimitValid = false;
}

if (statsLimitValid && dischargeCurrentLimitValid) {
// take the lowest limit
return min(statsCurrentLimit, dischargeCurrentLimit);
}
Expand All @@ -107,7 +119,7 @@ float BatteryClass::getDischargeCurrentLimit()
return statsCurrentLimit;
}

if (dischargeCurrentValid) {
if (dischargeCurrentLimitValid) {
return dischargeCurrentLimit;
}

Expand Down
4 changes: 4 additions & 0 deletions src/Configuration.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -88,6 +88,8 @@ void ConfigurationClass::serializeBatteryConfig(BatteryConfig const& source, Jso
target["mqtt_voltage_unit"] = config.Battery.MqttVoltageUnit;
target["enable_discharge_current_limit"] = config.Battery.EnableDischargeCurrentLimit;
target["discharge_current_limit"] = config.Battery.DischargeCurrentLimit;
target["discharge_current_limit_below_soc"] = config.Battery.DischargeCurrentLimitBelowSoc;
target["discharge_current_limit_below_voltage"] = config.Battery.DischargeCurrentLimitBelowVoltage;
target["use_battery_reported_discharge_current_limit"] = config.Battery.UseBatteryReportedDischargeCurrentLimit;
target["mqtt_discharge_current_topic"] = config.Battery.MqttDischargeCurrentTopic;
target["mqtt_discharge_current_json_path"] = config.Battery.MqttDischargeCurrentJsonPath;
Expand Down Expand Up @@ -383,6 +385,8 @@ void ConfigurationClass::deserializeBatteryConfig(JsonObject const& source, Batt
target.MqttVoltageUnit = source["mqtt_voltage_unit"] | BatteryVoltageUnit::Volts;
target.EnableDischargeCurrentLimit = source["enable_discharge_current_limit"] | BATTERY_ENABLE_DISCHARGE_CURRENT_LIMIT;
target.DischargeCurrentLimit = source["discharge_current_limit"] | BATTERY_DISCHARGE_CURRENT_LIMIT;
target.DischargeCurrentLimitBelowSoc = source["discharge_current_limit_below_soc"] | BATTERY_DISCHARGE_CURRENT_LIMIT_BELOW_SOC;
target.DischargeCurrentLimitBelowVoltage = source["discharge_current_limit_below_voltage"] | BATTERY_DISCHARGE_CURRENT_LIMIT_BELOW_VOLTAGE;
target.UseBatteryReportedDischargeCurrentLimit = source["use_battery_reported_discharge_current_limit"] | BATTERY_USE_BATTERY_REPORTED_DISCHARGE_CURRENT_LIMIT;
strlcpy(target.MqttDischargeCurrentTopic, source["mqtt_discharge_current_topic"] | "", sizeof(config.Battery.MqttDischargeCurrentTopic));
strlcpy(target.MqttDischargeCurrentJsonPath, source["mqtt_discharge_current_json_path"] | "", sizeof(config.Battery.MqttDischargeCurrentJsonPath));
Expand Down
4 changes: 4 additions & 0 deletions webapp/src/locales/de.json
Original file line number Diff line number Diff line change
Expand Up @@ -724,6 +724,10 @@
"DischargeCurrentLimitConfiguration": "Einstellungen Entladestromlimit",
"LimitDischargeCurrent": "Entladestrom limitieren",
"DischargeCurrentLimit": "max. Entladestrom",
"DischargeCurrentLimitBelowSoc": "Limitieren unter SoC",
"DischargeCurrentLimitBelowSocInfo": "Das Entladestromlimit wird nur unter dieser SoC-Schwelle angewendet (nicht verwendet falls 'Batterie SoC ignorieren' aktiviert ist).",
"DischargeCurrentLimitBelowVoltage": "Limitieren unter Spannung",
"DischargeCurrentLimitBelowVoltageInfo": "Das Entladestromlimit wird nur unter dieser Spannungs-Schwelle angewendet (wenn SoC ignoriert oder nicht verfügbar).",
"UseBatteryReportedDischargeCurrentLimit": "Von der Batterie übermitteltes Limit verwenden",
"BatteryReportedDischargeCurrentLimitInfo": "<b>Hinweis:</b> Das niedrigste Limit wird angewendet, wobei das von der Batterie übermittelte Entladestromlimit nur verwendet wird, wenn in der letzten Minute ein Update eingegangen ist; andernfalls dient das zuvor festgelegte Limit als Fallback.",
"MqttDischargeCurrentTopic": "Topic für Entladestromlimit",
Expand Down
4 changes: 4 additions & 0 deletions webapp/src/locales/en.json
Original file line number Diff line number Diff line change
Expand Up @@ -727,6 +727,10 @@
"DischargeCurrentLimitConfiguration": "Discharge Current Limit Settings",
"LimitDischargeCurrent": "Limit Discharge Current",
"DischargeCurrentLimit": "max. Discharge Current",
"DischargeCurrentLimitBelowSoc": "Apply limit below SoC",
"DischargeCurrentLimitBelowSocInfo": "The discharge current limit is not applied above this SoC (not used if 'Ignore Battery SoC' is enabled).",
"DischargeCurrentLimitBelowVoltage": "Apply limit below voltage",
"DischargeCurrentLimitBelowVoltageInfo": "The discharge current limit is not applied above this voltage (used if SoC ignored or unavailable).",
"UseBatteryReportedDischargeCurrentLimit": "Use Battery-Reported limit",
"BatteryReportedDischargeCurrentLimitInfo": "<b>Hint:</b> The lowest limit will be applied, with the battery-reported discharge current limit used only if an update was received in the last minute; otherwise, the previously specified limit will act as a fallback.",
"MqttDischargeCurrentTopic": "Discharge Current Limit Value Topic",
Expand Down
2 changes: 2 additions & 0 deletions webapp/src/types/BatteryConfig.ts
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,8 @@ export interface BatteryConfig {
mqtt_voltage_unit: number;
enable_discharge_current_limit: boolean;
discharge_current_limit: number;
discharge_current_limit_below_soc: number;
discharge_current_limit_below_voltage: number;
use_battery_reported_discharge_current_limit: boolean;
mqtt_discharge_current_topic: string;
mqtt_discharge_current_json_path: string;
Expand Down
22 changes: 22 additions & 0 deletions webapp/src/views/BatteryAdminView.vue
Original file line number Diff line number Diff line change
Expand Up @@ -141,6 +141,28 @@
postfix="A"
/>

<InputElement
:label="$t('batteryadmin.DischargeCurrentLimitBelowSoc')"
v-model="batteryConfigList.discharge_current_limit_below_soc"
type="number"
min="0"
max="100"
step="0.1"
postfix="%"
:tooltip="$t('batteryadmin.DischargeCurrentLimitBelowSocInfo')"
/>

<InputElement
:label="$t('batteryadmin.DischargeCurrentLimitBelowVoltage')"
v-model="batteryConfigList.discharge_current_limit_below_voltage"
type="number"
min="0"
max="60"
step="0.01"
postfix="V"
:tooltip="$t('batteryadmin.DischargeCurrentLimitBelowVoltageInfo')"
/>

<InputElement
:label="$t('batteryadmin.UseBatteryReportedDischargeCurrentLimit')"
v-model="batteryConfigList.use_battery_reported_discharge_current_limit"
Expand Down

0 comments on commit 2e85b42

Please sign in to comment.