Added more unittests
This commit is contained in:
parent
b98614fe8e
commit
9f95813f97
@ -416,6 +416,10 @@ pub fn calculate_axis_value(
|
||||
) -> u16 {
|
||||
use crate::hardware::{ADC_MAX, ADC_MIN, AXIS_CENTER};
|
||||
|
||||
if min >= max || center <= min || center >= max {
|
||||
return center;
|
||||
}
|
||||
|
||||
if value <= min {
|
||||
return ADC_MIN;
|
||||
}
|
||||
@ -660,6 +664,20 @@ mod tests {
|
||||
assert_eq!(result, AXIS_CENTER);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn test_calculate_axis_value_degenerate_calibration() {
|
||||
let expo_lut = ExpoLUT::new(0.0);
|
||||
|
||||
// When calibration collapses to a single point (min=max=center),
|
||||
// the output should remain at that center rather than clamping low/high.
|
||||
let result = calculate_axis_value(2100, 2100, 2100, 2100, (0, 0, 0), false, &expo_lut);
|
||||
assert_eq!(result, 2100);
|
||||
|
||||
// Also handle centers outside the valid window by returning center directly.
|
||||
let result = calculate_axis_value(1500, 1400, 2000, 1400, (0, 0, 0), false, &expo_lut);
|
||||
assert_eq!(result, 1400);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn test_remap_function() {
|
||||
// Test basic remapping
|
||||
|
||||
@ -8,9 +8,9 @@
|
||||
//! - Evaluate special combinations (bootloader, calibration, etc.)
|
||||
//! - Expose a compact state consumed by USB report generation
|
||||
|
||||
use crate::mapping::*;
|
||||
use crate::button_matrix::ButtonMatrix;
|
||||
use crate::hardware::{NUMBER_OF_BUTTONS, AXIS_CENTER, BUTTON_ROWS, BUTTON_COLS};
|
||||
use crate::hardware::{AXIS_CENTER, BUTTON_COLS, BUTTON_ROWS, NUMBER_OF_BUTTONS};
|
||||
use crate::mapping::*;
|
||||
use embedded_hal::digital::InputPin;
|
||||
use rp2040_hal::timer::Timer;
|
||||
|
||||
@ -39,7 +39,6 @@ pub struct Button {
|
||||
|
||||
// ==================== SPECIAL ACTIONS ====================
|
||||
/// High‑level actions triggered by dedicated button combinations.
|
||||
|
||||
#[derive(Debug, PartialEq)]
|
||||
pub enum SpecialAction {
|
||||
None,
|
||||
@ -55,7 +54,6 @@ pub enum SpecialAction {
|
||||
|
||||
// ==================== BUTTON MANAGER ====================
|
||||
/// Aggregates and processes all buttons, exposing a stable API to the rest of the firmware.
|
||||
|
||||
pub struct ButtonManager {
|
||||
pub buttons: [Button; TOTAL_BUTTONS],
|
||||
}
|
||||
@ -77,7 +75,10 @@ impl ButtonManager {
|
||||
}
|
||||
|
||||
/// Update button states from the button matrix snapshot.
|
||||
pub fn update_from_matrix(&mut self, matrix: &mut ButtonMatrix<BUTTON_ROWS, BUTTON_COLS, NUMBER_OF_BUTTONS>) {
|
||||
pub fn update_from_matrix(
|
||||
&mut self,
|
||||
matrix: &mut ButtonMatrix<BUTTON_ROWS, BUTTON_COLS, NUMBER_OF_BUTTONS>,
|
||||
) {
|
||||
for (index, key) in matrix.buttons_pressed().iter().enumerate() {
|
||||
self.buttons[index].pressed = *key;
|
||||
}
|
||||
@ -162,7 +163,11 @@ impl ButtonManager {
|
||||
}
|
||||
|
||||
/// Check for special button combinations (bootloader, calibration state/mode, VT, etc.).
|
||||
pub fn check_special_combinations(&self, unprocessed_axis_value: u16, calibration_active: bool) -> SpecialAction {
|
||||
pub fn check_special_combinations(
|
||||
&self,
|
||||
unprocessed_axis_value: u16,
|
||||
calibration_active: bool,
|
||||
) -> SpecialAction {
|
||||
// Secondary way to enter bootloader
|
||||
if self.buttons[BUTTON_FRONT_LEFT_LOWER].pressed
|
||||
&& self.buttons[BUTTON_TOP_LEFT_MODE].pressed
|
||||
@ -297,13 +302,14 @@ fn update_button_press_type(button: &mut Button, current_time: u32) {
|
||||
|
||||
// Auto‑release generated USB press after minimum hold time
|
||||
const USB_MIN_HOLD_MS: u32 = 50;
|
||||
if button.usb_press_active
|
||||
&& (!button.pressed
|
||||
&& !button.long_press_handled
|
||||
&& current_time - button.usb_press_start_time >= USB_MIN_HOLD_MS)
|
||||
|| (!button.enable_long_hold
|
||||
&& button.long_press_handled
|
||||
&& current_time - button.usb_press_start_time >= USB_MIN_HOLD_MS)
|
||||
let elapsed = current_time.saturating_sub(button.usb_press_start_time);
|
||||
let should_release = if button.long_press_handled {
|
||||
!button.enable_long_hold && elapsed >= USB_MIN_HOLD_MS
|
||||
} else {
|
||||
!button.pressed && elapsed >= USB_MIN_HOLD_MS
|
||||
};
|
||||
|
||||
if button.usb_press_active && should_release
|
||||
{
|
||||
button.usb_changed = true;
|
||||
button.usb_press_active = false;
|
||||
@ -483,6 +489,37 @@ mod tests {
|
||||
assert!(button.long_press_handled);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn test_button_press_type_long_press_auto_release_once() {
|
||||
let mut button = Button::default();
|
||||
button.usb_button_long = 2;
|
||||
button.enable_long_press = true;
|
||||
button.enable_long_hold = false;
|
||||
|
||||
// Press the button
|
||||
button.pressed = true;
|
||||
update_button_press_type(&mut button, 0);
|
||||
button.previous_pressed = button.pressed;
|
||||
|
||||
// Hold long enough to trigger the long press path
|
||||
update_button_press_type(&mut button, 250);
|
||||
assert!(button.usb_press_active);
|
||||
assert_eq!(button.active_usb_button, 2);
|
||||
|
||||
// Clear the changed flag to emulate USB stack observing it
|
||||
button.usb_changed = false;
|
||||
|
||||
// Keep holding and ensure we auto-release exactly once
|
||||
update_button_press_type(&mut button, 320);
|
||||
assert!(!button.usb_press_active);
|
||||
assert!(button.usb_changed);
|
||||
|
||||
button.usb_changed = false;
|
||||
update_button_press_type(&mut button, 400);
|
||||
assert!(!button.usb_press_active);
|
||||
assert!(!button.usb_changed);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn test_timer_integration_method_exists() {
|
||||
let manager = ButtonManager::new();
|
||||
|
||||
@ -135,7 +135,9 @@ impl CalibrationManager {
|
||||
];
|
||||
|
||||
// Save calibration data to storage
|
||||
let _ = storage::write_calibration_data(write_fn, &axis_data, self.gimbal_mode);
|
||||
if storage::write_calibration_data(write_fn, &axis_data, self.gimbal_mode).is_err() {
|
||||
return false;
|
||||
}
|
||||
|
||||
// End calibration mode
|
||||
self.active = false;
|
||||
@ -519,6 +521,20 @@ mod tests {
|
||||
assert!(!manager.is_active()); // Should end calibration
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn test_save_calibration_failure_keeps_active() {
|
||||
let mut manager = CalibrationManager::new();
|
||||
manager.start_calibration();
|
||||
let axes = [GimbalAxis::new(); NBR_OF_GIMBAL_AXIS];
|
||||
|
||||
let mut write_fn = |_page: u32, _data: &[u8]| Err(());
|
||||
|
||||
let result = manager.save_calibration(&axes, &mut write_fn);
|
||||
|
||||
assert!(!result);
|
||||
assert!(manager.is_active());
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn test_save_calibration_inactive() {
|
||||
let mut manager = CalibrationManager::new(); // Note: not starting calibration
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user