nbs/noteblocks/
instrument.rs1use crate::{header::Header, NbsError};
2
3pub const PIANO: Instrument = Instrument::Vanilla(0);
4pub const DOUBLE_BASS: Instrument = Instrument::Vanilla(1);
5pub const BASS_DRUM: Instrument = Instrument::Vanilla(2);
6pub const SNARE_DRUM: Instrument = Instrument::Vanilla(3);
7pub const CLICK: Instrument = Instrument::Vanilla(4);
8pub const GUITAR: Instrument = Instrument::Vanilla(5);
9pub const FLUTE: Instrument = Instrument::Vanilla(6);
10pub const BELL: Instrument = Instrument::Vanilla(7);
11pub const CHIME: Instrument = Instrument::Vanilla(8);
12pub const XYLOPHONE: Instrument = Instrument::Vanilla(9);
13pub const IRON_XYLOPHONE: Instrument = Instrument::Vanilla(10);
14pub const COW_BELL: Instrument = Instrument::Vanilla(11);
15pub const DIDGERIDOO: Instrument = Instrument::Vanilla(12);
16pub const BIT: Instrument = Instrument::Vanilla(13);
17pub const BANJO: Instrument = Instrument::Vanilla(14);
18pub const PLING: Instrument = Instrument::Vanilla(15);
19
20#[derive(Debug, Clone, Copy)]
21pub enum Instrument {
22 Vanilla(i8),
23 Custom(i8),
24}
25
26impl Instrument {
27 pub fn is_custom(&self) -> bool {
28 match self {
29 Instrument::Custom(_) => true,
30 _ => false,
31 }
32 }
33}
34
35impl Into<i8> for Instrument {
36 fn into(self) -> i8 {
37 match self {
38 Instrument::Custom(id) | Instrument::Vanilla(id) => id,
39 }
40 }
41}
42
43pub struct CustomInstruments {
44 instruments: Vec<CustomInstrumentInfo>,
45}
46
47impl CustomInstruments {
48 pub fn new() -> Self {
49 CustomInstruments {
50 instruments: Vec::new(),
51 }
52 }
53
54 pub fn decode<R>(reader: &mut R, header: &Header) -> Result<CustomInstruments, NbsError>
55 where
56 R: crate::ReadStringExt,
57 {
58 let instrument_count = reader.read_i8()?;
59 let mut custom_instruments = CustomInstruments {
60 instruments: Vec::with_capacity(instrument_count as usize),
61 };
62 for id in 0..instrument_count {
63 let instrument = Instrument::Custom(id + header.vannila_instrument_count()?);
65 let name = reader.read_string()?;
66 let file_name = reader.read_string()?;
67 let pitch = reader.read_i8()?;
68 let press_key = reader.read_i8()? == 1;
69 custom_instruments.instruments.push(CustomInstrumentInfo {
70 instrument,
71 name,
72 file_name,
73 pitch,
74 press_key,
75 })
76 }
77 Ok(custom_instruments)
78 }
79
80 pub fn encode<W>(&self, writer: &mut W) -> Result<(), NbsError>
81 where
82 W: crate::WriteStringExt,
83 {
84 writer.write_i8(self.instruments.len() as i8)?;
85 for instrument in &self.instruments {
86 writer.write_string(&instrument.name)?;
87 writer.write_string(&instrument.file_name)?;
88 writer.write_i8(instrument.pitch)?;
89 writer.write_i8(if instrument.press_key { 1 } else { 0 })?;
90 }
91 Ok(())
92 }
93}
94
95pub struct CustomInstrumentInfo {
96 pub instrument: Instrument,
97 pub name: String,
98 pub file_name: String,
99 pub pitch: i8,
100 pub press_key: bool,
101}