1 /*
2 Part.cpp - Part implementation
3
4 Original ZynAddSubFX author Nasca Octavian Paul
5 Copyright (C) 2002-2005 Nasca Octavian Paul
6 Copyright 2009, James Morris
7 Copyright 2009-2011, Alan Calvert
8 Copyright 2014-2019, Will Godfrey
9 Copyright 2021 Kristian Amlie & others
10
11 This file is part of yoshimi, which is free software: you can redistribute
12 it and/or modify it under the terms of the GNU Library General Public
13 License as published by the Free Software Foundation; either version 2 of
14 the License, or (at your option) any later version.
15
16 yoshimi is distributed in the hope that it will be useful, but WITHOUT ANY
17 WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
18 FOR A PARTICULAR PURPOSE. See the GNU General Public License (version 2 or
19 later) for more details.
20
21 You should have received a copy of the GNU General Public License along with
22 yoshimi; if not, write to the Free Software Foundation, Inc., 51 Franklin
23 Street, Fifth Floor, Boston, MA 02110-1301, USA.
24
25 This file is derivative of ZynAddSubFX original code.
26
27 */
28
29 #include "Params/ADnoteParameters.h"
30 #include "Params/SUBnoteParameters.h"
31 #include "Params/PADnoteParameters.h"
32 #include "Synth/ADnote.h"
33 #include "Synth/SUBnote.h"
34 #include "Synth/PADnote.h"
35 #include "Params/Controller.h"
36 #include "Effects/EffectMgr.h"
37 #include "DSP/FFTwrapper.h"
38 #include "Misc/Microtonal.h"
39 #include "Misc/XMLwrapper.h"
40 #include "Misc/SynthEngine.h"
41 #include "Misc/SynthHelper.h"
42 #include "Misc/FileMgrFuncs.h"
43 #include "Misc/NumericFuncs.h"
44 #include "Misc/FormatFuncs.h"
45 #include "Interface/TextLists.h"
46 #include "Synth/Resonance.h"
47 #include "Misc/Part.h"
48
49 using synth::velF;
50 using file::isRegularFile;
51 using file::setExtension;
52 using file::findLeafName;
53 using func::findSplitPoint;
54 using func::setAllPan;
55 using func::decibel;
56
Part(Microtonal * microtonal_,FFTwrapper * fft_,SynthEngine * _synth)57 Part::Part(Microtonal *microtonal_, FFTwrapper *fft_, SynthEngine *_synth) :
58 microtonal(microtonal_),
59 fft(fft_),
60 killallnotes(false),
61 synth(_synth)
62 {
63 ctl = new Controller(synth);
64 partoutl = (float*)fftwf_malloc(synth->bufferbytes);
65 memset(partoutl, 0, synth->bufferbytes);
66 partoutr = (float*)fftwf_malloc(synth->bufferbytes);
67 memset(partoutr, 0, synth->bufferbytes);
68
69 for (int n = 0; n < NUM_KIT_ITEMS; ++n)
70 {
71 kit[n].Pname.clear();
72 kit[n].adpars = NULL;
73 kit[n].subpars = NULL;
74 kit[n].padpars = NULL;
75 }
76
77 kit[0].adpars = new ADnoteParameters(fft, synth);
78 kit[0].subpars = new SUBnoteParameters(synth);
79 kit[0].padpars = new PADnoteParameters(fft, synth);
80
81 // Part's Insertion Effects init
82 for (int nefx = 0; nefx < NUM_PART_EFX; ++nefx)
83 partefx[nefx] = new EffectMgr(1, synth);
84
85 for (int n = 0; n < NUM_PART_EFX + 1; ++n)
86 {
87 partfxinputl[n] = (float*)fftwf_malloc(synth->bufferbytes);
88 memset(partfxinputl[n], 0, synth->bufferbytes);
89 partfxinputr[n] = (float*)fftwf_malloc(synth->bufferbytes);
90 memset(partfxinputr[n], 0, synth->bufferbytes);
91 Pefxbypass[n] = false;
92 }
93
94 oldfreq = -1.0f;
95
96 int i, j;
97 for (i = 0; i < POLIPHONY; ++i)
98 {
99 partnote[i].status = KEY_OFF;
100 partnote[i].note = -1;
101 partnote[i].itemsplaying = 0;
102 for (j = 0; j < NUM_KIT_ITEMS; ++j)
103 {
104 partnote[i].kititem[j].adnote = NULL;
105 partnote[i].kititem[j].subnote = NULL;
106 partnote[i].kititem[j].padnote = NULL;
107 }
108 partnote[i].time = 0;
109 }
110 cleanup();
111 Pname.clear();
112
113 lastnote = -1;
114 lastpos = 0; // lastpos will store previously used NoteOn(...)'s pos.
115 lastlegatomodevalid = false; // To store previous legatomodevalid value.
116 defaults();
117 }
118
119
defaults(void)120 void Part::defaults(void)
121 {
122 Penabled = 0;
123 Pminkey = 0;
124 Pmaxkey = 127;
125 Pkeymode = PART_NORMAL;
126 PchannelATchoice = 0;
127 PkeyATchoice = 0;
128 setVolume(96);
129 TransVolume = 128; // ensure it always gets set
130 Pkeyshift = 64;
131 PmapOffset = 0;
132 Prcvchn = 0;
133 oldFilterState = -1;
134 oldBendState = -1;
135 oldVolumeState = -1;
136 oldVolumeAdjust = 0;
137 oldModulationState = -1;
138 setPan(Ppanning = 64);
139 TransPanning = 128; // ensure it always gets set
140 Pvelsns = 64;
141 Pveloffs = 64;
142 Pkeylimit = PART_DEFAULT_LIMIT;
143 Pfrand = 0;
144 Pvelrand = 0;
145 PbreathControl = 2;
146 Peffnum = 0;
147 setDestination(1);
148 busy = false;
149 defaultsinstrument();
150 ctl->resetall();
151 setNoteMap(0);
152 }
153
setNoteMap(int keyshift)154 void Part::setNoteMap(int keyshift)
155 {
156 for (int i = 0; i < 128; ++i)
157 if (Pdrummode)
158 PnoteMap[128 - PmapOffset + i] = microtonal->getFixedNoteFreq(i);
159 else
160 PnoteMap[128 - PmapOffset + i] = microtonal->getNoteFreq(i, keyshift + synth->Pkeyshift - 64);
161 }
162
163
defaultsinstrument(void)164 void Part::defaultsinstrument(void)
165 {
166 Pname = DEFAULT_NAME;
167 Poriginal = "";
168 PyoshiType = 0;
169 info.Ptype = 0;
170 info.Pauthor.clear();
171 info.Pcomments.clear();
172
173 Pkitmode = 0;
174 Pkitfade = false;
175 Pdrummode = 0;
176 Pfrand = 0;
177 Pvelrand = 0;
178
179 for (int n = 0; n < NUM_KIT_ITEMS; ++n)
180 {
181 kit[n].Penabled = 0;
182 kit[n].Pmuted = 0;
183 kit[n].Pminkey = 0;
184 kit[n].Pmaxkey = 127;
185 kit[n].Padenabled = 0;
186 kit[n].Psubenabled = 0;
187 kit[n].Ppadenabled = 0;
188 kit[n].Pname.clear();
189 kit[n].Psendtoparteffect = 0;
190 if (n != 0)
191 setkititemstatus(n, 0);
192 }
193 kit[0].Penabled = 1;
194 kit[0].Padenabled = 1;
195 kit[0].adpars->defaults();
196 kit[0].subpars->defaults();
197 kit[0].padpars->defaults();
198
199 for (int nefx = 0; nefx < NUM_PART_EFX; ++nefx)
200 {
201 partefx[nefx]->defaults();
202 Pefxroute[nefx] = 0; // route to next effect
203 }
204 Peffnum = 0;
205 }
206
207
208 // Cleanup the part
cleanup(void)209 void Part::cleanup(void)
210 {
211 int enablepart = Penabled;
212 Penabled = 0;
213 for (int k = 0; k < POLIPHONY; ++k)
214 KillNotePos(k);
215 memset(partoutl, 0, synth->bufferbytes);
216 memset(partoutr, 0, synth->bufferbytes);
217
218 for (int nefx = 0; nefx < NUM_PART_EFX; ++nefx)
219 partefx[nefx]->cleanup();
220 for (int n = 0; n < NUM_PART_EFX + 1; ++n)
221 {
222 memset(partfxinputl[n], 0, synth->bufferbytes);
223 memset(partfxinputr[n], 0, synth->bufferbytes);
224
225 }
226 Penabled = enablepart;
227 }
228
229
~Part()230 Part::~Part()
231 {
232 cleanup();
233 for (int n = 0; n < NUM_KIT_ITEMS; ++n)
234 {
235 if (kit[n].adpars)
236 delete kit[n].adpars;
237 if (kit[n].subpars)
238 delete kit[n].subpars;
239 if (kit[n].padpars)
240 delete kit[n].padpars;
241 }
242 fftwf_free(partoutl);
243 fftwf_free(partoutr);
244 for (int nefx = 0; nefx < NUM_PART_EFX; ++nefx)
245 {
246 if (partefx[nefx])
247 delete partefx[nefx];
248 }
249 for (int n = 0; n < NUM_PART_EFX + 1; ++n)
250 {
251 if (partfxinputl[n])
252 fftwf_free(partfxinputl[n]);
253 if (partfxinputr[n])
254 fftwf_free(partfxinputr[n]);
255 }
256 if (ctl)
257 delete ctl;
258 }
259
260
setChannelAT(int type,int value)261 void Part::setChannelAT(int type, int value)
262 {
263 if (type & PART::aftertouchType::filterCutoff)
264 {
265 if (value > 0)
266 {
267 if (oldFilterState == -1)
268 oldFilterState = ctl->filtercutoff.data;
269 float adjust = oldFilterState / 127.0f;
270 if (type & PART::aftertouchType::filterCutoffDown)
271 ctl->setfiltercutoff(oldFilterState - (value * adjust));
272 else
273 ctl->setfiltercutoff(oldFilterState + (value * adjust));
274 }
275 else
276 {
277 ctl->setfiltercutoff(oldFilterState);
278 oldFilterState = -1;
279 }
280 }
281
282 if (type & PART::aftertouchType::filterQ)
283 {
284 if (value > 0)
285 {
286 if (oldFilterQstate == -1)
287 oldFilterQstate = ctl->filtercutoff.data;
288 float adjust = oldFilterQstate / 127.0f;
289 if (type & PART::aftertouchType::filterQdown)
290 ctl->setfilterq(oldFilterQstate - (value * adjust));
291 else
292 ctl->setfilterq(oldFilterQstate + (value * adjust));
293 }
294 else
295 {
296 ctl->setfilterq(oldFilterQstate);
297 oldFilterQstate = -1;
298 }
299 }
300
301 if (type & PART::aftertouchType::pitchBend)
302 {
303 if (value > 0)
304 {
305 if (oldBendState == -1)
306 oldBendState = ctl->pitchwheel.data;
307 value *= 64.0f;
308 if (type & PART::aftertouchType::pitchBendDown)
309 ctl->setpitchwheel(-value);
310 else
311 ctl->setpitchwheel(value);
312 }
313 else
314 {
315 ctl->setpitchwheel(oldBendState);
316 oldBendState = -1;
317 }
318 }
319
320 if (type & PART::aftertouchType::volume)
321 {
322 if (value > 0)
323 {
324 //float adjust = 0;
325 if (oldVolumeState == -1)
326 {
327 oldVolumeState = Pvolume;
328 oldVolumeAdjust = 127 - oldVolumeState;
329 }
330 //adjust = 127 - oldVolumeState;
331 setVolume(oldVolumeState + (value / 127.0f * oldVolumeAdjust));
332 }
333 else
334 {
335 setVolume(oldVolumeState);
336 oldVolumeState = -1;
337 }
338 }
339
340 if (type & PART::aftertouchType::modulation)
341 {
342 if (value > 1) // 1 seems to foldback :(
343 {
344 if (oldModulationState == -1)
345 oldModulationState = ctl->modwheel.data;
346 ctl->setmodwheel(value);
347 }
348 else
349 {
350 ctl->setmodwheel(oldModulationState);
351 oldModulationState = -1;
352 }
353 }
354 }
355
356
setKeyAT(int note,int type,int value)357 void Part::setKeyAT(int note, int type, int value)
358 {
359 if (note < Pminkey || note > Pmaxkey)
360 return;
361 for (int i = 0; i < POLIPHONY; ++i)
362 {
363 if (partnote[i].status != KEY_OFF && partnote[i].note == note)
364 {
365 partnote[i].keyATtype = type;
366 partnote[i].keyATvalue = value;
367 }
368 }
369 }
370
371
372 // Note On Messages
NoteOn(int note,int velocity,bool renote)373 void Part::NoteOn(int note, int velocity, bool renote)
374 {
375 if (note < Pminkey || note > Pmaxkey)
376 return;
377
378 // Legato and MonoMem used vars:
379 int posb = POLIPHONY - 1; // Just a dummy initial value.
380 bool legatomodevalid = false; // true when legato mode is determined applicable.
381 bool doinglegato = false; // true when we determined we do a legato note.
382 bool ismonofirstnote = false; // (In Mono/Legato) true when we determined
383 // no other notes are held down or sustained.*/
384 int lastnotecopy = lastnote; // Useful after lastnote has been changed.
385
386 // MonoMem stuff:
387 if (Pkeymode > PART_NORMAL) // if Poly is off
388 {
389 if (!renote)
390 monomemnotes.push_back(note); // Add note to the list.
391 monomem[note].velocity = velocity; // Store this note's velocity.
392 if (partnote[lastpos].status != KEY_PLAYING
393 && partnote[lastpos].status != KEY_RELEASED_AND_SUSTAINED)
394 {
395 ismonofirstnote = true; // No other keys are held or sustained.
396 }
397 }
398 else // Poly mode is On, so just make sure the list is empty.
399 {
400 monomemnotes.clear();
401 }
402 lastnote = note;
403 int pos = -1;
404 for (int i = 0; i < POLIPHONY; ++i)
405 {
406 if (partnote[i].status == KEY_OFF)
407 {
408 pos = i;
409 break;
410 }
411 }
412 if (Pkeymode > PART_MONO && !Pdrummode)
413 {
414 // Legato mode is on and applicable.
415 legatomodevalid = true;
416 if (!ismonofirstnote && lastlegatomodevalid)
417 {
418 // At least one other key is held or sustained, and the
419 // previous note was played while in valid legato mode.
420 doinglegato = true; // So we'll do a legato note.
421 pos = lastpos; // A legato note uses same pos as previous..
422 posb = lastposb; // .. same goes for posb.
423 }
424 else
425 {
426 // Legato mode is valid, but this is only a first note.
427 for (int i = 0; i < POLIPHONY; ++i)
428 if (partnote[i].status == KEY_PLAYING
429 || partnote[i].status == KEY_RELEASED_AND_SUSTAINED)
430 ReleaseNotePos(i);
431
432 // Set posb
433 posb = (pos + 1) % POLIPHONY; // We really want it (if the following fails)
434 for (int i = 0; i < POLIPHONY; ++i)
435 {
436 if (partnote[i].status == KEY_OFF && pos != i)
437 {
438 posb = i;
439 break;
440 }
441 }
442 }
443 lastposb = posb;// Keep a trace of used posb
444 }
445 else
446 {
447 // Legato mode is either off or non-applicable.
448 if ((Pkeymode & MIDI_NOT_LEGATO) == PART_MONO)
449 { // if the mode is 'mono' turn off all other notes
450 for (int i = 0; i < POLIPHONY; ++i)
451 {
452 if (partnote[i].status == KEY_PLAYING)
453 ReleaseNotePos(i);
454 }
455 ReleaseSustainedKeys();
456 }
457 }
458 lastlegatomodevalid = legatomodevalid;
459
460 if (pos == -1)
461 {
462 // test
463 synth->getRuntime().Log("Too many notes - notes > poliphony");
464 }
465 else
466 {
467 // start the note
468 partnote[pos].status = KEY_PLAYING;
469 partnote[pos].note = note;
470 partnote[pos].keyATtype = PART::aftertouchType::off;
471 partnote[pos].keyATvalue = 0;
472 if (legatomodevalid)
473 {
474 partnote[posb].status = KEY_PLAYING;
475 partnote[posb].note = note;
476 partnote[posb].keyATtype = PART::aftertouchType::off;
477 partnote[posb].keyATvalue = 0;
478 }
479
480 // compute the velocity offset
481 float newVel = velocity;
482 if (Pvelrand >= 1)
483 {
484 newVel *= (1 - (synth->numRandom() * Pvelrand * 0.0104f));
485 //std::cout << "Vel rand " << Pvelrand << " result " << newVel << std::endl;
486 }
487
488
489 float vel = velF(newVel / 127.0f, Pvelsns) + (Pveloffs - 64.0f) / 64.0f;
490 vel = (vel < 0.0f) ? 0.0f : vel;
491 vel = (vel > 1.0f) ? 1.0f : vel;
492
493 // initialise note frequency
494 float notebasefreq;
495 if ((notebasefreq = PnoteMap[PmapOffset + note]) < 0.0f)
496 return; // the key is not mapped
497
498 // Humanise
499 // cout << "\n" << notebasefreq << endl;
500 if (!Pdrummode && Pfrand >= 1) // otherwise 'off'
501 // this is an approximation to keep the math simple and is
502 // about 1 cent out at 50 cents
503 notebasefreq *= (1.0f + ((synth->numRandom() - 0.5f) * Pfrand * 0.00115f));
504 // cout << notebasefreq << endl;
505
506 // Portamento
507 if (oldfreq < 1.0f)
508 oldfreq = notebasefreq; // this is only the first note is played
509
510 // For Mono/Legato: Force Portamento Off on first
511 // notes. That means it is required that the previous note is
512 // still held down or sustained for the Portamento to activate
513 // (that's like Legato).
514 int portamento = 0;
515 if (Pkeymode == PART_NORMAL || !ismonofirstnote)
516 {
517 // I added a third argument to the
518 // ctl->initportamento(...) function to be able
519 // to tell it if we're doing a legato note.
520 portamento = ctl->initportamento(oldfreq, notebasefreq, doinglegato);
521 }
522
523 if (portamento)
524 ctl->portamento.noteusing = pos;
525 oldfreq = notebasefreq;
526 lastpos = pos; // Keep a trace of used pos.
527 if (doinglegato)
528 {
529 // Do Legato note
530 if (!Pkitmode)
531 { // "normal mode" legato note
532 if ((kit[0].Padenabled)
533 && (partnote[pos].kititem[0].adnote)
534 && (partnote[posb].kititem[0].adnote))
535 {
536 // Set posb to clone state from pos and fade out...
537 if (!portamento) // ...but only if portamento isn't in effect
538 partnote[posb].kititem[0].adnote->
539 legatoFadeOut(*partnote[pos].kititem[0].adnote);
540 // Then set pos to the new note and fade in.
541 // This function skips the fade if portamento is active.
542 partnote[pos].kititem[0].adnote->
543 legatoFadeIn(notebasefreq, vel, portamento, note);
544 }
545
546 if ((kit[0].Psubenabled)
547 && (partnote[pos].kititem[0].subnote)
548 && (partnote[posb].kititem[0].subnote))
549 {
550 if (!portamento)
551 partnote[posb].kititem[0].subnote->
552 legatoFadeOut(*partnote[pos].kititem[0].subnote);
553 partnote[pos].kititem[0].subnote->
554 legatoFadeIn(notebasefreq, vel, portamento, note);
555 }
556
557 if ((kit[0].Ppadenabled)
558 && (partnote[pos].kititem[0].padnote)
559 && (partnote[posb].kititem[0].padnote))
560 {
561 if (!portamento)
562 partnote[posb].kititem[0].padnote->
563 legatoFadeOut(*partnote[pos].kititem[0].padnote);
564 partnote[pos].kititem[0].padnote->
565 legatoFadeIn(notebasefreq, vel, portamento, note);
566 }
567
568 }
569 else
570 { // "kit mode" legato note
571 int ci = 0;
572 for (int item = 0; item < NUM_KIT_ITEMS; ++item)
573 {
574 if (kit[item].Pmuted)
575 continue;
576 if ((note < kit[item].Pminkey) || (note > kit[item].Pmaxkey))
577 continue;
578
579 if ((lastnotecopy < kit[item].Pminkey)
580 || (lastnotecopy > kit[item].Pmaxkey))
581 continue; // We will not perform legato across 2 key regions.
582
583 partnote[pos].kititem[ci].sendtoparteffect =
584 (kit[item].Psendtoparteffect < NUM_PART_EFX)
585 ? kit[item].Psendtoparteffect
586 : NUM_PART_EFX; // if this parameter is 127 for "unprocessed"
587 partnote[posb].kititem[ci].sendtoparteffect =
588 (kit[item].Psendtoparteffect < NUM_PART_EFX)
589 ? kit[item].Psendtoparteffect
590 : NUM_PART_EFX;
591
592 if ((kit[item].Padenabled)
593 && (kit[item].adpars)
594 && (partnote[pos].kititem[ci].adnote)
595 && (partnote[posb].kititem[ci].adnote))
596 {
597 // Set posb to clone state from pos and fade out...
598 if (!portamento) // ...but only if portamento isn't in effect
599 partnote[posb].kititem[ci].adnote->
600 legatoFadeOut(*partnote[pos].kititem[ci].adnote);
601 // Then set pos to the new note and fade in.
602 // This function skips the fade if portamento is active.
603 partnote[pos].kititem[ci].adnote->
604 legatoFadeIn(notebasefreq, vel, portamento, note);
605 }
606 if ((kit[item].Psubenabled)
607 && (kit[item].subpars)
608 && (partnote[pos].kititem[ci].subnote)
609 && (partnote[posb].kititem[ci].subnote))
610 {
611 if (!portamento)
612 partnote[posb].kititem[ci].subnote->
613 legatoFadeOut(*partnote[pos].kititem[ci].subnote);
614 partnote[pos].kititem[ci].subnote->
615 legatoFadeIn(notebasefreq, vel, portamento, note);
616 }
617 if ((kit[item].Ppadenabled)
618 && (kit[item].padpars)
619 && (partnote[pos].kititem[ci].padnote)
620 && (partnote[posb].kititem[ci].padnote))
621 {
622 if (!portamento)
623 partnote[posb].kititem[ci].padnote->
624 legatoFadeOut(*partnote[pos].kititem[ci].padnote);
625 partnote[pos].kititem[ci].padnote->
626 legatoFadeIn(notebasefreq, vel, portamento, note);
627 }
628
629 if ((kit[item].adpars)
630 || (kit[item].subpars)
631 || (kit[item].padpars))
632 {
633 ci++;
634 if (Pkitmode == 2
635 && (kit[item].Padenabled
636 || kit[item].Psubenabled
637 || kit[item].Ppadenabled))
638 break;
639 }
640 }
641 if (ci == 0)
642 {
643 // No legato were performed at all, so pretend nothing happened:
644 monomemnotes.pop_back(); // Remove last note from the list.
645 lastnote = lastnotecopy; // Set lastnote back to previous value.
646 }
647 }
648 return; // Ok, Legato note done, return.
649 }
650
651 partnote[pos].itemsplaying = 0;
652 if (legatomodevalid)
653 partnote[posb].itemsplaying = 0;
654
655 if (!Pkitmode)
656 { // init the notes for the "normal mode"
657 partnote[pos].kititem[0].sendtoparteffect = 0;
658 if (kit[0].Padenabled)
659 partnote[pos].kititem[0].adnote =
660 new ADnote(kit[0].adpars, ctl, notebasefreq, vel,
661 portamento, note, synth);
662 if (kit[0].Psubenabled)
663 partnote[pos].kititem[0].subnote =
664 new SUBnote(kit[0].subpars, ctl, notebasefreq, vel,
665 portamento, note, synth);
666 if (kit[0].Ppadenabled)
667 partnote[pos].kititem[0].padnote =
668 new PADnote(kit[0].padpars, ctl, notebasefreq, vel,
669 portamento, note, synth);
670 if (kit[0].Padenabled || kit[0].Psubenabled || kit[0].Ppadenabled)
671 partnote[pos].itemsplaying++;
672
673 // Spawn another note (but silent) if legatomodevalid==true
674 if (legatomodevalid)
675 {
676 partnote[posb].kititem[0].sendtoparteffect = 0;
677 if (kit[0].Padenabled)
678 partnote[posb].kititem[0].adnote =
679 new ADnote(*partnote[pos].kititem[0].adnote);
680 if (kit[0].Psubenabled)
681 partnote[posb].kititem[0].subnote =
682 new SUBnote(*partnote[pos].kititem[0].subnote);
683 if (kit[0].Ppadenabled)
684 partnote[posb].kititem[0].padnote =
685 new PADnote(*partnote[pos].kititem[0].padnote);
686 if (kit[0].Padenabled || kit[0].Psubenabled || kit[0].Ppadenabled)
687 partnote[posb].itemsplaying++;
688 }
689 }
690 else
691 { // init the notes for the "kit mode"
692 float truevel = vel; // we need this as cross fade modifies the value
693 for (int item = 0; item < NUM_KIT_ITEMS; ++item)
694 {
695 if (kit[item].Pmuted)
696 continue;
697 if (note < kit[item].Pminkey || note>kit[item].Pmaxkey)
698 continue;
699
700
701 // cross fade on multi
702 if (Pkitfade)
703 {
704 vel = truevel; // always start with correct value
705 int range = 0;
706 int position;
707 if ((item & 1) == 0 && kit[item + 1].Penabled) // crossfade lower item of pair
708 {
709 if (kit[item].Pmaxkey > kit[item + 1].Pminkey && kit[item].Pmaxkey < kit[item + 1].Pmaxkey)
710 {
711 if (note >= kit[item + 1].Pminkey)
712 {
713 range = kit[item].Pmaxkey - kit[item + 1].Pminkey;
714 position = kit[item].Pmaxkey - note;
715 }
716 }
717 else if (kit[item + 1].Pmaxkey > kit[item].Pminkey && kit[item + 1].Pmaxkey < kit[item].Pmaxkey ) // eliminate equal state
718 {
719 if (note <= kit[item + 1].Pmaxkey)
720 {
721 range = kit[item + 1].Pmaxkey - kit[item].Pminkey;
722 position = (note - kit[item].Pminkey);
723 }
724 }
725 }
726 else if ((item & 1) == 1 && kit[item - 1].Penabled) // crossfade upper item of pair
727 {
728
729 if (kit[item - 1].Pmaxkey > kit[item ].Pminkey && kit[item - 1].Pmaxkey < kit[item ].Pmaxkey)
730 {
731 if (note <= kit[item - 1].Pmaxkey)
732 {
733 range = kit[item - 1].Pmaxkey - kit[item].Pminkey;
734 position = (note - kit[item].Pminkey);
735 }
736 }
737 else if (kit[item].Pmaxkey > kit[item - 1].Pminkey && kit[item].Pmaxkey < kit[item - 1].Pmaxkey) // eliminate equal state
738 {
739 if (note >= kit[item - 1].Pminkey)
740 {
741 range = kit[item].Pmaxkey - kit[item - 1].Pminkey;
742 position = kit[item].Pmaxkey - note;
743 }
744 }
745 }
746 if (range)
747 {
748 vel = truevel * (float(position) / float(range));
749 //cout << item << " " << vel << endl;
750 }
751 }
752 // end of cross fade
753
754
755 int ci = partnote[pos].itemsplaying; // ci=current item
756
757 partnote[pos].kititem[ci].sendtoparteffect =
758 (kit[item].Psendtoparteffect < NUM_PART_EFX)
759 ? kit[item].Psendtoparteffect
760 : NUM_PART_EFX; // if this parameter is 127 for "unprocessed"
761
762 if (kit[item].adpars && kit[item].Padenabled)
763 {
764 partnote[pos].kititem[ci].adnote =
765 new ADnote(kit[item].adpars, ctl, notebasefreq, vel,
766 portamento, note, synth);
767 }
768 if (kit[item].subpars && kit[item].Psubenabled)
769 partnote[pos].kititem[ci].subnote =
770 new SUBnote(kit[item].subpars, ctl, notebasefreq, vel,
771 portamento, note, synth);
772
773 if (kit[item].padpars && kit[item].Ppadenabled)
774 partnote[pos].kititem[ci].padnote =
775 new PADnote(kit[item].padpars, ctl, notebasefreq, vel,
776 portamento, note, synth);
777
778 // Spawn another note (but silent) if legatomodevalid==true
779 if (legatomodevalid)
780 {
781 partnote[posb].kititem[ci].sendtoparteffect =
782 (kit[item].Psendtoparteffect < NUM_PART_EFX)
783 ? kit[item].Psendtoparteffect
784 : NUM_PART_EFX; // if this parameter is 127 for "unprocessed"
785
786 if (kit[item].adpars && kit[item].Padenabled)
787 {
788 partnote[posb].kititem[ci].adnote =
789 new ADnote(*partnote[pos].kititem[ci].adnote);
790 }
791 if (kit[item].subpars && kit[item].Psubenabled)
792 partnote[posb].kititem[ci].subnote =
793 new SUBnote(*partnote[pos].kititem[ci].subnote);
794 if (kit[item].padpars && kit[item].Ppadenabled)
795 partnote[posb].kititem[ci].padnote =
796 new PADnote(*partnote[pos].kititem[ci].padnote);
797
798 if (kit[item].adpars || kit[item].subpars)
799 partnote[posb].itemsplaying++;
800 }
801
802 if (kit[item].adpars || kit[item].subpars)
803 {
804 partnote[pos].itemsplaying++;
805 if (Pkitmode == 2 && (kit[item].Padenabled
806 || kit[item].Psubenabled
807 || kit[item].Ppadenabled))
808 break;
809 }
810 }
811 }
812 }
813
814 // this only release the keys if there is maximum number of keys allowed
815 //setkeylimit(Pkeylimit);
816 if (Pkeymode == PART_NORMAL)
817 enforcekeylimit();
818 }
819
820
821 // Note Off Messages
NoteOff(int note)822 void Part::NoteOff(int note) //release the key
823 {
824 // This note is released, so we remove it from the list.
825 monomemnotes.remove(note);
826
827 bool keep = Pkeymode > PART_NORMAL && !Pdrummode && !monomemnotes.empty();
828 for (int i = 0; i < POLIPHONY; ++i)
829 { //first note in, is first out if there are same note multiple times
830 if (partnote[i].status == KEY_PLAYING && partnote[i].note == note)
831 {
832 if (ctl->sustain.sustain)
833 partnote[i].status = KEY_RELEASED_AND_SUSTAINED;
834 else
835 { //the sustain pedal is not pushed
836 if (keep)
837 MonoMemRenote(); // To play most recent still held note.
838 else
839 {
840 ReleaseNotePos(i);
841 break; // only release one note.
842 }
843 }
844 }
845 }
846 }
847
848
849 // Controllers
SetController(unsigned int type,int par)850 void Part::SetController(unsigned int type, int par)
851 {
852 switch (type)
853 {
854 case MIDI::CC::pitchWheel:
855 ctl->setpitchwheel(par);
856 break;
857
858 case MIDI::CC::expression:
859 ctl->setexpression(par);
860 setVolume(Pvolume);
861 break;
862
863 case MIDI::CC::portamento:
864 ctl->setportamento(par);
865 break;
866
867 case MIDI::CC::panning:
868 par = 64 + (par - 64) * (ctl->panning.depth / 64.0); // force float during calculation
869 setPan(par);
870 break;
871
872 case MIDI::CC::filterCutoff:
873 ctl->setfiltercutoff(par);
874 break;
875
876 case MIDI::CC::filterQ:
877 ctl->setfilterq(par);
878 break;
879
880 case MIDI::CC::bandwidth:
881 ctl->setbandwidth(par);
882 break;
883
884 case MIDI::CC::modulation:
885 ctl->setmodwheel(par);
886 break;
887
888 case MIDI::CC::fmamp:
889 ctl->setfmamp(par);
890 break;
891
892 case MIDI::CC::volume:
893 if (ctl->volume.receive)
894 setVolume(par * ctl->volume.volume);
895 break;
896
897 case MIDI::CC::sustain:
898 ctl->setsustain(par);
899 if (!ctl->sustain.sustain)
900 ReleaseSustainedKeys();
901 break;
902
903 case MIDI::CC::allSoundOff:
904 AllNotesOff(); // Panic
905 break;
906
907 case MIDI::CC::resetAllControllers:
908 ctl->resetall();
909 ReleaseSustainedKeys();
910 setVolume(Pvolume);
911 setPan(Ppanning);
912 Pkeymode &= MIDI_NOT_LEGATO; // clear temporary legato mode
913
914 for (int item = 0; item < NUM_KIT_ITEMS; ++item)
915 {
916 if (!kit[item].adpars)
917 continue;
918 kit[item].adpars->GlobalPar.Reson->sendcontroller(MIDI::CC::resonanceCenter, 1.0);
919 kit[item].adpars->GlobalPar.Reson->sendcontroller(MIDI::CC::resonanceBandwidth, 1.0);
920 }
921 // more update to add here if I add controllers
922 break;
923
924 case MIDI::CC::allNotesOff:
925 ReleaseAllKeys();
926 break;
927
928 case MIDI::CC::resonanceCenter:
929 ctl->setresonancecenter(par);
930 for (int item = 0; item < NUM_KIT_ITEMS; ++item)
931 {
932 if (!kit[item].adpars)
933 continue;
934 kit[item].adpars->GlobalPar.Reson->sendcontroller(MIDI::CC::resonanceCenter, ctl->resonancecenter.relcenter);
935 }
936 break;
937
938 case MIDI::CC::resonanceBandwidth:
939 ctl->setresonancebw(par);
940 kit[0].adpars->GlobalPar.Reson->sendcontroller(MIDI::CC::resonanceBandwidth, ctl->resonancebandwidth.relbw);
941 break;
942
943 case MIDI::CC::channelPressure:
944 setChannelAT(PchannelATchoice, par);
945 break;
946
947 case MIDI::CC::keyPressure:
948 {
949 int note = par & 0xff;
950 int value = (par >> 8) & 0xff;
951 int type = PkeyATchoice;
952 if (value == 0)
953 type = 0;
954 setKeyAT(note, type, value);
955 break;
956 }
957 }
958 }
959
960
961 // Release the sustained keys
ReleaseSustainedKeys(void)962 void Part::ReleaseSustainedKeys(void)
963 {
964 // Let's call MonoMemRenote() on some conditions:
965 if ((Pkeymode < PART_MONO || Pkeymode > PART_LEGATO) && (!monomemnotes.empty()))
966 if (monomemnotes.back() != lastnote)
967 // Sustain controller manipulation would cause repeated same note
968 // respawn without this check.
969 MonoMemRenote(); // To play most recent still held note.
970
971 for (int i = 0; i < POLIPHONY; ++i)
972 if (partnote[i].status == KEY_RELEASED_AND_SUSTAINED)
973 ReleaseNotePos(i);
974 }
975
976
977 // Release all keys
ReleaseAllKeys(void)978 void Part::ReleaseAllKeys(void)
979 {
980 for (int i = 0; i < POLIPHONY; ++i)
981 {
982 if (partnote[i].status != KEY_RELEASED
983 && partnote[i].status != KEY_OFF) //thanks to Frank Neumann
984 ReleaseNotePos(i);
985 }
986 // Clear legato notes, if any.
987 monomemnotes.clear();
988 }
989
990
991 // Call NoteOn(...) with the most recent still held key as new note
992 // (Made for Mono/Legato).
MonoMemRenote(void)993 void Part::MonoMemRenote(void)
994 {
995 unsigned char mmrtempnote = monomemnotes.back(); // Last list element.
996 NoteOn(mmrtempnote, monomem[mmrtempnote].velocity, true);
997 }
998
999
1000 // Release note at position
ReleaseNotePos(int pos)1001 void Part::ReleaseNotePos(int pos)
1002 {
1003
1004 for (int j = 0; j < NUM_KIT_ITEMS; ++j)
1005 {
1006 if (partnote[pos].kititem[j].adnote)
1007 if (partnote[pos].kititem[j].adnote)
1008 partnote[pos].kititem[j].adnote->releasekey();
1009
1010 if (partnote[pos].kititem[j].subnote)
1011 if (partnote[pos].kititem[j].subnote)
1012 partnote[pos].kititem[j].subnote->releasekey();
1013
1014 if (partnote[pos].kititem[j].padnote)
1015 if (partnote[pos].kititem[j].padnote)
1016 partnote[pos].kititem[j].padnote->releasekey();
1017 }
1018 partnote[pos].status = KEY_RELEASED;
1019 }
1020
1021
1022 // Kill note at position
KillNotePos(int pos)1023 void Part::KillNotePos(int pos)
1024 {
1025 partnote[pos].status = KEY_OFF;
1026 partnote[pos].note = -1;
1027 partnote[pos].time = 0;
1028 partnote[pos].itemsplaying = 0;
1029
1030 for (int j = 0; j < NUM_KIT_ITEMS; ++j)
1031 {
1032 if (partnote[pos].kititem[j].adnote)
1033 {
1034 delete partnote[pos].kititem[j].adnote;
1035 partnote[pos].kititem[j].adnote = NULL;
1036 }
1037 if (partnote[pos].kititem[j].subnote)
1038 {
1039 delete partnote[pos].kititem[j].subnote;
1040 partnote[pos].kititem[j].subnote = NULL;
1041 }
1042 if (partnote[pos].kititem[j].padnote)
1043 {
1044 delete partnote[pos].kititem[j].padnote;
1045 partnote[pos].kititem[j].padnote = NULL;
1046 }
1047 }
1048 if (pos == ctl->portamento.noteusing)
1049 {
1050 ctl->portamento.noteusing = -1;
1051 ctl->portamento.used = 0;
1052 }
1053 }
1054
1055
enforcekeylimit()1056 void Part::enforcekeylimit()
1057 {
1058 // release old keys if the number of notes>keylimit
1059 int notecount = 0;
1060 for (int i = 0; i < POLIPHONY; ++i)
1061 {
1062 if (partnote[i].status == KEY_PLAYING
1063 || partnote[i].status == KEY_RELEASED_AND_SUSTAINED)
1064 notecount++;
1065 }
1066 while (notecount > Pkeylimit)
1067 { // find out the oldest note
1068 int oldestnotepos = 0;
1069 int maxtime = 0;
1070
1071 for (int i = 0; i < POLIPHONY; ++i)
1072 {
1073 if ((partnote[i].status == KEY_PLAYING
1074 || partnote[i].status == KEY_RELEASED_AND_SUSTAINED)
1075 && partnote[i].time > maxtime)
1076 {
1077 maxtime = partnote[i].time;
1078 oldestnotepos = i;
1079 }
1080 }
1081 ReleaseNotePos(oldestnotepos);
1082 --notecount;
1083 }
1084 }
1085
1086
1087 // Compute Part samples and store them in the partoutl[] and partoutr[]
ComputePartSmps(void)1088 void Part::ComputePartSmps(void)
1089 {
1090 tmpoutl = synth->getRuntime().genMixl;
1091 tmpoutr = synth->getRuntime().genMixr;
1092 for (int nefx = 0; nefx < NUM_PART_EFX + 1; ++nefx)
1093 {
1094 memset(partfxinputl[nefx], 0, synth->sent_bufferbytes);
1095 memset(partfxinputr[nefx], 0, synth->sent_bufferbytes);
1096 }
1097
1098 for (int k = 0; k < POLIPHONY; ++k)
1099 {
1100 int oldFilterState;
1101 int oldBendState;
1102 int oldModulationState;
1103 if (partnote[k].status == KEY_OFF)
1104 continue;
1105 int noteplay = 0; // 0 if there is nothing activated
1106 partnote[k].time++;
1107 int keyATtype = partnote[k].keyATtype;
1108 int keyATvalue = partnote[k].keyATvalue;
1109 if (keyATtype & PART::aftertouchType::filterCutoff)
1110 {
1111 oldFilterState = ctl->filtercutoff.data;
1112 float adjust = oldFilterState / 127.0f;
1113 if (keyATtype & PART::aftertouchType::filterCutoffDown)
1114 ctl->setfiltercutoff(oldFilterState - (keyATvalue * adjust));
1115 else
1116 ctl->setfiltercutoff(oldFilterState + (keyATvalue * adjust));
1117 }
1118 if (keyATtype & PART::aftertouchType::filterQ)
1119 {
1120 oldFilterQstate = ctl->filterq.data;
1121 float adjust = oldFilterQstate / 127.0f;
1122 if (keyATtype & PART::aftertouchType::filterQdown)
1123 ctl->setfilterq(oldFilterQstate - (keyATvalue * adjust));
1124 else
1125 ctl->setfilterq(oldFilterQstate + (keyATvalue * adjust));
1126 }
1127 if (keyATtype & PART::aftertouchType::pitchBend)
1128 {
1129 keyATvalue *= 64.0f;
1130 oldBendState = ctl->pitchwheel.data;
1131 if (keyATtype & PART::aftertouchType::pitchBendDown)
1132 ctl->setpitchwheel(-keyATvalue);
1133 else
1134 ctl->setpitchwheel(keyATvalue);
1135 }
1136 if (keyATtype & PART::aftertouchType::modulation)
1137 {
1138 oldModulationState = ctl->modwheel.data;
1139 ctl->setmodwheel(keyATvalue);
1140 }
1141
1142 // get the sampledata of the note and kill it if it's finished
1143 for (int item = 0; item < partnote[k].itemsplaying; ++item)
1144 {
1145 int sendcurrenttofx = partnote[k].kititem[item].sendtoparteffect;
1146 ADnote *adnote = partnote[k].kititem[item].adnote;
1147 SUBnote *subnote = partnote[k].kititem[item].subnote;
1148 PADnote *padnote = partnote[k].kititem[item].padnote;
1149 // get from the ADnote
1150 if (adnote)
1151 {
1152 noteplay++;
1153 if (adnote->ready())
1154 {
1155 adnote->noteout(tmpoutl, tmpoutr);
1156 for (int i = 0; i < synth->sent_buffersize; ++i)
1157 { // add the ADnote to part(mix)
1158 partfxinputl[sendcurrenttofx][i] += tmpoutl[i];
1159 partfxinputr[sendcurrenttofx][i] += tmpoutr[i];
1160 }
1161 }
1162 if (adnote->finished())
1163 {
1164 delete partnote[k].kititem[item].adnote;
1165 partnote[k].kititem[item].adnote = NULL;
1166 }
1167 }
1168 // get from the SUBnote
1169 if (subnote)
1170 {
1171 noteplay++;
1172 if (subnote->ready())
1173 {
1174 subnote->noteout(tmpoutl, tmpoutr);
1175 for (int i = 0; i < synth->sent_buffersize; ++i)
1176 { // add the SUBnote to part(mix)
1177 partfxinputl[sendcurrenttofx][i] += tmpoutl[i];
1178 partfxinputr[sendcurrenttofx][i] += tmpoutr[i];
1179 }
1180 }
1181 if (subnote->finished())
1182 {
1183 delete partnote[k].kititem[item].subnote;
1184 partnote[k].kititem[item].subnote = NULL;
1185 }
1186 }
1187 // get from the PADnote
1188 if (padnote)
1189 {
1190 noteplay++;
1191 if (padnote->ready())
1192 {
1193 padnote->noteout(tmpoutl, tmpoutr);
1194 for (int i = 0 ; i < synth->sent_buffersize; ++i)
1195 { // add the PADnote to part(mix)
1196 partfxinputl[sendcurrenttofx][i] += tmpoutl[i];
1197 partfxinputr[sendcurrenttofx][i] += tmpoutr[i];
1198 }
1199 }
1200 if (padnote->finished())
1201 {
1202 delete partnote[k].kititem[item].padnote;
1203 partnote[k].kititem[item].padnote = NULL;
1204 }
1205 }
1206 }
1207 // Kill note if there is no synth on that note
1208 if (noteplay == 0)
1209 KillNotePos(k);
1210
1211 if (keyATtype & PART::aftertouchType::filterCutoff)
1212 ctl->setfiltercutoff(oldFilterState);
1213 if (keyATtype & PART::aftertouchType::filterQ)
1214 ctl->setfilterq(oldFilterQstate);
1215 if (keyATtype & PART::aftertouchType::pitchBend)
1216 ctl->setpitchwheel(oldBendState);
1217 if (keyATtype & PART::aftertouchType::modulation)
1218 ctl->setmodwheel(oldModulationState);
1219 }
1220
1221 // Apply part's effects and mix them
1222 for (int nefx = 0; nefx < NUM_PART_EFX; ++nefx)
1223 {
1224 if (!Pefxbypass[nefx])
1225 {
1226 partefx[nefx]->out(partfxinputl[nefx], partfxinputr[nefx]);
1227 if (Pefxroute[nefx] == 2)
1228 {
1229 for (int i = 0; i < synth->sent_buffersize; ++i)
1230 {
1231 partfxinputl[nefx + 1][i] += partefx[nefx]->efxoutl[i];
1232 partfxinputr[nefx + 1][i] += partefx[nefx]->efxoutr[i];
1233 }
1234 }
1235 }
1236 int routeto = (Pefxroute[nefx] == 0) ? nefx + 1 : NUM_PART_EFX;
1237 for (int i = 0; i < synth->sent_buffersize; ++i)
1238 {
1239 partfxinputl[routeto][i] += partfxinputl[nefx][i];
1240 partfxinputr[routeto][i] += partfxinputr[nefx][i];
1241 }
1242 }
1243 memcpy(partoutl, partfxinputl[NUM_PART_EFX], synth->sent_bufferbytes);
1244 memcpy(partoutr, partfxinputr[NUM_PART_EFX], synth->sent_bufferbytes);
1245
1246 // Kill All Notes if killallnotes true
1247 if (killallnotes)
1248 {
1249 for (int i = 0; i < synth->sent_buffersize; ++i)
1250 {
1251 float tmp = (synth->sent_buffersize - i) / synth->sent_buffersize_f;
1252 partoutl[i] *= tmp;
1253 partoutr[i] *= tmp;
1254 }
1255 for (int k = 0; k < POLIPHONY; ++k)
1256 KillNotePos(k);
1257 killallnotes = 0;
1258 for (int nefx = 0; nefx < NUM_PART_EFX; ++nefx)
1259 partefx[nefx]->cleanup();
1260 }
1261 ctl->updateportamento();
1262 }
1263
1264
1265 // Parameter control
setVolume(float value)1266 void Part::setVolume(float value)
1267 {
1268 Pvolume = value;
1269 }
1270
1271
checkVolume(float step)1272 void Part::checkVolume(float step)
1273 {
1274 TransVolume += step;
1275 volume = decibel<-40>(1.0f - TransVolume/96.0f);
1276 if (volume < 0.01015f) // done to get a smooth cutoff at what was - 40dB
1277 volume = 0.0f;
1278 }
1279
1280
setDestination(int value)1281 void Part::setDestination(int value)
1282 {
1283 Paudiodest = value;
1284 }
1285
1286
setPan(float value)1287 void Part::setPan(float value)
1288 {
1289 Ppanning = value;
1290 }
1291
1292
checkPanning(float step,unsigned char panLaw)1293 void Part::checkPanning(float step, unsigned char panLaw)
1294 {
1295 //float t;
1296 TransPanning += step;
1297 float actualPan = ((TransPanning + 1.0f) * (126.0f / 127.0f));
1298 // resolves min value full Left
1299 setAllPan(actualPan, pangainL,pangainR, panLaw);
1300 }
1301
1302
1303 // Enable or disable a kit item
setkititemstatus(int kititem,int Penabled_)1304 void Part::setkititemstatus(int kititem, int Penabled_)
1305 {
1306 if (kititem == 0 || kititem >= NUM_KIT_ITEMS)
1307 return; // nonexistent kit item and the first kit item is always enabled
1308 kit[kititem].Penabled = Penabled_;
1309
1310 bool resetallnotes = false;
1311 if (!Penabled_)
1312 {
1313 kit[kititem].Pmuted = 0;
1314 kit[kititem].Padenabled = 0;
1315 kit[kititem].Psubenabled = 0;
1316 kit[kititem].Ppadenabled = 0;
1317 kit[kititem].Pname.clear();
1318 kit[kititem].Psendtoparteffect = 0;
1319 if (kit[kititem].adpars)
1320 {
1321 delete kit[kititem].adpars;
1322 kit[kititem].adpars = NULL;
1323 }
1324 if (kit[kititem].subpars)
1325 {
1326 delete kit[kititem].subpars;
1327 kit[kititem].subpars = NULL;
1328 }
1329 if (kit[kititem].padpars)
1330 {
1331 delete kit[kititem].padpars;
1332 kit[kititem].padpars = NULL;
1333 resetallnotes = true;
1334 }
1335 }
1336 else
1337 {
1338 if (!kit[kititem].adpars)
1339 kit[kititem].adpars = new ADnoteParameters(fft, synth);
1340 if (!kit[kititem].subpars)
1341 kit[kititem].subpars = new SUBnoteParameters(synth);
1342 if (!kit[kititem].padpars)
1343 kit[kititem].padpars = new PADnoteParameters(fft, synth);
1344 }
1345
1346 if (resetallnotes)
1347 for (int k = 0; k < POLIPHONY; ++k)
1348 KillNotePos(k);
1349 }
1350
1351
add2XMLinstrument(XMLwrapper * xml)1352 void Part::add2XMLinstrument(XMLwrapper *xml)
1353 {
1354 xml->beginbranch("INFO");
1355 xml->addparstr("name", Poriginal);
1356 xml->addparstr("author", info.Pauthor);
1357 xml->addparstr("comments", info.Pcomments);
1358 xml->addpar("type", type_offset[info.Ptype]);
1359 xml->addparstr("file", Pname);
1360 xml->endbranch();
1361 if (Pname == DEFAULT_NAME)
1362 return;
1363
1364 xml->beginbranch("INSTRUMENT_KIT");
1365 xml->addpar("kit_mode", Pkitmode);
1366 xml->addparbool("kit_crossfade", Pkitfade);
1367 xml->addparbool("drum_mode", Pdrummode);
1368
1369 for (int i = 0; i < NUM_KIT_ITEMS; ++i)
1370 {
1371 xml->beginbranch("INSTRUMENT_KIT_ITEM",i);
1372 xml->addparbool("enabled", kit[i].Penabled);
1373 if (kit[i].Penabled)
1374 {
1375 xml->addparstr("name", kit[i].Pname.c_str());
1376
1377 xml->addparbool("muted", kit[i].Pmuted);
1378 xml->addpar("min_key", kit[i].Pminkey);
1379 xml->addpar("max_key", kit[i].Pmaxkey);
1380
1381 xml->addpar("send_to_instrument_effect", kit[i].Psendtoparteffect);
1382
1383 xml->addparbool("add_enabled", kit[i].Padenabled);
1384 if (kit[i].Padenabled && kit[i].adpars)
1385 {
1386 xml->beginbranch("ADD_SYNTH_PARAMETERS");
1387 kit[i].adpars->add2XML(xml);
1388 xml->endbranch();
1389 }
1390
1391 xml->addparbool("sub_enabled", kit[i].Psubenabled);
1392 if (kit[i].Psubenabled && kit[i].subpars)
1393 {
1394 xml->beginbranch("SUB_SYNTH_PARAMETERS");
1395 kit[i].subpars->add2XML(xml);
1396 xml->endbranch();
1397 }
1398
1399 xml->addparbool("pad_enabled", kit[i].Ppadenabled);
1400 if (kit[i].Ppadenabled && kit[i].padpars)
1401 {
1402 xml->beginbranch("PAD_SYNTH_PARAMETERS");
1403 kit[i].padpars->add2XML(xml);
1404 xml->endbranch();
1405 }
1406 }
1407 xml->endbranch();
1408 }
1409 xml->endbranch();
1410
1411 xml->beginbranch("INSTRUMENT_EFFECTS");
1412 for (int nefx = 0; nefx < NUM_PART_EFX; ++nefx)
1413 {
1414 xml->beginbranch("INSTRUMENT_EFFECT",nefx);
1415 xml->beginbranch("EFFECT");
1416 partefx[nefx]->add2XML(xml);
1417 xml->endbranch();
1418
1419 xml->addpar("route", Pefxroute[nefx]);
1420 partefx[nefx]->setdryonly(Pefxroute[nefx] == 2);
1421 xml->addparbool("bypass",Pefxbypass[nefx]);
1422 xml->endbranch();
1423 }
1424 xml->endbranch();
1425 }
1426
1427
add2XML(XMLwrapper * xml,bool subset)1428 void Part::add2XML(XMLwrapper *xml, bool subset)
1429 {
1430 // parameters
1431 if (!subset)
1432 {
1433 xml->addparbool("enabled", (Penabled == 1));
1434
1435 xml->addpar("volume", Pvolume);
1436 xml->addpar("panning", Ppanning);
1437
1438 xml->addpar("min_key", Pminkey);
1439 xml->addpar("max_key", Pmaxkey);
1440 xml->addpar("key_shift", Pkeyshift);
1441 xml->addpar("rcv_chn", Prcvchn);
1442
1443 xml->addpar("velocity_sensing", Pvelsns);
1444 xml->addpar("velocity_offset", Pveloffs);
1445 // the following two lines maintain backward compatibility
1446 xml->addparbool("poly_mode", (Pkeymode & MIDI_NOT_LEGATO) == PART_NORMAL);
1447 xml->addpar("legato_mode", (Pkeymode & MIDI_NOT_LEGATO) == PART_LEGATO);
1448 xml->addpar("channel_aftertouch", PchannelATchoice);
1449 xml->addpar("key_aftertouch", PkeyATchoice);
1450 xml->addpar("key_limit", Pkeylimit);
1451 xml->addpar("random_detune", Pfrand);
1452 xml->addpar("random_velocity", Pvelrand);
1453 xml->addpar("destination", Paudiodest);
1454 }
1455 xml->beginbranch("INSTRUMENT");
1456 add2XMLinstrument(xml);
1457 if (subset)
1458 {
1459 xml->addpar("key_mode", Pkeymode & MIDI_NOT_LEGATO);
1460 xml->addpar("channel_aftertouch", PchannelATchoice);
1461 xml->addpar("key_aftertouch", PkeyATchoice);
1462 xml->addpar("random_detune", Pfrand);
1463 xml->addpar("random_velocity", Pvelrand);
1464 xml->addparbool("breath_disable", PbreathControl != 2);
1465 }
1466 xml->endbranch();
1467
1468 xml->beginbranch("CONTROLLER");
1469 ctl->add2XML(xml);
1470 xml->endbranch();
1471 }
1472
1473
saveXML(string filename,bool yoshiFormat)1474 bool Part::saveXML(string filename, bool yoshiFormat)
1475 {
1476 synth->usingYoshiType = yoshiFormat;
1477 synth->getRuntime().xmlType = TOPLEVEL::XML::Instrument;
1478 XMLwrapper *xml = new XMLwrapper(synth, yoshiFormat);
1479 if (!xml)
1480 {
1481 synth->getRuntime().Log("Part: saveXML failed to instantiate new XMLwrapper");
1482 return false;
1483 }
1484 if (Pname < "!") // this shouldn't be possible
1485 Pname = UNTITLED;
1486 else if (Poriginal.empty() && Pname != UNTITLED)
1487 Poriginal = Pname;
1488
1489 if (yoshiFormat)
1490 {
1491 filename = setExtension(filename, EXTEN::yoshInst);
1492 add2XML(xml, yoshiFormat);
1493 }
1494 else
1495 {
1496 filename = setExtension(filename, EXTEN::zynInst);
1497 xml->beginbranch("INSTRUMENT");
1498 add2XMLinstrument(xml);
1499 xml->endbranch();
1500 }
1501 bool result = xml->saveXMLfile(filename);
1502 delete xml;
1503 return result;
1504 }
1505
1506
loadXMLinstrument(string filename)1507 int Part::loadXMLinstrument(string filename)
1508 {
1509 bool hasYoshi = true;
1510 filename = setExtension(filename, EXTEN::yoshInst);
1511 if (!isRegularFile(filename))
1512 {
1513 hasYoshi = false;
1514 filename = setExtension(filename, EXTEN::zynInst);
1515 }
1516
1517 XMLwrapper *xml = new XMLwrapper(synth, hasYoshi);
1518 if (!xml)
1519 {
1520 synth->getRuntime().Log("Part: loadXML failed to instantiate new XMLwrapper");
1521 return 0;
1522 }
1523 if (!xml->loadXMLfile(filename))
1524 {
1525 synth->getRuntime().Log("Part: loadXML failed to load instrument file " + filename);
1526 delete xml;
1527 return 0;
1528 }
1529 if (xml->enterbranch("INSTRUMENT") == 0)
1530 {
1531 synth->getRuntime().Log(filename + " is not an instrument file");
1532 delete xml;
1533 return 0;
1534 }
1535 defaultsinstrument();
1536 PyoshiType = xml->information.yoshiType;
1537 Pname = findLeafName(filename);
1538 int chk = findSplitPoint(Pname);
1539 if (chk > 0)
1540 Pname = Pname.substr(chk + 1, Pname.size() - chk - 1);
1541 getfromXMLinstrument(xml);
1542
1543 if (hasYoshi)
1544 {
1545 Pkeymode = xml->getpar("key_mode", Pkeymode, PART_NORMAL, MIDI_LEGATO);
1546 Pfrand = xml->getpar127("random_detune", Pfrand);
1547 if (Pfrand > 50)
1548 Pfrand = 50;
1549 Pvelrand = xml->getpar127("random_velocity", Pvelrand);
1550 if (Pvelrand > 50)
1551 Pvelrand = 50;
1552 PbreathControl = xml->getparbool("breath_disable", PbreathControl);
1553 if (PbreathControl)
1554 PbreathControl = 255; // impossible value
1555 else
1556 PbreathControl = 2;
1557 }
1558 xml->exitbranch();
1559 if (xml->enterbranch("CONTROLLER"))
1560 {
1561 ctl->getfromXML(xml);
1562 xml->exitbranch();
1563 }
1564 xml->exitbranch();
1565 delete xml;
1566 return 1;
1567 }
1568
1569
getfromXMLinstrument(XMLwrapper * xml)1570 void Part::getfromXMLinstrument(XMLwrapper *xml)
1571 {
1572 string tempname;
1573 if (xml->enterbranch("INFO"))
1574 {
1575 Poriginal = xml->getparstr("name");
1576 // counting type numbers but checking the *contents* of type_offset()
1577 info.Pauthor = func::formatTextLines(xml->getparstr("author"), 54);
1578 info.Pcomments = func::formatTextLines(xml->getparstr("comments"), 54);
1579 int found = xml->getpar("type", 0, -20, 255); // should cover all!
1580 int type = 0;
1581 int offset = 0;
1582 while (offset != 255 && offset != found)
1583 {
1584 ++type;
1585 offset = type_offset[type];
1586 }
1587 if (offset == 255)
1588 type = 0; // undefined
1589 info.Ptype = type;
1590
1591 // The following is surprisingly complex!
1592 if (Pname.empty())
1593 Pname = xml->getparstr("file");
1594
1595 if (Poriginal == DEFAULT_NAME) // it's an old one
1596 Poriginal = "";
1597 if (Pname.empty()) // it's an older state file
1598 {
1599 if (Poriginal. empty())
1600 Pname = DEFAULT_NAME;
1601 else
1602 Pname = Poriginal;
1603 }
1604 else if (Poriginal.empty()) // it's one from zyn
1605 Poriginal = Pname;
1606 if (Pname.empty() && Poriginal == UNTITLED)
1607 {
1608 Pname = UNTITLED;
1609 Poriginal = "";
1610 }
1611 xml->exitbranch();
1612 }
1613
1614 if (!xml->enterbranch("INSTRUMENT_KIT"))
1615 {
1616 defaultsinstrument();
1617 return;
1618 }
1619 else
1620 {
1621 Pkitmode = xml->getpar127("kit_mode", Pkitmode);
1622 Pkitfade = xml->getparbool("kit_crossfade", Pkitfade);
1623 Pdrummode = xml->getparbool("drum_mode", Pdrummode);
1624
1625 for (int i = 0; i < NUM_KIT_ITEMS; ++i)
1626 {
1627 if (!xml->enterbranch("INSTRUMENT_KIT_ITEM", i))
1628 continue;
1629 setkititemstatus(i, xml->getparbool("enabled", kit[i].Penabled));
1630 if (!kit[i].Penabled)
1631 {
1632 xml->exitbranch();
1633 continue;
1634 }
1635 kit[i].Pname = xml->getparstr("name");
1636 kit[i].Pmuted = xml->getparbool("muted", kit[i].Pmuted);
1637 kit[i].Pminkey = xml->getpar127("min_key", kit[i].Pminkey);
1638 kit[i].Pmaxkey = xml->getpar127("max_key", kit[i].Pmaxkey);
1639 kit[i].Psendtoparteffect = xml->getpar127("send_to_instrument_effect",
1640 kit[i].Psendtoparteffect);
1641 kit[i].Padenabled = xml->getparbool("add_enabled", kit[i].Padenabled);
1642 if (xml->enterbranch("ADD_SYNTH_PARAMETERS"))
1643 {
1644 kit[i].adpars->getfromXML(xml);
1645 xml->exitbranch();
1646 }
1647 kit[i].Psubenabled = xml->getparbool("sub_enabled", kit[i].Psubenabled);
1648 if (xml->enterbranch("SUB_SYNTH_PARAMETERS"))
1649 {
1650 kit[i].subpars->getfromXML(xml);
1651 xml->exitbranch();
1652 }
1653 kit[i].Ppadenabled = xml->getparbool("pad_enabled", kit[i].Ppadenabled);
1654 if (xml->enterbranch("PAD_SYNTH_PARAMETERS"))
1655 {
1656 busy = true;
1657 kit[i].padpars->getfromXML(xml);
1658 busy = false;
1659 xml->exitbranch();
1660 }
1661 xml->exitbranch();
1662 }
1663 xml->exitbranch();
1664 }
1665 if (xml->enterbranch("INSTRUMENT_EFFECTS"))
1666 {
1667 for (int nefx = 0; nefx < NUM_PART_EFX; ++nefx)
1668 {
1669 if (!xml->enterbranch("INSTRUMENT_EFFECT", nefx))
1670 continue;
1671 if (xml->enterbranch("EFFECT"))
1672 {
1673 partefx[nefx]->getfromXML(xml);
1674 xml->exitbranch();
1675 }
1676 Pefxroute[nefx] = xml->getpar("route", Pefxroute[nefx], 0, NUM_PART_EFX);
1677 partefx[nefx]->setdryonly(Pefxroute[nefx] == 2);
1678 Pefxbypass[nefx] = xml->getparbool("bypass", Pefxbypass[nefx]);
1679 xml->exitbranch();
1680 }
1681 xml->exitbranch();
1682 }
1683 }
1684
1685
getfromXML(XMLwrapper * xml)1686 void Part::getfromXML(XMLwrapper *xml)
1687 {
1688 Penabled = (xml->getparbool("enabled", Penabled) == 1);
1689
1690 setVolume(xml->getpar127("volume", Pvolume));
1691 setPan(xml->getpar127("panning", Ppanning));
1692
1693 Pminkey = xml->getpar127("min_key", Pminkey);
1694 Pmaxkey = xml->getpar127("max_key", Pmaxkey);
1695 Pkeyshift = xml->getpar("key_shift", Pkeyshift, MIN_KEY_SHIFT + 64, MAX_KEY_SHIFT + 64);
1696
1697 Prcvchn = xml->getpar127("rcv_chn", Prcvchn);
1698
1699 Pvelsns = xml->getpar127("velocity_sensing", Pvelsns);
1700 Pveloffs = xml->getpar127("velocity_offset", Pveloffs);
1701
1702 bool Ppolymode = 1;
1703 bool Plegatomode = 0;
1704 Ppolymode = xml->getparbool("poly_mode", Ppolymode);
1705 Plegatomode = xml->getparbool("legato_mode", Plegatomode); // older versions
1706 if (!Plegatomode)
1707 Plegatomode = xml->getpar127("legato_mode", Plegatomode);
1708 if (Plegatomode) // these lines are for backward compatibility
1709 Pkeymode = PART_LEGATO;
1710 else if (Ppolymode)
1711 Pkeymode = PART_NORMAL;
1712 else
1713 Pkeymode = PART_MONO;
1714
1715 PchannelATchoice = xml->getpar("channel_aftertouch", PchannelATchoice, 0, 255);
1716 PkeyATchoice = xml->getpar("key_aftertouch", PkeyATchoice, 0, 255);
1717
1718 Pkeylimit = xml->getpar127("key_limit", Pkeylimit);
1719 if (Pkeylimit < 1 || Pkeylimit > POLIPHONY)
1720 Pkeylimit = POLIPHONY;
1721 Pfrand = xml->getpar127("random_detune", Pfrand);
1722 if (Pfrand > 50)
1723 Pfrand = 50;
1724 Pvelrand = xml->getpar127("random_velocity", Pvelrand);
1725 if (Pvelrand > 50)
1726 Pvelrand = 50;
1727 setDestination(xml->getpar127("destination", Paudiodest));
1728
1729 if (xml->enterbranch("INSTRUMENT"))
1730 {
1731 Pname = ""; // clear out any previous name
1732 getfromXMLinstrument(xml);
1733 xml->exitbranch();
1734 }
1735 if (xml->enterbranch("CONTROLLER"))
1736 {
1737 ctl->getfromXML(xml);
1738 xml->exitbranch();
1739 }
1740 }
1741
1742
getLimits(CommandBlock * getData)1743 float Part::getLimits(CommandBlock *getData)
1744 {
1745 float value = getData->data.value;
1746 int request = int(getData->data.type & TOPLEVEL::type::Default);
1747 int control = getData->data.control;
1748 int npart = getData->data.part;
1749
1750 unsigned char type = 0;
1751
1752 // part defaults
1753 int min = 0;
1754 float def = 64;
1755 int max = 127;
1756 type |= TOPLEVEL::type::Integer;
1757 unsigned char learnable = TOPLEVEL::type::Learnable;
1758 //cout << "part limits" << endl;
1759 if ((control >= PART::control::volumeRange && control <= PART::control::receivePortamento) || control == PART::control::resetAllControllers)
1760 return ctl->getLimits(getData);
1761
1762 switch (control)
1763 {
1764 case PART::control::enable:
1765 if (npart == 0)
1766 def = 1;
1767 else
1768 def = 0;
1769 max = 1;
1770 break;
1771 case PART::control::enableAdd:
1772 type |= learnable;
1773 if (npart == 0)
1774 def = 1;
1775 else
1776 def = 0;
1777 max = 1;
1778 break;
1779 case PART::control::enableSub:
1780 case PART::control::enablePad:
1781 type |= learnable;
1782 def = 0;
1783 max = 1;
1784 break;
1785 case PART::control::enableKitLine:
1786 def = 0;
1787 max = 1;
1788 break;
1789
1790 case PART::control::volume:
1791 type &= ~TOPLEVEL::type::Integer;
1792 type |= learnable;
1793 def = 96;
1794 break;
1795
1796 case PART::control::velocitySense:
1797 case PART::control::velocityOffset:
1798 type |= learnable;
1799 break;
1800
1801 case PART::control::panning:
1802 type &= ~TOPLEVEL::type::Integer;
1803 type |= learnable;
1804 break;
1805
1806 case PART::control::midiChannel:
1807 min = 0;
1808 def = 0;
1809 max = 16; // disabled
1810 break;
1811
1812 case PART::control::channelATset:
1813 case PART::control::keyATset:
1814 min = 0;
1815 def = 0;
1816 max = PART::aftertouchType::modulation * 2;
1817 break;
1818
1819 case PART::control::keyMode:
1820 def = 0;
1821 max = 2;
1822 break;
1823
1824 case PART::control::portamento:
1825 type |= learnable;
1826 def = 0;
1827 max = 1;
1828 break;
1829
1830 case PART::control::kitItemMute:
1831 type |= learnable;
1832 def = 0;
1833 max = 1;
1834 break;
1835
1836 case PART::control::minNote:
1837 def = 0;
1838 break;
1839
1840 case PART::control::maxNote:
1841 def = 127;
1842 break;
1843
1844 case PART::control::minToLastKey:
1845 case PART::control::maxToLastKey:
1846 case PART::control::resetMinMaxKey:
1847 def = 0;
1848 max = 0;
1849 break;
1850 case PART::control::kitEffectNum:
1851 def = 1; // may be local to GUI
1852 max = 3;
1853 break;
1854
1855 case PART::control::maxNotes:
1856 def = 20;
1857 max = POLIPHONY;
1858 break;
1859
1860 case PART::control::keyShift:
1861 min = -36;
1862 def = 0;
1863 max = 36;
1864 break;
1865
1866 case PART::control::partToSystemEffect1:
1867 case PART::control::partToSystemEffect2:
1868 case PART::control::partToSystemEffect3:
1869 case PART::control::partToSystemEffect4:
1870 type |= learnable;
1871 def = 0;
1872 break;
1873
1874 case PART::control::humanise:
1875 type |= learnable;
1876 def = 0;
1877 max = 50;
1878 break;
1879
1880 case PART::control::humanvelocity:
1881 type |= learnable;
1882 def = 0;
1883 max = 50;
1884 break;
1885
1886 case PART::control::drumMode:
1887 def = 0;
1888 max = 1;
1889 break;
1890
1891 case PART::control::kitMode:
1892 def = 0;
1893 max = 3;
1894 break;
1895 case PART::control::effectNumber:
1896 max = 2;
1897 def = 0;
1898 break;
1899 case PART::control::effectType:
1900 def = 0;
1901 break;
1902 case PART::control::effectDestination:
1903 max = 2;
1904 def = 0;
1905 break;
1906 case PART::control::effectBypass:
1907 type |= learnable;
1908 max = 1;
1909 def = 0;
1910 break;
1911
1912 case PART::control::audioDestination:
1913 min = 1;
1914 def = 1;
1915 max = 3;
1916 break;
1917
1918 case PART::control::midiModWheel:
1919 type |= learnable;
1920 break;
1921 case PART::control::midiBreath: // not done yet
1922 break;
1923 case PART::control::midiExpression:
1924 type |= learnable;
1925 def = 127;
1926 break;
1927 case PART::control::midiSustain: // not done yet
1928 break;
1929 case PART::control::midiPortamento: // not done yet
1930 break;
1931 case PART::control::midiFilterQ:
1932 type |= learnable;
1933 break;
1934 case PART::control::midiFilterCutoff:
1935 type |= learnable;
1936 break;
1937 case PART::control::midiBandwidth:
1938 type |= learnable;
1939 break;
1940
1941 // the following have no limits but are here so they don't
1942 // create errors when tested.
1943 case PART::control::instrumentCopyright:
1944 break;
1945 case PART::control::instrumentComments:
1946 break;
1947 case PART::control::instrumentName:
1948 break;
1949 case PART::control::instrumentType:
1950 break;
1951 case PART::control::defaultInstrumentCopyright:
1952 break;
1953
1954 case 255: // number of parts
1955 min = 16;
1956 def = 16;
1957 max = 64;
1958 break;
1959
1960 default:
1961 type |= TOPLEVEL::type::Error;
1962 break;
1963 }
1964 getData->data.type = type;
1965 if (type & TOPLEVEL::type::Error)
1966 return 1;
1967
1968 switch (request)
1969 {
1970 case TOPLEVEL::type::Adjust:
1971 if (value < min)
1972 value = min;
1973 else if (value > max)
1974 value = max;
1975 break;
1976 case TOPLEVEL::type::Minimum:
1977 value = min;
1978 break;
1979 case TOPLEVEL::type::Maximum:
1980 value = max;
1981 break;
1982 case TOPLEVEL::type::Default:
1983 value = def;
1984 break;
1985 }
1986 return value;
1987 }
1988