diff --git a/docs/Battery.md b/docs/Battery.md index c8d7008898..8432bbee48 100644 --- a/docs/Battery.md +++ b/docs/Battery.md @@ -59,7 +59,7 @@ Configure min/max cell voltages using the following CLI setting: `vbat_warning_cell_voltage` - Warning voltage per cell; this triggers battery-warning alarms, in 0.1V units, i.e. 34 = 3.4V -`vbat_hysteresis` - Sets the hysteresis value for low-battery alarms, in 0.1V units, i.e. 1 = 0.1V +`vbat_hysteresis` - Sets the hysteresis value for low-battery alarms, in 0.01V units, i.e. 10 = 0.10V `vbat_duration_for_warning` - Period voltage has to sustain before the battery state is set to battery-warning, in 0.1 s, i.e. 60 = 6.0 seconds diff --git a/docs/Cli.md b/docs/Cli.md index a1a1d2f2a7..1f1a22900a 100644 --- a/docs/Cli.md +++ b/docs/Cli.md @@ -180,7 +180,7 @@ Click on a variable to jump to the relevant documentation page. | [`vbat_max_cell_voltage`](Battery.md) | Maximum voltage per cell, used for auto-detecting battery voltage in 0.1V units, default is 43 (4.3V) | 10 | 50 | 43 | Master | UINT8 | | [`vbat_min_cell_voltage`](Battery.md) | Minimum voltage per cell, this triggers battery-critical alarms, in 0.1V units, default is 33 (3.3V) | 10 | 50 | 33 | Master | UINT8 | | [`vbat_warning_cell_voltage`](Battery.md) | Warning voltage per cell, this triggers battery-warning alarms, in 0.1V units, default is 35 (3.5V) | 10 | 50 | 35 | Master | UINT8 | -| [`vbat_hysteresis`](Battery.md) | Sets the hysteresis value for low-battery alarms, in 0.1V units, default is 1 (0.1V) | 10 | 250 | 1 | Master | UINT8 | +| [`vbat_hysteresis`](Battery.md) | Sets the hysteresis value for low-battery alarms, in 0.01V units, default is 1 (0.01V) | 10 | 250 | 1 | Master | UINT8 | | [`current_meter_scale`](Battery.md) | This sets the output voltage to current scaling for the current sensor in 0.1 mV/A steps. 400 is 40mV/A such as the ACS756 sensor outputs. 183 is the setting for the uberdistro with a 0.25mOhm shunt. | -10000 | 10000 | 400 | Master | INT16 | | [`current_meter_offset`](Battery.md) | This sets the output offset voltage of the current sensor in millivolts. | 0 | 3300 | 0 | Master | UINT16 | | [`multiwii_current_meter_output`](Battery.md) | Default current output via MSP is in 0.01A steps. Setting this to 1 causes output in default multiwii scaling (1mA steps). | OFF | ON | OFF | Master | UINT8 | diff --git a/src/main/sensors/battery.c b/src/main/sensors/battery.c index a1741315e0..9c6a3222b4 100644 --- a/src/main/sensors/battery.c +++ b/src/main/sensors/battery.c @@ -64,9 +64,11 @@ #define LVC_AFFECT_TIME 10000000 //10 secs for the LVC to slowly kick in // Battery monitoring stuff -uint8_t batteryCellCount; // Note: this can be 0 when no battery is detected or when the battery voltage sensor is missing or disabled. -uint16_t batteryWarningVoltage; -uint16_t batteryCriticalVoltage; +static uint8_t batteryCellCount; // Note: this can be 0 when no battery is detected or when the battery voltage sensor is missing or disabled. +static uint16_t batteryWarningVoltage; +static uint16_t batteryCriticalVoltage; +static uint16_t batteryWarningHysteresisVoltage; +static uint16_t batteryCriticalHysteresisVoltage; static lowVoltageCutoff_t lowVoltageCutoff; // static currentMeter_t currentMeter; @@ -114,7 +116,7 @@ PG_RESET_TEMPLATE(batteryConfig_t, batteryConfig, .useVBatAlerts = true, .useConsumptionAlerts = false, .consumptionWarningPercentage = 10, - .vbathysteresis = 1, + .vbathysteresis = 1, // 0.01V .vbatfullcellvoltage = 410, @@ -191,9 +193,7 @@ void batteryUpdatePresence(void) { - if ( - (voltageState == BATTERY_NOT_PRESENT || voltageState == BATTERY_INIT) && isVoltageFromBat() && isVoltageStable() - ) { + if ((voltageState == BATTERY_NOT_PRESENT || voltageState == BATTERY_INIT) && isVoltageFromBat() && isVoltageStable()) { // Battery has just been connected - calculate cells, warning voltages and reset state consumptionState = voltageState = BATTERY_OK; @@ -213,11 +213,11 @@ void batteryUpdatePresence(void) } batteryWarningVoltage = batteryCellCount * batteryConfig()->vbatwarningcellvoltage; batteryCriticalVoltage = batteryCellCount * batteryConfig()->vbatmincellvoltage; + batteryWarningHysteresisVoltage = (batteryWarningVoltage > batteryConfig()->vbathysteresis) ? batteryWarningVoltage - batteryConfig()->vbathysteresis : 0; + batteryCriticalHysteresisVoltage = (batteryCriticalVoltage > batteryConfig()->vbathysteresis) ? batteryCriticalVoltage - batteryConfig()->vbathysteresis : 0; lowVoltageCutoff.percentage = 100; lowVoltageCutoff.startTime = 0; - } else if ( - voltageState != BATTERY_NOT_PRESENT && isVoltageStable() && !isVoltageFromBat() - ) { + } else if (voltageState != BATTERY_NOT_PRESENT && isVoltageStable() && !isVoltageFromBat()) { /* battery has been disconnected - can take a while for filter cap to disharge so we use a threshold of batteryConfig()->vbatnotpresentcellvoltage */ consumptionState = voltageState = BATTERY_NOT_PRESENT; @@ -225,6 +225,8 @@ void batteryUpdatePresence(void) batteryCellCount = 0; batteryWarningVoltage = 0; batteryCriticalVoltage = 0; + batteryWarningHysteresisVoltage = 0; + batteryCriticalHysteresisVoltage = 0; } } @@ -234,7 +236,7 @@ static void batteryUpdateVoltageState(void) static uint32_t lastVoltageChangeMs; switch (voltageState) { case BATTERY_OK: - if (voltageMeter.displayFiltered <= (batteryWarningVoltage - batteryConfig()->vbathysteresis)) { + if (voltageMeter.displayFiltered <= batteryWarningHysteresisVoltage) { if (cmp32(millis(), lastVoltageChangeMs) >= batteryConfig()->vbatDurationForWarning * 100) { voltageState = BATTERY_WARNING; } @@ -244,7 +246,7 @@ static void batteryUpdateVoltageState(void) break; case BATTERY_WARNING: - if (voltageMeter.displayFiltered <= (batteryCriticalVoltage - batteryConfig()->vbathysteresis)) { + if (voltageMeter.displayFiltered <= batteryCriticalHysteresisVoltage) { if (cmp32(millis(), lastVoltageChangeMs) >= batteryConfig()->vbatDurationForCritical * 100) { voltageState = BATTERY_CRITICAL; } @@ -353,6 +355,8 @@ void batteryInit(void) voltageState = BATTERY_INIT; batteryWarningVoltage = 0; batteryCriticalVoltage = 0; + batteryWarningHysteresisVoltage = 0; + batteryCriticalHysteresisVoltage = 0; lowVoltageCutoff.enabled = false; lowVoltageCutoff.percentage = 100; lowVoltageCutoff.startTime = 0; diff --git a/src/main/sensors/battery.h b/src/main/sensors/battery.h index 9e743c1d96..7702d8c510 100644 --- a/src/main/sensors/battery.h +++ b/src/main/sensors/battery.h @@ -61,7 +61,7 @@ typedef struct batteryConfig_s { bool useVBatAlerts; // Issue alerts based on VBat readings bool useConsumptionAlerts; // Issue alerts based on total power consumption uint8_t consumptionWarningPercentage; // Percentage of remaining capacity that should trigger a battery warning - uint8_t vbathysteresis; // hysteresis for alarm, default 1 = 0.1V + uint8_t vbathysteresis; // hysteresis for alarm in 0.01V units, default 1 = 0.01V uint16_t vbatfullcellvoltage; // Cell voltage at which the battery is deemed to be "full" 0.01V units, default is 410 (4.1V)