/[svn]/linuxsampler/trunk/src/engines/sfz/SfzSignalUnitRack.cpp
ViewVC logotype

Annotation of /linuxsampler/trunk/src/engines/sfz/SfzSignalUnitRack.cpp

Parent Directory Parent Directory | Revision Log Revision Log


Revision 2296 - (hide annotations) (download)
Thu Dec 8 20:03:47 2011 UTC (12 years, 4 months ago) by iliev
File size: 48015 byte(s)
* fixed crash when trying to create an effect instance with controls
  which min and/or max values depend on the sample rate
* experimental support for per voice equalization (work in progress)
* sfz engine: implemented opcodes eq1_freq, eq2_freq, eq3_freq,
  eq1_freqccN, eq2_freqccN, eq3_freqccN, eq1_bw, eq2_bw, eq3_bw,
  eq1_bwccN, eq2_bwccN, eq3_bwccN, eq1_gain, eq2_gain, eq3_gain,
  eq1_gainccN, eq2_gainccN, eq3_gainccN

1 iliev 2218 /***************************************************************************
2     * *
3     * LinuxSampler - modular, streaming capable sampler *
4     * *
5     * Copyright (C) 2011 Grigor Iliev *
6     * *
7     * This program is free software; you can redistribute it and/or modify *
8     * it under the terms of the GNU General Public License as published by *
9     * the Free Software Foundation; either version 2 of the License, or *
10     * (at your option) any later version. *
11     * *
12     * This program is distributed in the hope that it will be useful, *
13     * but WITHOUT ANY WARRANTY; without even the implied warranty of *
14     * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
15     * GNU General Public License for more details. *
16     * *
17     * You should have received a copy of the GNU General Public License *
18     * along with this program; if not, write to the Free Software *
19     * Foundation, Inc., 59 Temple Place, Suite 330, Boston, *
20     * MA 02111-1307 USA *
21     ***************************************************************************/
22    
23     #include "SfzSignalUnitRack.h"
24 iliev 2244 #include "Engine.h"
25 iliev 2218
26 iliev 2244 #define _200TH_ROOT_OF_10 1.011579454259899
27    
28 iliev 2218 namespace LinuxSampler { namespace sfz {
29    
30 iliev 2244 double ToRatio(int Centibels) {
31     if (Centibels == 0) return 1.0;
32     return pow(_200TH_ROOT_OF_10, Centibels);
33     }
34    
35 iliev 2218 SfzSignalUnit::SfzSignalUnit(SfzSignalUnitRack* rack): SignalUnit(rack), pVoice(rack->pVoice) {
36    
37     }
38    
39     double SfzSignalUnit::GetSampleRate() {
40     return pVoice->GetSampleRate() / CONFIG_DEFAULT_SUBFRAGMENT_SIZE;
41     }
42    
43 iliev 2229 float SfzSignalUnit::GetInfluence(ArrayList< ::sfz::CC>& cc) {
44     float f = 0;
45     for (int i = 0; i < cc.size(); i++) {
46     int val = pVoice->GetControllerValue(cc[i].Controller);
47     f += (val / 127.0f) * cc[i].Influence;
48     }
49     return f;
50 iliev 2218 }
51    
52 iliev 2236 void XFInCCUnit::SetCrossFadeCCs(::sfz::Array<int>& loCCs, ::sfz::Array<int>& hiCCs) {
53     RemoveAllCCs();
54    
55     for (int cc = 0; cc < 128; cc++) {
56     if (loCCs[cc] == 0 && hiCCs[cc] == 0) continue;
57     int i = loCCs[cc];
58     int j = hiCCs[cc];
59     if (j == 0) j = 127;
60     i += j << 8; // workaround to keep both values in the Influence parameter
61     AddCC(cc, i);
62     }
63     }
64 iliev 2220
65 iliev 2236 void XFInCCUnit::Calculate() {
66     float l = 1;
67    
68 iliev 2244 RTList<CC>::Iterator ctrl = pCtrls->first();
69     RTList<CC>::Iterator end = pCtrls->end();
70     for(; ctrl != end; ++ctrl) {
71 iliev 2236 float c = 1;
72 iliev 2244 int influence = (*ctrl).Influence;
73 iliev 2236 int lo = influence & 0xff;
74     int hi = influence >> 8;
75 iliev 2244 if ((*ctrl).Value <= lo) {
76 iliev 2236 c = 0;
77 iliev 2244 } else if ((*ctrl).Value >= hi) {
78 iliev 2236 c = 1;
79     } else {
80     float xfVelSize = hi - lo;
81 iliev 2244 float velPos = (*ctrl).Value - lo;
82 iliev 2236 c = velPos / xfVelSize;
83     if (pVoice->pRegion->xf_cccurve == ::sfz::POWER) {
84     c = sin(c * M_PI / 2.0);
85     }
86     }
87    
88     l *= c;
89     }
90    
91     if (Level != l) {
92     Level = l;
93     if (pListener != NULL) pListener->ValueChanged(this);
94     }
95     }
96    
97    
98     void XFOutCCUnit::Calculate() {
99     float l = 1;
100    
101 iliev 2244 RTList<CC>::Iterator ctrl = pCtrls->first();
102     RTList<CC>::Iterator end = pCtrls->end();
103     for(; ctrl != end; ++ctrl) {
104 iliev 2236 float c = 1;
105 iliev 2244 int influence = (*ctrl).Influence;
106 iliev 2236 int lo = influence & 0xff;
107     int hi = influence >> 8;
108 iliev 2244 if ((*ctrl).Value >= hi) {
109 iliev 2236 c = 0;
110 iliev 2244 } else if ((*ctrl).Value <= lo) {
111 iliev 2236 c = 1;
112     } else {
113     float xfVelSize = hi - lo;
114 iliev 2244 float velPos = (*ctrl).Value - lo;
115 iliev 2236 c = 1.0f - velPos / xfVelSize;
116     if (pVoice->pRegion->xf_cccurve == ::sfz::POWER) {
117     c = sin(c * M_PI / 2.0);
118     }
119     }
120    
121     l *= c;
122     }
123    
124     if (Level != l) {
125     Level = l;
126     if (pListener != NULL) pListener->ValueChanged(this);
127     }
128     }
129    
130    
131 iliev 2235 EGv2Unit::EGv2Unit(SfzSignalUnitRack* rack)
132 iliev 2237 : EGUnit< ::LinuxSampler::sfz::EG>(rack), suAmpOnCC(rack), suVolOnCC(rack),
133     suPitchOnCC(rack), suCutoffOnCC(rack), suResOnCC(rack), suPanOnCC(rack)
134 iliev 2235 { }
135    
136 iliev 2218 void EGv2Unit::Trigger() {
137 iliev 2229 egInfo = *pEGInfo;
138     for (int i = 0; i < egInfo.node.size(); i++) {
139     float f = GetInfluence(egInfo.node[i].level_oncc);
140     egInfo.node[i].level = std::min(egInfo.node[i].level + f, 1.0f);
141    
142     f = GetInfluence(egInfo.node[i].time_oncc);
143     egInfo.node[i].time = std::min(egInfo.node[i].time + f, 100.0f);
144     }
145     EG.trigger(egInfo, GetSampleRate(), pVoice->MIDIVelocity);
146 iliev 2218 }
147 iliev 2219
148 iliev 2220
149     void PitchEGUnit::Trigger() {
150     ::sfz::Region* const pRegion = pVoice->pRegion;
151 iliev 2249 depth = pRegion->pitcheg_depth + GetInfluence(pRegion->pitcheg_depth_oncc);
152 iliev 2220
153     // the length of the decay and release curves are dependent on the velocity
154     const double velrelease = 1 / pVoice->GetVelocityRelease(pVoice->MIDIVelocity);
155 iliev 2218
156 iliev 2220 // set the delay trigger
157 iliev 2249 float delay = pRegion->pitcheg_delay + pRegion->pitcheg_vel2delay * velrelease;
158     delay += GetInfluence(pRegion->pitcheg_delay_oncc);
159     uiDelayTrigger = std::max(0.0f, delay) * GetSampleRate();
160 iliev 2220
161 iliev 2249 float start = (pRegion->pitcheg_start + GetInfluence(pRegion->pitcheg_start_oncc)) * 10;
162    
163     float attack = pRegion->pitcheg_attack + pRegion->pitcheg_vel2attack * velrelease;
164     attack = std::max(0.0f, attack + GetInfluence(pRegion->pitcheg_attack_oncc));
165    
166     float hold = pRegion->pitcheg_hold + pRegion->pitcheg_vel2hold * velrelease;
167     hold = std::max(0.0f, hold + GetInfluence(pRegion->pitcheg_hold_oncc));
168    
169     float decay = pRegion->pitcheg_decay + pRegion->pitcheg_vel2decay * velrelease;
170     decay = std::max(0.0f, decay + GetInfluence(pRegion->pitcheg_decay_oncc));
171    
172     float sustain = pRegion->pitcheg_sustain + pRegion->pitcheg_vel2sustain * velrelease;
173     sustain = 10 * (sustain + GetInfluence(pRegion->pitcheg_sustain_oncc));
174    
175     float release = pRegion->pitcheg_release + pRegion->pitcheg_vel2release * velrelease;
176     release = std::max(0.0f, release + GetInfluence(pRegion->pitcheg_release_oncc));
177    
178     EG.trigger (
179     uint(std::min(std::max(0.0f, start), 1000.0f)), attack, hold, decay,
180     uint(std::min(std::max(0.0f, sustain), 1000.0f)), release, GetSampleRate()
181     );
182 iliev 2220 }
183    
184 iliev 2222
185     void FilEGUnit::Trigger() {
186     ::sfz::Region* const pRegion = pVoice->pRegion;
187 iliev 2249 depth = pRegion->fileg_depth + GetInfluence(pRegion->fileg_depth_oncc);
188 iliev 2222
189     // the length of the decay and release curves are dependent on the velocity
190     const double velrelease = 1 / pVoice->GetVelocityRelease(pVoice->MIDIVelocity);
191 iliev 2220
192 iliev 2222 // set the delay trigger
193 iliev 2249 float delay = pRegion->fileg_delay + pRegion->fileg_vel2delay * velrelease;
194     delay += GetInfluence(pRegion->fileg_delay_oncc);
195     uiDelayTrigger = std::max(0.0f, delay) * GetSampleRate();
196 iliev 2222
197 iliev 2249 float start = (pRegion->fileg_start + GetInfluence(pRegion->fileg_start_oncc)) * 10;
198    
199     float attack = pRegion->fileg_attack + pRegion->fileg_vel2attack * velrelease;
200     attack = std::max(0.0f, attack + GetInfluence(pRegion->fileg_attack_oncc));
201    
202     float hold = pRegion->fileg_hold + pRegion->fileg_vel2hold * velrelease;
203     hold = std::max(0.0f, hold + GetInfluence(pRegion->fileg_hold_oncc));
204    
205     float decay = pRegion->fileg_decay + pRegion->fileg_vel2decay * velrelease;
206     decay = std::max(0.0f, decay + GetInfluence(pRegion->fileg_decay_oncc));
207    
208     float sustain = pRegion->fileg_sustain + pRegion->fileg_vel2sustain * velrelease;
209     sustain = 10 * (sustain + GetInfluence(pRegion->fileg_sustain_oncc));
210    
211     float release = pRegion->fileg_release + pRegion->fileg_vel2release * velrelease;
212     release = std::max(0.0f, release + GetInfluence(pRegion->fileg_release_oncc));
213    
214     EG.trigger (
215     uint(std::min(std::max(0.0f, start), 1000.0f)), attack, hold, decay,
216     uint(std::min(std::max(0.0f, sustain), 1000.0f)), release, GetSampleRate()
217     );
218 iliev 2222 }
219    
220 iliev 2226
221 iliev 2229 void AmpEGUnit::Trigger() {
222     ::sfz::Region* const pRegion = pVoice->pRegion;
223    
224     // the length of the decay and release curves are dependent on the velocity
225     const double velrelease = 1 / pVoice->GetVelocityRelease(pVoice->MIDIVelocity);
226    
227     // set the delay trigger
228     float delay = pRegion->ampeg_delay + pRegion->ampeg_vel2delay * velrelease;
229     delay += GetInfluence(pRegion->ampeg_delaycc);
230     uiDelayTrigger = std::max(0.0f, delay) * GetSampleRate();
231    
232     float start = (pRegion->ampeg_start + GetInfluence(pRegion->ampeg_startcc)) * 10;
233    
234     float attack = pRegion->ampeg_attack + pRegion->ampeg_vel2attack * velrelease;
235     attack = std::max(0.0f, attack + GetInfluence(pRegion->ampeg_attackcc));
236    
237     float hold = pRegion->ampeg_hold + pRegion->ampeg_vel2hold * velrelease;
238     hold = std::max(0.0f, hold + GetInfluence(pRegion->ampeg_holdcc));
239    
240     float decay = pRegion->ampeg_decay + pRegion->ampeg_vel2decay * velrelease;
241     decay = std::max(0.0f, decay + GetInfluence(pRegion->ampeg_decaycc));
242    
243     float sustain = pRegion->ampeg_sustain + pRegion->ampeg_vel2sustain * velrelease;
244     sustain = 10 * (sustain + GetInfluence(pRegion->ampeg_sustaincc));
245    
246     float release = pRegion->ampeg_release + pRegion->ampeg_vel2release * velrelease;
247     release = std::max(0.0f, release + GetInfluence(pRegion->ampeg_releasecc));
248    
249     EG.trigger (
250     uint(std::min(std::max(0.0f, start), 1000.0f)), attack, hold, decay,
251     uint(std::min(std::max(0.0f, sustain), 1000.0f)), release, GetSampleRate()
252     );
253     }
254    
255    
256 iliev 2227 LFOUnit::LFOUnit(SfzSignalUnitRack* rack)
257     : SfzSignalUnit(rack), pLfoInfo(NULL), pLFO(NULL),
258 iliev 2233 suFadeEG(rack), suFreqOnCC(rack, this), suDepthOnCC(rack)
259 iliev 2227 { }
260    
261     LFOUnit::LFOUnit(const LFOUnit& Unit)
262     : SfzSignalUnit(Unit), suFadeEG(static_cast<SfzSignalUnitRack*>(Unit.pRack)),
263 iliev 2233 suFreqOnCC(static_cast<SfzSignalUnitRack*>(Unit.pRack), this),
264     suDepthOnCC(static_cast<SfzSignalUnitRack*>(Unit.pRack))
265 iliev 2227 {
266 iliev 2226 Copy(Unit);
267     }
268 iliev 2222
269 iliev 2219 void LFOUnit::Increment() {
270     if (DelayStage()) return;
271    
272     SignalUnit::Increment();
273    
274 iliev 2223 Level = pLFO->Render();
275 iliev 2226 if (suFadeEG.Active()) Level *= suFadeEG.GetLevel();
276 iliev 2219 }
277    
278     void LFOUnit::Trigger() {
279     //reset
280     Level = 0;
281    
282     // set the delay trigger
283 iliev 2233 uiDelayTrigger = (pLfoInfo->delay + GetInfluence(pLfoInfo->delay_oncc)) * GetSampleRate();
284 iliev 2226 if(pLfoInfo->fade != 0 || !pLfoInfo->fade_oncc.empty()) {
285     float f = pLfoInfo->fade;
286 iliev 2229 f += GetInfluence(pLfoInfo->fade_oncc);
287 iliev 2226
288     if (f != 0) {
289     suFadeEG.uiDelayTrigger = pLfoInfo->delay * GetSampleRate();
290     suFadeEG.EG.trigger(0, f, 0, 0, 1000, 0, GetSampleRate());
291     }
292     }
293 iliev 2219 }
294    
295 iliev 2227 void LFOUnit::ValueChanged(CCSignalUnit* pUnit) {
296 iliev 2251 if (pLFO == NULL) return;
297 iliev 2229 pLFO->SetFrequency(std::max(0.0f, suFreqOnCC.GetLevel() + pLfoInfo->freq), GetSampleRate());
298 iliev 2227 }
299    
300    
301 iliev 2221 void LFOv1Unit::Trigger() {
302     LFOUnit::Trigger();
303    
304     lfo.trigger (
305 iliev 2227 pLfoInfo->freq + suFreqOnCC.GetLevel(),
306 iliev 2221 start_level_mid,
307     1, 0, false, GetSampleRate()
308     );
309     lfo.update(0);
310     }
311    
312 iliev 2223
313     LFOv2Unit::LFOv2Unit(SfzSignalUnitRack* rack)
314     : LFOUnit(rack), lfos(8), lfo0(1200.0f), lfo1(1200.0f), lfo2(1200.0f),
315 iliev 2225 lfo3(1200.0f), lfo4(1200.0f), lfo5(1200.0f), lfo6(1200.0f), lfo7(1200.0f),
316 iliev 2233 suVolOnCC(rack), suPitchOnCC(rack), suPanOnCC(rack), suCutoffOnCC(rack), suResOnCC(rack)
317 iliev 2223 {
318     lfos.add(&lfo0);
319     lfos.add(&lfo1);
320     lfos.add(&lfo2);
321     lfos.add(&lfo3);
322     lfos.add(&lfo4);
323     lfos.add(&lfo5);
324     lfos.add(&lfo6);
325     lfos.add(&lfo7);
326     }
327    
328 iliev 2219 void LFOv2Unit::Trigger() {
329     LFOUnit::Trigger();
330    
331 iliev 2223 if (pLfoInfo->wave < 0 || pLfoInfo->wave >= lfos.size()) pLFO = &lfo0;
332     else pLFO = lfos[pLfoInfo->wave];
333    
334     pLFO->Trigger (
335 iliev 2227 pLfoInfo->freq + suFreqOnCC.GetLevel(),
336 iliev 2219 start_level_mid,
337     1, 0, false, GetSampleRate()
338     );
339 iliev 2223 pLFO->Update(0);
340 iliev 2225
341 iliev 2229 float phase = pLfoInfo->phase + GetInfluence(pLfoInfo->phase_oncc);
342 iliev 2225 if (phase != 0) pLFO->SetPhase(phase);
343 iliev 2219 }
344 iliev 2221
345     void AmpLFOUnit::Trigger() {
346 iliev 2251 bActive = true;
347 iliev 2221 ::sfz::Region* const pRegion = pVoice->pRegion;
348 iliev 2248 pLfoInfo->delay = pRegion->amplfo_delay + GetInfluence(pRegion->amplfo_delay_oncc);
349 iliev 2226 pLfoInfo->freq = pRegion->amplfo_freq;
350 iliev 2248 pLfoInfo->fade = pRegion->amplfo_fade + GetInfluence(pRegion->amplfo_fade_oncc);
351 iliev 2221 pLfoInfo->volume = pRegion->amplfo_depth;
352    
353 iliev 2251 if (pLfoInfo->freq <= 0) {
354     if (!pRegion->amplfo_freqcc.empty()) pLfoInfo->freq = 0;
355     else bActive = false;
356     }
357    
358 iliev 2221 LFOv1Unit::Trigger();
359     }
360    
361     void PitchLFOUnit::Trigger() {
362 iliev 2251 bActive = true;
363 iliev 2221 ::sfz::Region* const pRegion = pVoice->pRegion;
364 iliev 2248 pLfoInfo->delay = pRegion->pitchlfo_delay + GetInfluence(pRegion->pitchlfo_delay_oncc);
365 iliev 2226 pLfoInfo->freq = pRegion->pitchlfo_freq;
366 iliev 2248 pLfoInfo->fade = pRegion->pitchlfo_fade + GetInfluence(pRegion->pitchlfo_fade_oncc);
367 iliev 2221 pLfoInfo->pitch = pRegion->pitchlfo_depth;
368    
369 iliev 2251 if (pLfoInfo->freq <= 0) {
370     if (!pRegion->pitchlfo_freqcc.empty()) pLfoInfo->freq = 0;
371     else bActive = false;
372     }
373    
374 iliev 2221 LFOv1Unit::Trigger();
375     }
376    
377     void FilLFOUnit::Trigger() {
378 iliev 2251 bActive = true;
379 iliev 2221 ::sfz::Region* const pRegion = pVoice->pRegion;
380 iliev 2248 pLfoInfo->delay = pRegion->fillfo_delay + GetInfluence(pRegion->fillfo_delay_oncc);
381 iliev 2226 pLfoInfo->freq = pRegion->fillfo_freq;
382 iliev 2248 pLfoInfo->fade = pRegion->fillfo_fade + GetInfluence(pRegion->fillfo_fade_oncc);
383 iliev 2221 pLfoInfo->cutoff = pRegion->fillfo_depth;
384    
385 iliev 2251 if (pLfoInfo->freq <= 0) {
386     if (!pRegion->fillfo_freqcc.empty()) pLfoInfo->freq = 0;
387     else bActive = false;
388     }
389    
390 iliev 2221 LFOv1Unit::Trigger();
391     }
392 iliev 2224
393 iliev 2227 CCUnit::CCUnit(SfzSignalUnitRack* rack, Listener* l): CCSignalUnit(rack, l) {
394     pVoice = NULL;
395     }
396 iliev 2224
397     void CCUnit::Trigger() {
398 iliev 2244 RTList<CC>::Iterator ctrl = pCtrls->first();
399     RTList<CC>::Iterator end = pCtrls->end();
400     for(; ctrl != end; ++ctrl) {
401     (*ctrl).Value = pVoice->GetControllerValue((*ctrl).Controller);
402 iliev 2264 if ((*ctrl).pSmoother != NULL) {
403     if ((*ctrl).Step > 0) {
404     float val = Normalize((*ctrl).Value, (*ctrl).Curve) * (*ctrl).Influence;
405     (*ctrl).pSmoother->setValue( ((int) (val / (*ctrl).Step)) * (*ctrl).Step );
406     } else {
407     (*ctrl).pSmoother->setValue((*ctrl).Value);
408     }
409     }
410 iliev 2224 }
411     CCSignalUnit::Trigger();
412     }
413    
414 iliev 2244 void CCUnit::SetCCs(::sfz::Array<int>& cc) {
415     RemoveAllCCs();
416     for (int i = 0; i < 128; i++) {
417     if (cc[i] != 0) AddCC(i, cc[i]);
418     }
419     }
420 iliev 2225
421 iliev 2296 void CCUnit::SetCCs(::sfz::Array<float>& cc) {
422     RemoveAllCCs();
423     for (int i = 0; i < 128; i++) {
424     if (cc[i] != 0) AddCC(i, cc[i]);
425     }
426     }
427    
428 iliev 2244 void CCUnit::SetCCs(ArrayList< ::sfz::CC>& cc) {
429     RemoveAllCCs();
430     for (int i = 0; i < cc.size(); i++) {
431     if (cc[i].Influence != 0) {
432     short int curve = cc[i].Curve;
433     if (curve >= GetCurveCount()) curve = -1;
434 iliev 2264 AddSmoothCC(cc[i].Controller, cc[i].Influence, curve, cc[i].Smooth, cc[i].Step);
435 iliev 2244 }
436     }
437     }
438 iliev 2230
439 iliev 2264 void CCUnit::AddSmoothCC(uint8_t Controller, float Influence, short int Curve, float Smooth, float Step) {
440     AddCC(Controller, Influence, Curve, NULL, Step);
441 iliev 2244 }
442 iliev 2232
443 iliev 2244 int CCUnit::GetCurveCount() {
444     return pVoice->pRegion->GetInstrument()->curves.size();
445     }
446 iliev 2230
447 iliev 2244 ::sfz::Curve* CCUnit::GetCurve(int idx) {
448     return &pVoice->pRegion->GetInstrument()->curves[idx];
449     }
450 iliev 2232
451 iliev 2244 double CCUnit::GetSampleRate() {
452 iliev 2232 return pVoice->GetSampleRate() / CONFIG_DEFAULT_SUBFRAGMENT_SIZE;
453     }
454 iliev 2244
455    
456     SmoothCCUnit::~SmoothCCUnit() {
457     if (pSmoothers != NULL) delete pSmoothers;
458     }
459 iliev 2232
460 iliev 2264 void SmoothCCUnit::AddSmoothCC(uint8_t Controller, float Influence, short int Curve, float Smooth, float Step) {
461 iliev 2244 if (Smooth > 0) {
462     if (pSmoothers->poolIsEmpty()) {
463     std::cerr << "Maximum number of smoothers reached" << std::endl;
464     return;
465     }
466     Smoother* smoother = &(*(pSmoothers->allocAppend()));
467     smoother->trigger(Smooth / 1000.0f, GetSampleRate());
468 iliev 2264 AddCC(Controller, Influence, Curve, smoother, Step);
469 iliev 2244 } else {
470 iliev 2264 AddCC(Controller, Influence, Curve, NULL, Step);
471 iliev 2244 }
472     }
473    
474     void SmoothCCUnit::InitSmoothers(Pool<Smoother>* pSmootherPool) {
475     if (pSmoothers != NULL) delete pSmoothers;
476     pSmoothers = new RTList<Smoother>(pSmootherPool);
477     }
478    
479     void SmoothCCUnit::InitCCList(Pool<CC>* pCCPool, Pool<Smoother>* pSmootherPool) {
480     CurveCCUnit::InitCCList(pCCPool, pSmootherPool);
481     InitSmoothers(pSmootherPool);
482     }
483 iliev 2218
484 iliev 2219
485 iliev 2237 EndpointUnit::EndpointUnit(SfzSignalUnitRack* rack)
486     : EndpointSignalUnit(rack), suXFInCC(rack), suXFOutCC(rack), suPanOnCC(rack), pitchVeltrackRatio(0)
487     {
488 iliev 2218
489     }
490    
491     SfzSignalUnitRack* const EndpointUnit::GetRack() {
492     return static_cast<SfzSignalUnitRack* const>(pRack);
493     }
494    
495     void EndpointUnit::Trigger() {
496 iliev 2236 float xfInVelCoeff = 1;
497 iliev 2218
498 iliev 2236 if (pVoice->MIDIVelocity <= pVoice->pRegion->xfin_lovel) {
499     xfInVelCoeff = 0;
500     } else if (pVoice->MIDIVelocity >= pVoice->pRegion->xfin_hivel) {
501     xfInVelCoeff = 1;
502     } else {
503     float xfVelSize = pVoice->pRegion->xfin_hivel - pVoice->pRegion->xfin_lovel;
504     float velPos = pVoice->MIDIVelocity - pVoice->pRegion->xfin_lovel;
505     xfInVelCoeff = velPos / xfVelSize;
506     if (pVoice->pRegion->xf_velcurve == ::sfz::POWER) {
507     xfInVelCoeff = sin(xfInVelCoeff * M_PI / 2.0);
508     }
509     }
510    
511     float xfOutVelCoeff = 1;
512    
513     if (pVoice->MIDIVelocity >= pVoice->pRegion->xfout_hivel) {
514     if (pVoice->pRegion->xfout_lovel < 127 /* is set */) xfOutVelCoeff = 0;
515     } else if (pVoice->MIDIVelocity <= pVoice->pRegion->xfout_lovel) {
516     xfOutVelCoeff = 1;
517     } else {
518     float xfVelSize = pVoice->pRegion->xfout_hivel - pVoice->pRegion->xfout_lovel;
519     float velPos = pVoice->MIDIVelocity - pVoice->pRegion->xfout_lovel;
520     xfOutVelCoeff = 1.0f - velPos / xfVelSize;
521     if (pVoice->pRegion->xf_velcurve == ::sfz::POWER) {
522     xfOutVelCoeff = sin(xfOutVelCoeff * M_PI / 2.0);
523     }
524     }
525    
526     float xfInKeyCoeff = 1;
527    
528     if (pVoice->MIDIKey <= pVoice->pRegion->xfin_lokey) {
529     if (pVoice->pRegion->xfin_hikey > 0 /* is set */) xfInKeyCoeff = 0;
530     } else if (pVoice->MIDIKey >= pVoice->pRegion->xfin_hikey) {
531     xfInKeyCoeff = 1;
532     } else {
533     float xfKeySize = pVoice->pRegion->xfin_hikey - pVoice->pRegion->xfin_lokey;
534     float keyPos = pVoice->MIDIKey - pVoice->pRegion->xfin_lokey;
535     xfInKeyCoeff = keyPos / xfKeySize;
536     if (pVoice->pRegion->xf_keycurve == ::sfz::POWER) {
537     xfInKeyCoeff = sin(xfInKeyCoeff * M_PI / 2.0);
538     }
539     }
540    
541     float xfOutKeyCoeff = 1;
542    
543     if (pVoice->MIDIKey >= pVoice->pRegion->xfout_hikey) {
544     if (pVoice->pRegion->xfout_lokey < 127 /* is set */) xfOutKeyCoeff = 0;
545     } else if (pVoice->MIDIKey <= pVoice->pRegion->xfout_lokey) {
546     xfOutKeyCoeff = 1;
547     } else {
548     float xfKeySize = pVoice->pRegion->xfout_hikey - pVoice->pRegion->xfout_lokey;
549     float keyPos = pVoice->MIDIKey - pVoice->pRegion->xfout_lokey;
550     xfOutKeyCoeff = 1.0f - keyPos / xfKeySize;
551     if (pVoice->pRegion->xf_keycurve == ::sfz::POWER) {
552     xfOutKeyCoeff = sin(xfOutKeyCoeff * M_PI / 2.0);
553     }
554     }
555    
556     xfCoeff = xfInVelCoeff * xfOutVelCoeff * xfInKeyCoeff * xfOutKeyCoeff;
557    
558     suXFInCC.SetCrossFadeCCs(pVoice->pRegion->xfin_locc, pVoice->pRegion->xfin_hicc);
559     suXFOutCC.SetCrossFadeCCs(pVoice->pRegion->xfout_locc, pVoice->pRegion->xfout_hicc);
560 iliev 2237
561     suPanOnCC.SetCCs(pVoice->pRegion->pan_oncc);
562    
563     pitchVeltrackRatio = RTMath::CentsToFreqRatioUnlimited((pVoice->MIDIVelocity / 127.0f) * pVoice->pRegion->pitch_veltrack);
564 iliev 2218 }
565    
566     bool EndpointUnit::Active() {
567     if (GetRack()->suVolEG.Active()) return true;
568    
569     bool b = false;
570     for (int i = 0; i < GetRack()->volEGs.size(); i++) {
571     if (GetRack()->volEGs[i]->Active()) { b = true; break; }
572     }
573    
574     return b;
575     }
576    
577     float EndpointUnit::GetVolume() {
578     float vol = GetRack()->suVolEG.Active() ? GetRack()->suVolEG.GetLevel() : 0;
579    
580     for (int i = 0; i < GetRack()->volEGs.size(); i++) {
581     EGv2Unit* eg = GetRack()->volEGs[i];
582     if (!eg->Active()) continue;
583 iliev 2229
584 iliev 2235 float dB = eg->suVolOnCC.Active() ? eg->suVolOnCC.GetLevel() : -200;
585     if (dB < -144) dB = eg->pEGInfo->volume;
586     else if (eg->pEGInfo->volume >= -144) dB += eg->pEGInfo->volume;
587    
588     float amp = eg->suAmpOnCC.Active() ? eg->suAmpOnCC.GetLevel() : 0;
589     amp = (amp + eg->pEGInfo->amplitude) / 100.0f;
590    
591     if (dB >= -144) {
592     if (amp == 0 && eg->suAmpOnCC.GetCCCount() == 0) amp = 1.0f;
593 iliev 2244 amp *= ToRatio(dB * 10.0);
594 iliev 2235 }
595    
596     vol += amp * eg->GetLevel();
597 iliev 2218 }
598    
599 iliev 2221 AmpLFOUnit* u = &(GetRack()->suAmpLFO);
600 iliev 2233 CCSignalUnit* u2 = &(GetRack()->suAmpLFO.suDepthOnCC);
601     float f = u2->Active() ? u2->GetLevel() : 0;
602 iliev 2244 vol *= u->Active() ? ToRatio((u->GetLevel() * (u->pLfoInfo->volume + f) * 10.0)) : 1;
603 iliev 2221
604 iliev 2244 vol *= ToRatio(GetRack()->suVolOnCC.GetLevel() * 10.0);
605 iliev 2230
606 iliev 2233 for (int i = 0; i < GetRack()->volLFOs.size(); i++) {
607     LFOv2Unit* lfo = GetRack()->volLFOs[i];
608     if (!lfo->Active()) continue;
609    
610     float f = lfo->suVolOnCC.Active() ? lfo->suVolOnCC.GetLevel() : 0;
611 iliev 2244 vol *= ToRatio(lfo->GetLevel() * (lfo->pLfoInfo->volume + f) * 10.0);
612 iliev 2233 }
613    
614 iliev 2236 if (suXFInCC.Active()) vol *= suXFInCC.GetLevel();
615     if (suXFOutCC.Active()) vol *= suXFOutCC.GetLevel();
616     return vol * xfCoeff;
617 iliev 2218 }
618    
619     float EndpointUnit::GetFilterCutoff() {
620 iliev 2252 float val = GetRack()->suCutoffOnCC.Active() ? RTMath::CentsToFreqRatioUnlimited(GetRack()->suCutoffOnCC.GetLevel()) : 1;
621 iliev 2219
622 iliev 2221 FilLFOUnit* u = &(GetRack()->suFilLFO);
623 iliev 2233 CCSignalUnit* u1 = &(GetRack()->suFilLFO.suDepthOnCC);
624     float f = u1->Active() ? u1->GetLevel() : 0;
625 iliev 2252 val *= u->Active() ? RTMath::CentsToFreqRatioUnlimited(u->GetLevel() * (u->pLfoInfo->cutoff + f)) : 1;
626 iliev 2221
627 iliev 2222 FilEGUnit* u2 = &(GetRack()->suFilEG);
628     val *= u2->Active() ? RTMath::CentsToFreqRatioUnlimited(u2->GetLevel() * u2->depth) : 1;
629    
630 iliev 2235 for (int i = 0; i < GetRack()->filEGs.size(); i++) {
631     EGv2Unit* eg = GetRack()->filEGs[i];
632     if (!eg->Active()) continue;
633    
634     float f = eg->suCutoffOnCC.Active() ? eg->suCutoffOnCC.GetLevel() : 0;
635     f = eg->GetLevel() * (eg->pEGInfo->cutoff + f);
636     val *= RTMath::CentsToFreqRatioUnlimited(f);
637     }
638    
639 iliev 2219 for (int i = 0; i < GetRack()->filLFOs.size(); i++) {
640     LFOv2Unit* lfo = GetRack()->filLFOs[i];
641     if (!lfo->Active()) continue;
642    
643 iliev 2233 float f = lfo->suCutoffOnCC.Active() ? lfo->suCutoffOnCC.GetLevel() : 0;
644     f = lfo->GetLevel() * (lfo->pLfoInfo->cutoff + f);
645 iliev 2219 val *= RTMath::CentsToFreqRatioUnlimited(f);
646     }
647    
648     return val;
649 iliev 2218 }
650    
651 iliev 2235 float EndpointUnit::CalculateFilterCutoff(float cutoff) {
652 iliev 2252 cutoff *= GetFilterCutoff();
653     float maxCutoff = 0.49 * pVoice->GetSampleRate();
654     return cutoff > maxCutoff ? maxCutoff : cutoff;
655 iliev 2235 }
656    
657 iliev 2218 float EndpointUnit::GetPitch() {
658 iliev 2264 double p = GetRack()->suPitchOnCC.Active() ? RTMath::CentsToFreqRatioUnlimited(GetRack()->suPitchOnCC.GetLevel()) : 1;
659    
660 iliev 2220 EGv1Unit* u = &(GetRack()->suPitchEG);
661 iliev 2264 p *= u->Active() ? RTMath::CentsToFreqRatioUnlimited(u->GetLevel() * u->depth) : 1;
662 iliev 2221
663 iliev 2235 for (int i = 0; i < GetRack()->pitchEGs.size(); i++) {
664     EGv2Unit* eg = GetRack()->pitchEGs[i];
665     if (!eg->Active()) continue;
666    
667     float f = eg->suPitchOnCC.Active() ? eg->suPitchOnCC.GetLevel() : 0;
668     p *= RTMath::CentsToFreqRatioUnlimited(eg->GetLevel() * (eg->pEGInfo->pitch + f));
669     }
670    
671 iliev 2221 PitchLFOUnit* u2 = &(GetRack()->suPitchLFO);
672 iliev 2233 CCSignalUnit* u3 = &(GetRack()->suPitchLFO.suDepthOnCC);
673 iliev 2224 float f = u3->Active() ? u3->GetLevel() : 0;
674     p *= u2->Active() ? RTMath::CentsToFreqRatioUnlimited(u2->GetLevel() * (u2->pLfoInfo->pitch + f)) : 1;
675 iliev 2225
676     for (int i = 0; i < GetRack()->pitchLFOs.size(); i++) {
677     LFOv2Unit* lfo = GetRack()->pitchLFOs[i];
678     if (!lfo->Active()) continue;
679    
680     float f = lfo->suPitchOnCC.Active() ? lfo->suPitchOnCC.GetLevel() : 0;
681     p *= RTMath::CentsToFreqRatioUnlimited(lfo->GetLevel() * (lfo->pLfoInfo->pitch + f));
682     }
683    
684 iliev 2237 return p * pitchVeltrackRatio;
685 iliev 2218 }
686    
687     float EndpointUnit::GetResonance() {
688 iliev 2252 float val = GetRack()->suResOnCC.Active() ? GetRack()->suResOnCC.GetLevel() : 0;
689 iliev 2219
690 iliev 2235 for (int i = 0; i < GetRack()->resEGs.size(); i++) {
691     EGv2Unit* eg = GetRack()->resEGs[i];
692     if (!eg->Active()) continue;
693    
694     float f = eg->suResOnCC.Active() ? eg->suResOnCC.GetLevel() : 0;
695     val += eg->GetLevel() * (eg->pEGInfo->resonance + f);
696     }
697    
698 iliev 2219 for (int i = 0; i < GetRack()->resLFOs.size(); i++) {
699     LFOv2Unit* lfo = GetRack()->resLFOs[i];
700     if (!lfo->Active()) continue;
701    
702 iliev 2233 float f = lfo->suResOnCC.Active() ? lfo->suResOnCC.GetLevel() : 0;
703     val += lfo->GetLevel() * (lfo->pLfoInfo->resonance + f);
704 iliev 2219 }
705    
706     return val;
707 iliev 2218 }
708    
709 iliev 2219 float EndpointUnit::GetPan() {
710 iliev 2237 float pan = suPanOnCC.Active() ? suPanOnCC.GetLevel() : 0;
711 iliev 2219
712 iliev 2237 for (int i = 0; i < GetRack()->panEGs.size(); i++) {
713     EGv2Unit* eg = GetRack()->panEGs[i];
714     if (!eg->Active()) continue;
715    
716     float f = eg->suPanOnCC.Active() ? eg->suPanOnCC.GetLevel() : 0;
717    
718     if (eg->pEGInfo->pan_curve >= 0 && eg->pEGInfo->pan_curve < suPanOnCC.GetCurveCount()) {
719     uint8_t val = eg->GetLevel() * 127;
720     if (val > 127) val = 127;
721     pan += eg->pEGInfo->pan * suPanOnCC.GetCurve(eg->pEGInfo->pan_curve)->v[val] + eg->GetLevel() * f;
722     } else {
723     pan += eg->GetLevel() * (eg->pEGInfo->pan + f);
724     }
725     }
726    
727 iliev 2219 for (int i = 0; i < GetRack()->panLFOs.size(); i++) {
728     LFOv2Unit* lfo = GetRack()->panLFOs[i];
729     if (!lfo->Active()) continue;
730    
731 iliev 2233 float f = lfo->suPanOnCC.Active() ? lfo->suPanOnCC.GetLevel() : 0;
732     pan += lfo->GetLevel() * (lfo->pLfoInfo->pan + f);
733 iliev 2219 }
734    
735     if(pan < -100) return -100;
736     if(pan > 100) return 100;
737    
738     return pan;
739     }
740 iliev 2218
741 iliev 2219
742 iliev 2218 SfzSignalUnitRack::SfzSignalUnitRack(Voice* voice)
743 iliev 2222 : SignalUnitRack(MaxUnitCount), pVoice(voice), suEndpoint(this), suVolEG(this), suFilEG(this), suPitchEG(this),
744 iliev 2252 EGs(maxEgCount), volEGs(maxEgCount), pitchEGs(maxEgCount), filEGs(maxEgCount), resEGs(maxEgCount), panEGs(maxEgCount),
745 iliev 2296 suEq1GainOnCC(this), suEq2GainOnCC(this), suEq3GainOnCC(this),
746     suEq1FreqOnCC(this), suEq2FreqOnCC(this), suEq3FreqOnCC(this),
747     suEq1BwOnCC(this), suEq2BwOnCC(this), suEq3BwOnCC(this),
748 iliev 2264 suVolOnCC(this), suPitchOnCC(this), suCutoffOnCC(this), suResOnCC(this),
749 iliev 2221 suAmpLFO(this), suPitchLFO(this), suFilLFO(this),
750 iliev 2233 LFOs(maxLfoCount), volLFOs(maxLfoCount), pitchLFOs(maxLfoCount),
751     filLFOs(maxLfoCount), resLFOs(maxLfoCount), panLFOs(maxLfoCount)
752 iliev 2218 {
753 iliev 2237 suEndpoint.pVoice = suEndpoint.suXFInCC.pVoice = suEndpoint.suXFOutCC.pVoice = suEndpoint.suPanOnCC.pVoice = voice;
754 iliev 2236 suVolEG.pVoice = suFilEG.pVoice = suPitchEG.pVoice = voice;
755 iliev 2264 suAmpLFO.pVoice = suPitchLFO.pVoice = suFilLFO.pVoice = voice;
756 iliev 2296
757     suEq1GainOnCC.pVoice = suEq2GainOnCC.pVoice = suEq3GainOnCC.pVoice = voice;
758     suEq1FreqOnCC.pVoice = suEq2FreqOnCC.pVoice = suEq3FreqOnCC.pVoice = voice;
759     suEq1BwOnCC.pVoice = suEq2BwOnCC.pVoice = suEq3BwOnCC.pVoice = voice;
760    
761 iliev 2264 suVolOnCC.pVoice = suPitchOnCC.pVoice = suCutoffOnCC.pVoice = suResOnCC.pVoice = voice;
762 iliev 2233 suPitchLFO.suDepthOnCC.pVoice = suPitchLFO.suFadeEG.pVoice = suPitchLFO.suFreqOnCC.pVoice = voice;
763     suFilLFO.suFadeEG.pVoice = suFilLFO.suDepthOnCC.pVoice = suFilLFO.suFreqOnCC.pVoice = voice;
764     suAmpLFO.suFadeEG.pVoice = suAmpLFO.suDepthOnCC.pVoice = suAmpLFO.suFreqOnCC.pVoice = voice;
765 iliev 2218
766     for (int i = 0; i < EGs.capacity(); i++) {
767     EGs[i] = new EGv2Unit(this);
768     EGs[i]->pVoice = voice;
769 iliev 2235 EGs[i]->suAmpOnCC.pVoice = voice;
770     EGs[i]->suVolOnCC.pVoice = voice;
771     EGs[i]->suPitchOnCC.pVoice = voice;
772     EGs[i]->suCutoffOnCC.pVoice = voice;
773     EGs[i]->suResOnCC.pVoice = voice;
774 iliev 2237 EGs[i]->suPanOnCC.pVoice = voice;
775 iliev 2218 }
776 iliev 2219
777     for (int i = 0; i < LFOs.capacity(); i++) {
778     LFOs[i] = new LFOv2Unit(this);
779     LFOs[i]->pVoice = voice;
780 iliev 2244 LFOs[i]->suDepthOnCC.pVoice = voice;
781     LFOs[i]->suFreqOnCC.pVoice = voice;
782 iliev 2226 LFOs[i]->suFadeEG.pVoice = voice;
783 iliev 2233 LFOs[i]->suVolOnCC.pVoice = voice;
784 iliev 2225 LFOs[i]->suPitchOnCC.pVoice = voice;
785 iliev 2227 LFOs[i]->suFreqOnCC.pVoice = voice;
786 iliev 2233 LFOs[i]->suPanOnCC.pVoice = voice;
787     LFOs[i]->suCutoffOnCC.pVoice = voice;
788     LFOs[i]->suResOnCC.pVoice = voice;
789 iliev 2219 }
790 iliev 2218 }
791    
792     SfzSignalUnitRack::~SfzSignalUnitRack() {
793 iliev 2219 for (int i = 0; i < EGs.capacity(); i++) {
794 iliev 2218 delete EGs[i]; EGs[i] = NULL;
795     }
796 iliev 2219
797     for (int i = 0; i < LFOs.capacity(); i++) {
798     delete LFOs[i]; LFOs[i] = NULL;
799     }
800 iliev 2218 }
801    
802 iliev 2244 void SfzSignalUnitRack::InitRTLists() {
803     Pool<CCSignalUnit::CC>* pCCPool = pVoice->pEngine->pCCPool;
804     Pool<Smoother>* pSmootherPool = pVoice->pEngine->pSmootherPool;
805    
806 iliev 2296 suEq1GainOnCC.InitCCList(pCCPool, pSmootherPool);
807     suEq2GainOnCC.InitCCList(pCCPool, pSmootherPool);
808     suEq3GainOnCC.InitCCList(pCCPool, pSmootherPool);
809     suEq1FreqOnCC.InitCCList(pCCPool, pSmootherPool);
810     suEq2FreqOnCC.InitCCList(pCCPool, pSmootherPool);
811     suEq3FreqOnCC.InitCCList(pCCPool, pSmootherPool);
812     suEq1BwOnCC.InitCCList(pCCPool, pSmootherPool);
813     suEq2BwOnCC.InitCCList(pCCPool, pSmootherPool);
814     suEq3BwOnCC.InitCCList(pCCPool, pSmootherPool);
815    
816 iliev 2244 suVolOnCC.InitCCList(pCCPool, pSmootherPool);
817 iliev 2264 suPitchOnCC.InitCCList(pCCPool, pSmootherPool);
818 iliev 2252 suCutoffOnCC.InitCCList(pCCPool, pSmootherPool);
819     suResOnCC.InitCCList(pCCPool, pSmootherPool);
820 iliev 2244 suEndpoint.suXFInCC.InitCCList(pCCPool, pSmootherPool);
821     suEndpoint.suXFOutCC.InitCCList(pCCPool, pSmootherPool);
822     suEndpoint.suPanOnCC.InitCCList(pCCPool, pSmootherPool);
823     suPitchLFO.suDepthOnCC.InitCCList(pCCPool, pSmootherPool);
824     suPitchLFO.suFreqOnCC.InitCCList(pCCPool, pSmootherPool);
825     suFilLFO.suDepthOnCC.InitCCList(pCCPool, pSmootherPool);
826     suFilLFO.suFreqOnCC.InitCCList(pCCPool, pSmootherPool);
827     suAmpLFO.suDepthOnCC.InitCCList(pCCPool, pSmootherPool);
828     suAmpLFO.suFreqOnCC.InitCCList(pCCPool, pSmootherPool);
829    
830     for (int i = 0; i < EGs.capacity(); i++) {
831     EGs[i]->suAmpOnCC.InitCCList(pCCPool, pSmootherPool);
832     EGs[i]->suVolOnCC.InitCCList(pCCPool, pSmootherPool);
833     EGs[i]->suPitchOnCC.InitCCList(pCCPool, pSmootherPool);
834     EGs[i]->suCutoffOnCC.InitCCList(pCCPool, pSmootherPool);
835     EGs[i]->suResOnCC.InitCCList(pCCPool, pSmootherPool);
836     EGs[i]->suPanOnCC.InitCCList(pCCPool, pSmootherPool);
837     }
838    
839     for (int i = 0; i < LFOs.capacity(); i++) {
840     LFOs[i]->suDepthOnCC.InitCCList(pCCPool, pSmootherPool);
841     LFOs[i]->suFreqOnCC.InitCCList(pCCPool, pSmootherPool);
842     LFOs[i]->suVolOnCC.InitCCList(pCCPool, pSmootherPool);
843     LFOs[i]->suPitchOnCC.InitCCList(pCCPool, pSmootherPool);
844     LFOs[i]->suFreqOnCC.InitCCList(pCCPool, pSmootherPool);
845     LFOs[i]->suPanOnCC.InitCCList(pCCPool, pSmootherPool);
846     LFOs[i]->suCutoffOnCC.InitCCList(pCCPool, pSmootherPool);
847     LFOs[i]->suResOnCC.InitCCList(pCCPool, pSmootherPool);
848     }
849     }
850    
851 iliev 2218 void SfzSignalUnitRack::Trigger() {
852     EGs.clear();
853     volEGs.clear();
854     pitchEGs.clear();
855 iliev 2235 filEGs.clear();
856     resEGs.clear();
857 iliev 2237 panEGs.clear();
858 iliev 2218
859 iliev 2219 LFOs.clear();
860 iliev 2233 volLFOs.clear();
861 iliev 2225 pitchLFOs.clear();
862 iliev 2219 filLFOs.clear();
863     resLFOs.clear();
864     panLFOs.clear();
865    
866 iliev 2218 ::sfz::Region* const pRegion = pVoice->pRegion;
867    
868 iliev 2296 suEq1GainOnCC.SetCCs(pRegion->eq1_gain_oncc);
869     suEq2GainOnCC.SetCCs(pRegion->eq2_gain_oncc);
870     suEq3GainOnCC.SetCCs(pRegion->eq3_gain_oncc);
871     suEq1FreqOnCC.SetCCs(pRegion->eq1_freq_oncc);
872     suEq2FreqOnCC.SetCCs(pRegion->eq2_freq_oncc);
873     suEq3FreqOnCC.SetCCs(pRegion->eq3_freq_oncc);
874     suEq1BwOnCC.SetCCs(pRegion->eq1_bw_oncc);
875     suEq2BwOnCC.SetCCs(pRegion->eq2_bw_oncc);
876     suEq3BwOnCC.SetCCs(pRegion->eq3_bw_oncc);
877    
878     bHasEq = pRegion->eq1_gain || pRegion->eq2_gain || pRegion->eq3_gain ||
879     suEq1GainOnCC.HasCCs() || suEq2GainOnCC.HasCCs() || suEq3GainOnCC.HasCCs();
880    
881 iliev 2230 suVolOnCC.SetCCs(pRegion->volume_oncc);
882 iliev 2264 suPitchOnCC.SetCCs(pRegion->pitch_oncc);
883 iliev 2252 suCutoffOnCC.SetCCs(pRegion->cutoff_oncc);
884     suResOnCC.SetCCs(pRegion->resonance_oncc);
885 iliev 2230
886 iliev 2219 for (int i = 0; i < pRegion->eg.size(); i++) {
887 iliev 2218 if (pRegion->eg[i].node.size() == 0) continue;
888    
889     if(EGs.size() < EGs.capacity()) {
890     EGv2Unit eg(this);
891     eg.pEGInfo = &(pRegion->eg[i]);
892     EGs.increment()->Copy(eg);
893 iliev 2235 EGs[EGs.size() - 1]->suAmpOnCC.SetCCs(pRegion->eg[i].amplitude_oncc);
894     EGs[EGs.size() - 1]->suVolOnCC.SetCCs(pRegion->eg[i].volume_oncc);
895     EGs[EGs.size() - 1]->suPitchOnCC.SetCCs(pRegion->eg[i].pitch_oncc);
896     EGs[EGs.size() - 1]->suCutoffOnCC.SetCCs(pRegion->eg[i].cutoff_oncc);
897     EGs[EGs.size() - 1]->suResOnCC.SetCCs(pRegion->eg[i].resonance_oncc);
898 iliev 2237 EGs[EGs.size() - 1]->suPanOnCC.SetCCs(pRegion->eg[i].pan_oncc);
899 iliev 2218 } else { std::cerr << "Maximum number of EGs reached!" << std::endl; break; }
900    
901 iliev 2235 if ( pRegion->eg[i].amplitude > 0 || !pRegion->eg[i].amplitude_oncc.empty() ||
902     pRegion->eg[i].volume > -145 || !pRegion->eg[i].volume_oncc.empty()
903     ) {
904 iliev 2218 if(volEGs.size() < volEGs.capacity()) volEGs.add(EGs[EGs.size() - 1]);
905     else std::cerr << "Maximum number of EGs reached!" << std::endl;
906     }
907 iliev 2235
908     if (pRegion->eg[i].cutoff != 0 || !pRegion->eg[i].cutoff_oncc.empty()) {
909     if(filEGs.size() < filEGs.capacity()) filEGs.add(EGs[EGs.size() - 1]);
910     else std::cerr << "Maximum number of EGs reached!" << std::endl;
911     }
912    
913     if (pRegion->eg[i].resonance != 0 || !pRegion->eg[i].resonance_oncc.empty()) {
914     if(resEGs.size() < resEGs.capacity()) resEGs.add(EGs[EGs.size() - 1]);
915     else std::cerr << "Maximum number of EGs reached!" << std::endl;
916     }
917    
918     if (pRegion->eg[i].pitch != 0 || !pRegion->eg[i].pitch_oncc.empty()) {
919     if(pitchEGs.size() < pitchEGs.capacity()) pitchEGs.add(EGs[EGs.size() - 1]);
920     else std::cerr << "Maximum number of EGs reached!" << std::endl;
921     }
922 iliev 2237
923     if (pRegion->eg[i].pan != 0 || !pRegion->eg[i].pan_oncc.empty()) {
924     if(panEGs.size() < panEGs.capacity()) panEGs.add(EGs[EGs.size() - 1]);
925     else std::cerr << "Maximum number of EGs reached!" << std::endl;
926     }
927 iliev 2218 }
928    
929     if (pRegion->ampeg_sustain == -1) {
930     if (volEGs.size() > 0) pRegion->ampeg_sustain = 0;
931     else pRegion->ampeg_sustain = 100;
932     }
933    
934 iliev 2219 // LFO
935     for (int i = 0; i < pRegion->lfos.size(); i++) {
936 iliev 2251 if (pRegion->lfos[i].freq <= 0) {
937     if (pRegion->lfos[i].freq_oncc.empty()) continue; // Not initialized
938     else pRegion->lfos[i].freq = 0;
939     }
940 iliev 2219
941     if(LFOs.size() < LFOs.capacity()) {
942     LFOv2Unit lfo(this);
943     lfo.pLfoInfo = &(pRegion->lfos[i]);
944     LFOs.increment()->Copy(lfo);
945 iliev 2233 LFOs[LFOs.size() - 1]->suVolOnCC.SetCCs(pRegion->lfos[i].volume_oncc);
946 iliev 2225 LFOs[LFOs.size() - 1]->suPitchOnCC.SetCCs(pRegion->lfos[i].pitch_oncc);
947 iliev 2227 LFOs[LFOs.size() - 1]->suFreqOnCC.SetCCs(pRegion->lfos[i].freq_oncc);
948 iliev 2233 LFOs[LFOs.size() - 1]->suPanOnCC.SetCCs(pRegion->lfos[i].pan_oncc);
949     LFOs[LFOs.size() - 1]->suCutoffOnCC.SetCCs(pRegion->lfos[i].cutoff_oncc);
950     LFOs[LFOs.size() - 1]->suResOnCC.SetCCs(pRegion->lfos[i].resonance_oncc);
951 iliev 2219 } else { std::cerr << "Maximum number of LFOs reached!" << std::endl; break; }
952    
953 iliev 2233 if (pRegion->lfos[i].volume != 0 || !pRegion->lfos[i].volume_oncc.empty()) {
954     if(volLFOs.size() < volLFOs.capacity()) volLFOs.add(LFOs[LFOs.size() - 1]);
955     else std::cerr << "Maximum number of LFOs reached!" << std::endl;
956     }
957    
958 iliev 2225 if (pRegion->lfos[i].pitch != 0 || !pRegion->lfos[i].pitch_oncc.empty()) {
959     if(pitchLFOs.size() < pitchLFOs.capacity()) pitchLFOs.add(LFOs[LFOs.size() - 1]);
960     else std::cerr << "Maximum number of LFOs reached!" << std::endl;
961     }
962    
963 iliev 2233 if (pRegion->lfos[i].cutoff != 0 || !pRegion->lfos[i].cutoff_oncc.empty()) {
964 iliev 2219 if(filLFOs.size() < filLFOs.capacity()) filLFOs.add(LFOs[LFOs.size() - 1]);
965     else std::cerr << "Maximum number of LFOs reached!" << std::endl;
966     }
967    
968 iliev 2233 if (pRegion->lfos[i].resonance != 0 || !pRegion->lfos[i].resonance_oncc.empty()) {
969 iliev 2219 if(resLFOs.size() < resLFOs.capacity()) resLFOs.add(LFOs[LFOs.size() - 1]);
970     else std::cerr << "Maximum number of LFOs reached!" << std::endl;
971     }
972    
973 iliev 2233 if (pRegion->lfos[i].pan != 0 || !pRegion->lfos[i].pan_oncc.empty()) {
974 iliev 2219 if(panLFOs.size() < panLFOs.capacity()) panLFOs.add(LFOs[LFOs.size() - 1]);
975     else std::cerr << "Maximum number of LFOs reached!" << std::endl;
976     }
977     }
978    
979 iliev 2233 suPitchLFO.suDepthOnCC.SetCCs(pRegion->pitchlfo_depthcc);
980 iliev 2227 suPitchLFO.suFreqOnCC.SetCCs(pRegion->pitchlfo_freqcc);
981 iliev 2224
982 iliev 2233 suFilLFO.suDepthOnCC.SetCCs(pRegion->fillfo_depthcc);
983 iliev 2227 suFilLFO.suFreqOnCC.SetCCs(pRegion->fillfo_freqcc);
984    
985 iliev 2233 suAmpLFO.suDepthOnCC.SetCCs(pRegion->amplfo_depthcc);
986 iliev 2227 suAmpLFO.suFreqOnCC.SetCCs(pRegion->amplfo_freqcc);
987    
988 iliev 2218 Units.clear();
989    
990 iliev 2296 Units.add(&suEq1GainOnCC);
991     Units.add(&suEq2GainOnCC);
992     Units.add(&suEq3GainOnCC);
993     Units.add(&suEq1FreqOnCC);
994     Units.add(&suEq2FreqOnCC);
995     Units.add(&suEq3FreqOnCC);
996     Units.add(&suEq1BwOnCC);
997     Units.add(&suEq2BwOnCC);
998     Units.add(&suEq3BwOnCC);
999    
1000 iliev 2230 Units.add(&suVolOnCC);
1001 iliev 2264 Units.add(&suPitchOnCC);
1002 iliev 2252 Units.add(&suCutoffOnCC);
1003     Units.add(&suResOnCC);
1004 iliev 2230
1005 iliev 2218 Units.add(&suVolEG);
1006 iliev 2222 Units.add(&suFilEG);
1007 iliev 2220 Units.add(&suPitchEG);
1008 iliev 2227
1009     Units.add(&suPitchLFO.suFreqOnCC); // Don't change order! (should be triggered before the LFO)
1010 iliev 2221 Units.add(&suPitchLFO);
1011 iliev 2233 Units.add(&suPitchLFO.suDepthOnCC);
1012 iliev 2226 Units.add(&suPitchLFO.suFadeEG);
1013 iliev 2227
1014     Units.add(&suAmpLFO.suFreqOnCC); // Don't change order! (should be triggered before the LFO)
1015 iliev 2233 Units.add(&suAmpLFO.suDepthOnCC);
1016 iliev 2221 Units.add(&suAmpLFO);
1017 iliev 2226 Units.add(&suAmpLFO.suFadeEG);
1018 iliev 2227
1019     Units.add(&suFilLFO.suFreqOnCC); // Don't change order! (should be triggered before the LFO)
1020 iliev 2233 Units.add(&suFilLFO.suDepthOnCC);
1021 iliev 2221 Units.add(&suFilLFO);
1022 iliev 2226 Units.add(&suFilLFO.suFadeEG);
1023 iliev 2218
1024 iliev 2219 for (int i = 0; i < EGs.size(); i++) {
1025 iliev 2218 Units.add(EGs[i]);
1026 iliev 2235 Units.add(&(EGs[i]->suAmpOnCC));
1027     Units.add(&(EGs[i]->suVolOnCC));
1028     Units.add(&(EGs[i]->suPitchOnCC));
1029     Units.add(&(EGs[i]->suCutoffOnCC));
1030     Units.add(&(EGs[i]->suResOnCC));
1031 iliev 2237 Units.add(&(EGs[i]->suPanOnCC));
1032 iliev 2218 }
1033    
1034 iliev 2219 for (int i = 0; i < LFOs.size(); i++) {
1035 iliev 2227 Units.add(&(LFOs[i]->suFreqOnCC)); // Don't change order! (should be triggered before the LFO)
1036 iliev 2219 Units.add(LFOs[i]);
1037 iliev 2226 Units.add(&(LFOs[i]->suFadeEG));
1038 iliev 2233 Units.add(&(LFOs[i]->suVolOnCC));
1039 iliev 2225 Units.add(&(LFOs[i]->suPitchOnCC));
1040 iliev 2233 Units.add(&(LFOs[i]->suPanOnCC));
1041     Units.add(&(LFOs[i]->suCutoffOnCC));
1042     Units.add(&(LFOs[i]->suResOnCC));
1043 iliev 2219 }
1044    
1045 iliev 2218 Units.add(&suEndpoint);
1046 iliev 2236 Units.add(&suEndpoint.suXFInCC);
1047     Units.add(&suEndpoint.suXFOutCC);
1048 iliev 2237 Units.add(&suEndpoint.suPanOnCC);
1049 iliev 2218
1050     SignalUnitRack::Trigger();
1051     }
1052    
1053     EndpointSignalUnit* SfzSignalUnitRack::GetEndpointUnit() {
1054     return &suEndpoint;
1055     }
1056    
1057     void SfzSignalUnitRack::EnterFadeOutStage() {
1058     suVolEG.EG.enterFadeOutStage();
1059    
1060     for (int i = 0; i < volEGs.size(); i++) {
1061     volEGs[i]->EG.enterFadeOutStage();
1062     }
1063     }
1064    
1065 iliev 2244 void SfzSignalUnitRack::Reset() {
1066 iliev 2296 suEq1GainOnCC.RemoveAllCCs();
1067     suEq2GainOnCC.RemoveAllCCs();
1068     suEq3GainOnCC.RemoveAllCCs();
1069     suEq1FreqOnCC.RemoveAllCCs();
1070     suEq2FreqOnCC.RemoveAllCCs();
1071     suEq3FreqOnCC.RemoveAllCCs();
1072     suEq1BwOnCC.RemoveAllCCs();
1073     suEq2BwOnCC.RemoveAllCCs();
1074     suEq3BwOnCC.RemoveAllCCs();
1075    
1076 iliev 2244 suVolOnCC.RemoveAllCCs();
1077 iliev 2264 suPitchOnCC.RemoveAllCCs();
1078 iliev 2252 suCutoffOnCC.RemoveAllCCs();
1079     suResOnCC.RemoveAllCCs();
1080 iliev 2244 suEndpoint.suXFInCC.RemoveAllCCs();
1081     suEndpoint.suXFOutCC.RemoveAllCCs();
1082     suEndpoint.suPanOnCC.RemoveAllCCs();
1083     suPitchLFO.suDepthOnCC.RemoveAllCCs();
1084     suPitchLFO.suFreqOnCC.RemoveAllCCs();
1085     suFilLFO.suDepthOnCC.RemoveAllCCs();
1086     suFilLFO.suFreqOnCC.RemoveAllCCs();
1087     suAmpLFO.suDepthOnCC.RemoveAllCCs();
1088     suAmpLFO.suFreqOnCC.RemoveAllCCs();
1089    
1090     for (int i = 0; i < EGs.capacity(); i++) {
1091     EGs[i]->suAmpOnCC.RemoveAllCCs();
1092     EGs[i]->suVolOnCC.RemoveAllCCs();
1093     EGs[i]->suPitchOnCC.RemoveAllCCs();
1094     EGs[i]->suCutoffOnCC.RemoveAllCCs();
1095     EGs[i]->suResOnCC.RemoveAllCCs();
1096     EGs[i]->suPanOnCC.RemoveAllCCs();
1097     }
1098    
1099     for (int i = 0; i < LFOs.capacity(); i++) {
1100     LFOs[i]->suDepthOnCC.RemoveAllCCs();
1101     LFOs[i]->suFreqOnCC.RemoveAllCCs();
1102     LFOs[i]->suVolOnCC.RemoveAllCCs();
1103     LFOs[i]->suPitchOnCC.RemoveAllCCs();
1104     LFOs[i]->suFreqOnCC.RemoveAllCCs();
1105     LFOs[i]->suPanOnCC.RemoveAllCCs();
1106     LFOs[i]->suCutoffOnCC.RemoveAllCCs();
1107     LFOs[i]->suResOnCC.RemoveAllCCs();
1108     }
1109     }
1110    
1111 iliev 2296 void SfzSignalUnitRack::UpdateEqSettings(EqSupport* pEqSupport) {
1112     if (!pEqSupport->HasSupport()) return;
1113     if (pEqSupport->GetBandCount() < 3) {
1114     std::cerr << "SfzSignalUnitRack::UpdateEqSettings: EQ should have at least 3 bands\n";
1115     return;
1116     }
1117    
1118     ::sfz::Region* const pRegion = pVoice->pRegion;
1119    
1120     float dB = (suEq1GainOnCC.Active() ? suEq1GainOnCC.GetLevel() : 0) + pRegion->eq1_gain;
1121     pEqSupport->SetGain(0, dB);
1122    
1123     dB = (suEq2GainOnCC.Active() ? suEq2GainOnCC.GetLevel() : 0) + pRegion->eq2_gain;
1124     pEqSupport->SetGain(1, dB);
1125    
1126     dB = (suEq3GainOnCC.Active() ? suEq3GainOnCC.GetLevel() : 0) + pRegion->eq3_gain;
1127     pEqSupport->SetGain(2, dB);
1128    
1129     float freq = (suEq1FreqOnCC.Active() ? suEq1FreqOnCC.GetLevel() : 0) + pRegion->eq1_freq;
1130     pEqSupport->SetFreq(0, freq);
1131    
1132     freq = (suEq2FreqOnCC.Active() ? suEq2FreqOnCC.GetLevel() : 0) + pRegion->eq2_freq;
1133     pEqSupport->SetFreq(1, freq);
1134    
1135     freq = (suEq3FreqOnCC.Active() ? suEq3FreqOnCC.GetLevel() : 0) + pRegion->eq3_freq;
1136     pEqSupport->SetFreq(2, freq);
1137    
1138     float bw = (suEq1BwOnCC.Active() ? suEq1BwOnCC.GetLevel() : 0) + pRegion->eq1_bw;
1139     pEqSupport->SetBandwidth(0, bw);
1140    
1141     bw = (suEq2BwOnCC.Active() ? suEq2BwOnCC.GetLevel() : 0) + pRegion->eq2_bw;
1142     pEqSupport->SetBandwidth(1, bw);
1143    
1144     bw = (suEq3BwOnCC.Active() ? suEq3BwOnCC.GetLevel() : 0) + pRegion->eq3_bw;
1145     pEqSupport->SetBandwidth(2, bw);
1146     }
1147    
1148 iliev 2218 }} // namespace LinuxSampler::sfz

  ViewVC Help
Powered by ViewVC