lasprs 0.14.2

Library for Acoustic Signal Processing (Rust edition, with optional Python bindings via pyo3)
//! All sources for a signal generator. Sine waves, sweeps, noise, etc.
use super::*;
use super::{
    noise::{ColoredNoise, WhiteNoise},
    silence::Silence,
    sine::Sine,
    sweep::Sweep,
};
use crate::*;
use rand::prelude::*;
use snafu::prelude::*;
use std::fmt::Debug;
use std::ops::{Deref, DerefMut};

type Result<T> = std::result::Result<T, SiggenError>;

/// Signal source for a signal generator. A signal source is capable of creating
/// new signal data. All of these implement SourceImpl.
#[enum_dispatch::enum_dispatch(SourceImpl)]
#[derive(Clone, Debug)]
pub enum Source {
    Sine(Sine),
    Silence(Silence),
    WhiteNoise(WhiteNoise),
    Sweep(Sweep),
    PinkNoise(ColoredNoise),
}

/// Source for the signal generator. Implementations are sine waves, sweeps, noise.
#[enum_dispatch::enum_dispatch]
pub trait SourceImpl: Send + Sync + Debug {
    /// Generate the 'pure' source signal. Output is placed inside the `sig` argument.
    fn genSignal_unscaled(&mut self, sig: &mut dyn ExactSizeIterator<Item = &mut Flt>);

    // Return the sampling frequency for which the source is configured in Hz
    fn fs(&self) -> StrictlyPositive;
}

impl Source {
    /// Create a new signal source from a descriptor, and sampling frequency. If
    /// the sampling frequency is incompatible with the source descriptor, an
    /// error is returned.
    ///
    /// # Args
    /// * `srcdesc`: The source descriptor.
    /// * `fs`: The sampling frequency in Hz.
    pub fn new(srcdesc: &SourceDescriptor, fs: StrictlyPositive) -> Result<Self> {
        match srcdesc {
            SourceDescriptor::Sine { frequency } => Ok(Sine::new(*frequency, fs)?.into()),
            SourceDescriptor::Silence {} => Ok(Silence::new(fs).into()),
            SourceDescriptor::WhiteNoise { interrupt_time } => {
                Ok(WhiteNoise::new(fs, *interrupt_time).into())
            }
            SourceDescriptor::PinkNoise {
                interrupt_time,
                rolloffPoint,
            } => Ok(ColoredNoise::newPinkNoise(fs, *rolloffPoint, *interrupt_time)?.into()),
            SourceDescriptor::Sweep { settings: params } => {
                Ok(Sweep::new(params.clone(), fs)?.into())
            }
        }
    }
}