px4sim 0.1.6

A wrapper to simplify creating a custom PX4 SITL simulator.
Documentation
use rand::random;
use std::{
    path::Path,
    process::{Child, Command},
    time::{SystemTime, UNIX_EPOCH},
};

pub fn start_px4(
    px4_project_root_path: &str,
    system_id: u8,
    airframe: &str,
) -> Result<Child, std::io::Error> {
    let px4_bin = Path::new(px4_project_root_path).join("build/px4_sitl_default/bin/px4");
    let romfs_dir = Path::new(px4_project_root_path).join("ROMFS/px4fmu_common/");

    Command::new(px4_bin)
        .arg(romfs_dir)
        .arg("-i").arg(system_id.to_string())
        .arg("-w").arg("px4files")
        .arg("-d")
        .env("PX4_SYS_AUTOSTART", airframe)
        .spawn()
}

pub fn time_since_epoch() -> u64 {
    SystemTime::now()
        .duration_since(UNIX_EPOCH)
        .unwrap()
        .as_micros() as u64
}

pub fn get_boot_time() -> u32 {
    SystemTime::now()
        .duration_since(UNIX_EPOCH)
        .unwrap()
        .as_millis() as u32
}

pub fn noise(range: f32) -> f32 {
    random::<f32>() * range
}

pub fn cnoise(range: f32) -> f32 {
    (random::<f32>() - 0.5) * range
}

pub trait CanAdd {
    fn add(self, other: Self) -> Self;
}

impl<T: std::ops::Add<Output = T>> CanAdd for (T, T) {
    fn add(self, other: Self) -> Self {
        (self.0 + other.0, self.1 + other.1)
    }
}

impl<T: std::ops::Add<Output = T>> CanAdd for (T, T, T) {
    fn add(self, other: Self) -> Self {
        (self.0 + other.0, self.1 + other.1, self.2 + other.2)
    }
}

impl<T: std::ops::Add<Output = T> + Copy> CanAdd for [T; 4] {
    fn add(self, other: Self) -> Self {
        std::array::from_fn(|i| self[i] + other[i])
    }
}