audio_processor_analysis/transient_detection/stft/
markers.rs

1// Augmented Audio: Audio libraries and applications
2// Copyright (c) 2022 Pedro Tacla Yamada
3//
4// The MIT License (MIT)
5//
6// Permission is hereby granted, free of charge, to any person obtaining a copy
7// of this software and associated documentation files (the "Software"), to deal
8// in the Software without restriction, including without limitation the rights
9// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
10// copies of the Software, and to permit persons to whom the Software is
11// furnished to do so, subject to the following conditions:
12//
13// The above copyright notice and this permission notice shall be included in
14// all copies or substantial portions of the Software.
15//
16// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
17// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
18// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
19// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
20// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
21// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
22// THE SOFTWARE.
23use audio_processor_traits::{AudioBuffer, AudioProcessorSettings};
24
25use super::{find_transients, IterativeTransientDetectionParams};
26
27#[derive(Clone, Debug)]
28pub struct AudioFileMarker {
29    pub position_samples: usize,
30}
31
32/// Helper for extracting vector of transient markers from buffer
33pub fn build_markers(
34    settings: &AudioProcessorSettings,
35    audio_file_buffer: &mut [f32],
36    params: IterativeTransientDetectionParams,
37    gate: f32,
38) -> Vec<AudioFileMarker> {
39    let transients = find_transients(
40        params,
41        &mut AudioBuffer::from_interleaved(1, audio_file_buffer),
42    );
43    let mut peak_detector = crate::peak_detector::PeakDetector::default();
44    let attack_mult = crate::peak_detector::calculate_multiplier(settings.sample_rate, 0.1);
45    let release_mult = crate::peak_detector::calculate_multiplier(settings.sample_rate, 15.0);
46    let transients: Vec<f32> = transients
47        .iter()
48        .map(|f| {
49            peak_detector.accept_frame(attack_mult, release_mult, &[*f]);
50            peak_detector.value()
51        })
52        .collect();
53
54    let markers_from_transients = {
55        let mut markers = vec![];
56        let mut inside_transient = false;
57        for (index, sample) in transients.iter().cloned().enumerate() {
58            if sample >= gate && !inside_transient {
59                inside_transient = true;
60                markers.push(index);
61            } else if sample < gate {
62                inside_transient = false;
63            }
64        }
65        markers
66    };
67
68    markers_from_transients
69        .into_iter()
70        .map(|position_samples| AudioFileMarker { position_samples })
71        .collect()
72}