PCM Digital Synthesizer

Dependencies:   LCD mbed

/media/uploads/p_igmon/img_1731-w480.jpg

Committer:
p_igmon
Date:
Fri Sep 02 13:24:16 2016 +0000
Revision:
0:ad6637c36dc7
for Micro Gen4 Synthesizer

Who changed what in which revision?

UserRevisionLine numberNew contents of line
p_igmon 0:ad6637c36dc7 1 #include "synthesizer.h"
p_igmon 0:ad6637c36dc7 2
p_igmon 0:ad6637c36dc7 3 extern GENERATOR sgen[];
p_igmon 0:ad6637c36dc7 4 extern GENERATOR dgen[];
p_igmon 0:ad6637c36dc7 5 extern GENERATOR_TEMP dgen_temp[];
p_igmon 0:ad6637c36dc7 6 extern GENERATOR *gen ;// = &sgen[PresetVoiceNum - 1] set by Menu PresetVoice
p_igmon 0:ad6637c36dc7 7 extern GENERATOR *pgen;// = &dgen[0];
p_igmon 0:ad6637c36dc7 8 extern GENERATOR_TEMP *pgen_temp;// = &dgen_temp[0];
p_igmon 0:ad6637c36dc7 9 extern PresetVoiceDef PresetVoice[];
p_igmon 0:ad6637c36dc7 10 extern STR_VOICE voice[];
p_igmon 0:ad6637c36dc7 11
p_igmon 0:ad6637c36dc7 12 extern int gen_encount;
p_igmon 0:ad6637c36dc7 13 extern U8 PresetVoiceNum;
p_igmon 0:ad6637c36dc7 14 extern U8 MidiChannel;
p_igmon 0:ad6637c36dc7 15
p_igmon 0:ad6637c36dc7 16 extern S16 MasterVolume;
p_igmon 0:ad6637c36dc7 17 extern volatile S16 mvoldiv;
p_igmon 0:ad6637c36dc7 18
p_igmon 0:ad6637c36dc7 19 void envelope_work(void)
p_igmon 0:ad6637c36dc7 20 {
p_igmon 0:ad6637c36dc7 21 U8 i;
p_igmon 0:ad6637c36dc7 22 U16 temp;
p_igmon 0:ad6637c36dc7 23 U8 temp1,temp2;
p_igmon 0:ad6637c36dc7 24 S16 *lfo1wave;
p_igmon 0:ad6637c36dc7 25 GENERATOR *gena;
p_igmon 0:ad6637c36dc7 26 GENERATOR_TEMP *gena_temp;
p_igmon 0:ad6637c36dc7 27 STR_VOICE *voicea;
p_igmon 0:ad6637c36dc7 28 gena = pgen;// 螳滉ス薙・縺サ縺・〒
p_igmon 0:ad6637c36dc7 29 gena_temp = pgen_temp;// 螳滉ス薙・縺サ縺・〒
p_igmon 0:ad6637c36dc7 30 voicea = &voice[0];
p_igmon 0:ad6637c36dc7 31 PresetVoiceDef *voice_ptr = (PresetVoiceDef *)&PresetVoice[PresetVoiceNum- 1];
p_igmon 0:ad6637c36dc7 32 MasterVolume += mvoldiv;
p_igmon 0:ad6637c36dc7 33 if(MasterVolume >(127<<8)){
p_igmon 0:ad6637c36dc7 34 MasterVolume = 127<<8;
p_igmon 0:ad6637c36dc7 35 mvoldiv = 0;
p_igmon 0:ad6637c36dc7 36 }else if(MasterVolume < 0){
p_igmon 0:ad6637c36dc7 37 MasterVolume = 0;
p_igmon 0:ad6637c36dc7 38 mvoldiv = 0;
p_igmon 0:ad6637c36dc7 39 }
p_igmon 0:ad6637c36dc7 40
p_igmon 0:ad6637c36dc7 41 for (i =0;i<GENMAX;i++){
p_igmon 0:ad6637c36dc7 42 if(gena_temp->status == GEN_IDLE){
p_igmon 0:ad6637c36dc7 43 // gena_temp->voltemp = 0;
p_igmon 0:ad6637c36dc7 44 gena_temp->lfo1delaycount = gena->lfo1delaytime;
p_igmon 0:ad6637c36dc7 45 gena_temp->lfo2delaycount = gena->lfo2delaytime;
p_igmon 0:ad6637c36dc7 46 #ifdef DCF
p_igmon 0:ad6637c36dc7 47 voicea->enable &= ~(1<<(i & (PRGGENMAX - 1)));// 1,2,4,8
p_igmon 0:ad6637c36dc7 48 #endif
p_igmon 0:ad6637c36dc7 49 }else{
p_igmon 0:ad6637c36dc7 50 if(gena_temp->status == GEN_NOTEOFF){
p_igmon 0:ad6637c36dc7 51 /* Function Release */
p_igmon 0:ad6637c36dc7 52 gena_temp->voltemp = (gena_temp->voltemp>>16) * releasetime_table[gena->releasetime];
p_igmon 0:ad6637c36dc7 53 if(gena_temp->voltemp == 0){
p_igmon 0:ad6637c36dc7 54 gena_temp->zerocount++;
p_igmon 0:ad6637c36dc7 55 }else{
p_igmon 0:ad6637c36dc7 56 gena_temp->zerocount = 0;
p_igmon 0:ad6637c36dc7 57 }
p_igmon 0:ad6637c36dc7 58 if(gena_temp->zerocount > 10){
p_igmon 0:ad6637c36dc7 59 gena_temp->status = GEN_IDLE;
p_igmon 0:ad6637c36dc7 60 gena_temp->eg_status = EG_IDLE;
p_igmon 0:ad6637c36dc7 61 #ifdef DCF
p_igmon 0:ad6637c36dc7 62 voicea->enable &= ~(1<<(i & (PRGGENMAX - 1)));// 1,2,4,8
p_igmon 0:ad6637c36dc7 63 #endif
p_igmon 0:ad6637c36dc7 64 gen_encount--;
p_igmon 0:ad6637c36dc7 65 //ledgreen_off();
p_igmon 0:ad6637c36dc7 66 }else{
p_igmon 0:ad6637c36dc7 67 gena_temp->eg_status = EG_RELEASE;
p_igmon 0:ad6637c36dc7 68 //ledred_off();
p_igmon 0:ad6637c36dc7 69 }
p_igmon 0:ad6637c36dc7 70
p_igmon 0:ad6637c36dc7 71 }else{ // NOTE ON
p_igmon 0:ad6637c36dc7 72 if(gena_temp->eg_status == EG_IDLE){
p_igmon 0:ad6637c36dc7 73 gena_temp->voltemp += gena_temp->voltemp1;
p_igmon 0:ad6637c36dc7 74 //ledred_on();
p_igmon 0:ad6637c36dc7 75 if(gena_temp->voltemp > gena->volume <<16){
p_igmon 0:ad6637c36dc7 76 gena_temp->voltemp = gena->volume <<16;
p_igmon 0:ad6637c36dc7 77 gena_temp->voltemp1 = ((gena->volume<<16) /100 * (100 - gena->sustainlevel))/(gena->decaytime);
p_igmon 0:ad6637c36dc7 78 gena_temp->eg_status = EG_DECAY;
p_igmon 0:ad6637c36dc7 79 }else{
p_igmon 0:ad6637c36dc7 80 gena_temp->eg_status = EG_ATTACK;
p_igmon 0:ad6637c36dc7 81 }
p_igmon 0:ad6637c36dc7 82 }else if(gena_temp->eg_status == EG_ATTACK){
p_igmon 0:ad6637c36dc7 83 gena_temp->voltemp += gena_temp->voltemp1;
p_igmon 0:ad6637c36dc7 84 //ledred_on();
p_igmon 0:ad6637c36dc7 85 if(gena_temp->voltemp > gena->volume <<16){
p_igmon 0:ad6637c36dc7 86 gena_temp->voltemp = gena->volume <<16;
p_igmon 0:ad6637c36dc7 87 gena_temp->voltemp1 = ((gena->volume<<16) /100 * (100 - gena->sustainlevel))/(gena->decaytime);
p_igmon 0:ad6637c36dc7 88 gena_temp->eg_status = EG_DECAY;
p_igmon 0:ad6637c36dc7 89 }
p_igmon 0:ad6637c36dc7 90 }else if(gena_temp->eg_status == EG_DECAY){
p_igmon 0:ad6637c36dc7 91 gena_temp->voltemp -= gena_temp->voltemp1;
p_igmon 0:ad6637c36dc7 92 if(gena_temp->voltemp < gena_temp->voltemp2){
p_igmon 0:ad6637c36dc7 93 gena_temp->voltemp = gena_temp->voltemp2;
p_igmon 0:ad6637c36dc7 94 gena_temp->eg_status = EG_SUSTAIN;
p_igmon 0:ad6637c36dc7 95
p_igmon 0:ad6637c36dc7 96 //ledgreen_on();
p_igmon 0:ad6637c36dc7 97 }
p_igmon 0:ad6637c36dc7 98
p_igmon 0:ad6637c36dc7 99 }
p_igmon 0:ad6637c36dc7 100
p_igmon 0:ad6637c36dc7 101 }
p_igmon 0:ad6637c36dc7 102 /* Note On/Off蜈ア騾壹・蜃ヲ逅・*/
p_igmon 0:ad6637c36dc7 103 if (gena_temp->dpf != 0){ // 110812
p_igmon 0:ad6637c36dc7 104 gena_temp->df += (S32)gena_temp->dpf;//
p_igmon 0:ad6637c36dc7 105 }
p_igmon 0:ad6637c36dc7 106
p_igmon 0:ad6637c36dc7 107 /* PitchBend 120617 */
p_igmon 0:ad6637c36dc7 108 // gena->bendvalue = ((((ADC.ADDRA.WORD>>6) - adc0bias) * gena->benddepth) >>10);// ADDR 縺ョ繝薙ャ繝・5・・縺後ョ繝シ繧ソ
p_igmon 0:ad6637c36dc7 109 // gena->bendvalue = ((gena->df>>26) * gena->bendvalue )>>2;
p_igmon 0:ad6637c36dc7 110
p_igmon 0:ad6637c36dc7 111 #ifdef BEND
p_igmon 0:ad6637c36dc7 112 gena_temp->xx = (((U32)gena_temp->df>>16) + (S16)gena->detune + gena->lfo1value + gena->bendvalue);
p_igmon 0:ad6637c36dc7 113 #else
p_igmon 0:ad6637c36dc7 114 gena_temp->xx = (((U32)gena_temp->df>>16) + (S32)gena->detune + gena_temp->lfo1value);
p_igmon 0:ad6637c36dc7 115 #endif
p_igmon 0:ad6637c36dc7 116
p_igmon 0:ad6637c36dc7 117 #if 1
p_igmon 0:ad6637c36dc7 118 /* Function LFO1 */
p_igmon 0:ad6637c36dc7 119 if(gena_temp->lfo1delaycount > 0){
p_igmon 0:ad6637c36dc7 120 gena_temp->lfo1delaycount--;
p_igmon 0:ad6637c36dc7 121 }else{
p_igmon 0:ad6637c36dc7 122 /* lof1speed 3e.5f */
p_igmon 0:ad6637c36dc7 123 gena_temp->lfo1count += (U8)gena->lfo1speed ;
p_igmon 0:ad6637c36dc7 124 if (gena_temp->lfo1count >= (256<<5)) gena_temp->lfo1count -=(256<<5);
p_igmon 0:ad6637c36dc7 125 // gena_temp->lfo1value = ((S16)sin_table[(gena_temp->lfo1count>>5)] * (U16)gena->lfo1depth) >>20;
p_igmon 0:ad6637c36dc7 126 switch(gena->lfo1type){
p_igmon 0:ad6637c36dc7 127 case 0:
p_igmon 0:ad6637c36dc7 128 lfo1wave = sin_table;
p_igmon 0:ad6637c36dc7 129 break;
p_igmon 0:ad6637c36dc7 130 case 1:
p_igmon 0:ad6637c36dc7 131 lfo1wave = saw1_table;
p_igmon 0:ad6637c36dc7 132 break;
p_igmon 0:ad6637c36dc7 133 case 2:
p_igmon 0:ad6637c36dc7 134 lfo1wave = saw2_table;
p_igmon 0:ad6637c36dc7 135 break;
p_igmon 0:ad6637c36dc7 136 case 3:
p_igmon 0:ad6637c36dc7 137 lfo1wave = tri_table;
p_igmon 0:ad6637c36dc7 138 break;
p_igmon 0:ad6637c36dc7 139 case 4:
p_igmon 0:ad6637c36dc7 140 lfo1wave = square_table;
p_igmon 0:ad6637c36dc7 141 break;
p_igmon 0:ad6637c36dc7 142 }
p_igmon 0:ad6637c36dc7 143
p_igmon 0:ad6637c36dc7 144 // gena_temp->lfo1value = ((S16)lfo1wave[(gena_temp->lfo1count>>5)] * (U16)gena->lfo1depth) >>20;
p_igmon 0:ad6637c36dc7 145 // gena_temp->lfo1value = ((gena_temp->df>>26) * gena_temp->lfo1value)<<4;// 140614
p_igmon 0:ad6637c36dc7 146 gena_temp->lfo1value = ((S16)lfo1wave[(gena_temp->lfo1count>>5)] * (U16)gena->lfo1depth) >>10;//140617
p_igmon 0:ad6637c36dc7 147 gena_temp->lfo1value = ((gena_temp->df>>16) * (gena_temp->lfo1value>>4))>>12;// 140617
p_igmon 0:ad6637c36dc7 148 }
p_igmon 0:ad6637c36dc7 149 #endif
p_igmon 0:ad6637c36dc7 150 gena_temp->voltempL = (((U32)gena_temp->voltemp>>7) * (U8)gena_temp->velocity) >>16;
p_igmon 0:ad6637c36dc7 151 #if 1
p_igmon 0:ad6637c36dc7 152 /* Function LFO2 */
p_igmon 0:ad6637c36dc7 153 if(gena_temp->lfo2delaycount > 0){
p_igmon 0:ad6637c36dc7 154 gena_temp->lfo2delaycount--;
p_igmon 0:ad6637c36dc7 155 }else{
p_igmon 0:ad6637c36dc7 156 /* lof2speed 3e.5f */
p_igmon 0:ad6637c36dc7 157 gena_temp->lfo2count += (U8)gena->lfo2speed ;
p_igmon 0:ad6637c36dc7 158 if (gena_temp->lfo2count >= (256<<5)) gena_temp->lfo2count -=(256<<5);
p_igmon 0:ad6637c36dc7 159 // temp = (U16)(( (U16)sin_table2[((U16)gena_temp->lfo2count>>5)] * (U16)gena->lfo2depth) >>16);
p_igmon 0:ad6637c36dc7 160 // gena_temp->voltempL += (gena_temp->voltempL * temp) >>15;
p_igmon 0:ad6637c36dc7 161 temp = (U16)(( (U16)sin_table2[((U16)gena_temp->lfo2count>>5)] * (U16)gena->lfo2depth) >>10);// 140618
p_igmon 0:ad6637c36dc7 162 gena_temp->voltempL += (gena_temp->voltempL * temp) >>11;// 140618
p_igmon 0:ad6637c36dc7 163
p_igmon 0:ad6637c36dc7 164 }
p_igmon 0:ad6637c36dc7 165 #endif
p_igmon 0:ad6637c36dc7 166 /* GEN_NOTEONOFF END */
p_igmon 0:ad6637c36dc7 167 }
p_igmon 0:ad6637c36dc7 168 #ifdef DCF
p_igmon 0:ad6637c36dc7 169 /* Voice Process */
p_igmon 0:ad6637c36dc7 170 if ((i & (PRGGENMAX - 1)) == 0){
p_igmon 0:ad6637c36dc7 171
p_igmon 0:ad6637c36dc7 172 temp1 = voice_ptr->dcf_freq +((30 - voice_ptr->dcf_freq)*((S16)gena_temp->voltempL * (voice_ptr->dcf_freqsence))>>16);
p_igmon 0:ad6637c36dc7 173 if (temp1 > 30) temp1 = 30;
p_igmon 0:ad6637c36dc7 174 temp2 = voice_ptr->dcf_q +((10 - voice_ptr->dcf_q)*((S16)gena_temp->voltempL * (voice_ptr->dcf_qsence))>>16);
p_igmon 0:ad6637c36dc7 175 if (temp2 > 10) temp2 = 10;
p_igmon 0:ad6637c36dc7 176
p_igmon 0:ad6637c36dc7 177 voicea->dcf_param = (S32 *)&dcf_table[temp1 * 11 + temp2][0];
p_igmon 0:ad6637c36dc7 178
p_igmon 0:ad6637c36dc7 179 }
p_igmon 0:ad6637c36dc7 180 #endif
p_igmon 0:ad6637c36dc7 181 gena++;
p_igmon 0:ad6637c36dc7 182 gena_temp++;
p_igmon 0:ad6637c36dc7 183 #ifdef DCF
p_igmon 0:ad6637c36dc7 184 if ((i & (PRGGENMAX - 1))== (PRGGENMAX - 1)) voicea++;
p_igmon 0:ad6637c36dc7 185 #endif
p_igmon 0:ad6637c36dc7 186 }
p_igmon 0:ad6637c36dc7 187 }
p_igmon 0:ad6637c36dc7 188