/[svn]/linuxsampler/trunk/src/engines/gig/Voice.cpp
ViewVC logotype

Annotation of /linuxsampler/trunk/src/engines/gig/Voice.cpp

Parent Directory Parent Directory | Revision Log Revision Log


Revision 285 - (hide annotations) (download)
Thu Oct 14 21:31:26 2004 UTC (19 years, 5 months ago) by schoenebeck
File size: 50226 byte(s)
* bunch of bugfixes (e.g. segfault on voice stealing)

1 schoenebeck 53 /***************************************************************************
2     * *
3     * LinuxSampler - modular, streaming capable sampler *
4     * *
5 schoenebeck 56 * Copyright (C) 2003, 2004 by Benno Senoner and Christian Schoenebeck *
6 schoenebeck 53 * *
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 "EGADSR.h"
24     #include "Manipulator.h"
25    
26     #include "Voice.h"
27    
28     namespace LinuxSampler { namespace gig {
29    
30     const float Voice::FILTER_CUTOFF_COEFF(CalculateFilterCutoffCoeff());
31    
32 schoenebeck 80 const int Voice::FILTER_UPDATE_MASK(CalculateFilterUpdateMask());
33    
34 schoenebeck 53 float Voice::CalculateFilterCutoffCoeff() {
35     return log(FILTER_CUTOFF_MIN / FILTER_CUTOFF_MAX);
36     }
37    
38 schoenebeck 80 int Voice::CalculateFilterUpdateMask() {
39     if (FILTER_UPDATE_PERIOD <= 0) return 0;
40     int power_of_two;
41     for (power_of_two = 0; 1<<power_of_two < FILTER_UPDATE_PERIOD; power_of_two++);
42     return (1 << power_of_two) - 1;
43     }
44    
45 schoenebeck 53 Voice::Voice() {
46     pEngine = NULL;
47     pDiskThread = NULL;
48 schoenebeck 285 PlaybackState = playback_state_end;
49 schoenebeck 53 pEG1 = NULL;
50     pEG2 = NULL;
51     pEG3 = NULL;
52     pVCAManipulator = NULL;
53     pVCFCManipulator = NULL;
54     pVCOManipulator = NULL;
55     pLFO1 = NULL;
56     pLFO2 = NULL;
57     pLFO3 = NULL;
58 schoenebeck 239 KeyGroup = 0;
59 schoenebeck 53 }
60    
61     Voice::~Voice() {
62     if (pEG1) delete pEG1;
63     if (pEG2) delete pEG2;
64     if (pEG3) delete pEG3;
65     if (pLFO1) delete pLFO1;
66     if (pLFO2) delete pLFO2;
67     if (pLFO3) delete pLFO3;
68     if (pVCAManipulator) delete pVCAManipulator;
69     if (pVCFCManipulator) delete pVCFCManipulator;
70     if (pVCOManipulator) delete pVCOManipulator;
71     }
72    
73     void Voice::SetEngine(Engine* pEngine) {
74     this->pEngine = pEngine;
75    
76     // delete old objects
77     if (pEG1) delete pEG1;
78     if (pEG2) delete pEG2;
79     if (pEG3) delete pEG3;
80     if (pVCAManipulator) delete pVCAManipulator;
81     if (pVCFCManipulator) delete pVCFCManipulator;
82     if (pVCOManipulator) delete pVCOManipulator;
83     if (pLFO1) delete pLFO1;
84     if (pLFO2) delete pLFO2;
85     if (pLFO3) delete pLFO3;
86    
87     // create new ones
88     pEG1 = new EGADSR(pEngine, Event::destination_vca);
89     pEG2 = new EGADSR(pEngine, Event::destination_vcfc);
90     pEG3 = new EGDecay(pEngine, Event::destination_vco);
91     pVCAManipulator = new VCAManipulator(pEngine);
92     pVCFCManipulator = new VCFCManipulator(pEngine);
93     pVCOManipulator = new VCOManipulator(pEngine);
94     pLFO1 = new LFO<gig::VCAManipulator>(0.0f, 1.0f, LFO<VCAManipulator>::propagation_top_down, pVCAManipulator, pEngine->pEventPool);
95     pLFO2 = new LFO<gig::VCFCManipulator>(0.0f, 1.0f, LFO<VCFCManipulator>::propagation_top_down, pVCFCManipulator, pEngine->pEventPool);
96     pLFO3 = new LFO<gig::VCOManipulator>(-1200.0f, 1200.0f, LFO<VCOManipulator>::propagation_middle_balanced, pVCOManipulator, pEngine->pEventPool); // +-1 octave (+-1200 cents) max.
97    
98     this->pDiskThread = pEngine->pDiskThread;
99 schoenebeck 64 dmsg(6,("Voice::SetEngine()\n"));
100 schoenebeck 53 }
101    
102     /**
103     * Initializes and triggers the voice, a disk stream will be launched if
104     * needed.
105     *
106 schoenebeck 271 * @param itNoteOnEvent - event that caused triggering of this voice
107 schoenebeck 242 * @param PitchBend - MIDI detune factor (-8192 ... +8191)
108     * @param pInstrument - points to the loaded instrument which provides sample wave(s) and articulation data
109     * @param iLayer - layer number this voice refers to (only if this is a layered sound of course)
110     * @param ReleaseTriggerVoice - if this new voice is a release trigger voice (optional, default = false)
111     * @returns 0 on success, a value < 0 if something failed
112 schoenebeck 53 */
113 schoenebeck 271 int Voice::Trigger(Pool<Event>::Iterator& itNoteOnEvent, int PitchBend, ::gig::Instrument* pInstrument, int iLayer, bool ReleaseTriggerVoice) {
114 schoenebeck 53 if (!pInstrument) {
115     dmsg(1,("voice::trigger: !pInstrument\n"));
116     exit(EXIT_FAILURE);
117     }
118    
119 schoenebeck 242 Type = type_normal;
120 schoenebeck 271 MIDIKey = itNoteOnEvent->Param.Note.Key;
121 schoenebeck 53 pRegion = pInstrument->GetRegion(MIDIKey);
122     PlaybackState = playback_state_ram; // we always start playback from RAM cache and switch then to disk if needed
123 schoenebeck 271 Delay = itNoteOnEvent->FragmentPos();
124     itTriggerEvent = itNoteOnEvent;
125     itKillEvent = Pool<Event>::Iterator();
126 schoenebeck 285 itChildVoice = Pool<Voice>::Iterator();
127 schoenebeck 53
128     if (!pRegion) {
129 schoenebeck 230 std::cerr << "gig::Voice: No Region defined for MIDI key " << MIDIKey << std::endl << std::flush;
130 schoenebeck 239 KillImmediately();
131 schoenebeck 53 return -1;
132     }
133    
134 schoenebeck 239 KeyGroup = pRegion->KeyGroup;
135    
136 schoenebeck 230 // get current dimension values to select the right dimension region
137     //FIXME: controller values for selecting the dimension region here are currently not sample accurate
138     uint DimValues[5] = {0,0,0,0,0};
139     for (int i = pRegion->Dimensions - 1; i >= 0; i--) {
140     switch (pRegion->pDimensionDefinitions[i].dimension) {
141     case ::gig::dimension_samplechannel:
142     DimValues[i] = 0; //TODO: we currently ignore this dimension
143     break;
144     case ::gig::dimension_layer:
145 schoenebeck 233 DimValues[i] = iLayer;
146     // if this is the 1st layer then spawn further voices for all the other layers
147     if (iLayer == 0)
148     for (int iNewLayer = 1; iNewLayer < pRegion->pDimensionDefinitions[i].zones; iNewLayer++)
149 schoenebeck 285 itChildVoice = pEngine->LaunchVoice(itNoteOnEvent, iNewLayer, ReleaseTriggerVoice);
150 schoenebeck 230 break;
151     case ::gig::dimension_velocity:
152 schoenebeck 271 DimValues[i] = itNoteOnEvent->Param.Note.Velocity;
153 schoenebeck 230 break;
154     case ::gig::dimension_channelaftertouch:
155     DimValues[i] = 0; //TODO: we currently ignore this dimension
156     break;
157     case ::gig::dimension_releasetrigger:
158 schoenebeck 242 Type = (ReleaseTriggerVoice) ? type_release_trigger : (!iLayer) ? type_release_trigger_required : type_normal;
159     DimValues[i] = (uint) ReleaseTriggerVoice;
160 schoenebeck 230 break;
161     case ::gig::dimension_keyboard:
162 schoenebeck 271 DimValues[i] = (uint) itNoteOnEvent->Param.Note.Key;
163 schoenebeck 230 break;
164     case ::gig::dimension_modwheel:
165     DimValues[i] = pEngine->ControllerTable[1];
166     break;
167     case ::gig::dimension_breath:
168     DimValues[i] = pEngine->ControllerTable[2];
169     break;
170     case ::gig::dimension_foot:
171     DimValues[i] = pEngine->ControllerTable[4];
172     break;
173     case ::gig::dimension_portamentotime:
174     DimValues[i] = pEngine->ControllerTable[5];
175     break;
176     case ::gig::dimension_effect1:
177     DimValues[i] = pEngine->ControllerTable[12];
178     break;
179     case ::gig::dimension_effect2:
180     DimValues[i] = pEngine->ControllerTable[13];
181     break;
182     case ::gig::dimension_genpurpose1:
183     DimValues[i] = pEngine->ControllerTable[16];
184     break;
185     case ::gig::dimension_genpurpose2:
186     DimValues[i] = pEngine->ControllerTable[17];
187     break;
188     case ::gig::dimension_genpurpose3:
189     DimValues[i] = pEngine->ControllerTable[18];
190     break;
191     case ::gig::dimension_genpurpose4:
192     DimValues[i] = pEngine->ControllerTable[19];
193     break;
194     case ::gig::dimension_sustainpedal:
195     DimValues[i] = pEngine->ControllerTable[64];
196     break;
197     case ::gig::dimension_portamento:
198     DimValues[i] = pEngine->ControllerTable[65];
199     break;
200     case ::gig::dimension_sostenutopedal:
201     DimValues[i] = pEngine->ControllerTable[66];
202     break;
203     case ::gig::dimension_softpedal:
204     DimValues[i] = pEngine->ControllerTable[67];
205     break;
206     case ::gig::dimension_genpurpose5:
207     DimValues[i] = pEngine->ControllerTable[80];
208     break;
209     case ::gig::dimension_genpurpose6:
210     DimValues[i] = pEngine->ControllerTable[81];
211     break;
212     case ::gig::dimension_genpurpose7:
213     DimValues[i] = pEngine->ControllerTable[82];
214     break;
215     case ::gig::dimension_genpurpose8:
216     DimValues[i] = pEngine->ControllerTable[83];
217     break;
218     case ::gig::dimension_effect1depth:
219     DimValues[i] = pEngine->ControllerTable[91];
220     break;
221     case ::gig::dimension_effect2depth:
222     DimValues[i] = pEngine->ControllerTable[92];
223     break;
224     case ::gig::dimension_effect3depth:
225     DimValues[i] = pEngine->ControllerTable[93];
226     break;
227     case ::gig::dimension_effect4depth:
228     DimValues[i] = pEngine->ControllerTable[94];
229     break;
230     case ::gig::dimension_effect5depth:
231     DimValues[i] = pEngine->ControllerTable[95];
232     break;
233     case ::gig::dimension_none:
234     std::cerr << "gig::Voice::Trigger() Error: dimension=none\n" << std::flush;
235     break;
236     default:
237     std::cerr << "gig::Voice::Trigger() Error: Unknown dimension\n" << std::flush;
238 schoenebeck 53 }
239     }
240 schoenebeck 236 pDimRgn = pRegion->GetDimensionRegionByValue(DimValues[4],DimValues[3],DimValues[2],DimValues[1],DimValues[0]);
241 schoenebeck 53
242 schoenebeck 236 // get starting crossfade volume level
243     switch (pDimRgn->AttenuationController.type) {
244     case ::gig::attenuation_ctrl_t::type_channelaftertouch:
245     CrossfadeVolume = 1.0f; //TODO: aftertouch not supported yet
246     break;
247     case ::gig::attenuation_ctrl_t::type_velocity:
248 schoenebeck 271 CrossfadeVolume = CrossfadeAttenuation(itNoteOnEvent->Param.Note.Velocity);
249 schoenebeck 236 break;
250     case ::gig::attenuation_ctrl_t::type_controlchange: //FIXME: currently not sample accurate
251     CrossfadeVolume = CrossfadeAttenuation(pEngine->ControllerTable[pDimRgn->AttenuationController.controller_number]);
252     break;
253     case ::gig::attenuation_ctrl_t::type_none: // no crossfade defined
254     default:
255     CrossfadeVolume = 1.0f;
256     }
257    
258 schoenebeck 271 PanLeft = 1.0f - float(RTMath::Max(pDimRgn->Pan, 0)) / 63.0f;
259     PanRight = 1.0f - float(RTMath::Min(pDimRgn->Pan, 0)) / -64.0f;
260 schoenebeck 245
261 schoenebeck 53 pSample = pDimRgn->pSample; // sample won't change until the voice is finished
262    
263 schoenebeck 236 Pos = pDimRgn->SampleStartOffset; // offset where we should start playback of sample (0 - 2000 sample points)
264    
265 schoenebeck 53 // Check if the sample needs disk streaming or is too short for that
266     long cachedsamples = pSample->GetCache().Size / pSample->FrameSize;
267     DiskVoice = cachedsamples < pSample->SamplesTotal;
268    
269     if (DiskVoice) { // voice to be streamed from disk
270 schoenebeck 225 MaxRAMPos = cachedsamples - (pEngine->MaxSamplesPerCycle << MAX_PITCH) / pSample->Channels; //TODO: this calculation is too pessimistic and may better be moved to Render() method, so it calculates MaxRAMPos dependent to the current demand of sample points to be rendered (e.g. in case of JACK)
271 schoenebeck 53
272     // check if there's a loop defined which completely fits into the cached (RAM) part of the sample
273     if (pSample->Loops && pSample->LoopEnd <= MaxRAMPos) {
274     RAMLoop = true;
275     LoopCyclesLeft = pSample->LoopPlayCount;
276     }
277     else RAMLoop = false;
278    
279     if (pDiskThread->OrderNewStream(&DiskStreamRef, pSample, MaxRAMPos, !RAMLoop) < 0) {
280     dmsg(1,("Disk stream order failed!\n"));
281 schoenebeck 239 KillImmediately();
282 schoenebeck 53 return -1;
283     }
284     dmsg(4,("Disk voice launched (cached samples: %d, total Samples: %d, MaxRAMPos: %d, RAMLooping: %s)\n", cachedsamples, pSample->SamplesTotal, MaxRAMPos, (RAMLoop) ? "yes" : "no"));
285     }
286     else { // RAM only voice
287     MaxRAMPos = cachedsamples;
288     if (pSample->Loops) {
289     RAMLoop = true;
290     LoopCyclesLeft = pSample->LoopPlayCount;
291     }
292     else RAMLoop = false;
293     dmsg(4,("RAM only voice launched (Looping: %s)\n", (RAMLoop) ? "yes" : "no"));
294     }
295    
296    
297     // calculate initial pitch value
298     {
299 schoenebeck 244 double pitchbasecents = pDimRgn->FineTune * 10 + (int) pEngine->ScaleTuning[MIDIKey % 12];
300 schoenebeck 53 if (pDimRgn->PitchTrack) pitchbasecents += (MIDIKey - (int) pDimRgn->UnityNote) * 100;
301 schoenebeck 233 this->PitchBase = RTMath::CentsToFreqRatio(pitchbasecents) * (double(pSample->SamplesPerSecond) / double(pEngine->pAudioOutputDevice->SampleRate()));
302 schoenebeck 53 this->PitchBend = RTMath::CentsToFreqRatio(((double) PitchBend / 8192.0) * 200.0); // pitchbend wheel +-2 semitones = 200 cents
303     }
304    
305    
306 schoenebeck 271 Volume = pDimRgn->GetVelocityAttenuation(itNoteOnEvent->Param.Note.Velocity) / 32768.0f; // we downscale by 32768 to convert from int16 value range to DSP value range (which is -1.0..1.0)
307 schoenebeck 53
308    
309     // setup EG 1 (VCA EG)
310     {
311     // get current value of EG1 controller
312     double eg1controllervalue;
313     switch (pDimRgn->EG1Controller.type) {
314     case ::gig::eg1_ctrl_t::type_none: // no controller defined
315     eg1controllervalue = 0;
316     break;
317     case ::gig::eg1_ctrl_t::type_channelaftertouch:
318     eg1controllervalue = 0; // TODO: aftertouch not yet supported
319     break;
320     case ::gig::eg1_ctrl_t::type_velocity:
321 schoenebeck 271 eg1controllervalue = itNoteOnEvent->Param.Note.Velocity;
322 schoenebeck 53 break;
323     case ::gig::eg1_ctrl_t::type_controlchange: // MIDI control change controller
324     eg1controllervalue = pEngine->ControllerTable[pDimRgn->EG1Controller.controller_number];
325     break;
326     }
327     if (pDimRgn->EG1ControllerInvert) eg1controllervalue = 127 - eg1controllervalue;
328    
329     // calculate influence of EG1 controller on EG1's parameters (TODO: needs to be fine tuned)
330     double eg1attack = (pDimRgn->EG1ControllerAttackInfluence) ? 0.0001 * (double) (1 << pDimRgn->EG1ControllerAttackInfluence) * eg1controllervalue : 0.0;
331     double eg1decay = (pDimRgn->EG1ControllerDecayInfluence) ? 0.0001 * (double) (1 << pDimRgn->EG1ControllerDecayInfluence) * eg1controllervalue : 0.0;
332     double eg1release = (pDimRgn->EG1ControllerReleaseInfluence) ? 0.0001 * (double) (1 << pDimRgn->EG1ControllerReleaseInfluence) * eg1controllervalue : 0.0;
333    
334     pEG1->Trigger(pDimRgn->EG1PreAttack,
335     pDimRgn->EG1Attack + eg1attack,
336     pDimRgn->EG1Hold,
337     pSample->LoopStart,
338     pDimRgn->EG1Decay1 + eg1decay,
339     pDimRgn->EG1Decay2 + eg1decay,
340     pDimRgn->EG1InfiniteSustain,
341     pDimRgn->EG1Sustain,
342     pDimRgn->EG1Release + eg1release,
343     Delay);
344     }
345    
346    
347     #if ENABLE_FILTER
348     // setup EG 2 (VCF Cutoff EG)
349     {
350     // get current value of EG2 controller
351     double eg2controllervalue;
352     switch (pDimRgn->EG2Controller.type) {
353     case ::gig::eg2_ctrl_t::type_none: // no controller defined
354     eg2controllervalue = 0;
355     break;
356     case ::gig::eg2_ctrl_t::type_channelaftertouch:
357     eg2controllervalue = 0; // TODO: aftertouch not yet supported
358     break;
359     case ::gig::eg2_ctrl_t::type_velocity:
360 schoenebeck 271 eg2controllervalue = itNoteOnEvent->Param.Note.Velocity;
361 schoenebeck 53 break;
362     case ::gig::eg2_ctrl_t::type_controlchange: // MIDI control change controller
363     eg2controllervalue = pEngine->ControllerTable[pDimRgn->EG2Controller.controller_number];
364     break;
365     }
366     if (pDimRgn->EG2ControllerInvert) eg2controllervalue = 127 - eg2controllervalue;
367    
368     // calculate influence of EG2 controller on EG2's parameters (TODO: needs to be fine tuned)
369     double eg2attack = (pDimRgn->EG2ControllerAttackInfluence) ? 0.0001 * (double) (1 << pDimRgn->EG2ControllerAttackInfluence) * eg2controllervalue : 0.0;
370     double eg2decay = (pDimRgn->EG2ControllerDecayInfluence) ? 0.0001 * (double) (1 << pDimRgn->EG2ControllerDecayInfluence) * eg2controllervalue : 0.0;
371     double eg2release = (pDimRgn->EG2ControllerReleaseInfluence) ? 0.0001 * (double) (1 << pDimRgn->EG2ControllerReleaseInfluence) * eg2controllervalue : 0.0;
372    
373     pEG2->Trigger(pDimRgn->EG2PreAttack,
374     pDimRgn->EG2Attack + eg2attack,
375     false,
376     pSample->LoopStart,
377     pDimRgn->EG2Decay1 + eg2decay,
378     pDimRgn->EG2Decay2 + eg2decay,
379     pDimRgn->EG2InfiniteSustain,
380     pDimRgn->EG2Sustain,
381     pDimRgn->EG2Release + eg2release,
382     Delay);
383     }
384     #endif // ENABLE_FILTER
385    
386    
387     // setup EG 3 (VCO EG)
388     {
389     double eg3depth = RTMath::CentsToFreqRatio(pDimRgn->EG3Depth);
390     pEG3->Trigger(eg3depth, pDimRgn->EG3Attack, Delay);
391     }
392    
393    
394     // setup LFO 1 (VCA LFO)
395     {
396     uint16_t lfo1_internal_depth;
397     switch (pDimRgn->LFO1Controller) {
398     case ::gig::lfo1_ctrl_internal:
399     lfo1_internal_depth = pDimRgn->LFO1InternalDepth;
400     pLFO1->ExtController = 0; // no external controller
401     break;
402     case ::gig::lfo1_ctrl_modwheel:
403     lfo1_internal_depth = 0;
404     pLFO1->ExtController = 1; // MIDI controller 1
405     break;
406     case ::gig::lfo1_ctrl_breath:
407     lfo1_internal_depth = 0;
408     pLFO1->ExtController = 2; // MIDI controller 2
409     break;
410     case ::gig::lfo1_ctrl_internal_modwheel:
411     lfo1_internal_depth = pDimRgn->LFO1InternalDepth;
412     pLFO1->ExtController = 1; // MIDI controller 1
413     break;
414     case ::gig::lfo1_ctrl_internal_breath:
415     lfo1_internal_depth = pDimRgn->LFO1InternalDepth;
416     pLFO1->ExtController = 2; // MIDI controller 2
417     break;
418     default:
419     lfo1_internal_depth = 0;
420     pLFO1->ExtController = 0; // no external controller
421     }
422     pLFO1->Trigger(pDimRgn->LFO1Frequency,
423     lfo1_internal_depth,
424     pDimRgn->LFO1ControlDepth,
425     pEngine->ControllerTable[pLFO1->ExtController],
426     pDimRgn->LFO1FlipPhase,
427 schoenebeck 225 pEngine->SampleRate,
428 schoenebeck 53 Delay);
429     }
430    
431     #if ENABLE_FILTER
432     // setup LFO 2 (VCF Cutoff LFO)
433     {
434     uint16_t lfo2_internal_depth;
435     switch (pDimRgn->LFO2Controller) {
436     case ::gig::lfo2_ctrl_internal:
437     lfo2_internal_depth = pDimRgn->LFO2InternalDepth;
438     pLFO2->ExtController = 0; // no external controller
439     break;
440     case ::gig::lfo2_ctrl_modwheel:
441     lfo2_internal_depth = 0;
442     pLFO2->ExtController = 1; // MIDI controller 1
443     break;
444     case ::gig::lfo2_ctrl_foot:
445     lfo2_internal_depth = 0;
446     pLFO2->ExtController = 4; // MIDI controller 4
447     break;
448     case ::gig::lfo2_ctrl_internal_modwheel:
449     lfo2_internal_depth = pDimRgn->LFO2InternalDepth;
450     pLFO2->ExtController = 1; // MIDI controller 1
451     break;
452     case ::gig::lfo2_ctrl_internal_foot:
453     lfo2_internal_depth = pDimRgn->LFO2InternalDepth;
454     pLFO2->ExtController = 4; // MIDI controller 4
455     break;
456     default:
457     lfo2_internal_depth = 0;
458     pLFO2->ExtController = 0; // no external controller
459     }
460     pLFO2->Trigger(pDimRgn->LFO2Frequency,
461     lfo2_internal_depth,
462     pDimRgn->LFO2ControlDepth,
463     pEngine->ControllerTable[pLFO2->ExtController],
464     pDimRgn->LFO2FlipPhase,
465 schoenebeck 225 pEngine->SampleRate,
466 schoenebeck 53 Delay);
467     }
468     #endif // ENABLE_FILTER
469    
470     // setup LFO 3 (VCO LFO)
471     {
472     uint16_t lfo3_internal_depth;
473     switch (pDimRgn->LFO3Controller) {
474     case ::gig::lfo3_ctrl_internal:
475     lfo3_internal_depth = pDimRgn->LFO3InternalDepth;
476     pLFO3->ExtController = 0; // no external controller
477     break;
478     case ::gig::lfo3_ctrl_modwheel:
479     lfo3_internal_depth = 0;
480     pLFO3->ExtController = 1; // MIDI controller 1
481     break;
482     case ::gig::lfo3_ctrl_aftertouch:
483     lfo3_internal_depth = 0;
484     pLFO3->ExtController = 0; // TODO: aftertouch not implemented yet
485     break;
486     case ::gig::lfo3_ctrl_internal_modwheel:
487     lfo3_internal_depth = pDimRgn->LFO3InternalDepth;
488     pLFO3->ExtController = 1; // MIDI controller 1
489     break;
490     case ::gig::lfo3_ctrl_internal_aftertouch:
491     lfo3_internal_depth = pDimRgn->LFO3InternalDepth;
492     pLFO1->ExtController = 0; // TODO: aftertouch not implemented yet
493     break;
494     default:
495     lfo3_internal_depth = 0;
496     pLFO3->ExtController = 0; // no external controller
497     }
498     pLFO3->Trigger(pDimRgn->LFO3Frequency,
499     lfo3_internal_depth,
500     pDimRgn->LFO3ControlDepth,
501     pEngine->ControllerTable[pLFO3->ExtController],
502     false,
503 schoenebeck 225 pEngine->SampleRate,
504 schoenebeck 53 Delay);
505     }
506    
507     #if ENABLE_FILTER
508     #if FORCE_FILTER_USAGE
509     FilterLeft.Enabled = FilterRight.Enabled = true;
510     #else // use filter only if instrument file told so
511     FilterLeft.Enabled = FilterRight.Enabled = pDimRgn->VCFEnabled;
512     #endif // FORCE_FILTER_USAGE
513     if (pDimRgn->VCFEnabled) {
514     #ifdef OVERRIDE_FILTER_CUTOFF_CTRL
515     VCFCutoffCtrl.controller = OVERRIDE_FILTER_CUTOFF_CTRL;
516     #else // use the one defined in the instrument file
517     switch (pDimRgn->VCFCutoffController) {
518     case ::gig::vcf_cutoff_ctrl_modwheel:
519     VCFCutoffCtrl.controller = 1;
520     break;
521     case ::gig::vcf_cutoff_ctrl_effect1:
522     VCFCutoffCtrl.controller = 12;
523     break;
524     case ::gig::vcf_cutoff_ctrl_effect2:
525     VCFCutoffCtrl.controller = 13;
526     break;
527     case ::gig::vcf_cutoff_ctrl_breath:
528     VCFCutoffCtrl.controller = 2;
529     break;
530     case ::gig::vcf_cutoff_ctrl_foot:
531     VCFCutoffCtrl.controller = 4;
532     break;
533     case ::gig::vcf_cutoff_ctrl_sustainpedal:
534     VCFCutoffCtrl.controller = 64;
535     break;
536     case ::gig::vcf_cutoff_ctrl_softpedal:
537     VCFCutoffCtrl.controller = 67;
538     break;
539     case ::gig::vcf_cutoff_ctrl_genpurpose7:
540     VCFCutoffCtrl.controller = 82;
541     break;
542     case ::gig::vcf_cutoff_ctrl_genpurpose8:
543     VCFCutoffCtrl.controller = 83;
544     break;
545     case ::gig::vcf_cutoff_ctrl_aftertouch: //TODO: not implemented yet
546     case ::gig::vcf_cutoff_ctrl_none:
547     default:
548     VCFCutoffCtrl.controller = 0;
549     break;
550     }
551     #endif // OVERRIDE_FILTER_CUTOFF_CTRL
552    
553     #ifdef OVERRIDE_FILTER_RES_CTRL
554     VCFResonanceCtrl.controller = OVERRIDE_FILTER_RES_CTRL;
555     #else // use the one defined in the instrument file
556     switch (pDimRgn->VCFResonanceController) {
557     case ::gig::vcf_res_ctrl_genpurpose3:
558     VCFResonanceCtrl.controller = 18;
559     break;
560     case ::gig::vcf_res_ctrl_genpurpose4:
561     VCFResonanceCtrl.controller = 19;
562     break;
563     case ::gig::vcf_res_ctrl_genpurpose5:
564     VCFResonanceCtrl.controller = 80;
565     break;
566     case ::gig::vcf_res_ctrl_genpurpose6:
567     VCFResonanceCtrl.controller = 81;
568     break;
569     case ::gig::vcf_res_ctrl_none:
570     default:
571     VCFResonanceCtrl.controller = 0;
572     }
573     #endif // OVERRIDE_FILTER_RES_CTRL
574    
575     #ifndef OVERRIDE_FILTER_TYPE
576     FilterLeft.SetType(pDimRgn->VCFType);
577     FilterRight.SetType(pDimRgn->VCFType);
578     #else // override filter type
579     FilterLeft.SetType(OVERRIDE_FILTER_TYPE);
580     FilterRight.SetType(OVERRIDE_FILTER_TYPE);
581     #endif // OVERRIDE_FILTER_TYPE
582    
583     VCFCutoffCtrl.value = pEngine->ControllerTable[VCFCutoffCtrl.controller];
584     VCFResonanceCtrl.value = pEngine->ControllerTable[VCFResonanceCtrl.controller];
585    
586     // calculate cutoff frequency
587     float cutoff = (!VCFCutoffCtrl.controller)
588 schoenebeck 271 ? exp((float) (127 - itNoteOnEvent->Param.Note.Velocity) * (float) pDimRgn->VCFVelocityScale * 6.2E-5f * FILTER_CUTOFF_COEFF) * FILTER_CUTOFF_MAX
589 schoenebeck 53 : exp((float) VCFCutoffCtrl.value * 0.00787402f * FILTER_CUTOFF_COEFF) * FILTER_CUTOFF_MAX;
590    
591     // calculate resonance
592     float resonance = (float) VCFResonanceCtrl.value * 0.00787f; // 0.0..1.0
593     if (pDimRgn->VCFKeyboardTracking) {
594 schoenebeck 271 resonance += (float) (itNoteOnEvent->Param.Note.Key - pDimRgn->VCFKeyboardTrackingBreakpoint) * 0.00787f;
595 schoenebeck 53 }
596     Constrain(resonance, 0.0, 1.0); // correct resonance if outside allowed value range (0.0..1.0)
597    
598     VCFCutoffCtrl.fvalue = cutoff - FILTER_CUTOFF_MIN;
599     VCFResonanceCtrl.fvalue = resonance;
600    
601 schoenebeck 225 FilterLeft.SetParameters(cutoff, resonance, pEngine->SampleRate);
602     FilterRight.SetParameters(cutoff, resonance, pEngine->SampleRate);
603 schoenebeck 53
604     FilterUpdateCounter = -1;
605     }
606     else {
607     VCFCutoffCtrl.controller = 0;
608     VCFResonanceCtrl.controller = 0;
609     }
610     #endif // ENABLE_FILTER
611    
612     return 0; // success
613     }
614    
615     /**
616     * Renders the audio data for this voice for the current audio fragment.
617     * The sample input data can either come from RAM (cached sample or sample
618     * part) or directly from disk. The output signal will be rendered by
619     * resampling / interpolation. If this voice is a disk streaming voice and
620     * the voice completely played back the cached RAM part of the sample, it
621     * will automatically switch to disk playback for the next RenderAudio()
622     * call.
623     *
624     * @param Samples - number of samples to be rendered in this audio fragment cycle
625     */
626     void Voice::Render(uint Samples) {
627    
628     // Reset the synthesis parameter matrix
629 schoenebeck 236 pEngine->ResetSynthesisParameters(Event::destination_vca, this->Volume * this->CrossfadeVolume * pEngine->GlobalVolume);
630 schoenebeck 53 pEngine->ResetSynthesisParameters(Event::destination_vco, this->PitchBase);
631     #if ENABLE_FILTER
632     pEngine->ResetSynthesisParameters(Event::destination_vcfc, VCFCutoffCtrl.fvalue);
633     pEngine->ResetSynthesisParameters(Event::destination_vcfr, VCFResonanceCtrl.fvalue);
634     #endif // ENABLE_FILTER
635    
636    
637     // Apply events to the synthesis parameter matrix
638     ProcessEvents(Samples);
639    
640    
641     // Let all modulators write their parameter changes to the synthesis parameter matrix for the current audio fragment
642 schoenebeck 271 pEG1->Process(Samples, pEngine->pMIDIKeyInfo[MIDIKey].pEvents, itTriggerEvent, this->Pos, this->PitchBase * this->PitchBend, itKillEvent);
643 schoenebeck 53 #if ENABLE_FILTER
644 schoenebeck 271 pEG2->Process(Samples, pEngine->pMIDIKeyInfo[MIDIKey].pEvents, itTriggerEvent, this->Pos, this->PitchBase * this->PitchBend);
645 schoenebeck 53 #endif // ENABLE_FILTER
646     pEG3->Process(Samples);
647     pLFO1->Process(Samples);
648     #if ENABLE_FILTER
649     pLFO2->Process(Samples);
650     #endif // ENABLE_FILTER
651     pLFO3->Process(Samples);
652    
653    
654 schoenebeck 80 #if ENABLE_FILTER
655     CalculateBiquadParameters(Samples); // calculate the final biquad filter parameters
656     #endif // ENABLE_FILTER
657    
658    
659 schoenebeck 53 switch (this->PlaybackState) {
660    
661     case playback_state_ram: {
662     if (RAMLoop) InterpolateAndLoop(Samples, (sample_t*) pSample->GetCache().pStart, Delay);
663 schoenebeck 245 else InterpolateNoLoop(Samples, (sample_t*) pSample->GetCache().pStart, Delay);
664 schoenebeck 53 if (DiskVoice) {
665     // check if we reached the allowed limit of the sample RAM cache
666     if (Pos > MaxRAMPos) {
667     dmsg(5,("Voice: switching to disk playback (Pos=%f)\n", Pos));
668     this->PlaybackState = playback_state_disk;
669     }
670     }
671     else if (Pos >= pSample->GetCache().Size / pSample->FrameSize) {
672     this->PlaybackState = playback_state_end;
673     }
674     }
675     break;
676    
677     case playback_state_disk: {
678     if (!DiskStreamRef.pStream) {
679     // check if the disk thread created our ordered disk stream in the meantime
680     DiskStreamRef.pStream = pDiskThread->AskForCreatedStream(DiskStreamRef.OrderID);
681     if (!DiskStreamRef.pStream) {
682     std::cout << stderr << "Disk stream not available in time!" << std::endl << std::flush;
683 schoenebeck 239 KillImmediately();
684 schoenebeck 53 return;
685     }
686     DiskStreamRef.pStream->IncrementReadPos(pSample->Channels * (RTMath::DoubleToInt(Pos) - MaxRAMPos));
687     Pos -= RTMath::DoubleToInt(Pos);
688     }
689    
690     // add silence sample at the end if we reached the end of the stream (for the interpolator)
691 schoenebeck 225 if (DiskStreamRef.State == Stream::state_end && DiskStreamRef.pStream->GetReadSpace() < (pEngine->MaxSamplesPerCycle << MAX_PITCH) / pSample->Channels) {
692     DiskStreamRef.pStream->WriteSilence((pEngine->MaxSamplesPerCycle << MAX_PITCH) / pSample->Channels);
693 schoenebeck 53 this->PlaybackState = playback_state_end;
694     }
695    
696     sample_t* ptr = DiskStreamRef.pStream->GetReadPtr(); // get the current read_ptr within the ringbuffer where we read the samples from
697 schoenebeck 245 InterpolateNoLoop(Samples, ptr, Delay);
698 schoenebeck 53 DiskStreamRef.pStream->IncrementReadPos(RTMath::DoubleToInt(Pos) * pSample->Channels);
699     Pos -= RTMath::DoubleToInt(Pos);
700     }
701     break;
702    
703     case playback_state_end:
704 schoenebeck 285 std::cerr << "gig::Voice::Render(): entered with playback_state_end, this is a bug!\n" << std::flush;
705 schoenebeck 53 break;
706     }
707    
708    
709 schoenebeck 236 // Reset synthesis event lists (except VCO, as VCO events apply channel wide currently)
710     pEngine->pSynthesisEvents[Event::destination_vca]->clear();
711 schoenebeck 53 #if ENABLE_FILTER
712     pEngine->pSynthesisEvents[Event::destination_vcfc]->clear();
713     pEngine->pSynthesisEvents[Event::destination_vcfr]->clear();
714     #endif // ENABLE_FILTER
715    
716     // Reset delay
717     Delay = 0;
718    
719 schoenebeck 271 itTriggerEvent = Pool<Event>::Iterator();
720 schoenebeck 53
721 schoenebeck 285 // If sample stream or release stage finished, kill the voice
722     if (PlaybackState == playback_state_end || pEG1->GetStage() == EGADSR::stage_end) KillImmediately();
723 schoenebeck 53 }
724    
725     /**
726     * Resets voice variables. Should only be called if rendering process is
727     * suspended / not running.
728     */
729     void Voice::Reset() {
730     pLFO1->Reset();
731     pLFO2->Reset();
732     pLFO3->Reset();
733     DiskStreamRef.pStream = NULL;
734     DiskStreamRef.hStream = 0;
735     DiskStreamRef.State = Stream::state_unused;
736     DiskStreamRef.OrderID = 0;
737 schoenebeck 285 PlaybackState = playback_state_end;
738     itTriggerEvent = Pool<Event>::Iterator();
739     itKillEvent = Pool<Event>::Iterator();
740 schoenebeck 53 }
741    
742     /**
743     * Process the control change event lists of the engine for the current
744     * audio fragment. Event values will be applied to the synthesis parameter
745     * matrix.
746     *
747     * @param Samples - number of samples to be rendered in this audio fragment cycle
748     */
749     void Voice::ProcessEvents(uint Samples) {
750    
751     // dispatch control change events
752 schoenebeck 271 RTList<Event>::Iterator itCCEvent = pEngine->pCCEvents->first();
753 schoenebeck 53 if (Delay) { // skip events that happened before this voice was triggered
754 schoenebeck 271 while (itCCEvent && itCCEvent->FragmentPos() <= Delay) ++itCCEvent;
755 schoenebeck 53 }
756 schoenebeck 271 while (itCCEvent) {
757     if (itCCEvent->Param.CC.Controller) { // if valid MIDI controller
758 schoenebeck 53 #if ENABLE_FILTER
759 schoenebeck 271 if (itCCEvent->Param.CC.Controller == VCFCutoffCtrl.controller) {
760     *pEngine->pSynthesisEvents[Event::destination_vcfc]->allocAppend() = *itCCEvent;
761 schoenebeck 53 }
762 schoenebeck 271 if (itCCEvent->Param.CC.Controller == VCFResonanceCtrl.controller) {
763     *pEngine->pSynthesisEvents[Event::destination_vcfr]->allocAppend() = *itCCEvent;
764 schoenebeck 53 }
765     #endif // ENABLE_FILTER
766 schoenebeck 271 if (itCCEvent->Param.CC.Controller == pLFO1->ExtController) {
767     pLFO1->SendEvent(itCCEvent);
768 schoenebeck 53 }
769     #if ENABLE_FILTER
770 schoenebeck 271 if (itCCEvent->Param.CC.Controller == pLFO2->ExtController) {
771     pLFO2->SendEvent(itCCEvent);
772 schoenebeck 53 }
773     #endif // ENABLE_FILTER
774 schoenebeck 271 if (itCCEvent->Param.CC.Controller == pLFO3->ExtController) {
775     pLFO3->SendEvent(itCCEvent);
776 schoenebeck 53 }
777 schoenebeck 236 if (pDimRgn->AttenuationController.type == ::gig::attenuation_ctrl_t::type_controlchange &&
778 schoenebeck 271 itCCEvent->Param.CC.Controller == pDimRgn->AttenuationController.controller_number) { // if crossfade event
779     *pEngine->pSynthesisEvents[Event::destination_vca]->allocAppend() = *itCCEvent;
780 schoenebeck 236 }
781 schoenebeck 53 }
782    
783 schoenebeck 271 ++itCCEvent;
784 schoenebeck 53 }
785    
786    
787     // process pitch events
788     {
789 schoenebeck 271 RTList<Event>* pVCOEventList = pEngine->pSynthesisEvents[Event::destination_vco];
790     RTList<Event>::Iterator itVCOEvent = pVCOEventList->first();
791 schoenebeck 53 if (Delay) { // skip events that happened before this voice was triggered
792 schoenebeck 271 while (itVCOEvent && itVCOEvent->FragmentPos() <= Delay) ++itVCOEvent;
793 schoenebeck 53 }
794     // apply old pitchbend value until first pitch event occurs
795     if (this->PitchBend != 1.0) {
796 schoenebeck 271 uint end = (itVCOEvent) ? itVCOEvent->FragmentPos() : Samples;
797 schoenebeck 53 for (uint i = Delay; i < end; i++) {
798     pEngine->pSynthesisParameters[Event::destination_vco][i] *= this->PitchBend;
799     }
800     }
801     float pitch;
802 schoenebeck 271 while (itVCOEvent) {
803     RTList<Event>::Iterator itNextVCOEvent = itVCOEvent;
804     ++itNextVCOEvent;
805 schoenebeck 53
806     // calculate the influence length of this event (in sample points)
807 schoenebeck 271 uint end = (itNextVCOEvent) ? itNextVCOEvent->FragmentPos() : Samples;
808 schoenebeck 53
809 schoenebeck 271 pitch = RTMath::CentsToFreqRatio(((double) itVCOEvent->Param.Pitch.Pitch / 8192.0) * 200.0); // +-two semitones = +-200 cents
810 schoenebeck 53
811     // apply pitch value to the pitch parameter sequence
812 schoenebeck 271 for (uint i = itVCOEvent->FragmentPos(); i < end; i++) {
813 schoenebeck 53 pEngine->pSynthesisParameters[Event::destination_vco][i] *= pitch;
814     }
815    
816 schoenebeck 271 itVCOEvent = itNextVCOEvent;
817 schoenebeck 53 }
818 schoenebeck 271 if (!pVCOEventList->isEmpty()) this->PitchBend = pitch;
819 schoenebeck 53 }
820    
821 schoenebeck 236 // process volume / attenuation events (TODO: we only handle and _expect_ crossfade events here ATM !)
822     {
823 schoenebeck 271 RTList<Event>* pVCAEventList = pEngine->pSynthesisEvents[Event::destination_vca];
824     RTList<Event>::Iterator itVCAEvent = pVCAEventList->first();
825 schoenebeck 236 if (Delay) { // skip events that happened before this voice was triggered
826 schoenebeck 271 while (itVCAEvent && itVCAEvent->FragmentPos() <= Delay) ++itVCAEvent;
827 schoenebeck 236 }
828     float crossfadevolume;
829 schoenebeck 271 while (itVCAEvent) {
830     RTList<Event>::Iterator itNextVCAEvent = itVCAEvent;
831     ++itNextVCAEvent;
832 schoenebeck 53
833 schoenebeck 236 // calculate the influence length of this event (in sample points)
834 schoenebeck 271 uint end = (itNextVCAEvent) ? itNextVCAEvent->FragmentPos() : Samples;
835 schoenebeck 236
836 schoenebeck 271 crossfadevolume = CrossfadeAttenuation(itVCAEvent->Param.CC.Value);
837 schoenebeck 236
838     float effective_volume = crossfadevolume * this->Volume * pEngine->GlobalVolume;
839    
840     // apply volume value to the volume parameter sequence
841 schoenebeck 271 for (uint i = itVCAEvent->FragmentPos(); i < end; i++) {
842 schoenebeck 236 pEngine->pSynthesisParameters[Event::destination_vca][i] = effective_volume;
843     }
844    
845 schoenebeck 271 itVCAEvent = itNextVCAEvent;
846 schoenebeck 236 }
847 schoenebeck 271 if (!pVCAEventList->isEmpty()) this->CrossfadeVolume = crossfadevolume;
848 schoenebeck 236 }
849    
850 schoenebeck 53 #if ENABLE_FILTER
851     // process filter cutoff events
852     {
853 schoenebeck 271 RTList<Event>* pCutoffEventList = pEngine->pSynthesisEvents[Event::destination_vcfc];
854     RTList<Event>::Iterator itCutoffEvent = pCutoffEventList->first();
855 schoenebeck 53 if (Delay) { // skip events that happened before this voice was triggered
856 schoenebeck 271 while (itCutoffEvent && itCutoffEvent->FragmentPos() <= Delay) ++itCutoffEvent;
857 schoenebeck 53 }
858     float cutoff;
859 schoenebeck 271 while (itCutoffEvent) {
860     RTList<Event>::Iterator itNextCutoffEvent = itCutoffEvent;
861     ++itNextCutoffEvent;
862 schoenebeck 53
863     // calculate the influence length of this event (in sample points)
864 schoenebeck 271 uint end = (itNextCutoffEvent) ? itNextCutoffEvent->FragmentPos() : Samples;
865 schoenebeck 53
866 schoenebeck 271 cutoff = exp((float) itCutoffEvent->Param.CC.Value * 0.00787402f * FILTER_CUTOFF_COEFF) * FILTER_CUTOFF_MAX - FILTER_CUTOFF_MIN;
867 schoenebeck 53
868     // apply cutoff frequency to the cutoff parameter sequence
869 schoenebeck 271 for (uint i = itCutoffEvent->FragmentPos(); i < end; i++) {
870 schoenebeck 53 pEngine->pSynthesisParameters[Event::destination_vcfc][i] = cutoff;
871     }
872    
873 schoenebeck 271 itCutoffEvent = itNextCutoffEvent;
874 schoenebeck 53 }
875 schoenebeck 271 if (!pCutoffEventList->isEmpty()) VCFCutoffCtrl.fvalue = cutoff; // needed for initialization of parameter matrix next time
876 schoenebeck 53 }
877    
878     // process filter resonance events
879     {
880 schoenebeck 271 RTList<Event>* pResonanceEventList = pEngine->pSynthesisEvents[Event::destination_vcfr];
881     RTList<Event>::Iterator itResonanceEvent = pResonanceEventList->first();
882 schoenebeck 53 if (Delay) { // skip events that happened before this voice was triggered
883 schoenebeck 271 while (itResonanceEvent && itResonanceEvent->FragmentPos() <= Delay) ++itResonanceEvent;
884 schoenebeck 53 }
885 schoenebeck 271 while (itResonanceEvent) {
886     RTList<Event>::Iterator itNextResonanceEvent = itResonanceEvent;
887     ++itNextResonanceEvent;
888 schoenebeck 53
889     // calculate the influence length of this event (in sample points)
890 schoenebeck 271 uint end = (itNextResonanceEvent) ? itNextResonanceEvent->FragmentPos() : Samples;
891 schoenebeck 53
892     // convert absolute controller value to differential
893 schoenebeck 271 int ctrldelta = itResonanceEvent->Param.CC.Value - VCFResonanceCtrl.value;
894     VCFResonanceCtrl.value = itResonanceEvent->Param.CC.Value;
895 schoenebeck 53
896     float resonancedelta = (float) ctrldelta * 0.00787f; // 0.0..1.0
897    
898     // apply cutoff frequency to the cutoff parameter sequence
899 schoenebeck 271 for (uint i = itResonanceEvent->FragmentPos(); i < end; i++) {
900 schoenebeck 53 pEngine->pSynthesisParameters[Event::destination_vcfr][i] += resonancedelta;
901     }
902    
903 schoenebeck 271 itResonanceEvent = itNextResonanceEvent;
904 schoenebeck 53 }
905 schoenebeck 271 if (!pResonanceEventList->isEmpty()) VCFResonanceCtrl.fvalue = pResonanceEventList->last()->Param.CC.Value * 0.00787f; // needed for initialization of parameter matrix next time
906 schoenebeck 53 }
907     #endif // ENABLE_FILTER
908     }
909    
910 schoenebeck 80 #if ENABLE_FILTER
911 schoenebeck 53 /**
912 schoenebeck 80 * Calculate all necessary, final biquad filter parameters.
913     *
914     * @param Samples - number of samples to be rendered in this audio fragment cycle
915     */
916     void Voice::CalculateBiquadParameters(uint Samples) {
917     if (!FilterLeft.Enabled) return;
918    
919     biquad_param_t bqbase;
920     biquad_param_t bqmain;
921     float prev_cutoff = pEngine->pSynthesisParameters[Event::destination_vcfc][0];
922     float prev_res = pEngine->pSynthesisParameters[Event::destination_vcfr][0];
923 schoenebeck 225 FilterLeft.SetParameters(&bqbase, &bqmain, prev_cutoff, prev_res, pEngine->SampleRate);
924 schoenebeck 80 pEngine->pBasicFilterParameters[0] = bqbase;
925     pEngine->pMainFilterParameters[0] = bqmain;
926    
927     float* bq;
928     for (int i = 1; i < Samples; i++) {
929     // recalculate biquad parameters if cutoff or resonance differ from previous sample point
930     if (!(i & FILTER_UPDATE_MASK)) if (pEngine->pSynthesisParameters[Event::destination_vcfr][i] != prev_res ||
931     pEngine->pSynthesisParameters[Event::destination_vcfc][i] != prev_cutoff) {
932     prev_cutoff = pEngine->pSynthesisParameters[Event::destination_vcfc][i];
933     prev_res = pEngine->pSynthesisParameters[Event::destination_vcfr][i];
934 schoenebeck 225 FilterLeft.SetParameters(&bqbase, &bqmain, prev_cutoff, prev_res, pEngine->SampleRate);
935 schoenebeck 80 }
936    
937     //same as 'pEngine->pBasicFilterParameters[i] = bqbase;'
938     bq = (float*) &pEngine->pBasicFilterParameters[i];
939     bq[0] = bqbase.a1;
940     bq[1] = bqbase.a2;
941     bq[2] = bqbase.b0;
942     bq[3] = bqbase.b1;
943     bq[4] = bqbase.b2;
944    
945     // same as 'pEngine->pMainFilterParameters[i] = bqmain;'
946     bq = (float*) &pEngine->pMainFilterParameters[i];
947     bq[0] = bqmain.a1;
948     bq[1] = bqmain.a2;
949     bq[2] = bqmain.b0;
950     bq[3] = bqmain.b1;
951     bq[4] = bqmain.b2;
952     }
953     }
954     #endif // ENABLE_FILTER
955    
956     /**
957 schoenebeck 245 * Interpolates the input audio data (without looping).
958 schoenebeck 53 *
959     * @param Samples - number of sample points to be rendered in this audio
960     * fragment cycle
961     * @param pSrc - pointer to input sample data
962     * @param Skip - number of sample points to skip in output buffer
963     */
964 schoenebeck 245 void Voice::InterpolateNoLoop(uint Samples, sample_t* pSrc, uint Skip) {
965 schoenebeck 53 int i = Skip;
966    
967     // FIXME: assuming either mono or stereo
968     if (this->pSample->Channels == 2) { // Stereo Sample
969 schoenebeck 245 while (i < Samples) InterpolateStereo(pSrc, i);
970 schoenebeck 53 }
971     else { // Mono Sample
972 schoenebeck 245 while (i < Samples) InterpolateMono(pSrc, i);
973 schoenebeck 53 }
974     }
975    
976     /**
977     * Interpolates the input audio data, this method honors looping.
978     *
979     * @param Samples - number of sample points to be rendered in this audio
980     * fragment cycle
981     * @param pSrc - pointer to input sample data
982     * @param Skip - number of sample points to skip in output buffer
983     */
984     void Voice::InterpolateAndLoop(uint Samples, sample_t* pSrc, uint Skip) {
985     int i = Skip;
986    
987     // FIXME: assuming either mono or stereo
988     if (pSample->Channels == 2) { // Stereo Sample
989     if (pSample->LoopPlayCount) {
990     // render loop (loop count limited)
991     while (i < Samples && LoopCyclesLeft) {
992 schoenebeck 245 InterpolateStereo(pSrc, i);
993 schoenebeck 53 if (Pos > pSample->LoopEnd) {
994     Pos = pSample->LoopStart + fmod(Pos - pSample->LoopEnd, pSample->LoopSize);;
995     LoopCyclesLeft--;
996     }
997     }
998     // render on without loop
999 schoenebeck 245 while (i < Samples) InterpolateStereo(pSrc, i);
1000 schoenebeck 53 }
1001     else { // render loop (endless loop)
1002     while (i < Samples) {
1003 schoenebeck 245 InterpolateStereo(pSrc, i);
1004 schoenebeck 53 if (Pos > pSample->LoopEnd) {
1005     Pos = pSample->LoopStart + fmod(Pos - pSample->LoopEnd, pSample->LoopSize);
1006     }
1007     }
1008     }
1009     }
1010     else { // Mono Sample
1011     if (pSample->LoopPlayCount) {
1012     // render loop (loop count limited)
1013     while (i < Samples && LoopCyclesLeft) {
1014 schoenebeck 245 InterpolateMono(pSrc, i);
1015 schoenebeck 53 if (Pos > pSample->LoopEnd) {
1016     Pos = pSample->LoopStart + fmod(Pos - pSample->LoopEnd, pSample->LoopSize);;
1017     LoopCyclesLeft--;
1018     }
1019     }
1020     // render on without loop
1021 schoenebeck 245 while (i < Samples) InterpolateMono(pSrc, i);
1022 schoenebeck 53 }
1023     else { // render loop (endless loop)
1024     while (i < Samples) {
1025 schoenebeck 245 InterpolateMono(pSrc, i);
1026 schoenebeck 53 if (Pos > pSample->LoopEnd) {
1027     Pos = pSample->LoopStart + fmod(Pos - pSample->LoopEnd, pSample->LoopSize);;
1028     }
1029     }
1030     }
1031     }
1032     }
1033    
1034     /**
1035 schoenebeck 239 * Immediately kill the voice. This method should not be used to kill
1036     * a normal, active voice, because it doesn't take care of things like
1037     * fading down the volume level to avoid clicks and regular processing
1038     * until the kill event actually occured!
1039     *
1040     * @see Kill()
1041 schoenebeck 53 */
1042 schoenebeck 239 void Voice::KillImmediately() {
1043 schoenebeck 53 if (DiskVoice && DiskStreamRef.State != Stream::state_unused) {
1044     pDiskThread->OrderDeletionOfStream(&DiskStreamRef);
1045     }
1046     Reset();
1047     }
1048    
1049 schoenebeck 239 /**
1050     * Kill the voice in regular sense. Let the voice render audio until
1051     * the kill event actually occured and then fade down the volume level
1052     * very quickly and let the voice die finally. Unlike a normal release
1053     * of a voice, a kill process cannot be cancalled and is therefore
1054     * usually used for voice stealing and key group conflicts.
1055     *
1056 schoenebeck 271 * @param itKillEvent - event which caused the voice to be killed
1057 schoenebeck 239 */
1058 schoenebeck 271 void Voice::Kill(Pool<Event>::Iterator& itKillEvent) {
1059     if (itTriggerEvent && itKillEvent->FragmentPos() <= itTriggerEvent->FragmentPos()) return;
1060     this->itKillEvent = itKillEvent;
1061 schoenebeck 239 }
1062    
1063 schoenebeck 53 }} // namespace LinuxSampler::gig

  ViewVC Help
Powered by ViewVC