mirror of
https://github.com/thestk/stk
synced 2026-01-15 14:01:52 +00:00
Version 4.2.0
This commit is contained in:
committed by
Stephen Sinclair
parent
cf06b7598b
commit
a6381b9d38
127
src/Drummer.cpp
127
src/Drummer.cpp
@@ -11,14 +11,14 @@
|
||||
of simultaneous voices) via a #define in the
|
||||
Drummer.h.
|
||||
|
||||
by Perry R. Cook and Gary P. Scavone, 1995 - 2002.
|
||||
by Perry R. Cook and Gary P. Scavone, 1995 - 2004.
|
||||
*/
|
||||
/***************************************************/
|
||||
|
||||
#include "Drummer.h"
|
||||
#include <math.h>
|
||||
|
||||
// Not really General MIDI yet. Coming soon.
|
||||
// Not really General MIDI yet.
|
||||
unsigned char genMIDIMap[128] =
|
||||
{ 0,0,0,0,0,0,0,0, // 0-7
|
||||
0,0,0,0,0,0,0,0, // 8-15
|
||||
@@ -55,122 +55,133 @@ char waveNames[DRUM_NUMWAVES][16] =
|
||||
|
||||
Drummer :: Drummer() : Instrmnt()
|
||||
{
|
||||
for (int i=0; i<DRUM_POLYPHONY; i++) {
|
||||
filters[i] = new OnePole;
|
||||
sounding[i] = -1;
|
||||
for ( int i=0; i<DRUM_POLYPHONY; i++ ) {
|
||||
filters_[i] = new OnePole;
|
||||
sounding_[i] = -1;
|
||||
}
|
||||
|
||||
// This counts the number of sounding voices.
|
||||
nSounding = 0;
|
||||
nSounding_ = 0;
|
||||
}
|
||||
|
||||
Drummer :: ~Drummer()
|
||||
{
|
||||
int i;
|
||||
for ( i=0; i<nSounding-1; i++ ) delete waves[i];
|
||||
for ( i=0; i<DRUM_POLYPHONY; i++ ) delete filters[i];
|
||||
for ( i=0; i<nSounding_; i++ ) delete waves_[i];
|
||||
for ( i=0; i<DRUM_POLYPHONY; i++ ) delete filters_[i];
|
||||
}
|
||||
|
||||
void Drummer :: noteOn(MY_FLOAT instrument, MY_FLOAT amplitude)
|
||||
void Drummer :: noteOn(StkFloat instrument, StkFloat amplitude)
|
||||
{
|
||||
#if defined(_STK_DEBUG_)
|
||||
std::cerr << "Drummer: NoteOn instrument = " << instrument << ", amplitude = " << amplitude << std::endl;
|
||||
errorString_ << "Drummer::NoteOn: instrument = " << instrument << ", amplitude = " << amplitude << '.';
|
||||
handleError( StkError::DEBUG_WARNING );
|
||||
#endif
|
||||
|
||||
MY_FLOAT gain = amplitude;
|
||||
StkFloat gain = amplitude;
|
||||
if ( amplitude > 1.0 ) {
|
||||
std::cerr << "Drummer: noteOn amplitude parameter is greater than 1.0!" << std::endl;
|
||||
errorString_ << "Drummer::noteOn: amplitude parameter is greater than 1.0 ... setting to 1.0!";
|
||||
handleError( StkError::WARNING );
|
||||
gain = 1.0;
|
||||
}
|
||||
else if ( amplitude < 0.0 ) {
|
||||
std::cerr << "Drummer: noteOn amplitude parameter is less than 0.0!" << std::endl;
|
||||
errorString_ << "Drummer::noteOn: amplitude parameter is less than 0.0 ... doing nothing!";
|
||||
handleError( StkError::WARNING );
|
||||
return;
|
||||
}
|
||||
|
||||
// Yes, this is tres kludgey.
|
||||
int noteNum = (int) ((12*log(instrument/220.0)/log(2.0)) + 57.01);
|
||||
int noteNum = (int) ( ( 12*log(instrument/220.0)/log(2.0) ) + 57.01 );
|
||||
|
||||
// Check first to see if there's already one like this sounding.
|
||||
int i, waveIndex = -1;
|
||||
for (i=0; i<DRUM_POLYPHONY; i++) {
|
||||
if (sounding[i] == noteNum) waveIndex = i;
|
||||
for ( i=0; i<DRUM_POLYPHONY; i++ ) {
|
||||
if (sounding_[i] == noteNum) waveIndex = i;
|
||||
}
|
||||
|
||||
if ( waveIndex >= 0 ) {
|
||||
// Reset this sound.
|
||||
waves[waveIndex]->reset();
|
||||
filters[waveIndex]->setPole((MY_FLOAT) 0.999 - (gain * 0.6));
|
||||
filters[waveIndex]->setGain(gain);
|
||||
waves_[waveIndex]->reset();
|
||||
filters_[waveIndex]->setPole( 0.999 - (gain * 0.6) );
|
||||
filters_[waveIndex]->setGain( gain );
|
||||
}
|
||||
else {
|
||||
if (nSounding == DRUM_POLYPHONY) {
|
||||
if (nSounding_ == DRUM_POLYPHONY) {
|
||||
// If we're already at maximum polyphony, then preempt the oldest voice.
|
||||
delete waves[0];
|
||||
filters[0]->clear();
|
||||
WvIn *tempWv = waves[0];
|
||||
OnePole *tempFilt = filters[0];
|
||||
delete waves_[0];
|
||||
filters_[0]->clear();
|
||||
OnePole *tempFilt = filters_[0];
|
||||
// Re-order the list.
|
||||
for (i=0; i<DRUM_POLYPHONY-1; i++) {
|
||||
waves[i] = waves[i+1];
|
||||
filters[i] = filters[i+1];
|
||||
for ( i=0; i<DRUM_POLYPHONY-1; i++ ) {
|
||||
waves_[i] = waves_[i+1];
|
||||
filters_[i] = filters_[i+1];
|
||||
}
|
||||
waves[DRUM_POLYPHONY-1] = tempWv;
|
||||
filters[DRUM_POLYPHONY-1] = tempFilt;
|
||||
waves_[DRUM_POLYPHONY-1] = 0;
|
||||
filters_[DRUM_POLYPHONY-1] = tempFilt;
|
||||
}
|
||||
else
|
||||
nSounding += 1;
|
||||
nSounding_ += 1;
|
||||
|
||||
sounding[nSounding-1] = noteNum;
|
||||
sounding_[nSounding_-1] = noteNum;
|
||||
// Concatenate the STK rawwave path to the rawwave file
|
||||
waves[nSounding-1] = new WvIn( (Stk::rawwavePath() + waveNames[genMIDIMap[noteNum]]).c_str(), TRUE );
|
||||
waves_[nSounding_-1] = new WvIn( (Stk::rawwavePath() + waveNames[genMIDIMap[noteNum]]).c_str(), true );
|
||||
if (Stk::sampleRate() != 22050.0)
|
||||
waves[nSounding-1]->setRate( 22050.0 / Stk::sampleRate() );
|
||||
filters[nSounding-1]->setPole((MY_FLOAT) 0.999 - (gain * 0.6) );
|
||||
filters[nSounding-1]->setGain( gain );
|
||||
waves_[nSounding_-1]->setRate( 22050.0 / Stk::sampleRate() );
|
||||
filters_[nSounding_-1]->setPole( 0.999 - (gain * 0.6) );
|
||||
filters_[nSounding_-1]->setGain( gain );
|
||||
}
|
||||
|
||||
#if defined(_STK_DEBUG_)
|
||||
std::cerr << "Number Sounding = " << nSounding << std::endl;
|
||||
for (i=0; i<nSounding; i++) std::cerr << sounding[i] << " ";
|
||||
std::cerr << "\n";
|
||||
errorString_ << "Drummer::noteOn: number sounding = " << nSounding_ << '\n';
|
||||
for (i=0; i<nSounding_; i++) errorString_ << sounding_[i] << " ";
|
||||
errorString_ << '\n';
|
||||
handleError( StkError::DEBUG_WARNING );
|
||||
#endif
|
||||
}
|
||||
|
||||
void Drummer :: noteOff(MY_FLOAT amplitude)
|
||||
void Drummer :: noteOff(StkFloat amplitude)
|
||||
{
|
||||
// Set all sounding wave filter gains low.
|
||||
int i = 0;
|
||||
while(i < nSounding) {
|
||||
filters[i++]->setGain( amplitude * 0.01 );
|
||||
}
|
||||
while ( i < nSounding_ ) filters_[i++]->setGain( amplitude * 0.01 );
|
||||
}
|
||||
|
||||
MY_FLOAT Drummer :: tick()
|
||||
StkFloat Drummer :: tick()
|
||||
{
|
||||
MY_FLOAT output = 0.0;
|
||||
OnePole *tempFilt;
|
||||
|
||||
int j, i = 0;
|
||||
while (i < nSounding) {
|
||||
if ( waves[i]->isFinished() ) {
|
||||
delete waves[i];
|
||||
tempFilt = filters[i];
|
||||
lastOutput_ = 0.0;
|
||||
while (i < nSounding_) {
|
||||
if ( waves_[i]->isFinished() ) {
|
||||
delete waves_[i];
|
||||
tempFilt = filters_[i];
|
||||
// Re-order the list.
|
||||
for (j=i; j<nSounding-1; j++) {
|
||||
sounding[j] = sounding[j+1];
|
||||
waves[j] = waves[j+1];
|
||||
filters[j] = filters[j+1];
|
||||
for ( j=i; j<nSounding_-1; j++ ) {
|
||||
sounding_[j] = sounding_[j+1];
|
||||
waves_[j] = waves_[j+1];
|
||||
filters_[j] = filters_[j+1];
|
||||
}
|
||||
filters[j] = tempFilt;
|
||||
filters[j]->clear();
|
||||
sounding[j] = -1;
|
||||
nSounding -= 1;
|
||||
filters_[j] = tempFilt;
|
||||
filters_[j]->clear();
|
||||
sounding_[j] = -1;
|
||||
nSounding_ -= 1;
|
||||
i -= 1;
|
||||
}
|
||||
else
|
||||
output += filters[i]->tick( waves[i]->tick() );
|
||||
lastOutput_ += filters_[i]->tick( waves_[i]->tick() );
|
||||
i++;
|
||||
}
|
||||
|
||||
return output;
|
||||
return lastOutput_;
|
||||
}
|
||||
|
||||
StkFloat *Drummer :: tick(StkFloat *vector, unsigned int vectorSize)
|
||||
{
|
||||
return Instrmnt::tick( vector, vectorSize );
|
||||
}
|
||||
|
||||
StkFrames& Drummer :: tick( StkFrames& frames, unsigned int channel )
|
||||
{
|
||||
return Instrmnt::tick( frames, channel );
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user