1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61
use std::collections::HashMap;
use std::fmt::Debug;
use crate::sfz::{Opcode, OpcodeMap};
/// A Region is the basic component of an instrument.
/// An instrument is defined by one or more regions.
///
/// A region starts with the <region> header, and finishes with
/// the next <region> header, <group> header, or the end of the file.
///
/// Following the <region> header one or more opcodes can be defined.
/// The opcodes are special keywords which instruct the player on what,
/// when and how to play a sample.
///
/// Opcodes within a region can appear in any order, and they have to be
/// separated by one or more spaces or tabulation controls.
/// Opcodes can appear in separated lines within a region.
///
/// All Input Controls defined in a region act using the AND boolean operator.
/// Consequently, all conditions must be matched for the region to play.
///
#[derive(Clone, Debug, Default)]
pub struct Region {
/// The opcodes of this group are applied and will override the defaults.
pub group: Option<usize>,
/// This list of opcodes will override both the default and inherited opcodes.
pub opcodes: OpcodeMap,
}
impl Region {
/// New region.
pub fn new() -> Self {
Self::default()
}
/// New region with some group.
// FIXME (add group at posteriori)
pub fn with_group(group: usize) -> Self {
Self {
group: Some(group),
opcodes: HashMap::new(),
}
}
/// Add an opcode to this Region
pub fn add_opcode(&mut self, opcode: &Opcode) {
self.opcodes.insert(opcode.str_name(), opcode.clone());
}
/// Set the group of this Region
pub fn set_group(&mut self, group: Option<usize>) {
self.group = group;
}
/// Get the group of this Region
pub fn group(&self) -> Option<usize> {
self.group
}
}