| 
							
							
							
						 |  |  | @@ -1,202 +1,157 @@ | 
		
	
		
			
				|  |  |  |  | use crate::to_string; | 
		
	
		
			
				|  |  |  |  | use anyhow::bail; | 
		
	
		
			
				|  |  |  |  | use anyhow::anyhow; | 
		
	
		
			
				|  |  |  |  | use bq34z100::{Bq34Z100Error, Bq34z100g1, Bq34z100g1Driver}; | 
		
	
		
			
				|  |  |  |  | use embedded_hal_bus::i2c::MutexDevice; | 
		
	
		
			
				|  |  |  |  | use esp_idf_hal::delay::Delay; | 
		
	
		
			
				|  |  |  |  | use esp_idf_hal::i2c::{I2cDriver, I2cError}; | 
		
	
		
			
				|  |  |  |  | use measurements::Temperature; | 
		
	
		
			
				|  |  |  |  | use serde::Serialize; | 
		
	
		
			
				|  |  |  |  | use std::result::Result::Ok as OkStd; | 
		
	
		
			
				|  |  |  |  |  | 
		
	
		
			
				|  |  |  |  | pub trait BatteryInteraction { | 
		
	
		
			
				|  |  |  |  |     fn state_charge_percent(&mut self) -> anyhow::Result<u8>; | 
		
	
		
			
				|  |  |  |  |     fn remaining_milli_ampere_hour(&mut self) -> anyhow::Result<u16>; | 
		
	
		
			
				|  |  |  |  |     fn max_milli_ampere_hour(&mut self) -> anyhow::Result<u16>; | 
		
	
		
			
				|  |  |  |  |     fn design_milli_ampere_hour(&mut self) -> anyhow::Result<u16>; | 
		
	
		
			
				|  |  |  |  |     fn voltage_milli_volt(&mut self) -> anyhow::Result<u16>; | 
		
	
		
			
				|  |  |  |  |     fn average_current_milli_ampere(&mut self) -> anyhow::Result<i16>; | 
		
	
		
			
				|  |  |  |  |     fn cycle_count(&mut self) -> anyhow::Result<u16>; | 
		
	
		
			
				|  |  |  |  |     fn state_health_percent(&mut self) -> anyhow::Result<u8>; | 
		
	
		
			
				|  |  |  |  |     fn bat_temperature(&mut self) -> anyhow::Result<u16>; | 
		
	
		
			
				|  |  |  |  |     fn get_battery_state(&mut self) -> String; | 
		
	
		
			
				|  |  |  |  | } | 
		
	
		
			
				|  |  |  |  | #[derive(Serialize)] | 
		
	
		
			
				|  |  |  |  | pub struct BatteryState { | 
		
	
		
			
				|  |  |  |  |     voltage_milli_volt: String, | 
		
	
		
			
				|  |  |  |  |     current_milli_ampere: String, | 
		
	
		
			
				|  |  |  |  |     cycle_count: String, | 
		
	
		
			
				|  |  |  |  |     design_milli_ampere: String, | 
		
	
		
			
				|  |  |  |  |     remaining_milli_ampere: String, | 
		
	
		
			
				|  |  |  |  |     state_of_charge: String, | 
		
	
		
			
				|  |  |  |  |     state_of_health: String, | 
		
	
		
			
				|  |  |  |  |     temperature: String, | 
		
	
		
			
				|  |  |  |  |     fn state_charge_percent(&mut self) -> Result<f32, BatteryError>; | 
		
	
		
			
				|  |  |  |  |     fn remaining_milli_ampere_hour(&mut self) -> Result<u16, BatteryError>; | 
		
	
		
			
				|  |  |  |  |     fn max_milli_ampere_hour(&mut self) -> Result<u16, BatteryError>; | 
		
	
		
			
				|  |  |  |  |     fn design_milli_ampere_hour(&mut self) -> Result<u16, BatteryError>; | 
		
	
		
			
				|  |  |  |  |     fn voltage_milli_volt(&mut self) -> Result<u16, BatteryError>; | 
		
	
		
			
				|  |  |  |  |     fn average_current_milli_ampere(&mut self) -> Result<i16, BatteryError>; | 
		
	
		
			
				|  |  |  |  |     fn cycle_count(&mut self) -> Result<u16, BatteryError>; | 
		
	
		
			
				|  |  |  |  |     fn state_health_percent(&mut self) -> Result<u16, BatteryError>; | 
		
	
		
			
				|  |  |  |  |     fn bat_temperature(&mut self) -> Result<u16, BatteryError>; | 
		
	
		
			
				|  |  |  |  |     fn get_battery_state(&mut self) -> Result<BatteryState, BatteryError>; | 
		
	
		
			
				|  |  |  |  | } | 
		
	
		
			
				|  |  |  |  |  | 
		
	
		
			
				|  |  |  |  | pub enum BatteryMonitor<'a> { | 
		
	
		
			
				|  |  |  |  |     Disabled {}, | 
		
	
		
			
				|  |  |  |  |     BQ34Z100G1 { | 
		
	
		
			
				|  |  |  |  |         battery_driver: Bq34z100g1Driver<MutexDevice<'a, I2cDriver<'a>>, Delay>, | 
		
	
		
			
				|  |  |  |  |     }, | 
		
	
		
			
				|  |  |  |  |     WchI2cSlave {}, | 
		
	
		
			
				|  |  |  |  | #[derive(Debug, Serialize)] | 
		
	
		
			
				|  |  |  |  | pub struct BatteryInfo { | 
		
	
		
			
				|  |  |  |  |     pub voltage_milli_volt: u16, | 
		
	
		
			
				|  |  |  |  |     pub average_current_milli_ampere: i16, | 
		
	
		
			
				|  |  |  |  |     pub cycle_count: u16, | 
		
	
		
			
				|  |  |  |  |     pub design_milli_ampere_hour: u16, | 
		
	
		
			
				|  |  |  |  |     pub remaining_milli_ampere_hour: u16, | 
		
	
		
			
				|  |  |  |  |     pub state_of_charge: f32, | 
		
	
		
			
				|  |  |  |  |     pub state_of_health: u16, | 
		
	
		
			
				|  |  |  |  |     pub temperature: u16, | 
		
	
		
			
				|  |  |  |  | } | 
		
	
		
			
				|  |  |  |  |  | 
		
	
		
			
				|  |  |  |  | impl BatteryInteraction for BatteryMonitor<'_> { | 
		
	
		
			
				|  |  |  |  |     fn state_charge_percent(&mut self) -> anyhow::Result<u8> { | 
		
	
		
			
				|  |  |  |  |         match self { | 
		
	
		
			
				|  |  |  |  |             BatteryMonitor::BQ34Z100G1 { battery_driver } => { | 
		
	
		
			
				|  |  |  |  |                 match battery_driver.state_of_charge() { | 
		
	
		
			
				|  |  |  |  |                     OkStd(r) => anyhow::Ok(r), | 
		
	
		
			
				|  |  |  |  |                     Err(err) => bail!("Error reading SoC {:?}", err), | 
		
	
		
			
				|  |  |  |  |                 } | 
		
	
		
			
				|  |  |  |  |             } | 
		
	
		
			
				|  |  |  |  |             BatteryMonitor::WchI2cSlave { .. } => { | 
		
	
		
			
				|  |  |  |  |                 bail!("Not implemented") | 
		
	
		
			
				|  |  |  |  |             } | 
		
	
		
			
				|  |  |  |  |             BatteryMonitor::Disabled {} => { | 
		
	
		
			
				|  |  |  |  |                 bail!("Battery monitor is disabled") | 
		
	
		
			
				|  |  |  |  |             } | 
		
	
		
			
				|  |  |  |  |         } | 
		
	
		
			
				|  |  |  |  | #[derive(Debug, Serialize)] | 
		
	
		
			
				|  |  |  |  | pub enum BatteryError { | 
		
	
		
			
				|  |  |  |  |     NoBatteryMonitor, | 
		
	
		
			
				|  |  |  |  |     CommunicationError(String), | 
		
	
		
			
				|  |  |  |  | } | 
		
	
		
			
				|  |  |  |  |  | 
		
	
		
			
				|  |  |  |  | impl From<Bq34Z100Error<esp_idf_hal::i2c::I2cError>> for BatteryError { | 
		
	
		
			
				|  |  |  |  |     fn from(err: Bq34Z100Error<esp_idf_hal::i2c::I2cError>) -> Self { | 
		
	
		
			
				|  |  |  |  |         BatteryError::CommunicationError( | 
		
	
		
			
				|  |  |  |  |             anyhow!("failed to communicate with battery monitor: {:?}", err).to_string(), | 
		
	
		
			
				|  |  |  |  |         ) | 
		
	
		
			
				|  |  |  |  |     } | 
		
	
		
			
				|  |  |  |  | } | 
		
	
		
			
				|  |  |  |  |  | 
		
	
		
			
				|  |  |  |  | #[derive(Debug, Serialize)] | 
		
	
		
			
				|  |  |  |  | pub enum BatteryState { | 
		
	
		
			
				|  |  |  |  |     Unknown, | 
		
	
		
			
				|  |  |  |  |     Info(BatteryInfo), | 
		
	
		
			
				|  |  |  |  | } | 
		
	
		
			
				|  |  |  |  |  | 
		
	
		
			
				|  |  |  |  | /// If no battery monitor is installed this implementation will be used | 
		
	
		
			
				|  |  |  |  | pub struct NoBatteryMonitor {} | 
		
	
		
			
				|  |  |  |  |  | 
		
	
		
			
				|  |  |  |  | impl BatteryInteraction for NoBatteryMonitor { | 
		
	
		
			
				|  |  |  |  |     fn state_charge_percent(&mut self) -> Result<f32, BatteryError> { | 
		
	
		
			
				|  |  |  |  |         Err(BatteryError::NoBatteryMonitor) | 
		
	
		
			
				|  |  |  |  |     } | 
		
	
		
			
				|  |  |  |  |  | 
		
	
		
			
				|  |  |  |  |     fn remaining_milli_ampere_hour(&mut self) -> anyhow::Result<u16> { | 
		
	
		
			
				|  |  |  |  |         match self { | 
		
	
		
			
				|  |  |  |  |             BatteryMonitor::BQ34Z100G1 { battery_driver } => { | 
		
	
		
			
				|  |  |  |  |                 match battery_driver.remaining_capacity() { | 
		
	
		
			
				|  |  |  |  |                     OkStd(r) => anyhow::Ok(r), | 
		
	
		
			
				|  |  |  |  |                     Err(err) => bail!("Error reading remaining_milli_ampere_hour {:?}", err), | 
		
	
		
			
				|  |  |  |  |                 } | 
		
	
		
			
				|  |  |  |  |             } | 
		
	
		
			
				|  |  |  |  |             BatteryMonitor::WchI2cSlave { .. } => { | 
		
	
		
			
				|  |  |  |  |                 bail!("Not implemented") | 
		
	
		
			
				|  |  |  |  |             } | 
		
	
		
			
				|  |  |  |  |             &mut BatteryMonitor::Disabled {} => { | 
		
	
		
			
				|  |  |  |  |                 bail!("Battery monitor is disabled") | 
		
	
		
			
				|  |  |  |  |             } | 
		
	
		
			
				|  |  |  |  |         } | 
		
	
		
			
				|  |  |  |  |     } | 
		
	
		
			
				|  |  |  |  |     fn max_milli_ampere_hour(&mut self) -> anyhow::Result<u16> { | 
		
	
		
			
				|  |  |  |  |         match self { | 
		
	
		
			
				|  |  |  |  |             BatteryMonitor::BQ34Z100G1 { battery_driver } => { | 
		
	
		
			
				|  |  |  |  |                 match battery_driver.full_charge_capacity() { | 
		
	
		
			
				|  |  |  |  |                     OkStd(r) => anyhow::Ok(r), | 
		
	
		
			
				|  |  |  |  |                     Err(err) => bail!("Error reading max_milli_ampere_hour {:?}", err), | 
		
	
		
			
				|  |  |  |  |                 } | 
		
	
		
			
				|  |  |  |  |             } | 
		
	
		
			
				|  |  |  |  |             BatteryMonitor::WchI2cSlave { .. } => { | 
		
	
		
			
				|  |  |  |  |                 bail!("Not implemented") | 
		
	
		
			
				|  |  |  |  |             } | 
		
	
		
			
				|  |  |  |  |             &mut BatteryMonitor::Disabled {} => { | 
		
	
		
			
				|  |  |  |  |                 bail!("Battery monitor is disabled") | 
		
	
		
			
				|  |  |  |  |             } | 
		
	
		
			
				|  |  |  |  |         } | 
		
	
		
			
				|  |  |  |  |     } | 
		
	
		
			
				|  |  |  |  |     fn design_milli_ampere_hour(&mut self) -> anyhow::Result<u16> { | 
		
	
		
			
				|  |  |  |  |         match self { | 
		
	
		
			
				|  |  |  |  |             BatteryMonitor::BQ34Z100G1 { battery_driver } => { | 
		
	
		
			
				|  |  |  |  |                 match battery_driver.design_capacity() { | 
		
	
		
			
				|  |  |  |  |                     OkStd(r) => anyhow::Ok(r), | 
		
	
		
			
				|  |  |  |  |                     Err(err) => bail!("Error reading design_milli_ampere_hour {:?}", err), | 
		
	
		
			
				|  |  |  |  |                 } | 
		
	
		
			
				|  |  |  |  |             } | 
		
	
		
			
				|  |  |  |  |             BatteryMonitor::WchI2cSlave { .. } => { | 
		
	
		
			
				|  |  |  |  |                 bail!("Not implemented") | 
		
	
		
			
				|  |  |  |  |             } | 
		
	
		
			
				|  |  |  |  |             &mut BatteryMonitor::Disabled {} => { | 
		
	
		
			
				|  |  |  |  |                 bail!("Battery monitor is disabled") | 
		
	
		
			
				|  |  |  |  |             } | 
		
	
		
			
				|  |  |  |  |         } | 
		
	
		
			
				|  |  |  |  |     } | 
		
	
		
			
				|  |  |  |  |     fn voltage_milli_volt(&mut self) -> anyhow::Result<u16> { | 
		
	
		
			
				|  |  |  |  |         match self { | 
		
	
		
			
				|  |  |  |  |             BatteryMonitor::BQ34Z100G1 { battery_driver } => match battery_driver.voltage() { | 
		
	
		
			
				|  |  |  |  |                 OkStd(r) => anyhow::Ok(r), | 
		
	
		
			
				|  |  |  |  |                 Err(err) => bail!("Error reading voltage_milli_volt {:?}", err), | 
		
	
		
			
				|  |  |  |  |             }, | 
		
	
		
			
				|  |  |  |  |             BatteryMonitor::WchI2cSlave { .. } => { | 
		
	
		
			
				|  |  |  |  |                 bail!("Not implemented") | 
		
	
		
			
				|  |  |  |  |             } | 
		
	
		
			
				|  |  |  |  |             &mut BatteryMonitor::Disabled {} => { | 
		
	
		
			
				|  |  |  |  |                 bail!("Battery monitor is disabled") | 
		
	
		
			
				|  |  |  |  |             } | 
		
	
		
			
				|  |  |  |  |         } | 
		
	
		
			
				|  |  |  |  |     } | 
		
	
		
			
				|  |  |  |  |     fn average_current_milli_ampere(&mut self) -> anyhow::Result<i16> { | 
		
	
		
			
				|  |  |  |  |         match self { | 
		
	
		
			
				|  |  |  |  |             BatteryMonitor::BQ34Z100G1 { battery_driver } => { | 
		
	
		
			
				|  |  |  |  |                 match battery_driver.average_current() { | 
		
	
		
			
				|  |  |  |  |                     OkStd(r) => anyhow::Ok(r), | 
		
	
		
			
				|  |  |  |  |                     Err(err) => bail!("Error reading average_current_milli_ampere {:?}", err), | 
		
	
		
			
				|  |  |  |  |                 } | 
		
	
		
			
				|  |  |  |  |             } | 
		
	
		
			
				|  |  |  |  |             BatteryMonitor::WchI2cSlave { .. } => { | 
		
	
		
			
				|  |  |  |  |                 bail!("Not implemented") | 
		
	
		
			
				|  |  |  |  |             } | 
		
	
		
			
				|  |  |  |  |             &mut BatteryMonitor::Disabled {} => { | 
		
	
		
			
				|  |  |  |  |                 bail!("Battery monitor is disabled") | 
		
	
		
			
				|  |  |  |  |             } | 
		
	
		
			
				|  |  |  |  |         } | 
		
	
		
			
				|  |  |  |  |     } | 
		
	
		
			
				|  |  |  |  |     fn cycle_count(&mut self) -> anyhow::Result<u16> { | 
		
	
		
			
				|  |  |  |  |         match self { | 
		
	
		
			
				|  |  |  |  |             BatteryMonitor::BQ34Z100G1 { battery_driver } => match battery_driver.cycle_count() { | 
		
	
		
			
				|  |  |  |  |                 OkStd(r) => anyhow::Ok(r), | 
		
	
		
			
				|  |  |  |  |                 Err(err) => bail!("Error reading cycle_count {:?}", err), | 
		
	
		
			
				|  |  |  |  |             }, | 
		
	
		
			
				|  |  |  |  |             BatteryMonitor::WchI2cSlave { .. } => { | 
		
	
		
			
				|  |  |  |  |                 bail!("Not implemented") | 
		
	
		
			
				|  |  |  |  |             } | 
		
	
		
			
				|  |  |  |  |             &mut BatteryMonitor::Disabled {} => { | 
		
	
		
			
				|  |  |  |  |                 bail!("Battery monitor is disabled") | 
		
	
		
			
				|  |  |  |  |             } | 
		
	
		
			
				|  |  |  |  |         } | 
		
	
		
			
				|  |  |  |  |     } | 
		
	
		
			
				|  |  |  |  |     fn state_health_percent(&mut self) -> anyhow::Result<u8> { | 
		
	
		
			
				|  |  |  |  |         match self { | 
		
	
		
			
				|  |  |  |  |             BatteryMonitor::BQ34Z100G1 { battery_driver } => { | 
		
	
		
			
				|  |  |  |  |                 match battery_driver.state_of_health() { | 
		
	
		
			
				|  |  |  |  |                     OkStd(r) => anyhow::Ok(r as u8), | 
		
	
		
			
				|  |  |  |  |                     Err(err) => bail!("Error reading state_health_percent {:?}", err), | 
		
	
		
			
				|  |  |  |  |                 } | 
		
	
		
			
				|  |  |  |  |             } | 
		
	
		
			
				|  |  |  |  |             BatteryMonitor::WchI2cSlave { .. } => { | 
		
	
		
			
				|  |  |  |  |                 bail!("Not implemented") | 
		
	
		
			
				|  |  |  |  |             } | 
		
	
		
			
				|  |  |  |  |             &mut BatteryMonitor::Disabled {} => { | 
		
	
		
			
				|  |  |  |  |                 bail!("Battery monitor is disabled") | 
		
	
		
			
				|  |  |  |  |             } | 
		
	
		
			
				|  |  |  |  |         } | 
		
	
		
			
				|  |  |  |  |     } | 
		
	
		
			
				|  |  |  |  |     fn bat_temperature(&mut self) -> anyhow::Result<u16> { | 
		
	
		
			
				|  |  |  |  |         match self { | 
		
	
		
			
				|  |  |  |  |             BatteryMonitor::BQ34Z100G1 { battery_driver } => match battery_driver.temperature() { | 
		
	
		
			
				|  |  |  |  |                 OkStd(r) => anyhow::Ok(r), | 
		
	
		
			
				|  |  |  |  |                 Err(err) => bail!("Error reading bat_temperature {:?}", err), | 
		
	
		
			
				|  |  |  |  |             }, | 
		
	
		
			
				|  |  |  |  |             BatteryMonitor::WchI2cSlave { .. } => { | 
		
	
		
			
				|  |  |  |  |                 bail!("Not implemented") | 
		
	
		
			
				|  |  |  |  |             } | 
		
	
		
			
				|  |  |  |  |             &mut BatteryMonitor::Disabled {} => { | 
		
	
		
			
				|  |  |  |  |                 bail!("Battery monitor is disabled") | 
		
	
		
			
				|  |  |  |  |             } | 
		
	
		
			
				|  |  |  |  |         } | 
		
	
		
			
				|  |  |  |  |     fn remaining_milli_ampere_hour(&mut self) -> Result<u16, BatteryError> { | 
		
	
		
			
				|  |  |  |  |         Err(BatteryError::NoBatteryMonitor) | 
		
	
		
			
				|  |  |  |  |     } | 
		
	
		
			
				|  |  |  |  |  | 
		
	
		
			
				|  |  |  |  |     fn get_battery_state(&mut self) -> String { | 
		
	
		
			
				|  |  |  |  |         let bat = BatteryState { | 
		
	
		
			
				|  |  |  |  |             voltage_milli_volt: to_string(self.voltage_milli_volt()), | 
		
	
		
			
				|  |  |  |  |             current_milli_ampere: to_string(self.average_current_milli_ampere()), | 
		
	
		
			
				|  |  |  |  |             cycle_count: to_string(self.cycle_count()), | 
		
	
		
			
				|  |  |  |  |             design_milli_ampere: to_string(self.design_milli_ampere_hour()), | 
		
	
		
			
				|  |  |  |  |             remaining_milli_ampere: to_string(self.remaining_milli_ampere_hour()), | 
		
	
		
			
				|  |  |  |  |             state_of_charge: to_string(self.state_charge_percent()), | 
		
	
		
			
				|  |  |  |  |             state_of_health: to_string(self.state_health_percent()), | 
		
	
		
			
				|  |  |  |  |             temperature: to_string(self.bat_temperature()), | 
		
	
		
			
				|  |  |  |  |         }; | 
		
	
		
			
				|  |  |  |  |     fn max_milli_ampere_hour(&mut self) -> Result<u16, BatteryError> { | 
		
	
		
			
				|  |  |  |  |         Err(BatteryError::NoBatteryMonitor) | 
		
	
		
			
				|  |  |  |  |     } | 
		
	
		
			
				|  |  |  |  |  | 
		
	
		
			
				|  |  |  |  |         match serde_json::to_string(&bat) { | 
		
	
		
			
				|  |  |  |  |             Ok(state) => state, | 
		
	
		
			
				|  |  |  |  |             Err(err) => format!("{:?}", err).to_owned(), | 
		
	
		
			
				|  |  |  |  |         } | 
		
	
		
			
				|  |  |  |  |     fn design_milli_ampere_hour(&mut self) -> Result<u16, BatteryError> { | 
		
	
		
			
				|  |  |  |  |         Err(BatteryError::NoBatteryMonitor) | 
		
	
		
			
				|  |  |  |  |     } | 
		
	
		
			
				|  |  |  |  |  | 
		
	
		
			
				|  |  |  |  |     fn voltage_milli_volt(&mut self) -> Result<u16, BatteryError> { | 
		
	
		
			
				|  |  |  |  |         Err(BatteryError::NoBatteryMonitor) | 
		
	
		
			
				|  |  |  |  |     } | 
		
	
		
			
				|  |  |  |  |  | 
		
	
		
			
				|  |  |  |  |     fn average_current_milli_ampere(&mut self) -> Result<i16, BatteryError> { | 
		
	
		
			
				|  |  |  |  |         Err(BatteryError::NoBatteryMonitor) | 
		
	
		
			
				|  |  |  |  |     } | 
		
	
		
			
				|  |  |  |  |  | 
		
	
		
			
				|  |  |  |  |     fn cycle_count(&mut self) -> Result<u16, BatteryError> { | 
		
	
		
			
				|  |  |  |  |         Err(BatteryError::NoBatteryMonitor) | 
		
	
		
			
				|  |  |  |  |     } | 
		
	
		
			
				|  |  |  |  |  | 
		
	
		
			
				|  |  |  |  |     fn state_health_percent(&mut self) -> Result<u16, BatteryError> { | 
		
	
		
			
				|  |  |  |  |         Err(BatteryError::NoBatteryMonitor) | 
		
	
		
			
				|  |  |  |  |     } | 
		
	
		
			
				|  |  |  |  |  | 
		
	
		
			
				|  |  |  |  |     fn bat_temperature(&mut self) -> Result<u16, BatteryError> { | 
		
	
		
			
				|  |  |  |  |         Err(BatteryError::NoBatteryMonitor) | 
		
	
		
			
				|  |  |  |  |     } | 
		
	
		
			
				|  |  |  |  |  | 
		
	
		
			
				|  |  |  |  |     fn get_battery_state(&mut self) -> Result<BatteryState, BatteryError> { | 
		
	
		
			
				|  |  |  |  |         Ok(BatteryState::Unknown) | 
		
	
		
			
				|  |  |  |  |     } | 
		
	
		
			
				|  |  |  |  | } | 
		
	
		
			
				|  |  |  |  |  | 
		
	
		
			
				|  |  |  |  | //TODO implement this battery monitor kind once controller is complete | 
		
	
		
			
				|  |  |  |  | pub struct WchI2cSlave {} | 
		
	
		
			
				|  |  |  |  |  | 
		
	
		
			
				|  |  |  |  | pub struct BQ34Z100G1<'a> { | 
		
	
		
			
				|  |  |  |  |     pub battery_driver: Bq34z100g1Driver<MutexDevice<'a, I2cDriver<'a>>, Delay>, | 
		
	
		
			
				|  |  |  |  | } | 
		
	
		
			
				|  |  |  |  |  | 
		
	
		
			
				|  |  |  |  | impl BatteryInteraction for BQ34Z100G1<'_> { | 
		
	
		
			
				|  |  |  |  |     fn state_charge_percent(&mut self) -> Result<f32, BatteryError> { | 
		
	
		
			
				|  |  |  |  |         Ok(self.battery_driver.state_of_charge().map(f32::from)?) | 
		
	
		
			
				|  |  |  |  |     } | 
		
	
		
			
				|  |  |  |  |  | 
		
	
		
			
				|  |  |  |  |     fn remaining_milli_ampere_hour(&mut self) -> Result<u16, BatteryError> { | 
		
	
		
			
				|  |  |  |  |         Ok(self.battery_driver.remaining_capacity()?) | 
		
	
		
			
				|  |  |  |  |     } | 
		
	
		
			
				|  |  |  |  |  | 
		
	
		
			
				|  |  |  |  |     fn max_milli_ampere_hour(&mut self) -> Result<u16, BatteryError> { | 
		
	
		
			
				|  |  |  |  |         Ok(self.battery_driver.full_charge_capacity()?) | 
		
	
		
			
				|  |  |  |  |     } | 
		
	
		
			
				|  |  |  |  |  | 
		
	
		
			
				|  |  |  |  |     fn design_milli_ampere_hour(&mut self) -> Result<u16, BatteryError> { | 
		
	
		
			
				|  |  |  |  |         Ok(self.battery_driver.design_capacity()?) | 
		
	
		
			
				|  |  |  |  |     } | 
		
	
		
			
				|  |  |  |  |  | 
		
	
		
			
				|  |  |  |  |     fn voltage_milli_volt(&mut self) -> Result<u16, BatteryError> { | 
		
	
		
			
				|  |  |  |  |         Ok(self.battery_driver.voltage()?) | 
		
	
		
			
				|  |  |  |  |     } | 
		
	
		
			
				|  |  |  |  |  | 
		
	
		
			
				|  |  |  |  |     fn average_current_milli_ampere(&mut self) -> Result<i16, BatteryError> { | 
		
	
		
			
				|  |  |  |  |         Ok(self.battery_driver.average_current()?) | 
		
	
		
			
				|  |  |  |  |     } | 
		
	
		
			
				|  |  |  |  |  | 
		
	
		
			
				|  |  |  |  |     fn cycle_count(&mut self) -> Result<u16, BatteryError> { | 
		
	
		
			
				|  |  |  |  |         Ok(self.battery_driver.cycle_count()?) | 
		
	
		
			
				|  |  |  |  |     } | 
		
	
		
			
				|  |  |  |  |  | 
		
	
		
			
				|  |  |  |  |     fn state_health_percent(&mut self) -> Result<u16, BatteryError> { | 
		
	
		
			
				|  |  |  |  |         Ok(self.battery_driver.state_of_health()?) | 
		
	
		
			
				|  |  |  |  |     } | 
		
	
		
			
				|  |  |  |  |  | 
		
	
		
			
				|  |  |  |  |     fn bat_temperature(&mut self) -> Result<u16, BatteryError> { | 
		
	
		
			
				|  |  |  |  |         Ok(self.battery_driver.temperature()?) | 
		
	
		
			
				|  |  |  |  |     } | 
		
	
		
			
				|  |  |  |  |  | 
		
	
		
			
				|  |  |  |  |     fn get_battery_state(&mut self) -> Result<BatteryState, BatteryError> { | 
		
	
		
			
				|  |  |  |  |         Ok(BatteryState::Info(BatteryInfo { | 
		
	
		
			
				|  |  |  |  |             voltage_milli_volt: self.voltage_milli_volt()?, | 
		
	
		
			
				|  |  |  |  |             average_current_milli_ampere: self.average_current_milli_ampere()?, | 
		
	
		
			
				|  |  |  |  |             cycle_count: self.cycle_count()?, | 
		
	
		
			
				|  |  |  |  |             design_milli_ampere_hour: self.design_milli_ampere_hour()?, | 
		
	
		
			
				|  |  |  |  |             remaining_milli_ampere_hour: self.remaining_milli_ampere_hour()?, | 
		
	
		
			
				|  |  |  |  |             state_of_charge: self.state_charge_percent()?, | 
		
	
		
			
				|  |  |  |  |             state_of_health: self.state_health_percent()?, | 
		
	
		
			
				|  |  |  |  |             temperature: self.bat_temperature()?, | 
		
	
		
			
				|  |  |  |  |         })) | 
		
	
		
			
				|  |  |  |  |     } | 
		
	
		
			
				|  |  |  |  | } | 
		
	
		
			
				|  |  |  |  |  | 
		
	
	
		
			
				
					
					|  |  |  |   |