#![no_std]
#![warn(missing_debug_implementations, missing_docs)]
use core::fmt::Debug;
use embedded_hal::blocking::i2c::{Read, Write};
#[derive(Debug)]
#[repr(u8)]
pub enum Address {
PinLow = 0x48,
PinHigh = 0x4a,
PinFloat = 0x4c,
}
#[derive(Debug)]
#[repr(u8)]
pub enum Channel {
A,
B,
C,
D,
E,
F,
G,
H,
All = 0xf,
}
impl From<u8> for Channel {
fn from(index: u8) -> Self {
match index {
0 => Channel::A,
1 => Channel::B,
2 => Channel::C,
3 => Channel::D,
4 => Channel::E,
5 => Channel::F,
6 => Channel::G,
7 => Channel::H,
_ => panic!("Unkown channel number {}", index),
}
}
}
#[derive(Debug)]
#[repr(u8)]
pub enum CommandType {
WriteToChannel = 0x0,
UpdateChannel = 0x10,
WriteToChannelAndUpdate = 0x30,
WriteToChannelAndUpdateAll = 0x20,
}
#[derive(Debug)]
#[repr(u8)]
pub enum ResetMode {
Por = 0b00,
SetHighSpeed = 0b01,
MaintainHighSpeed = 0b10,
}
#[derive(Debug)]
pub struct DAC5578<I2C>
where
I2C: Read + Write,
{
i2c: I2C,
address: u8,
}
impl<I2C, E> DAC5578<I2C>
where
I2C: Read<Error = E> + Write<Error = E>,
{
pub fn new(i2c: I2C, address: Address) -> Self {
DAC5578 {
i2c,
address: address as u8,
}
}
pub fn write(&mut self, channel: Channel, data: u8) -> Result<(), E> {
let bytes = Self::encode_command(CommandType::WriteToChannel, channel as u8, data);
self.i2c.write(self.address, &bytes)
}
pub fn update(&mut self, channel: Channel, data: u8) -> Result<(), E> {
let bytes = Self::encode_command(CommandType::UpdateChannel, channel as u8, data);
self.i2c.write(self.address, &bytes)
}
pub fn write_and_update(&mut self, channel: Channel, data: u8) -> Result<(), E> {
let bytes = Self::encode_command(CommandType::WriteToChannelAndUpdate, channel as u8, data);
self.i2c.write(self.address, &bytes)
}
pub fn write_and_update_all(&mut self, channel: Channel, data: u8) -> Result<(), E> {
let bytes =
Self::encode_command(CommandType::WriteToChannelAndUpdateAll, channel as u8, data);
self.i2c.write(self.address, &bytes)
}
pub fn reset(&mut self, mode: ResetMode) -> Result<(), E> {
let bytes = [0x70, mode as u8, 0];
self.i2c.write(self.address, &bytes)
}
pub fn wake_up_all(&mut self) -> Result<(), E> {
self.i2c.write(0x00, &[0x06u8])?;
Ok(())
}
pub fn reset_all(&mut self) -> Result<(), E> {
self.i2c.write(0x00, &[0x09u8])?;
Ok(())
}
pub fn destroy(self) -> I2C {
self.i2c
}
fn encode_command(command: CommandType, access: u8, msdb: u8) -> [u8; 3] {
[command as u8 | access, msdb, 0]
}
}