use core::fmt::Debug;
use accelerometer_hal::{
vector::{F32x3, I16x3},
Accelerometer, Error, RawAccelerometer,
};
use embedded_hal::i2c::I2c;
use crate::{
registers::{Axis, BwSel, Read},
Stk8ba58,
};
impl<I2C, E> Accelerometer for Stk8ba58<I2C>
where
I2C: I2c<Error = E>,
E: Debug,
{
type Error = E;
fn accel_norm(&mut self) -> Result<F32x3, Error<E>> {
const I12_MAX: f32 = 2048.0;
let raw_data: I16x3 = self.accel_raw()?;
let range: f32 = self.range.into();
let x = (raw_data.x as f32 / I12_MAX) * range;
let y = (raw_data.y as f32 / I12_MAX) * range;
let z = (raw_data.z as f32 / I12_MAX) * range;
Ok(F32x3::new(x, y, z))
}
fn sample_rate(&mut self) -> Result<f32, Error<Self::Error>> {
Ok(self.read_mode(BwSel::default())?.into())
}
}
impl<I2C, E> RawAccelerometer<I16x3> for Stk8ba58<I2C>
where
I2C: I2c<Error = E>,
E: Debug,
{
type Error = E;
fn accel_raw(&mut self) -> Result<I16x3, Error<E>> {
const NEGATIVE: i16 = 0b1000_0000_0000;
let mut xyz = [0, 0, 0];
let axis = [Axis::X, Axis::Y, Axis::Z];
for (i, axis) in axis.iter().enumerate() {
let lsb = self.axis_lsb(axis)?;
let lsb = (lsb as i16) >> 4;
let msb = self.axis_msb(axis)?;
let msb = (msb as i16) << 4;
let sign = if (msb & NEGATIVE) == NEGATIVE {
0b1111_1111_0000_0000u16 as i16 } else {
0
};
let accel_raw = msb | lsb | sign;
xyz[i] = accel_raw;
}
Ok(I16x3::new(xyz[0], xyz[1], xyz[2]))
}
}