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

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

Parent Directory Parent Directory | Revision Log Revision Log


Revision 829 - (show annotations) (download)
Sat Jan 14 14:07:47 2006 UTC (18 years, 3 months ago) by schoenebeck
File size: 46098 byte(s)
* implemented portamento mode and solo mode (a.k.a 'mono mode'):
  all modes can be altered via standard GM messages, that is CC5 for
  altering portamento time, CC65 for enabling / disabling portamento
  mode, CC126 for enabling solo mode and CC127 for disabling solo mode
* fixed EG3 (pitch envelope) synthesis which was neutral all the time
* configure.in: do not automatically pick optimized gcc flags if the user
  already provided some on his own (as CXXFLAGS)

1 /***************************************************************************
2 * *
3 * LinuxSampler - modular, streaming capable sampler *
4 * *
5 * Copyright (C) 2003, 2004 by Benno Senoner and Christian Schoenebeck *
6 * Copyright (C) 2005, 2006 Christian Schoenebeck *
7 * *
8 * This program is free software; you can redistribute it and/or modify *
9 * it under the terms of the GNU General Public License as published by *
10 * the Free Software Foundation; either version 2 of the License, or *
11 * (at your option) any later version. *
12 * *
13 * This program is distributed in the hope that it will be useful, *
14 * but WITHOUT ANY WARRANTY; without even the implied warranty of *
15 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
16 * GNU General Public License for more details. *
17 * *
18 * You should have received a copy of the GNU General Public License *
19 * along with this program; if not, write to the Free Software *
20 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, *
21 * MA 02111-1307 USA *
22 ***************************************************************************/
23
24 #include "../../common/Features.h"
25 #include "Synthesizer.h"
26 #include "Profiler.h"
27
28 #include "Voice.h"
29
30 namespace LinuxSampler { namespace gig {
31
32 const float Voice::FILTER_CUTOFF_COEFF(CalculateFilterCutoffCoeff());
33
34 float Voice::CalculateFilterCutoffCoeff() {
35 return log(CONFIG_FILTER_CUTOFF_MAX / CONFIG_FILTER_CUTOFF_MIN);
36 }
37
38 Voice::Voice() {
39 pEngine = NULL;
40 pDiskThread = NULL;
41 PlaybackState = playback_state_end;
42 pLFO1 = new LFOUnsigned(1.0f); // amplitude EG (0..1 range)
43 pLFO2 = new LFOUnsigned(1.0f); // filter EG (0..1 range)
44 pLFO3 = new LFOSigned(1200.0f); // pitch EG (-1200..+1200 range)
45 KeyGroup = 0;
46 SynthesisMode = 0; // set all mode bits to 0 first
47 // select synthesis implementation (currently either pure C++ or MMX+SSE(1))
48 #if CONFIG_ASM && ARCH_X86
49 SYNTHESIS_MODE_SET_IMPLEMENTATION(SynthesisMode, Features::supportsMMX() && Features::supportsSSE());
50 #else
51 SYNTHESIS_MODE_SET_IMPLEMENTATION(SynthesisMode, false);
52 #endif
53 SYNTHESIS_MODE_SET_PROFILING(SynthesisMode, Profiler::isEnabled());
54
55 finalSynthesisParameters.filterLeft.Reset();
56 finalSynthesisParameters.filterRight.Reset();
57 }
58
59 Voice::~Voice() {
60 if (pLFO1) delete pLFO1;
61 if (pLFO2) delete pLFO2;
62 if (pLFO3) delete pLFO3;
63 }
64
65 void Voice::SetEngine(Engine* pEngine) {
66 this->pEngine = pEngine;
67 this->pDiskThread = pEngine->pDiskThread;
68 dmsg(6,("Voice::SetEngine()\n"));
69 }
70
71 /**
72 * Initializes and triggers the voice, a disk stream will be launched if
73 * needed.
74 *
75 * @param pEngineChannel - engine channel on which this voice was ordered
76 * @param itNoteOnEvent - event that caused triggering of this voice
77 * @param PitchBend - MIDI detune factor (-8192 ... +8191)
78 * @param pDimRgn - points to the dimension region which provides sample wave(s) and articulation data
79 * @param VoiceType - type of this voice
80 * @param iKeyGroup - a value > 0 defines a key group in which this voice is member of
81 * @returns 0 on success, a value < 0 if the voice wasn't triggered
82 * (either due to an error or e.g. because no region is
83 * defined for the given key)
84 */
85 int Voice::Trigger(EngineChannel* pEngineChannel, Pool<Event>::Iterator& itNoteOnEvent, int PitchBend, ::gig::DimensionRegion* pDimRgn, type_t VoiceType, int iKeyGroup) {
86 this->pEngineChannel = pEngineChannel;
87 this->pDimRgn = pDimRgn;
88
89 #if CONFIG_DEVMODE
90 if (itNoteOnEvent->FragmentPos() > pEngine->MaxSamplesPerCycle) { // just a sanity check for debugging
91 dmsg(1,("Voice::Trigger(): ERROR, TriggerDelay > Totalsamples\n"));
92 }
93 #endif // CONFIG_DEVMODE
94
95 Type = VoiceType;
96 MIDIKey = itNoteOnEvent->Param.Note.Key;
97 PlaybackState = playback_state_init; // mark voice as triggered, but no audio rendered yet
98 Delay = itNoteOnEvent->FragmentPos();
99 itTriggerEvent = itNoteOnEvent;
100 itKillEvent = Pool<Event>::Iterator();
101 KeyGroup = iKeyGroup;
102 pSample = pDimRgn->pSample; // sample won't change until the voice is finished
103
104 // calculate volume
105 const double velocityAttenuation = pDimRgn->GetVelocityAttenuation(itNoteOnEvent->Param.Note.Velocity);
106
107 Volume = velocityAttenuation / 32768.0f; // we downscale by 32768 to convert from int16 value range to DSP value range (which is -1.0..1.0)
108
109 Volume *= pDimRgn->SampleAttenuation;
110
111 // the volume of release triggered samples depends on note length
112 if (Type == type_release_trigger) {
113 float noteLength = float(pEngine->FrameTime + Delay -
114 pEngineChannel->pMIDIKeyInfo[MIDIKey].NoteOnTime) / pEngine->SampleRate;
115 float attenuation = 1 - 0.01053 * (256 >> pDimRgn->ReleaseTriggerDecay) * noteLength;
116 if (attenuation <= 0) return -1;
117 Volume *= attenuation;
118 }
119
120 // select channel mode (mono or stereo)
121 SYNTHESIS_MODE_SET_CHANNELS(SynthesisMode, pSample->Channels == 2);
122
123 // get starting crossfade volume level
124 switch (pDimRgn->AttenuationController.type) {
125 case ::gig::attenuation_ctrl_t::type_channelaftertouch:
126 CrossfadeVolume = 1.0f; //TODO: aftertouch not supported yet
127 break;
128 case ::gig::attenuation_ctrl_t::type_velocity:
129 CrossfadeVolume = CrossfadeAttenuation(itNoteOnEvent->Param.Note.Velocity);
130 break;
131 case ::gig::attenuation_ctrl_t::type_controlchange: //FIXME: currently not sample accurate
132 CrossfadeVolume = CrossfadeAttenuation(pEngineChannel->ControllerTable[pDimRgn->AttenuationController.controller_number]);
133 break;
134 case ::gig::attenuation_ctrl_t::type_none: // no crossfade defined
135 default:
136 CrossfadeVolume = 1.0f;
137 }
138
139 PanLeft = 1.0f - float(RTMath::Max(pDimRgn->Pan, 0)) / 63.0f;
140 PanRight = 1.0f - float(RTMath::Min(pDimRgn->Pan, 0)) / -64.0f;
141
142 finalSynthesisParameters.dPos = pDimRgn->SampleStartOffset; // offset where we should start playback of sample (0 - 2000 sample points)
143 Pos = pDimRgn->SampleStartOffset;
144
145 // Check if the sample needs disk streaming or is too short for that
146 long cachedsamples = pSample->GetCache().Size / pSample->FrameSize;
147 DiskVoice = cachedsamples < pSample->SamplesTotal;
148
149 if (DiskVoice) { // voice to be streamed from disk
150 MaxRAMPos = cachedsamples - (pEngine->MaxSamplesPerCycle << CONFIG_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)
151
152 // check if there's a loop defined which completely fits into the cached (RAM) part of the sample
153 RAMLoop = (pSample->Loops && pSample->LoopEnd <= MaxRAMPos);
154
155 if (pDiskThread->OrderNewStream(&DiskStreamRef, pSample, MaxRAMPos, !RAMLoop) < 0) {
156 dmsg(1,("Disk stream order failed!\n"));
157 KillImmediately();
158 return -1;
159 }
160 dmsg(4,("Disk voice launched (cached samples: %d, total Samples: %d, MaxRAMPos: %d, RAMLooping: %s)\n", cachedsamples, pSample->SamplesTotal, MaxRAMPos, (RAMLoop) ? "yes" : "no"));
161 }
162 else { // RAM only voice
163 MaxRAMPos = cachedsamples;
164 RAMLoop = (pSample->Loops != 0);
165 dmsg(4,("RAM only voice launched (Looping: %s)\n", (RAMLoop) ? "yes" : "no"));
166 }
167 if (RAMLoop) {
168 loop.uiTotalCycles = pSample->LoopPlayCount;
169 loop.uiCyclesLeft = pSample->LoopPlayCount;
170 loop.uiStart = pSample->LoopStart;
171 loop.uiEnd = pSample->LoopEnd;
172 loop.uiSize = pSample->LoopSize;
173 }
174
175 // calculate initial pitch value
176 {
177 double pitchbasecents = pDimRgn->FineTune + (int) pEngine->ScaleTuning[MIDIKey % 12];
178 if (pDimRgn->PitchTrack) pitchbasecents += (MIDIKey - (int) pDimRgn->UnityNote) * 100;
179 this->PitchBase = RTMath::CentsToFreqRatio(pitchbasecents) * (double(pSample->SamplesPerSecond) / double(pEngine->SampleRate));
180 this->PitchBend = RTMath::CentsToFreqRatio(((double) PitchBend / 8192.0) * 200.0); // pitchbend wheel +-2 semitones = 200 cents
181 }
182
183 // the length of the decay and release curves are dependent on the velocity
184 const double velrelease = 1 / pDimRgn->GetVelocityRelease(itNoteOnEvent->Param.Note.Velocity);
185
186 // setup EG 1 (VCA EG)
187 {
188 // get current value of EG1 controller
189 double eg1controllervalue;
190 switch (pDimRgn->EG1Controller.type) {
191 case ::gig::eg1_ctrl_t::type_none: // no controller defined
192 eg1controllervalue = 0;
193 break;
194 case ::gig::eg1_ctrl_t::type_channelaftertouch:
195 eg1controllervalue = 0; // TODO: aftertouch not yet supported
196 break;
197 case ::gig::eg1_ctrl_t::type_velocity:
198 eg1controllervalue = itNoteOnEvent->Param.Note.Velocity;
199 break;
200 case ::gig::eg1_ctrl_t::type_controlchange: // MIDI control change controller
201 eg1controllervalue = pEngineChannel->ControllerTable[pDimRgn->EG1Controller.controller_number];
202 break;
203 }
204 if (pDimRgn->EG1ControllerInvert) eg1controllervalue = 127 - eg1controllervalue;
205
206 // calculate influence of EG1 controller on EG1's parameters
207 // (eg1attack is different from the others)
208 double eg1attack = (pDimRgn->EG1ControllerAttackInfluence) ?
209 1 + 0.031 * (double) (pDimRgn->EG1ControllerAttackInfluence == 1 ?
210 1 : 1 << pDimRgn->EG1ControllerAttackInfluence) * eg1controllervalue : 1.0;
211 double eg1decay = (pDimRgn->EG1ControllerDecayInfluence) ? 1 + 0.00775 * (double) (1 << pDimRgn->EG1ControllerDecayInfluence) * eg1controllervalue : 1.0;
212 double eg1release = (pDimRgn->EG1ControllerReleaseInfluence) ? 1 + 0.00775 * (double) (1 << pDimRgn->EG1ControllerReleaseInfluence) * eg1controllervalue : 1.0;
213
214 EG1.trigger(pDimRgn->EG1PreAttack,
215 pDimRgn->EG1Attack * eg1attack,
216 pDimRgn->EG1Hold,
217 pDimRgn->EG1Decay1 * eg1decay * velrelease,
218 pDimRgn->EG1Decay2 * eg1decay * velrelease,
219 pDimRgn->EG1InfiniteSustain,
220 pDimRgn->EG1Sustain,
221 pDimRgn->EG1Release * eg1release * velrelease,
222 velocityAttenuation,
223 pEngine->SampleRate / CONFIG_DEFAULT_SUBFRAGMENT_SIZE);
224 }
225
226
227 // setup EG 2 (VCF Cutoff EG)
228 {
229 // get current value of EG2 controller
230 double eg2controllervalue;
231 switch (pDimRgn->EG2Controller.type) {
232 case ::gig::eg2_ctrl_t::type_none: // no controller defined
233 eg2controllervalue = 0;
234 break;
235 case ::gig::eg2_ctrl_t::type_channelaftertouch:
236 eg2controllervalue = 0; // TODO: aftertouch not yet supported
237 break;
238 case ::gig::eg2_ctrl_t::type_velocity:
239 eg2controllervalue = itNoteOnEvent->Param.Note.Velocity;
240 break;
241 case ::gig::eg2_ctrl_t::type_controlchange: // MIDI control change controller
242 eg2controllervalue = pEngineChannel->ControllerTable[pDimRgn->EG2Controller.controller_number];
243 break;
244 }
245 if (pDimRgn->EG2ControllerInvert) eg2controllervalue = 127 - eg2controllervalue;
246
247 // calculate influence of EG2 controller on EG2's parameters
248 double eg2attack = (pDimRgn->EG2ControllerAttackInfluence) ? 1 + 0.00775 * (double) (1 << pDimRgn->EG2ControllerAttackInfluence) * eg2controllervalue : 1.0;
249 double eg2decay = (pDimRgn->EG2ControllerDecayInfluence) ? 1 + 0.00775 * (double) (1 << pDimRgn->EG2ControllerDecayInfluence) * eg2controllervalue : 1.0;
250 double eg2release = (pDimRgn->EG2ControllerReleaseInfluence) ? 1 + 0.00775 * (double) (1 << pDimRgn->EG2ControllerReleaseInfluence) * eg2controllervalue : 1.0;
251
252 EG2.trigger(pDimRgn->EG2PreAttack,
253 pDimRgn->EG2Attack * eg2attack,
254 false,
255 pDimRgn->EG2Decay1 * eg2decay * velrelease,
256 pDimRgn->EG2Decay2 * eg2decay * velrelease,
257 pDimRgn->EG2InfiniteSustain,
258 pDimRgn->EG2Sustain,
259 pDimRgn->EG2Release * eg2release * velrelease,
260 velocityAttenuation,
261 pEngine->SampleRate / CONFIG_DEFAULT_SUBFRAGMENT_SIZE);
262 }
263
264
265 // setup EG 3 (VCO EG)
266 {
267 // if portamento mode is on, we dedicate EG3 purely for portamento, otherwise if portamento is off we do as told by the patch
268 bool bPortamento = pEngineChannel->PortamentoMode && pEngineChannel->PortamentoPos >= 0.0f;
269 float eg3depth = (bPortamento)
270 ? RTMath::CentsToFreqRatio((pEngineChannel->PortamentoPos - (float) MIDIKey) * 100)
271 : RTMath::CentsToFreqRatio(pDimRgn->EG3Depth);
272 float eg3time = (bPortamento)
273 ? pEngineChannel->PortamentoTime
274 : pDimRgn->EG3Attack;
275 EG3.trigger(eg3depth, eg3time, pEngine->SampleRate / CONFIG_DEFAULT_SUBFRAGMENT_SIZE);
276 dmsg(5,("PortamentoPos=%f, depth=%f, time=%f\n", pEngineChannel->PortamentoPos, eg3depth, eg3time));
277 }
278
279
280 // setup LFO 1 (VCA LFO)
281 {
282 uint16_t lfo1_internal_depth;
283 switch (pDimRgn->LFO1Controller) {
284 case ::gig::lfo1_ctrl_internal:
285 lfo1_internal_depth = pDimRgn->LFO1InternalDepth;
286 pLFO1->ExtController = 0; // no external controller
287 bLFO1Enabled = (lfo1_internal_depth > 0);
288 break;
289 case ::gig::lfo1_ctrl_modwheel:
290 lfo1_internal_depth = 0;
291 pLFO1->ExtController = 1; // MIDI controller 1
292 bLFO1Enabled = (pDimRgn->LFO1ControlDepth > 0);
293 break;
294 case ::gig::lfo1_ctrl_breath:
295 lfo1_internal_depth = 0;
296 pLFO1->ExtController = 2; // MIDI controller 2
297 bLFO1Enabled = (pDimRgn->LFO1ControlDepth > 0);
298 break;
299 case ::gig::lfo1_ctrl_internal_modwheel:
300 lfo1_internal_depth = pDimRgn->LFO1InternalDepth;
301 pLFO1->ExtController = 1; // MIDI controller 1
302 bLFO1Enabled = (lfo1_internal_depth > 0 || pDimRgn->LFO1ControlDepth > 0);
303 break;
304 case ::gig::lfo1_ctrl_internal_breath:
305 lfo1_internal_depth = pDimRgn->LFO1InternalDepth;
306 pLFO1->ExtController = 2; // MIDI controller 2
307 bLFO1Enabled = (lfo1_internal_depth > 0 || pDimRgn->LFO1ControlDepth > 0);
308 break;
309 default:
310 lfo1_internal_depth = 0;
311 pLFO1->ExtController = 0; // no external controller
312 bLFO1Enabled = false;
313 }
314 if (bLFO1Enabled) pLFO1->trigger(pDimRgn->LFO1Frequency,
315 start_level_max,
316 lfo1_internal_depth,
317 pDimRgn->LFO1ControlDepth,
318 pDimRgn->LFO1FlipPhase,
319 pEngine->SampleRate / CONFIG_DEFAULT_SUBFRAGMENT_SIZE);
320 }
321
322
323 // setup LFO 2 (VCF Cutoff LFO)
324 {
325 uint16_t lfo2_internal_depth;
326 switch (pDimRgn->LFO2Controller) {
327 case ::gig::lfo2_ctrl_internal:
328 lfo2_internal_depth = pDimRgn->LFO2InternalDepth;
329 pLFO2->ExtController = 0; // no external controller
330 bLFO2Enabled = (lfo2_internal_depth > 0);
331 break;
332 case ::gig::lfo2_ctrl_modwheel:
333 lfo2_internal_depth = 0;
334 pLFO2->ExtController = 1; // MIDI controller 1
335 bLFO2Enabled = (pDimRgn->LFO2ControlDepth > 0);
336 break;
337 case ::gig::lfo2_ctrl_foot:
338 lfo2_internal_depth = 0;
339 pLFO2->ExtController = 4; // MIDI controller 4
340 bLFO2Enabled = (pDimRgn->LFO2ControlDepth > 0);
341 break;
342 case ::gig::lfo2_ctrl_internal_modwheel:
343 lfo2_internal_depth = pDimRgn->LFO2InternalDepth;
344 pLFO2->ExtController = 1; // MIDI controller 1
345 bLFO2Enabled = (lfo2_internal_depth > 0 || pDimRgn->LFO2ControlDepth > 0);
346 break;
347 case ::gig::lfo2_ctrl_internal_foot:
348 lfo2_internal_depth = pDimRgn->LFO2InternalDepth;
349 pLFO2->ExtController = 4; // MIDI controller 4
350 bLFO2Enabled = (lfo2_internal_depth > 0 || pDimRgn->LFO2ControlDepth > 0);
351 break;
352 default:
353 lfo2_internal_depth = 0;
354 pLFO2->ExtController = 0; // no external controller
355 bLFO2Enabled = false;
356 }
357 if (bLFO2Enabled) pLFO2->trigger(pDimRgn->LFO2Frequency,
358 start_level_max,
359 lfo2_internal_depth,
360 pDimRgn->LFO2ControlDepth,
361 pDimRgn->LFO2FlipPhase,
362 pEngine->SampleRate / CONFIG_DEFAULT_SUBFRAGMENT_SIZE);
363 }
364
365
366 // setup LFO 3 (VCO LFO)
367 {
368 uint16_t lfo3_internal_depth;
369 switch (pDimRgn->LFO3Controller) {
370 case ::gig::lfo3_ctrl_internal:
371 lfo3_internal_depth = pDimRgn->LFO3InternalDepth;
372 pLFO3->ExtController = 0; // no external controller
373 bLFO3Enabled = (lfo3_internal_depth > 0);
374 break;
375 case ::gig::lfo3_ctrl_modwheel:
376 lfo3_internal_depth = 0;
377 pLFO3->ExtController = 1; // MIDI controller 1
378 bLFO3Enabled = (pDimRgn->LFO3ControlDepth > 0);
379 break;
380 case ::gig::lfo3_ctrl_aftertouch:
381 lfo3_internal_depth = 0;
382 pLFO3->ExtController = 0; // TODO: aftertouch not implemented yet
383 bLFO3Enabled = false; // see TODO comment in line above
384 break;
385 case ::gig::lfo3_ctrl_internal_modwheel:
386 lfo3_internal_depth = pDimRgn->LFO3InternalDepth;
387 pLFO3->ExtController = 1; // MIDI controller 1
388 bLFO3Enabled = (lfo3_internal_depth > 0 || pDimRgn->LFO3ControlDepth > 0);
389 break;
390 case ::gig::lfo3_ctrl_internal_aftertouch:
391 lfo3_internal_depth = pDimRgn->LFO3InternalDepth;
392 pLFO1->ExtController = 0; // TODO: aftertouch not implemented yet
393 bLFO3Enabled = (lfo3_internal_depth > 0 /*|| pDimRgn->LFO3ControlDepth > 0*/); // see TODO comment in line above
394 break;
395 default:
396 lfo3_internal_depth = 0;
397 pLFO3->ExtController = 0; // no external controller
398 bLFO3Enabled = false;
399 }
400 if (bLFO3Enabled) pLFO3->trigger(pDimRgn->LFO3Frequency,
401 start_level_mid,
402 lfo3_internal_depth,
403 pDimRgn->LFO3ControlDepth,
404 false,
405 pEngine->SampleRate / CONFIG_DEFAULT_SUBFRAGMENT_SIZE);
406 }
407
408
409 #if CONFIG_FORCE_FILTER
410 const bool bUseFilter = true;
411 #else // use filter only if instrument file told so
412 const bool bUseFilter = pDimRgn->VCFEnabled;
413 #endif // CONFIG_FORCE_FILTER
414 SYNTHESIS_MODE_SET_FILTER(SynthesisMode, bUseFilter);
415 if (bUseFilter) {
416 #ifdef CONFIG_OVERRIDE_CUTOFF_CTRL
417 VCFCutoffCtrl.controller = CONFIG_OVERRIDE_CUTOFF_CTRL;
418 #else // use the one defined in the instrument file
419 switch (pDimRgn->VCFCutoffController) {
420 case ::gig::vcf_cutoff_ctrl_modwheel:
421 VCFCutoffCtrl.controller = 1;
422 break;
423 case ::gig::vcf_cutoff_ctrl_effect1:
424 VCFCutoffCtrl.controller = 12;
425 break;
426 case ::gig::vcf_cutoff_ctrl_effect2:
427 VCFCutoffCtrl.controller = 13;
428 break;
429 case ::gig::vcf_cutoff_ctrl_breath:
430 VCFCutoffCtrl.controller = 2;
431 break;
432 case ::gig::vcf_cutoff_ctrl_foot:
433 VCFCutoffCtrl.controller = 4;
434 break;
435 case ::gig::vcf_cutoff_ctrl_sustainpedal:
436 VCFCutoffCtrl.controller = 64;
437 break;
438 case ::gig::vcf_cutoff_ctrl_softpedal:
439 VCFCutoffCtrl.controller = 67;
440 break;
441 case ::gig::vcf_cutoff_ctrl_genpurpose7:
442 VCFCutoffCtrl.controller = 82;
443 break;
444 case ::gig::vcf_cutoff_ctrl_genpurpose8:
445 VCFCutoffCtrl.controller = 83;
446 break;
447 case ::gig::vcf_cutoff_ctrl_aftertouch: //TODO: not implemented yet
448 case ::gig::vcf_cutoff_ctrl_none:
449 default:
450 VCFCutoffCtrl.controller = 0;
451 break;
452 }
453 #endif // CONFIG_OVERRIDE_CUTOFF_CTRL
454
455 #ifdef CONFIG_OVERRIDE_RESONANCE_CTRL
456 VCFResonanceCtrl.controller = CONFIG_OVERRIDE_RESONANCE_CTRL;
457 #else // use the one defined in the instrument file
458 switch (pDimRgn->VCFResonanceController) {
459 case ::gig::vcf_res_ctrl_genpurpose3:
460 VCFResonanceCtrl.controller = 18;
461 break;
462 case ::gig::vcf_res_ctrl_genpurpose4:
463 VCFResonanceCtrl.controller = 19;
464 break;
465 case ::gig::vcf_res_ctrl_genpurpose5:
466 VCFResonanceCtrl.controller = 80;
467 break;
468 case ::gig::vcf_res_ctrl_genpurpose6:
469 VCFResonanceCtrl.controller = 81;
470 break;
471 case ::gig::vcf_res_ctrl_none:
472 default:
473 VCFResonanceCtrl.controller = 0;
474 }
475 #endif // CONFIG_OVERRIDE_RESONANCE_CTRL
476
477 #ifndef CONFIG_OVERRIDE_FILTER_TYPE
478 finalSynthesisParameters.filterLeft.SetType(pDimRgn->VCFType);
479 finalSynthesisParameters.filterRight.SetType(pDimRgn->VCFType);
480 #else // override filter type
481 FilterLeft.SetType(CONFIG_OVERRIDE_FILTER_TYPE);
482 FilterRight.SetType(CONFIG_OVERRIDE_FILTER_TYPE);
483 #endif // CONFIG_OVERRIDE_FILTER_TYPE
484
485 VCFCutoffCtrl.value = pEngineChannel->ControllerTable[VCFCutoffCtrl.controller];
486 VCFResonanceCtrl.value = pEngineChannel->ControllerTable[VCFResonanceCtrl.controller];
487
488 // calculate cutoff frequency
489 float cutoff = pDimRgn->GetVelocityCutoff(itNoteOnEvent->Param.Note.Velocity);
490 if (pDimRgn->VCFKeyboardTracking) {
491 cutoff *= exp((itNoteOnEvent->Param.Note.Key - pDimRgn->VCFKeyboardTrackingBreakpoint) * 0.057762265f); // (ln(2) / 12)
492 }
493 CutoffBase = cutoff;
494
495 int cvalue;
496 if (VCFCutoffCtrl.controller) {
497 cvalue = pEngineChannel->ControllerTable[VCFCutoffCtrl.controller];
498 if (pDimRgn->VCFCutoffControllerInvert) cvalue = 127 - cvalue;
499 // VCFVelocityScale in this case means Minimum cutoff
500 if (cvalue < pDimRgn->VCFVelocityScale) cvalue = pDimRgn->VCFVelocityScale;
501 }
502 else {
503 cvalue = pDimRgn->VCFCutoff;
504 }
505 cutoff *= float(cvalue) * 0.00787402f; // (1 / 127)
506 if (cutoff > 1.0) cutoff = 1.0;
507 cutoff = (cutoff < 0.5 ? cutoff * 4826 - 1 : cutoff * 5715 - 449);
508 if (cutoff < 1.0) cutoff = 1.0;
509
510 // calculate resonance
511 float resonance = (float) (VCFResonanceCtrl.controller ? VCFResonanceCtrl.value : pDimRgn->VCFResonance) * 0.00787f; // 0.0..1.0
512
513 VCFCutoffCtrl.fvalue = cutoff - 1.0;
514 VCFResonanceCtrl.fvalue = resonance;
515 }
516 else {
517 VCFCutoffCtrl.controller = 0;
518 VCFResonanceCtrl.controller = 0;
519 }
520
521 return 0; // success
522 }
523
524 /**
525 * Renders the audio data for this voice for the current audio fragment.
526 * The sample input data can either come from RAM (cached sample or sample
527 * part) or directly from disk. The output signal will be rendered by
528 * resampling / interpolation. If this voice is a disk streaming voice and
529 * the voice completely played back the cached RAM part of the sample, it
530 * will automatically switch to disk playback for the next RenderAudio()
531 * call.
532 *
533 * @param Samples - number of samples to be rendered in this audio fragment cycle
534 */
535 void Voice::Render(uint Samples) {
536
537 // select default values for synthesis mode bits
538 SYNTHESIS_MODE_SET_LOOP(SynthesisMode, false);
539
540 switch (this->PlaybackState) {
541
542 case playback_state_init:
543 this->PlaybackState = playback_state_ram; // we always start playback from RAM cache and switch then to disk if needed
544 // no break - continue with playback_state_ram
545
546 case playback_state_ram: {
547 if (RAMLoop) SYNTHESIS_MODE_SET_LOOP(SynthesisMode, true); // enable looping
548
549 // render current fragment
550 Synthesize(Samples, (sample_t*) pSample->GetCache().pStart, Delay);
551
552 if (DiskVoice) {
553 // check if we reached the allowed limit of the sample RAM cache
554 if (finalSynthesisParameters.dPos > MaxRAMPos) {
555 dmsg(5,("Voice: switching to disk playback (Pos=%f)\n", finalSynthesisParameters.dPos));
556 this->PlaybackState = playback_state_disk;
557 }
558 } else if (finalSynthesisParameters.dPos >= pSample->GetCache().Size / pSample->FrameSize) {
559 this->PlaybackState = playback_state_end;
560 }
561 }
562 break;
563
564 case playback_state_disk: {
565 if (!DiskStreamRef.pStream) {
566 // check if the disk thread created our ordered disk stream in the meantime
567 DiskStreamRef.pStream = pDiskThread->AskForCreatedStream(DiskStreamRef.OrderID);
568 if (!DiskStreamRef.pStream) {
569 std::cout << stderr << "Disk stream not available in time!" << std::endl << std::flush;
570 KillImmediately();
571 return;
572 }
573 DiskStreamRef.pStream->IncrementReadPos(pSample->Channels * (int(finalSynthesisParameters.dPos) - MaxRAMPos));
574 finalSynthesisParameters.dPos -= int(finalSynthesisParameters.dPos);
575 RealSampleWordsLeftToRead = -1; // -1 means no silence has been added yet
576 }
577
578 const int sampleWordsLeftToRead = DiskStreamRef.pStream->GetReadSpace();
579
580 // add silence sample at the end if we reached the end of the stream (for the interpolator)
581 if (DiskStreamRef.State == Stream::state_end) {
582 const int maxSampleWordsPerCycle = (pEngine->MaxSamplesPerCycle << CONFIG_MAX_PITCH) * pSample->Channels + 6; // +6 for the interpolator algorithm
583 if (sampleWordsLeftToRead <= maxSampleWordsPerCycle) {
584 // remember how many sample words there are before any silence has been added
585 if (RealSampleWordsLeftToRead < 0) RealSampleWordsLeftToRead = sampleWordsLeftToRead;
586 DiskStreamRef.pStream->WriteSilence(maxSampleWordsPerCycle - sampleWordsLeftToRead);
587 }
588 }
589
590 sample_t* ptr = DiskStreamRef.pStream->GetReadPtr(); // get the current read_ptr within the ringbuffer where we read the samples from
591
592 // render current audio fragment
593 Synthesize(Samples, ptr, Delay);
594
595 const int iPos = (int) finalSynthesisParameters.dPos;
596 const int readSampleWords = iPos * pSample->Channels; // amount of sample words actually been read
597 DiskStreamRef.pStream->IncrementReadPos(readSampleWords);
598 finalSynthesisParameters.dPos -= iPos; // just keep fractional part of playback position
599
600 // change state of voice to 'end' if we really reached the end of the sample data
601 if (RealSampleWordsLeftToRead >= 0) {
602 RealSampleWordsLeftToRead -= readSampleWords;
603 if (RealSampleWordsLeftToRead <= 0) this->PlaybackState = playback_state_end;
604 }
605 }
606 break;
607
608 case playback_state_end:
609 std::cerr << "gig::Voice::Render(): entered with playback_state_end, this is a bug!\n" << std::flush;
610 break;
611 }
612
613 // Reset delay
614 Delay = 0;
615
616 itTriggerEvent = Pool<Event>::Iterator();
617
618 // If sample stream or release stage finished, kill the voice
619 if (PlaybackState == playback_state_end || EG1.getSegmentType() == EGADSR::segment_end) KillImmediately();
620 }
621
622 /**
623 * Resets voice variables. Should only be called if rendering process is
624 * suspended / not running.
625 */
626 void Voice::Reset() {
627 finalSynthesisParameters.filterLeft.Reset();
628 finalSynthesisParameters.filterRight.Reset();
629 DiskStreamRef.pStream = NULL;
630 DiskStreamRef.hStream = 0;
631 DiskStreamRef.State = Stream::state_unused;
632 DiskStreamRef.OrderID = 0;
633 PlaybackState = playback_state_end;
634 itTriggerEvent = Pool<Event>::Iterator();
635 itKillEvent = Pool<Event>::Iterator();
636 }
637
638 /**
639 * Process given list of MIDI note on, note off and sustain pedal events
640 * for the given time.
641 *
642 * @param itEvent - iterator pointing to the next event to be processed
643 * @param End - youngest time stamp where processing should be stopped
644 */
645 void Voice::processTransitionEvents(RTList<Event>::Iterator& itEvent, uint End) {
646 for (; itEvent && itEvent->FragmentPos() <= End; ++itEvent) {
647 if (itEvent->Type == Event::type_release) {
648 EG1.update(EGADSR::event_release, pEngine->SampleRate / CONFIG_DEFAULT_SUBFRAGMENT_SIZE);
649 EG2.update(EGADSR::event_release, pEngine->SampleRate / CONFIG_DEFAULT_SUBFRAGMENT_SIZE);
650 } else if (itEvent->Type == Event::type_cancel_release) {
651 EG1.update(EGADSR::event_cancel_release, pEngine->SampleRate / CONFIG_DEFAULT_SUBFRAGMENT_SIZE);
652 EG2.update(EGADSR::event_cancel_release, pEngine->SampleRate / CONFIG_DEFAULT_SUBFRAGMENT_SIZE);
653 }
654 }
655 }
656
657 /**
658 * Process given list of MIDI control change and pitch bend events for
659 * the given time.
660 *
661 * @param itEvent - iterator pointing to the next event to be processed
662 * @param End - youngest time stamp where processing should be stopped
663 */
664 void Voice::processCCEvents(RTList<Event>::Iterator& itEvent, uint End) {
665 for (; itEvent && itEvent->FragmentPos() <= End; ++itEvent) {
666 if (itEvent->Type == Event::type_control_change &&
667 itEvent->Param.CC.Controller) { // if (valid) MIDI control change event
668 if (itEvent->Param.CC.Controller == VCFCutoffCtrl.controller) {
669 processCutoffEvent(itEvent);
670 }
671 if (itEvent->Param.CC.Controller == VCFResonanceCtrl.controller) {
672 processResonanceEvent(itEvent);
673 }
674 if (itEvent->Param.CC.Controller == pLFO1->ExtController) {
675 pLFO1->update(itEvent->Param.CC.Value);
676 }
677 if (itEvent->Param.CC.Controller == pLFO2->ExtController) {
678 pLFO2->update(itEvent->Param.CC.Value);
679 }
680 if (itEvent->Param.CC.Controller == pLFO3->ExtController) {
681 pLFO3->update(itEvent->Param.CC.Value);
682 }
683 if (pDimRgn->AttenuationController.type == ::gig::attenuation_ctrl_t::type_controlchange &&
684 itEvent->Param.CC.Controller == pDimRgn->AttenuationController.controller_number) {
685 processCrossFadeEvent(itEvent);
686 }
687 } else if (itEvent->Type == Event::type_pitchbend) { // if pitch bend event
688 processPitchEvent(itEvent);
689 }
690 }
691 }
692
693 void Voice::processPitchEvent(RTList<Event>::Iterator& itEvent) {
694 const float pitch = RTMath::CentsToFreqRatio(((double) itEvent->Param.Pitch.Pitch / 8192.0) * 200.0); // +-two semitones = +-200 cents
695 finalSynthesisParameters.fFinalPitch *= pitch;
696 PitchBend = pitch;
697 }
698
699 void Voice::processCrossFadeEvent(RTList<Event>::Iterator& itEvent) {
700 CrossfadeVolume = CrossfadeAttenuation(itEvent->Param.CC.Value);
701 #if CONFIG_PROCESS_MUTED_CHANNELS
702 const float effectiveVolume = CrossfadeVolume * Volume * (pEngineChannel->GetMute() ? 0 : pEngineChannel->GlobalVolume);
703 #else
704 const float effectiveVolume = CrossfadeVolume * Volume * pEngineChannel->GlobalVolume;
705 #endif
706 fFinalVolume = effectiveVolume;
707 }
708
709 void Voice::processCutoffEvent(RTList<Event>::Iterator& itEvent) {
710 int ccvalue = itEvent->Param.CC.Value;
711 if (VCFCutoffCtrl.value == ccvalue) return;
712 VCFCutoffCtrl.value == ccvalue;
713 if (pDimRgn->VCFCutoffControllerInvert) ccvalue = 127 - ccvalue;
714 if (ccvalue < pDimRgn->VCFVelocityScale) ccvalue = pDimRgn->VCFVelocityScale;
715 float cutoff = CutoffBase * float(ccvalue) * 0.00787402f; // (1 / 127)
716 if (cutoff > 1.0) cutoff = 1.0;
717 cutoff = (cutoff < 0.5 ? cutoff * 4826 - 1 : cutoff * 5715 - 449);
718 if (cutoff < 1.0) cutoff = 1.0;
719
720 VCFCutoffCtrl.fvalue = cutoff - 1.0; // needed for initialization of fFinalCutoff next time
721 fFinalCutoff = cutoff;
722 }
723
724 void Voice::processResonanceEvent(RTList<Event>::Iterator& itEvent) {
725 // convert absolute controller value to differential
726 const int ctrldelta = itEvent->Param.CC.Value - VCFResonanceCtrl.value;
727 VCFResonanceCtrl.value = itEvent->Param.CC.Value;
728 const float resonancedelta = (float) ctrldelta * 0.00787f; // 0.0..1.0
729 fFinalResonance += resonancedelta;
730 // needed for initialization of parameter
731 VCFResonanceCtrl.fvalue = itEvent->Param.CC.Value * 0.00787f;
732 }
733
734 /**
735 * Synthesizes the current audio fragment for this voice.
736 *
737 * @param Samples - number of sample points to be rendered in this audio
738 * fragment cycle
739 * @param pSrc - pointer to input sample data
740 * @param Skip - number of sample points to skip in output buffer
741 */
742 void Voice::Synthesize(uint Samples, sample_t* pSrc, uint Skip) {
743 finalSynthesisParameters.pOutLeft = &pEngineChannel->pOutputLeft[Skip];
744 finalSynthesisParameters.pOutRight = &pEngineChannel->pOutputRight[Skip];
745 finalSynthesisParameters.pSrc = pSrc;
746
747 RTList<Event>::Iterator itCCEvent = pEngineChannel->pEvents->first();
748 RTList<Event>::Iterator itNoteEvent = pEngineChannel->pMIDIKeyInfo[MIDIKey].pEvents->first();
749
750 if (Skip) { // skip events that happened before this voice was triggered
751 while (itCCEvent && itCCEvent->FragmentPos() <= Skip) ++itCCEvent;
752 while (itNoteEvent && itNoteEvent->FragmentPos() <= Skip) ++itNoteEvent;
753 }
754
755 uint killPos;
756 if (itKillEvent) killPos = RTMath::Min(itKillEvent->FragmentPos(), pEngine->MaxFadeOutPos);
757
758 uint i = Skip;
759 while (i < Samples) {
760 int iSubFragmentEnd = RTMath::Min(i + CONFIG_DEFAULT_SUBFRAGMENT_SIZE, Samples);
761
762 // initialize all final synthesis parameters
763 finalSynthesisParameters.fFinalPitch = PitchBase * PitchBend;
764 #if CONFIG_PROCESS_MUTED_CHANNELS
765 fFinalVolume = this->Volume * this->CrossfadeVolume * (pEngineChannel->GetMute() ? 0 : pEngineChannel->GlobalVolume);
766 #else
767 fFinalVolume = this->Volume * this->CrossfadeVolume * pEngineChannel->GlobalVolume;
768 #endif
769 fFinalCutoff = VCFCutoffCtrl.fvalue;
770 fFinalResonance = VCFResonanceCtrl.fvalue;
771
772 // process MIDI control change and pitchbend events for this subfragment
773 processCCEvents(itCCEvent, iSubFragmentEnd);
774
775 // process transition events (note on, note off & sustain pedal)
776 processTransitionEvents(itNoteEvent, iSubFragmentEnd);
777
778 // if the voice was killed in this subfragment switch EG1 to fade out stage
779 if (itKillEvent && killPos <= iSubFragmentEnd) {
780 EG1.enterFadeOutStage();
781 itKillEvent = Pool<Event>::Iterator();
782 }
783
784 // process envelope generators
785 switch (EG1.getSegmentType()) {
786 case EGADSR::segment_lin:
787 fFinalVolume *= EG1.processLin();
788 break;
789 case EGADSR::segment_exp:
790 fFinalVolume *= EG1.processExp();
791 break;
792 case EGADSR::segment_end:
793 fFinalVolume *= EG1.getLevel();
794 break; // noop
795 }
796 switch (EG2.getSegmentType()) {
797 case EGADSR::segment_lin:
798 fFinalCutoff *= EG2.processLin();
799 break;
800 case EGADSR::segment_exp:
801 fFinalCutoff *= EG2.processExp();
802 break;
803 case EGADSR::segment_end:
804 fFinalCutoff *= EG2.getLevel();
805 break; // noop
806 }
807 if (EG3.active()) finalSynthesisParameters.fFinalPitch *= EG3.render();
808
809 // process low frequency oscillators
810 if (bLFO1Enabled) fFinalVolume *= pLFO1->render();
811 if (bLFO2Enabled) fFinalCutoff *= pLFO2->render();
812 if (bLFO3Enabled) finalSynthesisParameters.fFinalPitch *= RTMath::CentsToFreqRatio(pLFO3->render());
813
814 // if filter enabled then update filter coefficients
815 if (SYNTHESIS_MODE_GET_FILTER(SynthesisMode)) {
816 finalSynthesisParameters.filterLeft.SetParameters(fFinalCutoff + 1.0, fFinalResonance, pEngine->SampleRate);
817 finalSynthesisParameters.filterRight.SetParameters(fFinalCutoff + 1.0, fFinalResonance, pEngine->SampleRate);
818 }
819
820 // do we need resampling?
821 const float __PLUS_ONE_CENT = 1.000577789506554859250142541782224725466f;
822 const float __MINUS_ONE_CENT = 0.9994225441413807496009516495583113737666f;
823 const bool bResamplingRequired = !(finalSynthesisParameters.fFinalPitch <= __PLUS_ONE_CENT &&
824 finalSynthesisParameters.fFinalPitch >= __MINUS_ONE_CENT);
825 SYNTHESIS_MODE_SET_INTERPOLATE(SynthesisMode, bResamplingRequired);
826
827 // prepare final synthesis parameters structure
828 finalSynthesisParameters.fFinalVolumeLeft = fFinalVolume * PanLeft;
829 finalSynthesisParameters.fFinalVolumeRight = fFinalVolume * PanRight;
830 finalSynthesisParameters.uiToGo = iSubFragmentEnd - i;
831
832 // render audio for one subfragment
833 RunSynthesisFunction(SynthesisMode, &finalSynthesisParameters, &loop);
834
835 const double newPos = Pos + (iSubFragmentEnd - i) * finalSynthesisParameters.fFinalPitch;
836
837 // increment envelopes' positions
838 if (EG1.active()) {
839
840 // if sample has a loop and loop start has been reached in this subfragment, send a special event to EG1 to let it finish the attack hold stage
841 if (pSample->Loops && Pos <= pSample->LoopStart && pSample->LoopStart < newPos) {
842 EG1.update(EGADSR::event_hold_end, pEngine->SampleRate / CONFIG_DEFAULT_SUBFRAGMENT_SIZE);
843 }
844
845 EG1.increment(1);
846 if (!EG1.toStageEndLeft()) EG1.update(EGADSR::event_stage_end, pEngine->SampleRate / CONFIG_DEFAULT_SUBFRAGMENT_SIZE);
847 }
848 if (EG2.active()) {
849 EG2.increment(1);
850 if (!EG2.toStageEndLeft()) EG2.update(EGADSR::event_stage_end, pEngine->SampleRate / CONFIG_DEFAULT_SUBFRAGMENT_SIZE);
851 }
852 EG3.increment(1);
853 if (!EG3.toEndLeft()) EG3.update(); // neutralize envelope coefficient if end reached
854
855 Pos = newPos;
856 i = iSubFragmentEnd;
857 }
858 }
859
860 /** @brief Update current portamento position.
861 *
862 * Will be called when portamento mode is enabled to get the final
863 * portamento position of this active voice from where the next voice(s)
864 * might continue to slide on.
865 *
866 * @param itNoteOffEvent - event which causes this voice to die soon
867 */
868 void Voice::UpdatePortamentoPos(Pool<Event>::Iterator& itNoteOffEvent) {
869 const float fFinalEG3Level = EG3.level(itNoteOffEvent->FragmentPos());
870 pEngineChannel->PortamentoPos = (float) MIDIKey + RTMath::FreqRatioToCents(fFinalEG3Level) * 0.01f;
871 }
872
873 /**
874 * Immediately kill the voice. This method should not be used to kill
875 * a normal, active voice, because it doesn't take care of things like
876 * fading down the volume level to avoid clicks and regular processing
877 * until the kill event actually occured!
878 *
879 * @see Kill()
880 */
881 void Voice::KillImmediately() {
882 if (DiskVoice && DiskStreamRef.State != Stream::state_unused) {
883 pDiskThread->OrderDeletionOfStream(&DiskStreamRef);
884 }
885 Reset();
886 }
887
888 /**
889 * Kill the voice in regular sense. Let the voice render audio until
890 * the kill event actually occured and then fade down the volume level
891 * very quickly and let the voice die finally. Unlike a normal release
892 * of a voice, a kill process cannot be cancalled and is therefore
893 * usually used for voice stealing and key group conflicts.
894 *
895 * @param itKillEvent - event which caused the voice to be killed
896 */
897 void Voice::Kill(Pool<Event>::Iterator& itKillEvent) {
898 #if CONFIG_DEVMODE
899 if (!itKillEvent) dmsg(1,("gig::Voice::Kill(): ERROR, !itKillEvent !!!\n"));
900 if (itKillEvent && !itKillEvent.isValid()) dmsg(1,("gig::Voice::Kill(): ERROR, itKillEvent invalid !!!\n"));
901 #endif // CONFIG_DEVMODE
902
903 if (itTriggerEvent && itKillEvent->FragmentPos() <= itTriggerEvent->FragmentPos()) return;
904 this->itKillEvent = itKillEvent;
905 }
906
907 }} // namespace LinuxSampler::gig

  ViewVC Help
Powered by ViewVC