use std::sync::{
atomic::{AtomicBool, Ordering},
Arc,
};
use device::{init_devices, Class, Device, Devices};
use stream::PwInitGuard;
use crate::{traits::HostTrait, Error, ErrorKind};
mod device;
mod stream;
mod utils;
pub struct Host {
_pw: PwInitGuard,
devices: Vec<Device>,
connect_automatically: Arc<AtomicBool>,
}
impl Host {
pub fn new() -> Result<Self, Error> {
let _pw = PwInitGuard::new();
let connect_automatically = Arc::new(AtomicBool::new(true));
let devices = init_devices(connect_automatically.clone()).ok_or_else(|| {
Error::with_message(ErrorKind::HostUnavailable, "PipeWire is not available")
})?;
Ok(Self {
_pw,
devices,
connect_automatically,
})
}
pub fn set_connect_automatically(&mut self, connect: bool) {
self.connect_automatically.store(connect, Ordering::Relaxed);
}
}
impl HostTrait for Host {
type Devices = Devices;
type Device = Device;
fn is_available() -> bool {
utils::find_socket_path().is_some()
}
fn devices(&self) -> Result<Self::Devices, Error> {
Ok(self.devices.clone().into_iter())
}
fn default_input_device(&self) -> Option<Self::Device> {
self.devices
.iter()
.find(|device| matches!(device.class(), Class::DefaultInput))
.cloned()
}
fn default_output_device(&self) -> Option<Self::Device> {
self.devices
.iter()
.find(|device| matches!(device.class(), Class::DefaultOutput))
.cloned()
}
}