…Show last 106 lines
61 {
62 result = calcOperator(6, op6_2,op6_2,op6_2,adlibfreq(op6_2), result, 0x08); //Calculate the carrier with applied modulator!
63 }
64
65 return result; //Apply the exponential! The volume is always doubled!
66 break;
67
68 //Comments with information from fmopl.c:
69 /* Phase generation is based on: */
70 /* HH (13) channel 7->slot 1 combined with channel 8->slot 2 (same combination as TOP CYMBAL but different output phases) */
71 /* SD (16) channel 7->slot 1 */
72 /* TOM (14) channel 8->slot 1 */
73 /* TOP (17) channel 7->slot 1 combined with channel 8->slot 2 (same combination as HIGH HAT but different output phases) */
74
75
76 /* Envelope generation based on: */
77 /* HH channel 7->slot1 */
78 /* SD channel 7->slot2 */
79 /* TOM channel 8->slot1 */
80 /* TOP channel 8->slot2 */
81 //So phase modulation is based on the Modulator signal. The volume envelope is in the Modulator signal (Hi-hat/Tom-tom) or Carrier signal ()
82 case 7: //Hi-hat(Carrier)/Snare drum(Modulator)? High-hat uses modulator, Snare drum uses Carrier signals.
83 immresult = 0.0f; //Initialize immediate result!
84 if (adlibop[op7_1].volenvstatus) //Hi-hat on Modulator?
85 {
86 //Derive frequency from channel 7(modulator) and 8(carrier).
87 tempop_phase = getphase(op7_1,adlibfreq(op7_1)); //Save the phase!
88 tempphase = (tempop_phase>>2);
89 tempphase ^= (tempop_phase>>7);
90 tempphase |= (tempop_phase>>3);
91 tempphase &= 1; //Only 1 bit is used!
92 tempphase = tempphase?(0x200|(0xD0>>2)):0xD0;
93 tempop_phase = getphase(op8_2,adlibfreq(op8_2)); //Calculate the phase of channel 8 carrier signal!
94 if (((tempop_phase>>3)^(tempop_phase>>5))&1) tempphase = 0x200|(0xD0>>2);
95 if (tempphase&0x200)
96 {
97 if (OPL2_RNG) tempphase = 0x2D0;
98 }
99 else if (OPL2_RNG) tempphase = (0xD0>>2);
100
101 result = calcOperator(8, op8_2,op8_2,op8_2,adlibfreq(op8_2), 0.0f,((adlibop[op8_2].volenvstatus)?1:0)); //Calculate the modulator, but only use the current time(position in the sine wave)!
102 result = calcOperator(7, op7_1,op7_1,op7_1,adlibfreq(op7_1), convertphase(tempphase), 2|((adlibop[op8_2].volenvstatus||adlibop[op7_2].volenvstatus)?0x09:0x08)); //Calculate the carrier with applied modulator!
103 immresult += result; //Apply the tremolo!
104 }
105 if (adlibop[op7_2].volenvstatus) //Snare drum on Carrier volume?
106 {
107 //Derive frequency from channel 0.
108 tempphase = 0x100 << ((getphase(op7_1, adlibfreq(op7_1)) >> 8) & 1); //Bit8=0(Positive) then 0x100, else 0x200! Based on the phase to generate!
109 tempphase ^= (OPL2_RNG << 8); //Noise bits XOR'es phase by 0x100 when set!
110 result = calcOperator(7, op7_2,op7_2,op7_2,adlibfreq(op7_2), convertphase(tempphase), 0); //Calculate the carrier with applied modulator!
111 result = calcOperator(7, op7_1,op7_1,op7_2,adlibfreq(op7_1), convertphase(tempphase), ((adlibop[op8_2].volenvstatus) ? 0x09 : 0x08)); //Calculate the carrier with applied modulator!
112 immresult += result; //Apply the tremolo!
113 }
114 result = immresult; //Load the resulting channel!
115 result *= 0.5; //We only have half(two channels combined)!
116 return result; //Give the result, converted to short!
117 break;
118 case 8: //Tom-tom(Carrier)/Cymbal(Modulator)? Tom-tom uses Modulator, Cymbal uses Carrier signals.
119 immresult = 0.0f; //Initialize immediate result!
120 if (adlibop[op8_1].volenvstatus) //Tom-tom(Modulator)?
121 {
122 result = calcOperator(8, op8_1, op8_1, op8_1, adlibfreq(op8_1), 0.0f, 0x8); //Calculate the carrier without applied modulator additive! Ignore volume!
123 immresult += result*2.0f; //Apply the exponential!
124 }
125 if (adlibop[op8_2].volenvstatus) //Cymbal(Carrier)?
126 {
127 //Derive frequency from channel 7(modulator) and 8(carrier).
128 tempop_phase = getphase(op7_1,adlibfreq(op7_1)); //Save the phase!
129 tempphase = (tempop_phase>>2);
130 tempphase ^= (tempop_phase>>7);
131 tempphase |= (tempop_phase>>3);
132 tempphase &= 1; //Only 1 bit is used!
133 tempphase <<= 9; //0x200 when 1 makes it become 0x300
134 tempphase |= 0x100; //0x100 is always!
135 tempop_phase = getphase(op8_1,adlibfreq(op8_1)); //Calculate the phase of channel 8 carrier signal!
136 if (((tempop_phase>>3)^(tempop_phase>>5))&1) tempphase = 0x300;
137
138 result = calcOperator(7, op7_1,op7_1,op7_1, adlibfreq(op7_1), 0.0f,0); //Calculate the modulator, but only use the current time(position in the sine wave)!
139 result = calcOperator(8, op8_2,op8_2,op8_2, adlibfreq(op8_2), convertphase(tempphase), 0x8); //Calculate the carrier with applied modulator! Use volume!
140 immresult += result; //Apply the exponential!
141 }
142 result = immresult; //Load the resulting channel!
143 result *= 0.5; //We only have half(two channels combined)!
144 return result; //Give the result, converted to short!
145 break;
146 }
147 #endif
148 //Not a percussion channel? Pass through!
149 }
150
151 //Operator 1!
152 //Calculate the frequency to use!
153 result = calcOperator(curchan, op1,op1,op1, op1frequency, 0.0f,0x80); //Calculate the modulator for feedback!
154
155 if (adlibch[curchan].synthmode) //Additive synthesis?
156 {
157 result += calcOperator(curchan, op2,op2,op2, op2frequency, 0.0f,0x00); //Calculate the carrier without applied modulator additive!
158 }
159 else //FM synthesis?
160 {
161 result = calcOperator(curchan, op2,op2,op2, op2frequency, result, 0x00); //Calculate the carrier with applied modulator!
162 }
163
164 return result; //Give the result!
165}