use bytes::Bytes;
use std::time::Duration;
#[derive(Clone, Debug, PartialEq, Eq, Hash)]
pub struct DeviceId(pub String);
#[derive(Clone, Copy, Debug, PartialEq, Eq, Hash)]
#[non_exhaustive]
pub enum Position {
Unspecified,
Front,
Back,
External,
}
#[derive(Clone, Copy, Debug, PartialEq, Eq, Hash)]
#[non_exhaustive]
pub enum Transport {
BuiltIn,
Usb,
Virtual,
Network,
Other,
}
#[derive(Clone, Debug)]
pub struct Credentials {
pub username: String,
pub password: String,
}
#[derive(Clone, Debug)]
#[non_exhaustive]
pub struct Device {
pub id: DeviceId,
pub name: String,
pub position: Position,
pub transport: Transport,
}
#[derive(Clone, Copy, Debug, PartialEq, Eq, Hash)]
pub struct Resolution {
pub width: u32,
pub height: u32,
}
#[derive(Clone, Copy, Debug, PartialEq, Eq, Hash)]
#[non_exhaustive]
pub enum PixelFormat {
Bgra8,
Rgb8,
Rgba8,
Yuyv,
Nv12,
Mjpeg,
}
#[derive(Clone, Copy, Debug, PartialEq)]
#[non_exhaustive]
pub struct FramerateRange {
pub min: f64,
pub max: f64,
}
#[derive(Clone, Debug)]
#[non_exhaustive]
pub struct FormatDescriptor {
pub resolution: Resolution,
pub framerate_range: FramerateRange,
pub pixel_format: PixelFormat,
}
#[derive(Clone, Debug)]
#[non_exhaustive]
pub struct Capabilities {
pub formats: Vec<FormatDescriptor>,
}
#[derive(Clone, Copy, Debug, PartialEq)]
pub struct StreamConfig {
pub resolution: Resolution,
pub framerate: u32,
pub pixel_format: PixelFormat,
}
#[derive(Clone, Copy, Debug, PartialEq, Eq, Hash)]
#[non_exhaustive]
pub enum FrameQuality {
Intact,
Recovering,
}
#[derive(Clone, Debug)]
#[non_exhaustive]
pub struct Frame {
pub width: u32,
pub height: u32,
pub stride: u32,
pub timestamp: Duration,
pub pixel_format: PixelFormat,
pub quality: FrameQuality,
pub plane_primary: Bytes,
pub plane_secondary: Bytes,
}
#[cfg(feature = "analysis")]
#[derive(Clone, Copy, Debug, PartialEq, Eq, Hash)]
pub struct Rect {
pub x: u32,
pub y: u32,
pub width: u32,
pub height: u32,
}
#[derive(Clone, Debug)]
#[non_exhaustive]
pub enum DeviceEvent {
Added(Device),
Removed(DeviceId),
}
#[cfg(feature = "controls")]
#[derive(Copy, Clone, Debug, PartialEq, Eq, Hash)]
#[non_exhaustive]
pub enum PowerLineFrequency {
Disabled,
Hz50,
Hz60,
Auto,
}
#[cfg(feature = "controls")]
#[derive(Clone, Debug, Default, PartialEq)]
pub struct Controls {
pub focus: Option<f32>,
pub auto_focus: Option<bool>,
pub exposure: Option<f32>,
pub auto_exposure: Option<bool>,
pub white_balance_temperature: Option<f32>,
pub auto_white_balance: Option<bool>,
pub brightness: Option<f32>,
pub contrast: Option<f32>,
pub saturation: Option<f32>,
pub sharpness: Option<f32>,
pub gain: Option<f32>,
pub backlight_compensation: Option<f32>,
pub power_line_frequency: Option<PowerLineFrequency>,
pub pan: Option<f32>,
pub tilt: Option<f32>,
pub zoom: Option<f32>,
}
#[cfg(feature = "controls")]
#[derive(Copy, Clone, Debug, PartialEq)]
#[non_exhaustive]
pub struct ControlRange {
pub min: f32,
pub max: f32,
pub step: f32,
pub default: f32,
}
#[cfg(feature = "controls")]
#[derive(Copy, Clone, Debug, PartialEq, Eq, Hash)]
#[non_exhaustive]
pub struct PowerLineFrequencyCapability {
pub hz50: bool,
pub hz60: bool,
pub disabled: bool,
pub auto: bool,
pub default: PowerLineFrequency,
}
#[cfg(feature = "controls")]
#[derive(Copy, Clone, Debug, PartialEq, Eq, Hash)]
#[non_exhaustive]
pub enum ControlKind {
Focus,
AutoFocus,
Exposure,
AutoExposure,
WhiteBalanceTemperature,
AutoWhiteBalance,
Brightness,
Contrast,
Saturation,
Sharpness,
Gain,
BacklightCompensation,
PowerLineFrequency,
Pan,
Tilt,
Zoom,
}
#[cfg(feature = "controls")]
impl ControlKind {
pub const ALL: [ControlKind; 16] = [
ControlKind::Focus,
ControlKind::AutoFocus,
ControlKind::Exposure,
ControlKind::AutoExposure,
ControlKind::WhiteBalanceTemperature,
ControlKind::AutoWhiteBalance,
ControlKind::Brightness,
ControlKind::Contrast,
ControlKind::Saturation,
ControlKind::Sharpness,
ControlKind::Gain,
ControlKind::BacklightCompensation,
ControlKind::PowerLineFrequency,
ControlKind::Pan,
ControlKind::Tilt,
ControlKind::Zoom,
];
pub fn label(&self) -> &'static str {
match self {
ControlKind::Focus => "focus",
ControlKind::AutoFocus => "auto_focus",
ControlKind::Exposure => "exposure",
ControlKind::AutoExposure => "auto_exposure",
ControlKind::WhiteBalanceTemperature => "white_balance_temperature",
ControlKind::AutoWhiteBalance => "auto_white_balance",
ControlKind::Brightness => "brightness",
ControlKind::Contrast => "contrast",
ControlKind::Saturation => "saturation",
ControlKind::Sharpness => "sharpness",
ControlKind::Gain => "gain",
ControlKind::BacklightCompensation => "backlight_compensation",
ControlKind::PowerLineFrequency => "power_line_frequency",
ControlKind::Pan => "pan",
ControlKind::Tilt => "tilt",
ControlKind::Zoom => "zoom",
}
}
pub fn caveat(&self) -> Option<&'static str> {
#[cfg(target_os = "macos")]
{
match self {
ControlKind::Brightness
| ControlKind::Contrast
| ControlKind::Saturation
| ControlKind::Sharpness
| ControlKind::BacklightCompensation => Some(
"macOS: AVFoundation doesn't expose per-channel image-processing controls. \
Apply CPU/GPU post-processing (shaders, color matrices) over the Frame \
bytes in your app. The library is capture-only.",
),
ControlKind::PowerLineFrequency => {
Some("macOS: AVFoundation doesn't expose AC mains frequency filtering.")
}
ControlKind::Pan | ControlKind::Tilt => Some(
"macOS: AVFoundation doesn't expose pan/tilt controls for built-in or UVC cameras.",
),
ControlKind::Focus
| ControlKind::AutoFocus
| ControlKind::Exposure
| ControlKind::AutoExposure
| ControlKind::WhiteBalanceTemperature
| ControlKind::AutoWhiteBalance
| ControlKind::Gain
| ControlKind::Zoom => None,
}
}
#[cfg(not(target_os = "macos"))]
{
None
}
}
}
#[cfg(feature = "controls")]
#[derive(Clone, Debug, Default, PartialEq)]
#[non_exhaustive]
pub struct ControlCapabilities {
pub focus: Option<ControlRange>,
pub auto_focus: Option<bool>,
pub exposure: Option<ControlRange>,
pub auto_exposure: Option<bool>,
pub white_balance_temperature: Option<ControlRange>,
pub auto_white_balance: Option<bool>,
pub brightness: Option<ControlRange>,
pub contrast: Option<ControlRange>,
pub saturation: Option<ControlRange>,
pub sharpness: Option<ControlRange>,
pub gain: Option<ControlRange>,
pub backlight_compensation: Option<ControlRange>,
pub power_line_frequency: Option<PowerLineFrequencyCapability>,
pub pan: Option<ControlRange>,
pub tilt: Option<ControlRange>,
pub zoom: Option<ControlRange>,
}