use crate::error::MmResult;
use crate::types::{DeviceType, FocusDirection, ImageRoi, PropertyValue};
pub trait Device: Send {
fn name(&self) -> &str;
fn description(&self) -> &str;
fn initialize(&mut self) -> MmResult<()>;
fn shutdown(&mut self) -> MmResult<()>;
fn get_property(&self, name: &str) -> MmResult<PropertyValue>;
fn set_property(&mut self, name: &str, val: PropertyValue) -> MmResult<()>;
fn property_names(&self) -> Vec<String>;
fn has_property(&self, name: &str) -> bool;
fn is_property_read_only(&self, name: &str) -> bool;
fn device_type(&self) -> DeviceType;
fn busy(&self) -> bool;
}
pub trait Camera: Device {
fn snap_image(&mut self) -> MmResult<()>;
fn get_image_buffer(&self) -> MmResult<&[u8]>;
fn get_image_width(&self) -> u32;
fn get_image_height(&self) -> u32;
fn get_image_bytes_per_pixel(&self) -> u32;
fn get_bit_depth(&self) -> u32;
fn get_number_of_components(&self) -> u32;
fn get_number_of_channels(&self) -> u32;
fn get_exposure(&self) -> f64;
fn set_exposure(&mut self, exp_ms: f64);
fn get_binning(&self) -> i32;
fn set_binning(&mut self, bin: i32) -> MmResult<()>;
fn get_roi(&self) -> MmResult<ImageRoi>;
fn set_roi(&mut self, roi: ImageRoi) -> MmResult<()>;
fn clear_roi(&mut self) -> MmResult<()>;
fn start_sequence_acquisition(&mut self, count: i64, interval_ms: f64) -> MmResult<()>;
fn stop_sequence_acquisition(&mut self) -> MmResult<()>;
fn is_capturing(&self) -> bool;
}
pub trait Stage: Device {
fn set_position_um(&mut self, pos: f64) -> MmResult<()>;
fn get_position_um(&self) -> MmResult<f64>;
fn set_relative_position_um(&mut self, d: f64) -> MmResult<()>;
fn home(&mut self) -> MmResult<()>;
fn stop(&mut self) -> MmResult<()>;
fn get_limits(&self) -> MmResult<(f64, f64)>;
fn get_focus_direction(&self) -> FocusDirection;
fn is_continuous_focus_drive(&self) -> bool;
}
pub trait XYStage: Device {
fn set_xy_position_um(&mut self, x: f64, y: f64) -> MmResult<()>;
fn get_xy_position_um(&self) -> MmResult<(f64, f64)>;
fn set_relative_xy_position_um(&mut self, dx: f64, dy: f64) -> MmResult<()>;
fn home(&mut self) -> MmResult<()>;
fn stop(&mut self) -> MmResult<()>;
fn get_limits_um(&self) -> MmResult<(f64, f64, f64, f64)>;
fn get_step_size_um(&self) -> (f64, f64);
fn set_origin(&mut self) -> MmResult<()>;
}
pub trait Shutter: Device {
fn set_open(&mut self, open: bool) -> MmResult<()>;
fn get_open(&self) -> MmResult<bool>;
fn fire(&mut self, delta_t: f64) -> MmResult<()>;
}
pub trait StateDevice: Device {
fn set_position(&mut self, pos: u64) -> MmResult<()>;
fn get_position(&self) -> MmResult<u64>;
fn get_number_of_positions(&self) -> u64;
fn get_position_label(&self, pos: u64) -> MmResult<String>;
fn set_position_by_label(&mut self, label: &str) -> MmResult<()>;
fn set_position_label(&mut self, pos: u64, label: &str) -> MmResult<()>;
fn set_gate_open(&mut self, open: bool) -> MmResult<()>;
fn get_gate_open(&self) -> MmResult<bool>;
}
pub trait Hub: Device {
fn detect_installed_devices(&mut self) -> MmResult<Vec<String>>;
}
pub trait AutoFocus: Device {
fn set_continuous_focusing(&mut self, state: bool) -> MmResult<()>;
fn get_continuous_focusing(&self) -> MmResult<bool>;
fn is_continuous_focus_locked(&self) -> bool;
fn full_focus(&mut self) -> MmResult<()>;
fn incremental_focus(&mut self) -> MmResult<()>;
fn get_last_focus_score(&self) -> MmResult<f64>;
fn get_current_focus_score(&self) -> MmResult<f64>;
fn get_offset(&self) -> MmResult<f64>;
fn set_offset(&mut self, offset: f64) -> MmResult<()>;
}
pub trait ImageProcessor: Device {
fn process(&mut self, buffer: &mut [u8], width: u32, height: u32, byte_depth: u32) -> MmResult<()>;
}
pub trait SignalIO: Device {
fn set_gate_open(&mut self, open: bool) -> MmResult<()>;
fn get_gate_open(&self) -> MmResult<bool>;
fn set_signal(&mut self, volts: f64) -> MmResult<()>;
fn get_signal(&self) -> MmResult<f64>;
fn get_limits(&self) -> MmResult<(f64, f64)>;
}
pub trait MagnifierDevice: Device {
fn get_magnification(&self) -> MmResult<f64>;
}
pub trait Slm: Device {
fn set_image(&mut self, pixels: &[u8]) -> MmResult<()>;
fn display_image(&mut self) -> MmResult<()>;
fn set_exposure(&mut self, exp_ms: f64) -> MmResult<()>;
fn get_exposure(&self) -> MmResult<f64>;
fn get_width(&self) -> u32;
fn get_height(&self) -> u32;
fn get_number_of_components(&self) -> u32;
fn get_bytes_per_pixel(&self) -> u32;
}
pub trait Galvo: Device {
fn set_position(&mut self, x: f64, y: f64) -> MmResult<()>;
fn get_position(&self) -> MmResult<(f64, f64)>;
fn set_illumination_state(&mut self, on: bool) -> MmResult<()>;
fn get_x_range(&self) -> MmResult<(f64, f64)>;
fn get_y_range(&self) -> MmResult<(f64, f64)>;
}
pub trait Generic: Device {}
pub trait SerialPort: Device {
fn send_command(&mut self, command: &str, terminator: &str) -> MmResult<()>;
fn get_answer(&mut self, max_chars: usize, terminator: &str) -> MmResult<String>;
fn write_raw(&mut self, buf: &[u8]) -> MmResult<()>;
fn read_raw(&mut self, buf: &mut [u8]) -> MmResult<usize>;
fn purge(&mut self) -> MmResult<()>;
}
pub trait PressurePump: Device {
fn set_pressure(&mut self, pressure: f64) -> MmResult<()>;
fn get_pressure(&self) -> MmResult<f64>;
fn start(&mut self) -> MmResult<()>;
fn stop(&mut self) -> MmResult<()>;
}
pub trait VolumetricPump: Device {
fn set_volume_ul(&mut self, volume: f64) -> MmResult<()>;
fn get_volume_ul(&self) -> MmResult<f64>;
fn set_flow_rate(&mut self, rate_ul_per_s: f64) -> MmResult<()>;
fn get_flow_rate(&self) -> MmResult<f64>;
fn start(&mut self) -> MmResult<()>;
fn stop(&mut self) -> MmResult<()>;
fn is_running(&self) -> bool;
}
pub enum AnyDevice {
Camera(Box<dyn Camera>),
Stage(Box<dyn Stage>),
XYStage(Box<dyn XYStage>),
Shutter(Box<dyn Shutter>),
StateDevice(Box<dyn StateDevice>),
Hub(Box<dyn Hub>),
AutoFocus(Box<dyn AutoFocus>),
ImageProcessor(Box<dyn ImageProcessor>),
SignalIO(Box<dyn SignalIO>),
MagnifierDevice(Box<dyn MagnifierDevice>),
Slm(Box<dyn Slm>),
Galvo(Box<dyn Galvo>),
Generic(Box<dyn Generic>),
SerialPort(Box<dyn SerialPort>),
PressurePump(Box<dyn PressurePump>),
VolumetricPump(Box<dyn VolumetricPump>),
}
impl AnyDevice {
pub fn as_device(&self) -> &dyn Device {
match self {
AnyDevice::Camera(d) => d.as_ref(),
AnyDevice::Stage(d) => d.as_ref(),
AnyDevice::XYStage(d) => d.as_ref(),
AnyDevice::Shutter(d) => d.as_ref(),
AnyDevice::StateDevice(d) => d.as_ref(),
AnyDevice::Hub(d) => d.as_ref(),
AnyDevice::AutoFocus(d) => d.as_ref(),
AnyDevice::ImageProcessor(d) => d.as_ref(),
AnyDevice::SignalIO(d) => d.as_ref(),
AnyDevice::MagnifierDevice(d) => d.as_ref(),
AnyDevice::Slm(d) => d.as_ref(),
AnyDevice::Galvo(d) => d.as_ref(),
AnyDevice::Generic(d) => d.as_ref(),
AnyDevice::SerialPort(d) => d.as_ref(),
AnyDevice::PressurePump(d) => d.as_ref(),
AnyDevice::VolumetricPump(d) => d.as_ref(),
}
}
pub fn as_device_mut(&mut self) -> &mut dyn Device {
match self {
AnyDevice::Camera(d) => d.as_mut(),
AnyDevice::Stage(d) => d.as_mut(),
AnyDevice::XYStage(d) => d.as_mut(),
AnyDevice::Shutter(d) => d.as_mut(),
AnyDevice::StateDevice(d) => d.as_mut(),
AnyDevice::Hub(d) => d.as_mut(),
AnyDevice::AutoFocus(d) => d.as_mut(),
AnyDevice::ImageProcessor(d) => d.as_mut(),
AnyDevice::SignalIO(d) => d.as_mut(),
AnyDevice::MagnifierDevice(d) => d.as_mut(),
AnyDevice::Slm(d) => d.as_mut(),
AnyDevice::Galvo(d) => d.as_mut(),
AnyDevice::Generic(d) => d.as_mut(),
AnyDevice::SerialPort(d) => d.as_mut(),
AnyDevice::PressurePump(d) => d.as_mut(),
AnyDevice::VolumetricPump(d) => d.as_mut(),
}
}
pub fn as_camera(&self) -> Option<&dyn Camera> {
if let AnyDevice::Camera(d) = self { Some(d.as_ref()) } else { None }
}
pub fn as_camera_mut(&mut self) -> Option<&mut dyn Camera> {
if let AnyDevice::Camera(d) = self { Some(d.as_mut()) } else { None }
}
pub fn as_stage(&self) -> Option<&dyn Stage> {
if let AnyDevice::Stage(d) = self { Some(d.as_ref()) } else { None }
}
pub fn as_stage_mut(&mut self) -> Option<&mut dyn Stage> {
if let AnyDevice::Stage(d) = self { Some(d.as_mut()) } else { None }
}
pub fn as_xystage(&self) -> Option<&dyn XYStage> {
if let AnyDevice::XYStage(d) = self { Some(d.as_ref()) } else { None }
}
pub fn as_xystage_mut(&mut self) -> Option<&mut dyn XYStage> {
if let AnyDevice::XYStage(d) = self { Some(d.as_mut()) } else { None }
}
pub fn as_shutter(&self) -> Option<&dyn Shutter> {
if let AnyDevice::Shutter(d) = self { Some(d.as_ref()) } else { None }
}
pub fn as_shutter_mut(&mut self) -> Option<&mut dyn Shutter> {
if let AnyDevice::Shutter(d) = self { Some(d.as_mut()) } else { None }
}
pub fn as_state_device(&self) -> Option<&dyn StateDevice> {
if let AnyDevice::StateDevice(d) = self { Some(d.as_ref()) } else { None }
}
pub fn as_state_device_mut(&mut self) -> Option<&mut dyn StateDevice> {
if let AnyDevice::StateDevice(d) = self { Some(d.as_mut()) } else { None }
}
}
#[derive(Debug, Clone)]
pub struct DeviceInfo {
pub name: &'static str,
pub description: &'static str,
pub device_type: DeviceType,
}
pub trait AdapterModule: Send + Sync {
fn module_name(&self) -> &'static str;
fn devices(&self) -> &'static [DeviceInfo];
fn create_device(&self, name: &str) -> Option<AnyDevice>;
}