mirror of
https://codeberg.org/unspeaker/tek.git
synced 2026-04-03 21:00:44 +02:00
104 lines
3.2 KiB
Rust
104 lines
3.2 KiB
Rust
/// Plays [Voice]s from [Sample]s.
|
|
///
|
|
/// ```
|
|
/// let sampler = tek::Sampler::default();
|
|
/// ```
|
|
#[derive(Debug, Default)] pub struct Sampler {
|
|
/// Name of sampler.
|
|
pub name: Arc<str>,
|
|
/// Device color.
|
|
pub color: ItemTheme,
|
|
/// Sample currently being recorded.
|
|
pub recording: Option<(usize, Option<Arc<RwLock<Sample>>>)>,
|
|
/// Recording buffer.
|
|
pub buffer: Vec<Vec<f32>>,
|
|
/// Samples mapped to MIDI notes.
|
|
pub samples: SampleKit<128>,
|
|
/// Collection of currently playing instances of samples.
|
|
pub voices: Arc<RwLock<Vec<Voice>>>,
|
|
/// Samples that are not mapped to MIDI notes.
|
|
pub unmapped: Vec<Arc<RwLock<Sample>>>,
|
|
/// Sample currently being edited.
|
|
pub editing: Option<Arc<RwLock<Sample>>>,
|
|
/// How to mix the voices.
|
|
pub mixing_mode: MixingMode,
|
|
/// How to meter the inputs and outputs.
|
|
pub metering_mode: MeteringMode,
|
|
/// Fixed gain applied to all output.
|
|
pub output_gain: f32,
|
|
/// Currently active modal, if any.
|
|
pub mode: Option<SamplerMode>,
|
|
/// Size of rendered sampler.
|
|
pub size: Measure<Tui>,
|
|
/// Lowest note displayed.
|
|
pub note_lo: AtomicUsize,
|
|
/// Currently selected note.
|
|
pub note_pt: AtomicUsize,
|
|
/// Selected note as row/col.
|
|
pub cursor: (AtomicUsize, AtomicUsize),
|
|
/// Audio input meters.
|
|
#[cfg(feature = "meter")] pub input_meters: Vec<f32>,
|
|
/// Audio input ports. Samples are recorded from here.
|
|
#[cfg(feature = "port")] pub audio_ins: Vec<AudioInput>,
|
|
/// MIDI input port. Sampler are triggered from here.
|
|
#[cfg(feature = "port")] pub midi_in: Option<MidiInput>,
|
|
/// Audio output ports. Voices are played into here.
|
|
#[cfg(feature = "port")] pub audio_outs: Vec<AudioOutput>,
|
|
/// Audio output meters.
|
|
#[cfg(feature = "meter")] pub output_meters: Vec<f32>,
|
|
}
|
|
|
|
/// Collection of samples, one per slot, fixed number of slots.
|
|
///
|
|
/// History: Separated to cleanly implement [Default].
|
|
///
|
|
/// ```
|
|
/// let samples = tek::SampleKit([None, None, None, None]);
|
|
/// ```
|
|
#[derive(Debug)] pub struct SampleKit<const N: usize>(
|
|
pub [Option<Arc<RwLock<Sample>>>;N]
|
|
);
|
|
|
|
/// A sound cut.
|
|
///
|
|
/// ```
|
|
/// let sample = tek::Sample::default();
|
|
/// let sample = tek::Sample::new("test", 0, 0, vec![]);
|
|
/// ```
|
|
#[derive(Default, Debug)] pub struct Sample {
|
|
pub name: Arc<str>,
|
|
pub start: usize,
|
|
pub end: usize,
|
|
pub channels: Vec<Vec<f32>>,
|
|
pub rate: Option<usize>,
|
|
pub gain: f32,
|
|
pub color: ItemTheme,
|
|
}
|
|
|
|
/// A currently playing instance of a sample.
|
|
#[derive(Default, Debug, Clone)] pub struct Voice {
|
|
pub sample: Arc<RwLock<Sample>>,
|
|
pub after: usize,
|
|
pub position: usize,
|
|
pub velocity: f32,
|
|
}
|
|
|
|
#[derive(Default, Debug)] pub struct SampleAdd {
|
|
pub exited: bool,
|
|
pub dir: PathBuf,
|
|
pub subdirs: Vec<OsString>,
|
|
pub files: Vec<OsString>,
|
|
pub cursor: usize,
|
|
pub offset: usize,
|
|
pub sample: Arc<RwLock<Sample>>,
|
|
pub voices: Arc<RwLock<Vec<Voice>>>,
|
|
pub _search: Option<String>,
|
|
}
|
|
|
|
#[derive(Debug)] pub enum SamplerMode {
|
|
// Load sample from path
|
|
Import(usize, Browse),
|
|
}
|
|
|
|
pub type MidiSample =
|
|
(Option<u7>, Arc<RwLock<crate::Sample>>);
|