1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83
#![no_std]
mod person_sensor;
mod person_sensor_builder;
pub use person_sensor::PersonSensor;
pub use person_sensor_builder::PersonSensorBuilder;
/// The number of detections returned by the sensor.
const NUM_DETECTIONS: usize = 4;
#[repr(C, packed)]
#[derive(Debug, Clone, Copy)]
pub struct Face {
/// Confidence of the box prediction, ranges from 1 to 100.
pub box_confidence: u8,
pub box_left: u8,
pub box_top: u8,
pub box_right: u8,
pub box_bottom: u8,
/// The confidence of "calibrated" identities ranges from 1 to 100, and will be 0 or less if
/// this face is not recognized as any of the calibrated identities or is not the largest face
/// in the frame.
pub id_confidence: i8,
/// The ID number of the face, if it is recognized as any of the
/// calibrated identities *and* is the largest face in the frame.
/// By default, the sensor will not run any recognition until calibration has been performed.
/// After at least one person has been calibrated, the sensor will always run recognition on
/// the largest face present, and assign an ID number if it’s recognized as one that it has been calibrated on.
pub id: i8,
/// Indicates if somebody is looking directly at the device
/// Note ID works most reliably when the face is straight on to the sensor
pub is_facing: u8,
}
#[repr(C, packed)]
#[derive(Debug, Clone, Copy)]
struct ResultsHeader {
reserved: [u8; 2],
data_size: u16,
}
#[repr(C, packed)]
#[derive(Debug, Clone, Copy)]
pub struct PersonSensorResults {
header: ResultsHeader,
pub num_faces: i8,
pub faces: [Face; NUM_DETECTIONS],
checksum: u16,
}
#[derive(Debug)]
pub enum PersonIDError {
/// IDs can only range from 0 to 7.
InvalidId,
}
#[repr(transparent)]
#[derive(Debug, Clone, Copy, PartialEq, Eq, PartialOrd, Ord, Hash)]
pub struct PersonID(u8);
impl PersonID {
pub fn new(id: u8) -> Result<Self, PersonIDError> {
if id < 8 {
Ok(PersonID(id))
} else {
Err(PersonIDError::InvalidId)
}
}
}
impl TryFrom<u8> for PersonID {
type Error = PersonIDError;
fn try_from(value: u8) -> Result<Self, Self::Error> {
Self::new(value)
}
}
impl From<PersonID> for u8 {
fn from(id: PersonID) -> u8 {
id.0
}
}