1 use crate::audio::buffer::BufferInfo; 2 use crate::audio::sealed::Sealed; 3 4 pub trait BufferLayout: Sized + Sealed { 5 fn index_of(info: &BufferInfo<Self>, channel: usize, frame: usize) -> usize; 6 } 7 8 #[derive(Eq, PartialEq, Copy, Clone, Debug)] 9 pub enum Deinterleaved {} 10 11 impl Sealed for Deinterleaved {} 12 13 impl BufferLayout for Deinterleaved { 14 #[inline] 15 fn index_of(info: &BufferInfo<Self>, channel: usize, frame: usize) -> usize { 16 (channel * info.frames()) + frame 17 } 18 } 19 20 #[derive(Eq, PartialEq, Copy, Clone, Debug)] 21 pub enum Interleaved {} 22 23 impl Sealed for Interleaved {} 24 25 impl BufferLayout for Interleaved { 26 #[inline] 27 fn index_of(info: &BufferInfo<Self>, channel: usize, frame: usize) -> usize { 28 (frame * info.channels()) + channel 29 } 30 } 31 32 #[cfg(test)] 33 #[inline(always)] 34 pub(crate) fn deinterleaved<T>(input: &[T], output: &mut [T], channels: usize) 35 where 36 T: Copy, 37 { 38 deinterleaved_by(input, output, channels, |sample| *sample) 39 } 40 41 /// De-interleaves an interleaved slice using a memory access pattern 42 /// that's optimized for efficient cached (i.e. sequential) reads. 43 pub(crate) fn deinterleaved_by<T, U, F>(input: &[T], output: &mut [U], channels: usize, f: F) 44 where 45 F: Fn(&T) -> U, 46 { 47 assert_eq!(input.len(), output.len()); 48 assert_eq!(input.len() % channels, 0); 49 50 let frames = input.len() / channels; 51 let mut interleaved_index = 0; 52 for frame in 0..frames { 53 let mut deinterleaved_index = frame; 54 for _channel in 0..channels { 55 output[deinterleaved_index] = f(&input[interleaved_index]); 56 interleaved_index += 1; 57 deinterleaved_index += frames; 58 } 59 } 60 } 61 62 #[cfg(test)] 63 #[inline(always)] 64 pub(crate) fn interleaved<T>(input: &[T], output: &mut [T], channels: usize) 65 where 66 T: Copy, 67 { 68 interleaved_by(input, output, channels, |sample| *sample) 69 } 70 71 /// Interleaves an de-interleaved slice using a memory access pattern 72 /// that's optimized for efficient cached (i.e. sequential) reads. 73 pub(crate) fn interleaved_by<T, U, F>(input: &[T], output: &mut [U], channels: usize, f: F) 74 where 75 F: Fn(&T) -> U, 76 { 77 assert_eq!(input.len(), output.len()); 78 assert_eq!(input.len() % channels, 0); 79 80 let frames = input.len() / channels; 81 let mut deinterleaved_index = 0; 82 for channel in 0..channels { 83 let mut interleaved_index = channel; 84 for _frame in 0..frames { 85 output[interleaved_index] = f(&input[deinterleaved_index]); 86 deinterleaved_index += 1; 87 interleaved_index += channels; 88 } 89 } 90 } 91 92 #[cfg(test)] 93 mod tests { 94 use super::*; 95 96 #[test] 97 fn interleaved_1_channel() { 98 let input: Vec<_> = vec![0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15]; 99 let mut output = vec![0; input.len()]; 100 let channels = 1; 101 102 interleaved(&input[..], &mut output[..], channels); 103 104 let actual = output; 105 let expected = vec![0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15]; 106 107 assert_eq!(actual, expected); 108 } 109 110 #[test] 111 fn deinterleaved_1_channel() { 112 let input: Vec<_> = vec![0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15]; 113 let mut output = vec![0; input.len()]; 114 let channels = 1; 115 116 deinterleaved(&input[..], &mut output[..], channels); 117 118 let actual = output; 119 let expected = vec![0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15]; 120 121 assert_eq!(actual, expected); 122 } 123 124 #[test] 125 fn interleaved_2_channel() { 126 let input: Vec<_> = vec![0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15]; 127 let mut output = vec![0; input.len()]; 128 let channels = 2; 129 130 interleaved(&input[..], &mut output[..], channels); 131 132 let actual = output; 133 let expected = vec![0, 8, 1, 9, 2, 10, 3, 11, 4, 12, 5, 13, 6, 14, 7, 15]; 134 135 assert_eq!(actual, expected); 136 } 137 138 #[test] 139 fn deinterleaved_2_channel() { 140 let input: Vec<_> = vec![0, 8, 1, 9, 2, 10, 3, 11, 4, 12, 5, 13, 6, 14, 7, 15]; 141 let mut output = vec![0; input.len()]; 142 let channels = 2; 143 144 deinterleaved(&input[..], &mut output[..], channels); 145 146 let actual = output; 147 let expected = vec![0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15]; 148 149 assert_eq!(actual, expected); 150 } 151 152 #[test] 153 fn interleaved_3_channel() { 154 let input: Vec<_> = vec![0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14]; 155 let mut output = vec![0; input.len()]; 156 let channels = 3; 157 158 interleaved(&input[..], &mut output[..], channels); 159 160 let actual = output; 161 let expected = vec![0, 5, 10, 1, 6, 11, 2, 7, 12, 3, 8, 13, 4, 9, 14]; 162 163 assert_eq!(actual, expected); 164 } 165 166 #[test] 167 fn deinterleaved_3_channel() { 168 let input: Vec<_> = vec![0, 5, 10, 1, 6, 11, 2, 7, 12, 3, 8, 13, 4, 9, 14]; 169 let mut output = vec![0; input.len()]; 170 let channels = 3; 171 172 deinterleaved(&input[..], &mut output[..], channels); 173 174 let actual = output; 175 let expected = vec![0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14]; 176 177 assert_eq!(actual, expected); 178 } 179 } 180