mirror of
https://github.com/LMMS/lmms.git
synced 2026-01-30 17:23:26 -05:00
LB302: Fix playback bugs (sticking pitch), add bandlimited waves
This commit is contained in:
@@ -1,14 +1,14 @@
|
||||
/*
|
||||
* lb302.cpp - implementation of class lb302 which is a bass synth attempting
|
||||
* lb302.cpp - implementation of class lb302 which is a bass synth attempting
|
||||
* to emulate the Roland TB303 bass synth
|
||||
*
|
||||
* Copyright (c) 2006-2008 Paul Giblock <pgib/at/users.sourceforge.net>
|
||||
*
|
||||
*
|
||||
* This file is part of Linux MultiMedia Studio - http://lmms.sourceforge.net
|
||||
*
|
||||
* lb302FilterIIR2 is based on the gsyn filter code by Andy Sloane.
|
||||
*
|
||||
* lb302Filter3Pole is based on the TB303 instrument written by
|
||||
*
|
||||
* lb302Filter3Pole is based on the TB303 instrument written by
|
||||
* Josep M Comajuncosas for the CSounds library
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or
|
||||
@@ -39,6 +39,7 @@
|
||||
#include "pixmap_button.h"
|
||||
#include "templates.h"
|
||||
#include "tooltip.h"
|
||||
#include "BandLimitedWave.h"
|
||||
|
||||
#include "embed.cpp"
|
||||
#include "moc_lb302.cxx"
|
||||
@@ -49,10 +50,10 @@
|
||||
//
|
||||
// New config
|
||||
//
|
||||
#define LB_24_IGNORE_ENVELOPE
|
||||
#define LB_FILTERED
|
||||
#define LB_24_IGNORE_ENVELOPE
|
||||
#define LB_FILTERED
|
||||
//#define LB_DECAY
|
||||
//#define LB_24_RES_TRICK
|
||||
//#define LB_24_RES_TRICK
|
||||
|
||||
#define LB_DIST_RATIO 4.0
|
||||
#define LB_24_VOL_ADJUST 3.0
|
||||
@@ -143,7 +144,7 @@ lb302FilterIIR2::lb302FilterIIR2(lb302FilterKnobState* p_fs) :
|
||||
{
|
||||
|
||||
m_dist = new DspEffectLibrary::Distortion( 1.0, 1.0f);
|
||||
|
||||
|
||||
};
|
||||
|
||||
|
||||
@@ -183,7 +184,7 @@ float lb302FilterIIR2::process(const float& samp)
|
||||
vcf_d2 = vcf_d1;
|
||||
vcf_d1 = ret;
|
||||
|
||||
if(fs->dist > 0)
|
||||
if(fs->dist > 0)
|
||||
ret=m_dist->nextSample(ret);
|
||||
|
||||
// output = IIR2 + dry
|
||||
@@ -200,7 +201,7 @@ lb302Filter3Pole::lb302Filter3Pole(lb302FilterKnobState *p_fs) :
|
||||
ay1(0),
|
||||
ay2(0),
|
||||
aout(0),
|
||||
lastin(0)
|
||||
lastin(0)
|
||||
{
|
||||
};
|
||||
|
||||
@@ -225,7 +226,7 @@ void lb302Filter3Pole::envRecalc()
|
||||
w = vcf_e0 + vcf_c0;
|
||||
k = (fs->cutoff > 0.975)?0.975:fs->cutoff;
|
||||
kfco = 50.f + (k)*((2300.f-1600.f*(fs->envmod))+(w) *
|
||||
(700.f+1500.f*(k)+(1500.f+(k)*(engine::mixer()->processingSampleRate()/2.f-6000.f)) *
|
||||
(700.f+1500.f*(k)+(1500.f+(k)*(engine::mixer()->processingSampleRate()/2.f-6000.f)) *
|
||||
(fs->envmod)) );
|
||||
//+iacc*(.3+.7*kfco*kenvmod)*kaccent*kaccurve*2000
|
||||
|
||||
@@ -249,7 +250,7 @@ void lb302Filter3Pole::envRecalc()
|
||||
}
|
||||
|
||||
|
||||
float lb302Filter3Pole::process(const float& samp)
|
||||
float lb302Filter3Pole::process(const float& samp)
|
||||
{
|
||||
float ax1 = lastin;
|
||||
float ay11 = ay1;
|
||||
@@ -274,12 +275,12 @@ lb302Synth::lb302Synth( InstrumentTrack * _instrumentTrack ) :
|
||||
vcf_mod_knob( 0.1f, 0.0f, 1.0f, 0.005f, this, tr( "VCF Envelope Mod" ) ),
|
||||
vcf_dec_knob( 0.1f, 0.0f, 1.0f, 0.005f, this, tr( "VCF Envelope Decay" ) ),
|
||||
dist_knob( 0.0f, 0.0f, 1.0f, 0.01f, this, tr( "Distortion" ) ),
|
||||
wave_shape( 0.0f, 0.0f, 7.0f, this, tr( "Waveform" ) ),
|
||||
wave_shape( 8.0f, 0.0f, 11.0f, this, tr( "Waveform" ) ),
|
||||
slide_dec_knob( 0.6f, 0.0f, 1.0f, 0.005f, this, tr( "Slide Decay" ) ),
|
||||
slideToggle( false, this, tr( "Slide" ) ),
|
||||
accentToggle( false, this, tr( "Accent" ) ),
|
||||
deadToggle( false, this, tr( "Dead" ) ),
|
||||
db24Toggle( false, this, tr( "24dB/oct Filter" ) )
|
||||
db24Toggle( false, this, tr( "24dB/oct Filter" ) )
|
||||
|
||||
{
|
||||
|
||||
@@ -330,7 +331,7 @@ lb302Synth::lb302Synth( InstrumentTrack * _instrumentTrack ) :
|
||||
vca_attack = 1.0 - 0.96406088;
|
||||
vca_decay = 0.99897516;
|
||||
|
||||
vco_shape = SAWTOOTH;
|
||||
vco_shape = SAWTOOTH;
|
||||
|
||||
// Experimenting with a0 between original (0.5) and 1.0
|
||||
vca_a0 = 0.5;
|
||||
@@ -425,7 +426,7 @@ void lb302Synth::filterChanged()
|
||||
void lb302Synth::db24Toggled()
|
||||
{
|
||||
vcf = vcfs[db24Toggle.value()];
|
||||
// These recalcFilter calls might suck
|
||||
// These recalcFilter calls might suck
|
||||
recalcFilter();
|
||||
}
|
||||
|
||||
@@ -487,14 +488,14 @@ int lb302Synth::process(sampleFrame *outbuf, const int size)
|
||||
note.dead = deadToggle.value();
|
||||
initNote(¬e);
|
||||
//printf("%f %f, ", vco_inc, vco_c);
|
||||
|
||||
current_freq = new_freq;
|
||||
|
||||
current_freq = new_freq;
|
||||
|
||||
new_freq = -1.0f;
|
||||
//printf("GOT_INC %f %f %d\n\n", note.vco_inc, new_freq, vca_mode );
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
// TODO: NORMAL RELEASE
|
||||
// vca_mode = 1;
|
||||
@@ -543,6 +544,10 @@ int lb302Synth::process(sampleFrame *outbuf, const int size)
|
||||
case 5: vco_shape = SINE; break;
|
||||
case 6: vco_shape = EXPONENTIAL; break;
|
||||
case 7: vco_shape = WHITE_NOISE; break;
|
||||
case 8: vco_shape = BL_SAWTOOTH; break;
|
||||
case 9: vco_shape = BL_SQUARE; break;
|
||||
case 10: vco_shape = BL_TRIANGLE; break;
|
||||
case 11: vco_shape = BL_MOOG; break;
|
||||
default: vco_shape = SAWTOOTH; break;
|
||||
}
|
||||
|
||||
@@ -568,7 +573,7 @@ int lb302Synth::process(sampleFrame *outbuf, const int size)
|
||||
break;
|
||||
|
||||
case MOOG: // Maybe the fall should be exponential/sinsoidal instead of quadric.
|
||||
// [-0.5, 0]: Rise, [0,0.25]: Slope down, [0.25,0.5]: Low
|
||||
// [-0.5, 0]: Rise, [0,0.25]: Slope down, [0.25,0.5]: Low
|
||||
vco_k = (vco_c*2.0)+0.5;
|
||||
if (vco_k>1.0) {
|
||||
vco_k = -0.5 ;
|
||||
@@ -577,7 +582,7 @@ int lb302Synth::process(sampleFrame *outbuf, const int size)
|
||||
w = 2.0*(vco_k-0.5)-1.0;
|
||||
vco_k = 0.5 - sqrtf(1.0-(w*w));
|
||||
}
|
||||
vco_k *= 2.0; // MOOG wave gets filtered away
|
||||
vco_k *= 2.0; // MOOG wave gets filtered away
|
||||
break;
|
||||
|
||||
case SINE:
|
||||
@@ -592,6 +597,22 @@ int lb302Synth::process(sampleFrame *outbuf, const int size)
|
||||
case WHITE_NOISE:
|
||||
vco_k = 0.5 * Oscillator::noiseSample( vco_c );
|
||||
break;
|
||||
|
||||
case BL_SAWTOOTH:
|
||||
vco_k = BandLimitedWave::oscillate( vco_c + 0.5f, BandLimitedWave::pdToLen( vco_inc ), BandLimitedWave::BLSaw ) * 0.5f;
|
||||
break;
|
||||
|
||||
case BL_SQUARE:
|
||||
vco_k = BandLimitedWave::oscillate( vco_c + 0.5f, BandLimitedWave::pdToLen( vco_inc ), BandLimitedWave::BLSquare ) * 0.5f;
|
||||
break;
|
||||
|
||||
case BL_TRIANGLE:
|
||||
vco_k = BandLimitedWave::oscillate( vco_c + 0.5f, BandLimitedWave::pdToLen( vco_inc ), BandLimitedWave::BLTriangle ) * 0.5f;
|
||||
break;
|
||||
|
||||
case BL_MOOG:
|
||||
vco_k = BandLimitedWave::oscillate( vco_c + 0.5f, BandLimitedWave::pdToLen( vco_inc ), BandLimitedWave::BLMoog );
|
||||
break;
|
||||
}
|
||||
|
||||
//vca_a = 0.5;
|
||||
@@ -600,8 +621,8 @@ int lb302Synth::process(sampleFrame *outbuf, const int size)
|
||||
//samp = vcf->process(vco_k)*2.0*vca_a;
|
||||
//samp = vcf->process(vco_k)*2.0;
|
||||
samp = filter->process(vco_k) * vca_a;
|
||||
//printf("%f %d\n", vco_c, sample_cnt);
|
||||
|
||||
//printf("%f %d\n", vco_c, sample_cnt);
|
||||
|
||||
|
||||
//samp = vco_k * vca_a;
|
||||
|
||||
@@ -609,7 +630,7 @@ int lb302Synth::process(sampleFrame *outbuf, const int size)
|
||||
{
|
||||
// vca_a = 0;
|
||||
}
|
||||
|
||||
|
||||
#else
|
||||
//samp = vco_k*vca_a;
|
||||
#endif
|
||||
@@ -633,7 +654,7 @@ int lb302Synth::process(sampleFrame *outbuf, const int size)
|
||||
// Handle Envelope
|
||||
if(vca_mode==0) {
|
||||
vca_a+=(vca_a0-vca_a)*vca_attack;
|
||||
if(sample_cnt>=0.5*engine::mixer()->processingSampleRate())
|
||||
if(sample_cnt>=0.5*engine::mixer()->processingSampleRate())
|
||||
vca_mode = 2;
|
||||
}
|
||||
else if(vca_mode == 1) {
|
||||
@@ -661,7 +682,7 @@ void lb302Synth::initNote( lb302Note *n)
|
||||
catch_decay = 0;
|
||||
|
||||
vco_inc = n->vco_inc;
|
||||
|
||||
|
||||
// Always reset vca on non-dead notes, and
|
||||
// Only reset vca on decaying(decayed) and never-played
|
||||
if(n->dead == 0 || (vca_mode==1 || vca_mode==3)) {
|
||||
@@ -695,14 +716,14 @@ void lb302Synth::initNote( lb302Note *n)
|
||||
|
||||
|
||||
recalcFilter();
|
||||
|
||||
|
||||
if(n->dead ==0){
|
||||
// Swap next two blocks??
|
||||
vcf->playNote();
|
||||
// Ensure envelope is recalculated
|
||||
vcf_envpos = ENVINC;
|
||||
|
||||
// Double Check
|
||||
// Double Check
|
||||
//vca_mode = 0;
|
||||
//vca_a = 0.0;
|
||||
}
|
||||
@@ -711,13 +732,30 @@ void lb302Synth::initNote( lb302Note *n)
|
||||
|
||||
void lb302Synth::playNote( NotePlayHandle * _n, sampleFrame * _working_buffer )
|
||||
{
|
||||
//fpp_t framesPerPeriod = engine::mixer()->framesPerPeriod();
|
||||
|
||||
if( _n->isMasterNote() )
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
// sort notes: new notes to the end
|
||||
m_notesMutex.lock();
|
||||
if( _n->totalFramesPlayed() == 0 )
|
||||
{
|
||||
m_notes.append( _n );
|
||||
}
|
||||
else
|
||||
{
|
||||
m_notes.prepend( _n );
|
||||
}
|
||||
m_notesMutex.unlock();
|
||||
}
|
||||
|
||||
|
||||
|
||||
void lb302Synth::processNote( NotePlayHandle * _n )
|
||||
{
|
||||
//fpp_t framesPerPeriod = engine::mixer()->framesPerPeriod();
|
||||
|
||||
// Currently have release/decay disabled
|
||||
// Start the release decay if this is the first release period.
|
||||
//if (_n->released() && catch_decay == 0)
|
||||
@@ -731,7 +769,7 @@ void lb302Synth::playNote( NotePlayHandle * _n, sampleFrame * _working_buffer )
|
||||
//LB303 if ( _n->totalFramesPlayed() <= 0 ) {
|
||||
// This code is obsolete, hence the "if false"
|
||||
|
||||
// Existing note. Allow it to decay.
|
||||
// Existing note. Allow it to decay.
|
||||
if(deadToggle.value() == 0 && decay_note) {
|
||||
|
||||
/* lb302Note note;
|
||||
@@ -743,7 +781,7 @@ void lb302Synth::playNote( NotePlayHandle * _n, sampleFrame * _working_buffer )
|
||||
|
||||
}
|
||||
/// Start a new note.
|
||||
else if( _n->totalFramesPlayed() == 0 ) {
|
||||
else if( _n->m_pluginData == NULL ) {
|
||||
new_freq = _n->unpitchedFrequency();
|
||||
true_freq = _n->frequency();
|
||||
_n->m_pluginData = this;
|
||||
@@ -770,10 +808,14 @@ void lb302Synth::playNote( NotePlayHandle * _n, sampleFrame * _working_buffer )
|
||||
|
||||
void lb302Synth::play( sampleFrame * _working_buffer )
|
||||
{
|
||||
//printf(".");
|
||||
while( ! m_notes.isEmpty() )
|
||||
{
|
||||
processNote( m_notes.takeFirst() );
|
||||
};
|
||||
|
||||
const fpp_t frames = engine::mixer()->framesPerPeriod();
|
||||
|
||||
process( _working_buffer, frames);
|
||||
process( _working_buffer, frames);
|
||||
instrumentTrack()->processAudioBuffer( _working_buffer, frames,
|
||||
NULL );
|
||||
}
|
||||
@@ -783,7 +825,7 @@ void lb302Synth::play( sampleFrame * _working_buffer )
|
||||
void lb302Synth::deleteNotePluginData( NotePlayHandle * _n )
|
||||
{
|
||||
//printf("GONE\n");
|
||||
if( _n->unpitchedFrequency() == current_freq )
|
||||
if( _n->unpitchedFrequency() == current_freq )
|
||||
{
|
||||
delete_freq = current_freq;
|
||||
}
|
||||
@@ -831,7 +873,7 @@ lb302SynthView::lb302SynthView( Instrument * _instrument, QWidget * _parent ) :
|
||||
m_deadToggle->move( 10, 220 );
|
||||
|
||||
m_db24Toggle = new ledCheckBox( "", this );
|
||||
m_db24Toggle->setWhatsThis(
|
||||
m_db24Toggle->setWhatsThis(
|
||||
tr( "303-es-que, 24dB/octave, 3 pole filter" ) );
|
||||
m_db24Toggle->move( 10, 150);
|
||||
|
||||
@@ -888,8 +930,8 @@ lb302SynthView::lb302SynthView( Instrument * _instrument, QWidget * _parent ) :
|
||||
"round_square_wave_inactive" ) );
|
||||
toolTip::add( roundSqrWaveBtn,
|
||||
tr( "Click here for a square-wave with a rounded end." ) );
|
||||
|
||||
pixmapButton * moogWaveBtn =
|
||||
|
||||
pixmapButton * moogWaveBtn =
|
||||
new pixmapButton( this, tr( "Moog wave" ) );
|
||||
moogWaveBtn->move( waveBtnX+(16*4), waveBtnY );
|
||||
moogWaveBtn->setActiveGraphic(
|
||||
@@ -929,6 +971,47 @@ lb302SynthView::lb302SynthView( Instrument * _instrument, QWidget * _parent ) :
|
||||
toolTip::add( whiteNoiseWaveBtn,
|
||||
tr( "Click here for white-noise." ) );
|
||||
|
||||
pixmapButton * blSawWaveBtn =
|
||||
new pixmapButton( this, tr( "Bandlimited saw wave" ) );
|
||||
blSawWaveBtn->move( waveBtnX+(16*9)-8, waveBtnY );
|
||||
blSawWaveBtn->setActiveGraphic(
|
||||
embed::getIconPixmap( "saw_wave_active" ) );
|
||||
blSawWaveBtn->setInactiveGraphic(
|
||||
embed::getIconPixmap( "saw_wave_inactive" ) );
|
||||
toolTip::add( blSawWaveBtn,
|
||||
tr( "Click here for bandlimited saw wave." ) );
|
||||
|
||||
pixmapButton * blSquareWaveBtn =
|
||||
new pixmapButton( this, tr( "Bandlimited square wave" ) );
|
||||
blSquareWaveBtn->move( waveBtnX+(16*10)-8, waveBtnY );
|
||||
blSquareWaveBtn->setActiveGraphic(
|
||||
embed::getIconPixmap( "square_wave_active" ) );
|
||||
blSquareWaveBtn->setInactiveGraphic(
|
||||
embed::getIconPixmap( "square_wave_inactive" ) );
|
||||
toolTip::add( blSquareWaveBtn,
|
||||
tr( "Click here for bandlimited square wave." ) );
|
||||
|
||||
pixmapButton * blTriangleWaveBtn =
|
||||
new pixmapButton( this, tr( "Bandlimited triangle wave" ) );
|
||||
blTriangleWaveBtn->move( waveBtnX+(16*11)-8, waveBtnY );
|
||||
blTriangleWaveBtn->setActiveGraphic(
|
||||
embed::getIconPixmap( "triangle_wave_active" ) );
|
||||
blTriangleWaveBtn->setInactiveGraphic(
|
||||
embed::getIconPixmap( "triangle_wave_inactive" ) );
|
||||
toolTip::add( blTriangleWaveBtn,
|
||||
tr( "Click here for bandlimited triangle wave." ) );
|
||||
|
||||
pixmapButton * blMoogWaveBtn =
|
||||
new pixmapButton( this, tr( "Bandlimited moog saw wave" ) );
|
||||
blMoogWaveBtn->move( waveBtnX+(16*12)-8, waveBtnY );
|
||||
blMoogWaveBtn->setActiveGraphic(
|
||||
embed::getIconPixmap( "moog_saw_wave_active" ) );
|
||||
blMoogWaveBtn->setInactiveGraphic(
|
||||
embed::getIconPixmap( "moog_saw_wave_inactive" ) );
|
||||
toolTip::add( blMoogWaveBtn,
|
||||
tr( "Click here for bandlimited moog saw wave." ) );
|
||||
|
||||
|
||||
m_waveBtnGrp = new automatableButtonGroup( this );
|
||||
m_waveBtnGrp->addButton( sawWaveBtn );
|
||||
m_waveBtnGrp->addButton( triangleWaveBtn );
|
||||
@@ -938,6 +1021,10 @@ lb302SynthView::lb302SynthView( Instrument * _instrument, QWidget * _parent ) :
|
||||
m_waveBtnGrp->addButton( sinWaveBtn );
|
||||
m_waveBtnGrp->addButton( exponentialWaveBtn );
|
||||
m_waveBtnGrp->addButton( whiteNoiseWaveBtn );
|
||||
m_waveBtnGrp->addButton( blSawWaveBtn );
|
||||
m_waveBtnGrp->addButton( blSquareWaveBtn );
|
||||
m_waveBtnGrp->addButton( blTriangleWaveBtn );
|
||||
m_waveBtnGrp->addButton( blMoogWaveBtn );
|
||||
|
||||
setAutoFillBackground( true );
|
||||
QPalette pal;
|
||||
@@ -955,7 +1042,7 @@ lb302SynthView::~lb302SynthView()
|
||||
void lb302SynthView::modelChanged()
|
||||
{
|
||||
lb302Synth * syn = castModel<lb302Synth>();
|
||||
|
||||
|
||||
m_vcfCutKnob->setModel( &syn->vcf_cut_knob );
|
||||
m_vcfResKnob->setModel( &syn->vcf_res_knob );
|
||||
m_vcfDecKnob->setModel( &syn->vcf_dec_knob );
|
||||
@@ -964,7 +1051,7 @@ void lb302SynthView::modelChanged()
|
||||
|
||||
m_distKnob->setModel( &syn->dist_knob );
|
||||
m_waveBtnGrp->setModel( &syn->wave_shape );
|
||||
|
||||
|
||||
m_slideToggle->setModel( &syn->slideToggle );
|
||||
m_accentToggle->setModel( &syn->accentToggle );
|
||||
m_deadToggle->setModel( &syn->deadToggle );
|
||||
|
||||
@@ -3,12 +3,12 @@
|
||||
* emulate the Roland TB303 bass synth
|
||||
*
|
||||
* Copyright (c) 2006-2008 Paul Giblock <pgib/at/users.sourceforge.net>
|
||||
*
|
||||
*
|
||||
* This file is part of Linux MultiMedia Studio - http://lmms.sourceforge.net
|
||||
*
|
||||
* lb302FilterIIR2 is based on the gsyn filter code by Andy Sloane.
|
||||
*
|
||||
* lb302Filter3Pole is based on the TB303 instrument written by
|
||||
*
|
||||
* lb302Filter3Pole is based on the TB303 instrument written by
|
||||
* Josep M Comajuncosas for the CSounds library
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or
|
||||
@@ -29,8 +29,8 @@
|
||||
*/
|
||||
|
||||
|
||||
#ifndef _LB302_H_
|
||||
#define _LB302_H_
|
||||
#ifndef LB302_H_
|
||||
#define LB302_H_
|
||||
|
||||
#include "DspEffectLibrary.h"
|
||||
#include "Instrument.h"
|
||||
@@ -38,6 +38,8 @@
|
||||
#include "led_checkbox.h"
|
||||
#include "knob.h"
|
||||
#include "Mixer.h"
|
||||
#include "NotePlayHandle.h"
|
||||
#include <QMutex>
|
||||
|
||||
static const int NUM_FILTERS = 2;
|
||||
|
||||
@@ -67,12 +69,12 @@ class lb302Filter
|
||||
virtual void playNote();
|
||||
|
||||
protected:
|
||||
lb302FilterKnobState *fs;
|
||||
lb302FilterKnobState *fs;
|
||||
|
||||
// Filter Decay
|
||||
float vcf_c0; // c0=e1 on retrigger; c0*=ed every sample; cutoff=e0+c0
|
||||
float vcf_e0, // e0 and e1 for interpolation
|
||||
vcf_e1;
|
||||
vcf_e1;
|
||||
float vcf_rescoeff; // Resonance coefficient [0.30,9.54]
|
||||
};
|
||||
|
||||
@@ -87,13 +89,13 @@ class lb302FilterIIR2 : public lb302Filter
|
||||
virtual float process(const float& samp);
|
||||
|
||||
protected:
|
||||
float vcf_d1, // d1 and d2 are added back into the sample with
|
||||
float vcf_d1, // d1 and d2 are added back into the sample with
|
||||
vcf_d2; // vcf_a and b as coefficients. IIR2 resonance
|
||||
// loop.
|
||||
|
||||
// IIR2 Coefficients for mixing dry and delay.
|
||||
float vcf_a, // Mixing coefficients for the final sound.
|
||||
vcf_b, //
|
||||
float vcf_a, // Mixing coefficients for the final sound.
|
||||
vcf_b, //
|
||||
vcf_c;
|
||||
|
||||
DspEffectLibrary::Distortion * m_dist;
|
||||
@@ -111,15 +113,15 @@ class lb302Filter3Pole : public lb302Filter
|
||||
virtual float process(const float& samp);
|
||||
|
||||
protected:
|
||||
float kfcn,
|
||||
kp,
|
||||
kp1,
|
||||
kp1h,
|
||||
float kfcn,
|
||||
kp,
|
||||
kp1,
|
||||
kp1h,
|
||||
kres;
|
||||
float ay1,
|
||||
ay2,
|
||||
aout,
|
||||
lastin,
|
||||
float ay1,
|
||||
ay2,
|
||||
aout,
|
||||
lastin,
|
||||
value;
|
||||
};
|
||||
|
||||
@@ -164,10 +166,10 @@ public:
|
||||
virtual PluginView * instantiateView( QWidget * _parent );
|
||||
|
||||
private:
|
||||
void processNote( NotePlayHandle * n );
|
||||
|
||||
void initNote(lb302Note *note);
|
||||
|
||||
|
||||
private:
|
||||
FloatModel vcf_cut_knob;
|
||||
FloatModel vcf_res_knob;
|
||||
@@ -179,7 +181,7 @@ private:
|
||||
FloatModel dist_knob;
|
||||
IntModel wave_shape;
|
||||
FloatModel slide_dec_knob;
|
||||
|
||||
|
||||
BoolModel slideToggle;
|
||||
BoolModel accentToggle;
|
||||
BoolModel deadToggle;
|
||||
@@ -200,7 +202,8 @@ private:
|
||||
vco_slideinc, //* Slide base to use in next node. Nonzero=slide next note
|
||||
vco_slidebase; //* The base vco_inc while sliding.
|
||||
|
||||
enum vco_shape_t { SAWTOOTH, SQUARE, TRIANGLE, MOOG, ROUND_SQUARE, SINE, EXPONENTIAL, WHITE_NOISE };
|
||||
enum vco_shape_t { SAWTOOTH, SQUARE, TRIANGLE, MOOG, ROUND_SQUARE, SINE, EXPONENTIAL, WHITE_NOISE,
|
||||
BL_SAWTOOTH, BL_SQUARE, BL_TRIANGLE, BL_MOOG };
|
||||
vco_shape_t vco_shape;
|
||||
|
||||
// Filters (just keep both loaded and switch)
|
||||
@@ -215,9 +218,9 @@ private:
|
||||
// More States
|
||||
int vcf_envpos; // Update counter. Updates when >= ENVINC
|
||||
|
||||
float vca_attack, // Amp attack
|
||||
float vca_attack, // Amp attack
|
||||
vca_decay, // Amp decay
|
||||
vca_a0, // Initial amplifier coefficient
|
||||
vca_a0, // Initial amplifier coefficient
|
||||
vca_a; // Amplifier coefficient.
|
||||
|
||||
// Envelope State
|
||||
@@ -242,6 +245,8 @@ private:
|
||||
|
||||
friend class lb302SynthView;
|
||||
|
||||
NotePlayHandleList m_notes;
|
||||
QMutex m_notesMutex;
|
||||
} ;
|
||||
|
||||
|
||||
@@ -254,7 +259,7 @@ public:
|
||||
|
||||
private:
|
||||
virtual void modelChanged();
|
||||
|
||||
|
||||
knob * m_vcfCutKnob;
|
||||
knob * m_vcfResKnob;
|
||||
knob * m_vcfDecKnob;
|
||||
@@ -263,7 +268,7 @@ private:
|
||||
knob * m_distKnob;
|
||||
knob * m_slideDecKnob;
|
||||
automatableButtonGroup * m_waveBtnGrp;
|
||||
|
||||
|
||||
ledCheckBox * m_slideToggle;
|
||||
ledCheckBox * m_accentToggle;
|
||||
ledCheckBox * m_deadToggle;
|
||||
|
||||
Reference in New Issue
Block a user