1use std;
2use std::rc::Rc;
3use std::ops::{Deref, DerefMut};
4use log;
5use num_derive::FromPrimitive;
6use crate::{ll, fmod_result, reverb3d, Channelmask, Error, Speakermode, System};
7
8pub mod parameter;
9
10pub use parameter::{Echo, Lowpass, MultibandEq, MultibandEqFilterType,
11 Sfxreverb};
12
13pub const GETPARAM_VALUESTR_LENGTH : u32 = ll::FMOD_DSP_GETPARAM_VALUESTR_LENGTH;
19pub const REVERB_MAXINSTANCES : u32 = ll::FMOD_REVERB_MAXINSTANCES;
25
26#[derive(Clone, Debug, PartialEq)]
27pub struct Dsp {
28 inner : Rc <Inner>,
29 #[allow(dead_code)]
30 system : System
31}
32
33#[derive(Clone, Debug, PartialEq)]
34pub struct DspRef {
35 pub (crate) dsp : Dsp
36}
37
38#[derive(PartialEq)]
39struct Inner {
40 raw : *mut ll::FMOD_DSP,
41 owned : bool
42}
43
44pub struct State {
46 pub instance : *const std::ffi::c_void,
47 pub plugindata : Vec <u8>,
48 pub channelmask : Channelmask,
49 pub source_speakermode : Speakermode,
50 pub sidechaindata : *const std::ffi::c_void,
51 pub sidechainchannels : i32,
52 pub functions : StateFunctions,
53 pub systemobject : i32
54}
55
56pub struct StateFunctions {
58 pub alloc : ll::FMOD_DSP_ALLOC_FUNC,
59 pub realloc : ll::FMOD_DSP_REALLOC_FUNC,
60 pub free : ll::FMOD_DSP_FREE_FUNC,
61 pub getsamplerate : ll::FMOD_DSP_GETSAMPLERATE_FUNC,
62 pub getblocksize : ll::FMOD_DSP_GETBLOCKSIZE_FUNC,
63 pub dft : StateDftFunctions,
64 pub pan : StatePanFunctions,
65 pub getspeakermode : ll::FMOD_DSP_GETSPEAKERMODE_FUNC,
66 pub getclock : ll::FMOD_DSP_GETCLOCK_FUNC,
67 pub getlistenerattributes : ll::FMOD_DSP_GETLISTENERATTRIBUTES_FUNC,
68 pub log : ll::FMOD_DSP_LOG_FUNC,
69 pub getuserdata : ll::FMOD_DSP_GETUSERDATA_FUNC
70}
71
72pub struct StateDftFunctions {
74 pub fftreal : ll::FMOD_DSP_DFT_FFTREAL_FUNC,
75 pub inversefftreal : ll::FMOD_DSP_DFT_IFFTREAL_FUNC,
76}
77
78pub struct StatePanFunctions {
80 pub summonomatrix : ll::FMOD_DSP_PAN_SUMMONOMATRIX_FUNC,
81 pub sumstereomatrix : ll::FMOD_DSP_PAN_SUMSTEREOMATRIX_FUNC,
82 pub sumsurroundmatrix : ll::FMOD_DSP_PAN_SUMSURROUNDMATRIX_FUNC,
83 pub summonotosurroundmatrix : ll::FMOD_DSP_PAN_SUMMONOTOSURROUNDMATRIX_FUNC,
84 pub sumstereotosurroundmatrix : ll::FMOD_DSP_PAN_SUMSTEREOTOSURROUNDMATRIX_FUNC,
85 pub getrolloffgain : ll::FMOD_DSP_PAN_GETROLLOFFGAIN_FUNC,
86}
87
88pub struct Description {
90 pub pluginsdkversion : u32,
91 pub name : String,
92 pub version : u32,
93 pub numinputbuffers : i32,
94 pub numoutputbuffers : i32,
95 pub numparameters : i32,
96 pub paramdesc : parameter::Desc,
97 pub userdata : Vec <u8>,
98 pub create : ll::FMOD_DSP_CREATE_CALLBACK,
99 pub release : ll::FMOD_DSP_RELEASE_CALLBACK,
100 pub reset : ll::FMOD_DSP_RESET_CALLBACK,
101 pub read : ll::FMOD_DSP_READ_CALLBACK,
102 pub process : ll::FMOD_DSP_PROCESS_CALLBACK,
103 pub setposition : ll::FMOD_DSP_SETPOSITION_CALLBACK,
104 pub setparameterfloat : ll::FMOD_DSP_SETPARAM_FLOAT_CALLBACK,
105 pub setparameterint : ll::FMOD_DSP_SETPARAM_INT_CALLBACK,
106 pub setparameterbool : ll::FMOD_DSP_SETPARAM_BOOL_CALLBACK,
107 pub setparameterdata : ll::FMOD_DSP_SETPARAM_DATA_CALLBACK,
108 pub getparameterfloat : ll::FMOD_DSP_GETPARAM_FLOAT_CALLBACK,
109 pub getparameterint : ll::FMOD_DSP_GETPARAM_INT_CALLBACK,
110 pub getparameterbool : ll::FMOD_DSP_GETPARAM_BOOL_CALLBACK,
111 pub getparameterdata : ll::FMOD_DSP_GETPARAM_DATA_CALLBACK,
112 pub shouldiprocess : ll::FMOD_DSP_SHOULDIPROCESS_CALLBACK,
113 pub sys_register : ll::FMOD_DSP_SYSTEM_REGISTER_CALLBACK,
114 pub sys_deregister : ll::FMOD_DSP_SYSTEM_DEREGISTER_CALLBACK,
115 pub sys_mix : ll::FMOD_DSP_SYSTEM_MIX_CALLBACK,
116 ll : ll::FMOD_DSP_DESCRIPTION
117}
118
119#[derive(Copy, Clone, Debug, Eq, PartialEq, FromPrimitive)]
120pub enum Type {
121 Unknown = ll::FMOD_DSP_TYPE_FMOD_DSP_TYPE_UNKNOWN as isize,
122 Mixer = ll::FMOD_DSP_TYPE_FMOD_DSP_TYPE_MIXER as isize,
123 Oscillator = ll::FMOD_DSP_TYPE_FMOD_DSP_TYPE_OSCILLATOR as isize,
124 Lowpass = ll::FMOD_DSP_TYPE_FMOD_DSP_TYPE_LOWPASS as isize,
125 Itlowpass = ll::FMOD_DSP_TYPE_FMOD_DSP_TYPE_ITLOWPASS as isize,
126 Highpass = ll::FMOD_DSP_TYPE_FMOD_DSP_TYPE_HIGHPASS as isize,
127 Echo = ll::FMOD_DSP_TYPE_FMOD_DSP_TYPE_ECHO as isize,
128 Fader = ll::FMOD_DSP_TYPE_FMOD_DSP_TYPE_FADER as isize,
129 Flange = ll::FMOD_DSP_TYPE_FMOD_DSP_TYPE_FLANGE as isize,
130 Distortion = ll::FMOD_DSP_TYPE_FMOD_DSP_TYPE_DISTORTION as isize,
131 Normalize = ll::FMOD_DSP_TYPE_FMOD_DSP_TYPE_NORMALIZE as isize,
132 Limiter = ll::FMOD_DSP_TYPE_FMOD_DSP_TYPE_LIMITER as isize,
133 Parameq = ll::FMOD_DSP_TYPE_FMOD_DSP_TYPE_PARAMEQ as isize,
134 Pitchshift = ll::FMOD_DSP_TYPE_FMOD_DSP_TYPE_PITCHSHIFT as isize,
135 Chorus = ll::FMOD_DSP_TYPE_FMOD_DSP_TYPE_CHORUS as isize,
136 Vstplugin = ll::FMOD_DSP_TYPE_FMOD_DSP_TYPE_VSTPLUGIN as isize,
137 Winampplugin = ll::FMOD_DSP_TYPE_FMOD_DSP_TYPE_WINAMPPLUGIN as isize,
138 Itecho = ll::FMOD_DSP_TYPE_FMOD_DSP_TYPE_ITECHO as isize,
139 Compressor = ll::FMOD_DSP_TYPE_FMOD_DSP_TYPE_COMPRESSOR as isize,
140 Sfxreverb = ll::FMOD_DSP_TYPE_FMOD_DSP_TYPE_SFXREVERB as isize,
141 LowpassSimple = ll::FMOD_DSP_TYPE_FMOD_DSP_TYPE_LOWPASS_SIMPLE as isize,
142 Delay = ll::FMOD_DSP_TYPE_FMOD_DSP_TYPE_DELAY as isize,
143 Tremolo = ll::FMOD_DSP_TYPE_FMOD_DSP_TYPE_TREMOLO as isize,
144 Ladspaplugin = ll::FMOD_DSP_TYPE_FMOD_DSP_TYPE_LADSPAPLUGIN as isize,
145 Send = ll::FMOD_DSP_TYPE_FMOD_DSP_TYPE_SEND as isize,
146 Return = ll::FMOD_DSP_TYPE_FMOD_DSP_TYPE_RETURN as isize,
147 HighpassSimple = ll::FMOD_DSP_TYPE_FMOD_DSP_TYPE_HIGHPASS_SIMPLE as isize,
148 Pan = ll::FMOD_DSP_TYPE_FMOD_DSP_TYPE_PAN as isize,
149 ThreeEq = ll::FMOD_DSP_TYPE_FMOD_DSP_TYPE_THREE_EQ as isize,
150 FFT = ll::FMOD_DSP_TYPE_FMOD_DSP_TYPE_FFT as isize,
151 LoudnessMeter = ll::FMOD_DSP_TYPE_FMOD_DSP_TYPE_LOUDNESS_METER as isize,
152 Envelopefollower = ll::FMOD_DSP_TYPE_FMOD_DSP_TYPE_ENVELOPEFOLLOWER as isize,
153 Convolutionreverb = ll::FMOD_DSP_TYPE_FMOD_DSP_TYPE_CONVOLUTIONREVERB as isize,
154 Channelmix = ll::FMOD_DSP_TYPE_FMOD_DSP_TYPE_CHANNELMIX as isize,
155 Transceiver = ll::FMOD_DSP_TYPE_FMOD_DSP_TYPE_TRANSCEIVER as isize,
156 Objectpan = ll::FMOD_DSP_TYPE_FMOD_DSP_TYPE_OBJECTPAN as isize,
157 MultibandEq = ll::FMOD_DSP_TYPE_FMOD_DSP_TYPE_MULTIBAND_EQ as isize,
158 MAX = ll::FMOD_DSP_TYPE_FMOD_DSP_TYPE_MAX as isize
159}
160
161impl Dsp {
162 #[inline]
163 pub fn from_raw_parts (raw : *mut ll::FMOD_DSP, owned : bool, system : System)
164 -> Self
165 {
166 let inner = Rc::new (Inner { raw, owned });
167 Dsp { inner, system }
168 }
169
170 #[inline]
171 pub (crate) fn raw (&self) -> *mut ll::FMOD_DSP {
172 (*self.inner).raw
173 }
174
175 #[inline]
176 pub (crate) fn raw_mut (&mut self) -> *mut ll::FMOD_DSP {
177 (*self.inner).raw
178 }
179
180 #[inline]
181 pub fn dsp_ref (&self) -> DspRef {
182 let dsp = {
183 let inner = Rc::new (Inner {
184 raw: self.raw(),
185 owned: false
186 });
187 let system = self.system.clone();
188 Dsp { inner, system }
189 };
190 DspRef { dsp }
191 }
192
193 #[inline]
194 pub fn get_active (&self) -> Result <bool, Error> {
195 let mut active = 0;
196 unsafe {
197 fmod_result!(ll::FMOD_DSP_GetActive (self.raw(), &mut active))?;
198 }
199 Ok (active != 0)
200 }
201
202 #[inline]
203 pub fn get_bypass (&self) -> Result <bool, Error> {
204 let mut bypass = 0;
205 unsafe {
206 fmod_result!(ll::FMOD_DSP_GetBypass (self.raw(), &mut bypass))?;
207 }
208 Ok (bypass != 0)
209 }
210
211 #[inline]
212 pub fn get_num_inputs (&self) -> Result <i32, Error> {
213 let mut numinputs = 0;
214 unsafe {
215 fmod_result!(ll::FMOD_DSP_GetNumInputs (self.raw(), &mut numinputs))?;
216 }
217 Ok (numinputs)
218 }
219
220 #[inline]
221 pub fn get_num_outputs (&self) -> Result <i32, Error> {
222 let mut numoutputs = 0;
223 unsafe {
224 fmod_result!(ll::FMOD_DSP_GetNumOutputs (self.raw(), &mut numoutputs))?;
225 }
226 Ok (numoutputs)
227 }
228
229 #[inline]
230 pub fn get_parameter_float (&mut self, index : i32)
231 -> Result <f32, Error>
232 {
233 let mut value = 0.0;
234 unsafe {
235 fmod_result!(
236 ll::FMOD_DSP_GetParameterFloat (
237 self.raw_mut(), index, &mut value, std::ptr::null_mut(), 0
238 )
239 )?;
240 }
241 Ok (value)
242 }
243
244 #[inline]
247 pub fn get_parameter_float_description (&mut self, index : i32)
248 -> Result <(f32, String), Error>
249 {
250 let mut value = 0.0;
251 const VALUESTRLEN : usize = 33;
254 let mut valuestr = vec![0; VALUESTRLEN as usize];
255 unsafe {
256 fmod_result!(
257 ll::FMOD_DSP_GetParameterFloat (
258 self.raw_mut(),
259 index,
260 &mut value,
261 valuestr.as_mut_ptr() as *mut i8,
262 VALUESTRLEN as i32
263 ))?;
264 }
265 valuestr.retain (|c| *c != 0x0);
266 let description = String::from_utf8 (valuestr).unwrap();
267 Ok ((value, description))
268 }
269
270 #[inline]
271 pub fn get_type (&self) -> Result <Type, Error> {
272 let mut type_ = 0;
273 unsafe {
274 fmod_result!(ll::FMOD_DSP_GetType (self.raw(), &mut type_))?;
275 }
276 Ok (Type::from_ll (type_))
277 }
278
279 #[inline]
280 pub fn set_active (&mut self, active : bool) -> Result <(), Error> {
281 unsafe {
282 fmod_result!(ll::FMOD_DSP_SetActive (self.raw_mut(), active as i32))
283 }
284 }
285
286 #[inline]
287 pub fn set_bypass (&mut self, bypass : bool) -> Result <(), Error> {
288 unsafe {
289 fmod_result!(ll::FMOD_DSP_SetBypass (self.raw_mut(), bypass as i32))
290 }
291 }
292
293 #[inline]
294 pub fn set_parameter_float (&mut self, index : i32, value : f32)
295 -> Result <(), Error>
296 {
297 unsafe {
298 fmod_result!(ll::FMOD_DSP_SetParameterFloat (self.raw_mut(), index, value))
299 }
300 }
301
302 #[inline]
303 pub fn set_parameter_int (&mut self, index : i32, value : i32)
304 -> Result <(), Error>
305 {
306 unsafe {
307 fmod_result!(ll::FMOD_DSP_SetParameterInt (self.raw_mut(), index, value))
308 }
309 }
310
311 pub fn get_parameters_sfxreverb (&mut self)
316 -> Result <(reverb3d::Properties, f32), Error>
317 {
318 assert_eq!(self.get_type().unwrap(), Type::Sfxreverb);
319 let properties = reverb3d::Properties {
320 decay_time: self.get_parameter_float (Sfxreverb::DecayTime as i32)?,
321 early_delay: self.get_parameter_float (Sfxreverb::EarlyDelay as i32)?,
322 late_delay: self.get_parameter_float (Sfxreverb::LateDelay as i32)?,
323 hf_reference: self.get_parameter_float (Sfxreverb::HfReference as i32)?,
324 hf_decay_ratio: self.get_parameter_float (Sfxreverb::HfDecayRatio as i32)?,
325 diffusion: self.get_parameter_float (Sfxreverb::Diffusion as i32)?,
326 density: self.get_parameter_float (Sfxreverb::Density as i32)?,
327 low_shelf_frequency:
328 self.get_parameter_float (Sfxreverb::LowShelfFrequency as i32)?,
329 low_shelf_gain: self.get_parameter_float (Sfxreverb::LowShelfGain as i32)?,
330 high_cut: self.get_parameter_float (Sfxreverb::HighCut as i32)?,
331 early_late_mix: self.get_parameter_float (Sfxreverb::EarlyLateMix as i32)?,
332 wet_level: self.get_parameter_float (Sfxreverb::WetLevel as i32)?
333 };
334 let dry_level = self.get_parameter_float (Sfxreverb::DryLevel as i32)?;
335 Ok ((properties, dry_level))
336 }
337
338 pub fn set_parameters_sfxreverb (&mut self,
343 properties : &reverb3d::Properties,
344 dry_level : f32
345 ) -> Result <(), Error> {
346 assert_eq!(self.get_type().unwrap(), Type::Sfxreverb);
347 self.set_parameter_float (
348 Sfxreverb::DecayTime as i32, properties.decay_time)?;
349 self.set_parameter_float (
350 Sfxreverb::EarlyDelay as i32, properties.early_delay)?;
351 self.set_parameter_float (
352 Sfxreverb::LateDelay as i32, properties.late_delay)?;
353 self.set_parameter_float (
354 Sfxreverb::HfReference as i32, properties.hf_reference)?;
355 self.set_parameter_float (
356 Sfxreverb::HfDecayRatio as i32, properties.hf_decay_ratio)?;
357 self.set_parameter_float (
358 Sfxreverb::Diffusion as i32, properties.diffusion)?;
359 self.set_parameter_float (
360 Sfxreverb::Density as i32, properties.density)?;
361 self.set_parameter_float (
362 Sfxreverb::LowShelfFrequency as i32, properties.low_shelf_frequency)?;
363 self.set_parameter_float (
364 Sfxreverb::LowShelfGain as i32, properties.low_shelf_gain)?;
365 self.set_parameter_float (
366 Sfxreverb::HighCut as i32, properties.high_cut)?;
367 self.set_parameter_float (
368 Sfxreverb::EarlyLateMix as i32, properties.early_late_mix)?;
369 self.set_parameter_float (
370 Sfxreverb::WetLevel as i32, properties.wet_level)?;
371 self.set_parameter_float (
372 Sfxreverb::DryLevel as i32, dry_level)?;
373 Ok (())
374 }
375}
376
377impl Deref for DspRef {
378 type Target = Dsp;
379 fn deref (&self) -> &Dsp {
380 &self.dsp
381 }
382}
383
384impl DerefMut for DspRef {
385 fn deref_mut (&mut self) -> &mut Dsp {
386 &mut self.dsp
387 }
388}
389
390impl Type {
391 pub fn from_ll (ll : ll::FMOD_DSP_TYPE) -> Self {
392 use num_traits::FromPrimitive;
393 Self::from_u32 (ll as u32).unwrap()
394 }
395}
396
397impl AsRef <ll::FMOD_DSP_DESCRIPTION> for Description {
398 fn as_ref (&self) -> &ll::FMOD_DSP_DESCRIPTION {
399 &self.ll
400 }
401}
402
403impl std::fmt::Debug for Inner {
404 fn fmt (&self, f : &mut std::fmt::Formatter) -> std::fmt::Result {
405 write!(f, "Inner {{ raw: {:p}, owned: {} }}", self.raw, self.owned)
406 }
407}
408
409impl Drop for Inner {
410 fn drop (&mut self) {
411 if self.owned {
412 unsafe {
413 let _ = fmod_result!(ll::FMOD_DSP_Release (self.raw)).map_err (
414 |err| log::error!("error releasing FMOD DSP@{:?}: {:?}", self, err));
415 }
416 }
417 }
418}