euphony_compiler/
buffer.rs1use crate::{
2 sample::{DefaultRate, DefaultSample, Rate as _},
3 CachedBuffer, Hash, Writer,
4};
5use euphony_buffer::{decode, symphonia};
6use euphony_node::BufferMap;
7use std::{collections::HashMap, fmt, ops, sync::Arc};
8
9#[derive(Debug)]
10pub struct Map {
11 buffers: HashMap<(u64, u64), Buffer>,
12}
13
14impl Map {
15 pub fn new(buffers: HashMap<(u64, u64), Buffer>) -> Self {
16 Self { buffers }
17 }
18}
19
20impl BufferMap for Map {
21 fn get(&self, id: u64, channel: u64) -> euphony_node::Buffer {
22 let buffer = self
23 .buffers
24 .get(&(id, channel))
25 .unwrap_or_else(|| panic!("missing buffer {} channel {}", id, channel));
26 euphony_node::Buffer {
27 samples: buffer,
28 hash: &buffer.hash,
29 }
30 }
31}
32
33pub struct Buffer {
34 samples: Arc<[f64]>,
35 hash: Hash,
36}
37
38impl Buffer {
39 fn open(cached: CachedBuffer) -> std::io::Result<Self> {
40 Ok(Self {
41 samples: cached.samples,
42 hash: cached.hash,
43 })
44 }
45
46 pub(crate) fn load<W: Writer>(
47 id: u64,
48 path: &str,
49 ext: &str,
50 cache: &W,
51 ) -> symphonia::core::errors::Result<Vec<((u64, u64), Self)>> {
52 let paths = cache.buffer::<_, symphonia::core::errors::Error>(
53 path,
54 DefaultRate::COUNT,
55 |reader| {
56 let mut stream = decode::reader(reader, ext)?;
57 let mut samples = decode::Samples::from_reader(&mut *stream)?;
58
59 samples
60 .resample(DefaultRate::COUNT as _)
61 .map_err(|e| std::io::Error::new(std::io::ErrorKind::Other, e))?;
62
63 Ok(samples.channels)
64 },
65 )?;
66
67 Ok(paths
68 .into_iter()
69 .enumerate()
70 .map(|(channel, cached)| {
71 let buf = Buffer::open(cached).unwrap();
72 ((id, channel as u64), buf)
73 })
74 .collect())
75 }
76}
77
78impl fmt::Debug for Buffer {
79 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
80 f.debug_struct("Buffer").field("len", &self.len()).finish()
81 }
82}
83
84impl ops::Deref for Buffer {
85 type Target = [DefaultSample];
86
87 #[inline]
88 fn deref(&self) -> &Self::Target {
89 self.samples.deref()
90 }
91}