Show power-saving warning in Quick Test modal when battery is low

This commit is contained in:
Mathias Malmqvist
2025-10-28 01:10:45 +01:00
parent b72c9c93c9
commit 1138440119
6 changed files with 40 additions and 22 deletions

View File

@@ -35,7 +35,7 @@ class ControllerManager {
this.batteryStatus = {
bat_txt: "",
changed: false,
bat_capacity: 0,
charge_level: 0,
cable_connected: false,
is_charging: false,
is_error: false
@@ -578,7 +578,7 @@ class ControllerManager {
/**
* Convert battery percentage to display text with icons
*/
_batteryPercentToText({bat_capacity, is_charging, is_error}) {
_batteryPercentToText({charge_level, is_charging, is_error}) {
if (is_error) {
return '<font color="red">' + l("error") + '</font>';
}
@@ -590,10 +590,10 @@ class ControllerManager {
{ threshold: 80, icon: 'fa-battery-three-quarters' },
];
const icon_txt = batteryIcons.find(item => bat_capacity < item.threshold)?.icon || 'fa-battery-full';
const icon_txt = batteryIcons.find(item => charge_level < item.threshold)?.icon || 'fa-battery-full';
const icon_full = `<i class="fa-solid ${icon_txt}"></i>`;
const bolt_txt = is_charging ? '<i class="fa-solid fa-bolt"></i>' : '';
return [`${bat_capacity}%`, icon_full, bolt_txt].join(' ');
return [`${charge_level}%`, icon_full, bolt_txt].join(' ');
}
/**

View File

@@ -420,29 +420,29 @@ class DS4Controller extends BaseController {
const bat_status = (bat >> 4) & 1;
const cable_connected = bat_status === 1;
let bat_capacity = 0;
let charge_level = 0;
let is_charging = false;
let is_error = false;
if (cable_connected) {
if (bat_data < 10) {
bat_capacity = Math.min(bat_data * 10 + 5, 100);
charge_level = Math.min(bat_data * 10 + 5, 100);
is_charging = true;
} else if (bat_data === 10) {
bat_capacity = 100;
charge_level = 100;
is_charging = true;
} else if (bat_data === 11) {
bat_capacity = 100; // Fully charged
charge_level = 100; // Fully charged
} else {
bat_capacity = 0;
charge_level = 0;
is_error = true;
}
} else {
// On battery power
bat_capacity = bat_data < 10 ? bat_data * 10 + 5 : 100;
charge_level = bat_data < 10 ? bat_data * 10 + 5 : 100;
}
return { bat_capacity, cable_connected, is_charging, is_error };
return { charge_level, cable_connected, is_charging, is_error };
}
/**

View File

@@ -844,7 +844,7 @@ class DS5Controller extends BaseController {
const bat_charge = bat & 0x0f;
const bat_status = bat >> 4;
let bat_capacity = 0;
let charge_level = 0;
let cable_connected = false;
let is_charging = false;
let is_error = false;
@@ -852,32 +852,33 @@ class DS5Controller extends BaseController {
switch (bat_status) {
case 0:
// On battery power
bat_capacity = Math.min(bat_charge * 10 + 5, 100);
charge_level = Math.min(bat_charge * 10 + 5, 100);
break;
case 1:
// Charging
bat_capacity = Math.min(bat_charge * 10 + 5, 100);
charge_level = Math.min(bat_charge * 10 + 5, 100);
is_charging = true;
cable_connected = true;
break;
case 2:
// Fully charged
bat_capacity = 100;
charge_level = 100;
cable_connected = true;
break;
case 15:
// Battery is flat
bat_capacity = 0;
charge_level = 0;
is_charging = true;
cable_connected = true;
break;
case 11: // not sure yet what this error means
default:
// Error state
is_error = true;
break;
}
return { bat_capacity, cable_connected, is_charging, is_error };
return { charge_level, cable_connected, is_charging, is_error };
}
}

View File

@@ -623,7 +623,7 @@ const throttled_refresh_sticks = (() => {
const update_stick_graphics = (changes) => throttled_refresh_sticks(changes);
function update_battery_status({/* bat_capacity, cable_connected, is_charging, is_error, */ bat_txt, changed}) {
function update_battery_status({/* charge_level, cable_connected, is_charging, is_error, */ bat_txt, changed}) {
if(changed) {
$("#d-bat").html(bat_txt);
}
@@ -760,7 +760,7 @@ function handleControllerInput({ changes, inputConfig, touchPoints, batteryStatu
// Handle Quick Test Modal input (can be open from any tab)
if (isQuickTestVisible()) {
quicktest_handle_controller_input(changes);
quicktest_handle_controller_input(changes, batteryStatus);
return;
}

View File

@@ -93,6 +93,7 @@ export class QuickTestModal {
isTransitioning: false,
skippedTests: [],
lightsAnimationInterval: null,
batteryAlertShown: false,
};
}
@@ -1275,9 +1276,21 @@ export class QuickTestModal {
/**
* Handle controller input for test navigation and control
*/
handleControllerInput(changes) {
handleControllerInput(changes, batteryStatus) {
if(this.state.isTransitioning) return;
// Check battery status and show/hide warning if charge is 5% or less
if (batteryStatus) {
// Only update visibility if alert hasn't been shown or charge level changed
if (!this.state.batteryAlertShown || batteryStatus.changed ) {
console.log("Battery status changed:", batteryStatus);
const { charge_level, is_error } = batteryStatus;
const $batteryWarning = $('#battery-warning-alert');
$batteryWarning.toggle(charge_level <= 5 || is_error);
this.state.batteryAlertShown = true;
}
}
const activeTest = this._getCurrentActiveTest();
// If buttons test is active, track button presses
@@ -1572,9 +1585,9 @@ export function isQuickTestVisible() {
/**
* Handle controller input for the Quick Test Modal
*/
export function quicktest_handle_controller_input(changes) {
export function quicktest_handle_controller_input(changes, batteryStatus) {
if (currentQuickTestInstance && isQuickTestVisible()) {
currentQuickTestInstance.handleControllerInput(changes);
currentQuickTestInstance.handleControllerInput(changes, batteryStatus);
}
}

View File

@@ -8,6 +8,10 @@
</div>
<div class="modal-body">
<p class="ds-i18n mb-3">Run through these tests to verify your controller's functionality.</p>
<div id="battery-warning-alert" style="display: none; background-color: white; color: #ff4000cb; padding: 12px 16px; border-radius: 4px; margin-bottom: 16px; border: 2px solid;">
<i class="fas fa-exclamation-triangle me-2"></i>
<span class="ds-i18n">Battery level is low. Tests may fail due to the controller being in power saving mode.</span>
</div>
<div class="alert alert-info mb-4" id="quick-test-instructions">
<i class="fas fa-gamepad me-2"></i>
<span class="ds-i18n" id="quick-test-instructions-text"></span>