- use jsy_min/jsy_max
- fixed includes - removed redundant MW table - added Missing JK_MidiClock
This commit is contained in:
@@ -0,0 +1,189 @@
|
||||
/*
|
||||
|
||||
//#######################################################################################
|
||||
//Class to insert Midiclock messages into a given MidiBuffer, suitable for block
|
||||
//based audio callbacks. The class can act on position jumps e.g. "Loops" by sending a
|
||||
//positioning message.
|
||||
//NOTE: No ballistik came in to play so I wouldn't recommend using it to drive a mechanical
|
||||
//tape deck!!!
|
||||
//
|
||||
//solar3d-software, April- 10- 2012
|
||||
//#######################################################################################
|
||||
|
||||
*/
|
||||
#include "JK_MidiClock.h"
|
||||
|
||||
JK_MidiClock::JK_MidiClock()
|
||||
:wasPlaying(false),
|
||||
syncPpqPosition(-999.0),
|
||||
posChangeThreshold(0.001),
|
||||
ppqToStartSyncAt(0.0),
|
||||
followSongPosition(true),
|
||||
syncFlag(0),
|
||||
ppqOffset(0)
|
||||
{
|
||||
//Prepare Midi messages to avoid blocking the caller of generateMidiclock()!
|
||||
continueMessage = new MidiMessage(MidiMessage::midiContinue());
|
||||
stopMessage = new MidiMessage(MidiMessage::midiStop());
|
||||
clockMessage = new MidiMessage(MidiMessage::midiClock());
|
||||
songPositionMessage = new MidiMessage(MidiMessage::songPositionPointer(0));
|
||||
}
|
||||
//=================================================================================================
|
||||
void JK_MidiClock::generateMidiclock(AudioPlayHead::CurrentPositionInfo &lastPosInfo,
|
||||
MidiBuffer* midiBuffer, const int bufferSize, const double sampleRate)
|
||||
{
|
||||
//###################################Some explanation about musical tempo #################
|
||||
//A Time Signature, is two numbers, one on top of the other. The numerator describes the #
|
||||
//number of Beats in a Bar, while the denominator describes of what note value a Beat is. #
|
||||
//So 4/4 would be four quarter-notes per Bar, while 4/2 would be four half-notes per Bar, #
|
||||
//4/8 would be four eighth-notes per Bar, and 2/4 would be two quarter-notes per Bar. #
|
||||
//#########################################################################################
|
||||
|
||||
|
||||
if (midiBuffer != nullptr)
|
||||
{
|
||||
//PPQ value of one sample
|
||||
const double ppqPerSample = (lastPosInfo.bpm / 60.0) / sampleRate;
|
||||
|
||||
//PPQ offset to compensate Midi interface latency
|
||||
double hostPpqPosition = lastPosInfo.ppqPosition + ppqOffset * ppqPerSample;;
|
||||
|
||||
if (lastPosInfo.isPlaying || lastPosInfo.isRecording)
|
||||
{
|
||||
if (! wasPlaying)
|
||||
{
|
||||
//set the point where to start the slave
|
||||
ppqToStartSyncAt = getNearestSixteenthInPPQ(hostPpqPosition);
|
||||
|
||||
//Special case: Master is set to always start playback from the previous start position...
|
||||
if (positionJumped(syncPpqPosition, hostPpqPosition, sampleRate, ppqPerSample))
|
||||
{
|
||||
//Cue Midiclock slave to the nearest sixteenth note to new start position
|
||||
//because the one calculated in stop mode isn't valid anymore.
|
||||
sendSongPositionPointerMessage(ppqToStartSyncAt, 0, midiBuffer);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
//Position jump (loop or manually position change while playing)
|
||||
if (positionJumped(syncPpqPosition, hostPpqPosition, sampleRate, ppqPerSample))
|
||||
{
|
||||
//set the point where to start the slave
|
||||
ppqToStartSyncAt = getNearestSixteenthInPPQ(hostPpqPosition);
|
||||
|
||||
//User has changed position manually while playing
|
||||
if (syncFlag == 0)
|
||||
{
|
||||
midiBuffer->addEvent(*stopMessage, 0);
|
||||
sendSongPositionPointerMessage(hostPpqPosition, 0, midiBuffer);
|
||||
|
||||
syncFlag = startSlave_;
|
||||
}
|
||||
else
|
||||
{
|
||||
if (followSongPosition)
|
||||
{
|
||||
sendSongPositionPointerMessage(hostPpqPosition, 0, midiBuffer);
|
||||
|
||||
syncFlag = startSlave_;
|
||||
}
|
||||
else
|
||||
syncFlag = 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
for (int posInBuffer = 0; posInBuffer < bufferSize; ++posInBuffer)
|
||||
{
|
||||
syncPpqPosition = hostPpqPosition + (posInBuffer * ppqPerSample);
|
||||
|
||||
const int clockDistanceInSamples = roundToInt((60.0 * sampleRate) / (lastPosInfo.bpm * 24.0));
|
||||
const int64 hostSamplePos = roundToInt64((hostPpqPosition * (60.0 / lastPosInfo.bpm)) * sampleRate);
|
||||
const int64 syncSamplePos = hostSamplePos + posInBuffer;
|
||||
|
||||
//Some hosts like Cubase come up with a wacky ppqPosition
|
||||
//that could break the timing! Best is to "wait"
|
||||
//here for the right ppqPosition to jump on.
|
||||
if (syncPpqPosition >= ppqToStartSyncAt)
|
||||
{
|
||||
if ((syncFlag & startSlave_) == startSlave_)
|
||||
{
|
||||
midiBuffer->addEvent(*continueMessage, posInBuffer);
|
||||
|
||||
syncFlag &= cycleEnd_;
|
||||
}
|
||||
|
||||
//Cycle mode on
|
||||
if (lastPosInfo.isLooping && lastPosInfo.ppqLoopStart != lastPosInfo.ppqLoopEnd)
|
||||
{
|
||||
const double ppqToCycleEnd = fabs(lastPosInfo.ppqLoopEnd - syncPpqPosition);
|
||||
const int64 samplesToCycleEnd = roundToInt64(ppqToCycleEnd * (60.0 / lastPosInfo.bpm) * sampleRate);
|
||||
|
||||
if ((syncFlag & cycleEnd_) == 0)
|
||||
{
|
||||
if (samplesToCycleEnd <= clockDistanceInSamples) //For fine tuning tweak here
|
||||
{
|
||||
//We have reached the cycle- end position
|
||||
//and must stop the Midiclock slave here
|
||||
if (followSongPosition)
|
||||
midiBuffer->addEvent(*stopMessage, posInBuffer);
|
||||
|
||||
syncFlag |= cycleEnd_;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
//For best timing we should never interupt Midiclock messages!
|
||||
//Seems that some slaves constantly adjusting their internal clock
|
||||
//to Midiclock even if they are in stop mode.
|
||||
if (syncSamplePos % clockDistanceInSamples == 0)
|
||||
midiBuffer->addEvent(*clockMessage, posInBuffer);
|
||||
}
|
||||
|
||||
wasPlaying = true;
|
||||
}
|
||||
else
|
||||
{
|
||||
//Send positioning message if the user has stopped or if he changed the playhead position
|
||||
//manually in stop mode! This will also initially cue slave after loading plugin instance.
|
||||
if (wasPlaying || positionJumped(syncPpqPosition, hostPpqPosition, sampleRate, ppqPerSample))
|
||||
{
|
||||
midiBuffer->addEvent(*stopMessage, 0);
|
||||
sendSongPositionPointerMessage(hostPpqPosition, 0, midiBuffer);
|
||||
}
|
||||
|
||||
syncPpqPosition = hostPpqPosition;
|
||||
|
||||
syncFlag = startSlave_;
|
||||
|
||||
wasPlaying = false;
|
||||
}
|
||||
}
|
||||
}
|
||||
//=================================================================================================
|
||||
bool JK_MidiClock::positionJumped(const double lastPosInPPQ, const double currentPosInPPQ,
|
||||
const double sampleRate, const double ppqPerSample)
|
||||
{
|
||||
//This returns true if the user has changed the playhead position manually or if
|
||||
//a jump has occured! The comperator's default threshold is lastPosInPPQ +- 10ms.
|
||||
if (currentPosInPPQ < lastPosInPPQ - ((posChangeThreshold * sampleRate) * ppqPerSample) ||
|
||||
currentPosInPPQ > lastPosInPPQ + ((posChangeThreshold * sampleRate) * ppqPerSample))
|
||||
return true;
|
||||
|
||||
return false;
|
||||
}
|
||||
//=================================================================================================
|
||||
void JK_MidiClock::sendSongPositionPointerMessage(const double ppqPosition, const int posInBuffer, MidiBuffer* buffer)
|
||||
{
|
||||
//This will cue the slave to the NEAREST
|
||||
//16th note to the given ppqPosition.
|
||||
int intBeat = int(ceil(ppqPosition * 4));
|
||||
|
||||
uint8* pSongPositionTime((uint8*)(songPositionMessage->getRawData()));
|
||||
|
||||
*(pSongPositionTime + 1) = (uint8)(intBeat & 0x7f);
|
||||
*(pSongPositionTime + 2) = (uint8)((intBeat & 0x3f80)>>7);
|
||||
|
||||
buffer->addEvent(*songPositionMessage, posInBuffer);
|
||||
}
|
||||
@@ -0,0 +1,73 @@
|
||||
/*
|
||||
|
||||
//#######################################################################################
|
||||
//Class to insert Midiclock messages into a given MidiBuffer, suitable for block
|
||||
//based audio callbacks. The class can act on position jumps e.g. "Loops" by sending a
|
||||
//positioning message.
|
||||
//NOTE: No ballistik came in to play so I wouldn't recommend using it to drive a mechanical
|
||||
//tape deck!!!
|
||||
//
|
||||
//solar3d-software, April- 10- 2012
|
||||
//#######################################################################################
|
||||
|
||||
*/
|
||||
#ifndef __JK_MIDICLOCK
|
||||
#define __JK_MIDICLOCK
|
||||
|
||||
#include "../JuceLibraryCode/JuceHeader.h"
|
||||
|
||||
//#include "Includes.h"
|
||||
|
||||
class JK_MidiClock
|
||||
{
|
||||
public:
|
||||
JK_MidiClock();
|
||||
|
||||
void setPositionJumpThreshold(const double ms) {posChangeThreshold = ms / 1000.0;}
|
||||
double getPositionJumpThreshold() {return posChangeThreshold;}
|
||||
void setFollowSongPosition(const bool shouldFollow) {followSongPosition = shouldFollow;}
|
||||
bool getFollowSongPosition() {return followSongPosition;}
|
||||
void setOffset(const int offset) {ppqOffset = offset;}
|
||||
int getOffset() {return ppqOffset;}
|
||||
|
||||
void generateMidiclock(AudioPlayHead::CurrentPositionInfo &lastPosInfo,
|
||||
MidiBuffer* midiBuffer,
|
||||
const int bufferSize,
|
||||
const double sampleRate);
|
||||
|
||||
//=================================================================================================
|
||||
juce_UseDebuggingNewOperator
|
||||
|
||||
private:
|
||||
inline int64 roundToInt64 (const double val) noexcept
|
||||
{
|
||||
return (val - floor(val) >= 0.5) ? (int64)(ceil(val)) : (int64)(floor(val));
|
||||
}
|
||||
|
||||
|
||||
bool wasPlaying;
|
||||
double syncPpqPosition;
|
||||
double posChangeThreshold;
|
||||
double ppqToStartSyncAt;
|
||||
bool followSongPosition;
|
||||
uint8 syncFlag;
|
||||
int ppqOffset;
|
||||
|
||||
static const int cycleEnd_ = 1;
|
||||
static const int startSlave_ = 2;
|
||||
|
||||
ScopedPointer <MidiMessage> clockMessage;
|
||||
ScopedPointer <MidiMessage> continueMessage;
|
||||
ScopedPointer <MidiMessage> stopMessage;
|
||||
ScopedPointer <MidiMessage> songPositionMessage;
|
||||
|
||||
void sendSongPositionPointerMessage(const double ppqPosition, const int posInBuffer, MidiBuffer* buffer);
|
||||
|
||||
bool positionJumped(const double lastPosInPPQ, const double currentPosInPPQ,
|
||||
const double sampleRate, const double ppqPerSample);
|
||||
|
||||
double getNearestSixteenthInPPQ(const double ppqPosition) {return ceil(ppqPosition * 4.0) / 4.0;}
|
||||
|
||||
JUCE_DECLARE_NON_COPYABLE_WITH_LEAK_DETECTOR(JK_MidiClock);
|
||||
};
|
||||
#endif
|
||||
@@ -712,11 +712,11 @@ synth_float_t JaySynthMidiCC::getVelKeyControl(int paramID, synth_float_t vel, s
|
||||
switch (midiCC_containers[paramID].velKeyCombineOP)
|
||||
{
|
||||
case VELKEY_OP_ADD:
|
||||
result = min(1, max(-1, result_vel + result_key));
|
||||
result = jsy_min(1, jsy_max(-1, result_vel + result_key));
|
||||
break;
|
||||
|
||||
case VELKEY_OP_SUB:
|
||||
result = min(1, max(-1, result_vel - result_key));
|
||||
result = jsy_min(1, jsy_max(-1, result_vel - result_key));
|
||||
break;
|
||||
|
||||
case VELKEY_OP_MUL:
|
||||
|
||||
@@ -576,7 +576,7 @@ void JaySynthAudioProcessor::processBlock (AudioSampleBuffer& buffer, MidiBuffer
|
||||
|
||||
for (i=0; i <numSamples; i++)
|
||||
{
|
||||
x = max(fabs(buf[0][i]), fabs(buf[1][i]));
|
||||
x = jsy_max(fabs(buf[0][i]), fabs(buf[1][i]));
|
||||
if (x > m_limiter_env)
|
||||
{
|
||||
m_limiter_env = (1.0-limiter_ar)*m_limiter_env + limiter_ar*x;
|
||||
@@ -592,7 +592,7 @@ void JaySynthAudioProcessor::processBlock (AudioSampleBuffer& buffer, MidiBuffer
|
||||
m_limiter_active = 0;
|
||||
for (i=0; i <numSamples; i++)
|
||||
{
|
||||
limiter_gain[i] = min(1.0, 1.0/(limiter_env[i] + 1.0e-6));
|
||||
limiter_gain[i] = jsy_min(1.0, 1.0/(limiter_env[i] + 1.0e-6));
|
||||
if (limiter_gain[i] < 1.0)
|
||||
{
|
||||
m_limiter_active = 1;
|
||||
|
||||
@@ -555,7 +555,7 @@ VelKey_PopUp::VelKey_PopUp (JaySynthMidiCC *pMidiCC, int paramID, synth_float_t
|
||||
pMidiCC_container = pMidiCC->getAtParamID(m_paramID);
|
||||
paramInfoInit(&m_velKey_constraints, 0, pMidiCC->getConstraints(pMidiCC_container)->pName);
|
||||
paramInfoCopy(&m_velKey_constraints, pMidiCC->getConstraints(pMidiCC_container));
|
||||
m_velKey_constraints.pmax = max(fabs(pMidiCC->getConstraints(pMidiCC_container)->pmin), fabs(pMidiCC->getConstraints(pMidiCC_container)->pmax));
|
||||
m_velKey_constraints.pmax = jsy_max(fabs(pMidiCC->getConstraints(pMidiCC_container)->pmin), fabs(pMidiCC->getConstraints(pMidiCC_container)->pmax));
|
||||
m_velKey_constraints.pmin = -m_velKey_constraints.pmax;
|
||||
m_velKey_constraints.scenter = 0.5;
|
||||
m_velKey_constraints.pcenter = -1E18;
|
||||
@@ -580,15 +580,15 @@ VelKey_PopUp::VelKey_PopUp (JaySynthMidiCC *pMidiCC, int paramID, synth_float_t
|
||||
|
||||
m_label_prec = 3;
|
||||
if (pMidiCC->getConstraints(pMidiCC_container)->pinterval > 0)
|
||||
m_label_prec = max(1, (int)(-log(pMidiCC->getConstraints(pMidiCC_container)->pinterval)/log(10.0) + 0.5));
|
||||
m_label_prec = jsy_max(1, (int)(-log(pMidiCC->getConstraints(pMidiCC_container)->pinterval)/log(10.0) + 0.5));
|
||||
|
||||
m_label_shape_prec = 3;
|
||||
if (m_shape_xform.pinterval > 0)
|
||||
m_label_shape_prec = max(1, (int)(-log(m_shape_xform.pinterval)/log(10.0) + 0.5));
|
||||
m_label_shape_prec = jsy_max(1, (int)(-log(m_shape_xform.pinterval)/log(10.0) + 0.5));
|
||||
|
||||
m_label_skew_prec = 3;
|
||||
if (m_skew_xform.pinterval > 0)
|
||||
m_label_skew_prec = max(1, (int)(-log(m_skew_xform.pinterval)/log(10.0) + 0.5));
|
||||
m_label_skew_prec = jsy_max(1, (int)(-log(m_skew_xform.pinterval)/log(10.0) + 0.5));
|
||||
|
||||
displayUpdate();
|
||||
//[/Constructor]
|
||||
|
||||
+5
-5
@@ -8,7 +8,7 @@
|
||||
|
||||
#include "synth_defs.h"
|
||||
#include "blit.h"
|
||||
#include "fir/fir2.h"
|
||||
#include <fir/fir2.h>
|
||||
#include "vector_utils.h"
|
||||
|
||||
// --------------------------------------------------------------
|
||||
@@ -144,8 +144,8 @@ void BLIT_ModInit(blit_common_t *pCom)
|
||||
blep = 0;
|
||||
for (n=0; n < pCom->pTableSizes[m]; n++)
|
||||
{
|
||||
a = sin(x*pi);
|
||||
b = sin(m*x*pi);
|
||||
a = sin(x*jsy_pi);
|
||||
b = sin(m*x*jsy_pi);
|
||||
if (a == 0)
|
||||
blit = (synth_float_t)m;
|
||||
else
|
||||
@@ -234,7 +234,7 @@ void BLIT_Prepare(blit_t *pObj, UINT32 len)
|
||||
synth_float_t pitch_buf[SYNTH_MAX_BUFSIZE];
|
||||
synth_float_t out_buf[SYNTH_MAX_BUFSIZE];
|
||||
|
||||
len = min(len, SYNTH_MAX_BUFSIZE);
|
||||
len = jsy_min(len, SYNTH_MAX_BUFSIZE);
|
||||
|
||||
// Let Oscillators run with different pitches to randomize phase
|
||||
Add_inplace_VS(pitch_buf, 0, 8*440.0*(1+0.01*(synth_float_t)rand()/RAND_MAX), len);
|
||||
@@ -343,7 +343,7 @@ void BLIT_Process_SQR_Vector(blit_t *pObj, synth_float_t *pPitch, synth_float_t
|
||||
{
|
||||
pObj->pwm = (synth_float_t)pCV_pwm[i];
|
||||
}
|
||||
dutycycle = min(1, max(0, pObj->dutycycle + pObj->pwm));
|
||||
dutycycle = jsy_min(1, jsy_max(0, pObj->dutycycle + pObj->pwm));
|
||||
pObj->pulse_offset = 2*(dutycycle-0.5);
|
||||
pObj->sqr_x2 = pObj->sqr_x1 + dutycycle - 1;
|
||||
pObj->sqr_pol2 = pObj->sqr_pol1;
|
||||
|
||||
+3
-3
@@ -102,13 +102,13 @@ void ENV_Param2Set(envgen_t *pObj, UINT32 type, synth_float_t value)
|
||||
switch(type)
|
||||
{
|
||||
case ENV_PARAM2_A:
|
||||
pObj->param.Ta = max(ENV_MIN_A, value);
|
||||
pObj->param.Ta = jsy_max(ENV_MIN_A, value);
|
||||
pObj->a_a = 1.f/(pObj->param.Ta*pObj->fs);
|
||||
pObj->b_a = 1.f - pObj->a_a;
|
||||
break;
|
||||
|
||||
case ENV_PARAM2_D:
|
||||
pObj->param.Td = max(ENV_MIN_D, value);
|
||||
pObj->param.Td = jsy_max(ENV_MIN_D, value);
|
||||
pObj->a_d = 5.f/(pObj->param.Td*pObj->fs);
|
||||
pObj->b_d = 1.f - pObj->a_d;
|
||||
|
||||
@@ -119,7 +119,7 @@ void ENV_Param2Set(envgen_t *pObj, UINT32 type, synth_float_t value)
|
||||
break;
|
||||
|
||||
case ENV_PARAM2_R:
|
||||
pObj->param.Tr = max(ENV_MIN_R, value);
|
||||
pObj->param.Tr = jsy_max(ENV_MIN_R, value);
|
||||
pObj->a_r = 5.f/(pObj->param.Tr*pObj->fs);
|
||||
pObj->b_r = 1.f - pObj->a_r;
|
||||
break;
|
||||
|
||||
@@ -736,7 +736,7 @@ synth_float_t quantizeParam(param_info_t *pObj, synth_float_t p)
|
||||
|
||||
synth_float_t clampParam(param_info_t *pObj, synth_float_t p)
|
||||
{
|
||||
return (synth_float_t)min(pObj->pmax, max(pObj->pmin, quantizeParam(pObj, p)));
|
||||
return (synth_float_t)jsy_min(pObj->pmax, jsy_max(pObj->pmin, quantizeParam(pObj, p)));
|
||||
}
|
||||
|
||||
synth_float_t toParam(param_info_t *pObj, synth_float_t s)
|
||||
@@ -758,7 +758,7 @@ synth_float_t toParam(param_info_t *pObj, synth_float_t s)
|
||||
if ((pcenter < pmin) || (pcenter > pmax))
|
||||
pcenter = pmax*scenter + pmin*(1-scenter);
|
||||
|
||||
s = (synth_float_t)min(1, max(0, s));
|
||||
s = (synth_float_t)jsy_min(1, jsy_max(0, s));
|
||||
if (s < scenter)
|
||||
{
|
||||
if (base == 1)
|
||||
|
||||
+3
-3
@@ -34,8 +34,8 @@ void Sine_SetFS(sine_gen_t *pObj, synth_float_t fs)
|
||||
|
||||
void Sine_Reset(sine_gen_t *pObj, synth_float_t phase)
|
||||
{
|
||||
pObj->y[0] = cos(2*pi*phase);
|
||||
pObj->y[1] = sin(2*pi*phase);
|
||||
pObj->y[0] = cos(2*jsy_pi*phase);
|
||||
pObj->y[1] = sin(2*jsy_pi*phase);
|
||||
pObj->fscale = 1;
|
||||
}
|
||||
|
||||
@@ -54,7 +54,7 @@ void Sine_Update(sine_gen_t *pObj)
|
||||
{
|
||||
synth_float_t freq;
|
||||
freq = pObj->fscale * pObj->pitch;
|
||||
pObj->b = 2.0 * sin(freq*pi / pObj->fs);
|
||||
pObj->b = 2.0 * sin(freq*jsy_pi / pObj->fs);
|
||||
}
|
||||
|
||||
synth_float_t Sine_Process_Scalar(sine_gen_t *pObj, synth_float_t pitch, synth_float_t CV_fm)
|
||||
|
||||
@@ -1,7 +1,9 @@
|
||||
// --------------------------------------------------------------
|
||||
// --------------------------------------------------------------
|
||||
|
||||
#ifdef WIN32
|
||||
#include <windows.h>
|
||||
#endif
|
||||
#include <stdarg.h>
|
||||
#include <stdlib.h>
|
||||
#include <stdio.h>
|
||||
|
||||
@@ -3,6 +3,8 @@
|
||||
#ifndef _SYNTH_DEFS_H_
|
||||
#define _SYNTH_DEFS_H_
|
||||
|
||||
#include <limits.h>
|
||||
#include <math.h>
|
||||
#include "synth_types.h"
|
||||
|
||||
// --------------------------------------------------------------
|
||||
@@ -43,10 +45,10 @@
|
||||
|
||||
#define SYNTH_MAX_BUFSIZE 8192
|
||||
|
||||
#ifndef pi
|
||||
#define pi 3.1415926535897932384626433832795
|
||||
#define pi_mult_2 (2*pi)
|
||||
#define pi_div_2 (0.5*pi)
|
||||
#ifndef jsy_pi
|
||||
#define jsy_pi 3.1415926535897932384626433832795
|
||||
#define pi_mult_2 (2*jsy_pi)
|
||||
#define pi_div_2 (0.5*jsy_pi)
|
||||
#endif
|
||||
|
||||
#if defined(__cplusplus)
|
||||
@@ -57,12 +59,12 @@ void SynthDebug(const char *fmtstr, ...);
|
||||
}
|
||||
#endif
|
||||
|
||||
#ifndef max
|
||||
#define max(a,b) (((a) > (b)) ? (a) : (b))
|
||||
#ifndef jsy_max
|
||||
#define jsy_max(a,b) (((a) > (b)) ? (a) : (b))
|
||||
#endif
|
||||
|
||||
#ifndef min
|
||||
#define min(a,b) (((a) < (b)) ? (a) : (b))
|
||||
#ifndef jsy_min
|
||||
#define jsy_min(a,b) (((a) < (b)) ? (a) : (b))
|
||||
#endif
|
||||
|
||||
|
||||
|
||||
@@ -6,7 +6,9 @@
|
||||
// --------------------------------------------------------------
|
||||
// Types
|
||||
// --------------------------------------------------------------
|
||||
#ifndef synth_float_t
|
||||
#define synth_float_t double
|
||||
#endif
|
||||
|
||||
#ifndef UINT32
|
||||
#define UINT32 unsigned int
|
||||
|
||||
+13
-13
@@ -77,8 +77,8 @@ void VCF_LUT_gen(vcf_t *pObj)
|
||||
{
|
||||
cv = (synth_float_t)i/(FILTER_TABLE_SIZE-1);
|
||||
omega = VCF_cv2omega(pObj, cv);
|
||||
pCom->pLUT_cos[i] = cos(pi*omega);
|
||||
pCom->pLUT_sin[i] = sin(pi*omega);
|
||||
pCom->pLUT_cos[i] = cos(jsy_pi*omega);
|
||||
pCom->pLUT_sin[i] = sin(jsy_pi*omega);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -100,10 +100,10 @@ synth_float_t VCF_LUT_get_cos(vcf_t *pObj, synth_float_t cv)
|
||||
synth_float_t n, nf;
|
||||
vcf_common_t *pCom = pObj->pCom;
|
||||
|
||||
n = min(1, max(0, cv))*(FILTER_TABLE_SIZE-1);
|
||||
n = jsy_min(1, jsy_max(0, cv))*(FILTER_TABLE_SIZE-1);
|
||||
ni = (int)n;
|
||||
nf = n - (synth_float_t)ni;
|
||||
ni_next = min(FILTER_TABLE_SIZE-1, ni+1);
|
||||
ni_next = jsy_min(FILTER_TABLE_SIZE-1, ni+1);
|
||||
|
||||
return (pCom->pLUT_cos[ni_next] - pCom->pLUT_cos[ni])*nf + pCom->pLUT_cos[ni];
|
||||
}
|
||||
@@ -114,10 +114,10 @@ synth_float_t VCF_LUT_get_sin(vcf_t *pObj, synth_float_t cv)
|
||||
synth_float_t n, nf;
|
||||
vcf_common_t *pCom = pObj->pCom;
|
||||
|
||||
n = min(1, max(0, cv))*(FILTER_TABLE_SIZE-1);
|
||||
n = jsy_min(1, jsy_max(0, cv))*(FILTER_TABLE_SIZE-1);
|
||||
ni = (int)n;
|
||||
nf = n - (synth_float_t)ni;
|
||||
ni_next = min(FILTER_TABLE_SIZE-1, ni+1);
|
||||
ni_next = jsy_min(FILTER_TABLE_SIZE-1, ni+1);
|
||||
|
||||
return (pCom->pLUT_sin[ni_next] - pCom->pLUT_sin[ni])*nf + pCom->pLUT_sin[ni];
|
||||
}
|
||||
@@ -172,7 +172,7 @@ void VCF_SetF(vcf_t *pObj, synth_float_t f)
|
||||
|
||||
void VCF_SetQ(vcf_t *pObj, synth_float_t q)
|
||||
{
|
||||
pObj->cv_q_bias = max(FILTER_Q_MIN, q);
|
||||
pObj->cv_q_bias = jsy_max(FILTER_Q_MIN, q);
|
||||
pObj->req_filter_update = 1;
|
||||
}
|
||||
|
||||
@@ -186,7 +186,7 @@ void VCF_SetType(vcf_t *pObj, UINT32 type)
|
||||
|
||||
synth_float_t IIRCalcQp(unsigned p, unsigned N)
|
||||
{
|
||||
return 1.0f/(synth_float_t)(2*sin(pi*(2*p-1)/(2*N)));
|
||||
return 1.0f/(synth_float_t)(2*sin(jsy_pi*(2*p-1)/(2*N)));
|
||||
}
|
||||
|
||||
void VCF_SetOrder(vcf_t *pObj, UINT32 order)
|
||||
@@ -238,14 +238,14 @@ synth_float_t VCF_omega2cv(vcf_t *pObj, synth_float_t omega)
|
||||
synth_float_t cv;
|
||||
|
||||
cv = log(omega/pObj->omega_min)/(pObj->num_octaves * log(FILTER_SWEEP_BASE));
|
||||
return min(1, max(0, cv));
|
||||
return jsy_min(1, jsy_max(0, cv));
|
||||
}
|
||||
|
||||
synth_float_t VCF_cv2omega(vcf_t *pObj, synth_float_t cv)
|
||||
{
|
||||
synth_float_t omega;
|
||||
|
||||
omega = pObj->omega_min*pow(FILTER_SWEEP_BASE, pObj->num_octaves*min(1, max(0, cv)));
|
||||
omega = pObj->omega_min*pow(FILTER_SWEEP_BASE, pObj->num_octaves*jsy_min(1, jsy_max(0, cv)));
|
||||
return omega;
|
||||
}
|
||||
|
||||
@@ -275,7 +275,7 @@ void VCF_CalcCoeff_LPF(vcf_t *pObj, vcf_coef_t *pCoeff, synth_float_t *pCV_f, sy
|
||||
cv = pObj->cv_f_bias + pCV_f[n];
|
||||
ks = VCF_LUT_get_sin(pObj, cv);
|
||||
kc = VCF_LUT_get_cos(pObj, cv);
|
||||
q = min(FILTER_Q_MAX, max(FILTER_Q_MIN, pObj->cv_q_bias + FILTER_Q_MAX*pCV_q[n]));
|
||||
q = jsy_min(FILTER_Q_MAX, jsy_max(FILTER_Q_MIN, pObj->cv_q_bias + FILTER_Q_MAX*pCV_q[n]));
|
||||
pObj->cv_q_last = q;
|
||||
if (pObj->order == 2)
|
||||
q *= q;
|
||||
@@ -334,7 +334,7 @@ void VCF_CalcCoeff_HPF(vcf_t *pObj, vcf_coef_t *pCoeff, synth_float_t *pCV_f, sy
|
||||
cv = pObj->cv_f_bias + pCV_f[n];
|
||||
ks = VCF_LUT_get_sin(pObj, cv);
|
||||
kc = VCF_LUT_get_cos(pObj, cv);
|
||||
q = min(FILTER_Q_MAX, max(FILTER_Q_MIN, pObj->cv_q_bias + FILTER_Q_MAX*pCV_q[n]));
|
||||
q = jsy_min(FILTER_Q_MAX, jsy_max(FILTER_Q_MIN, pObj->cv_q_bias + FILTER_Q_MAX*pCV_q[n]));
|
||||
pObj->cv_q_last = q;
|
||||
if (pObj->order == 2)
|
||||
q *= q;
|
||||
@@ -393,7 +393,7 @@ void VCF_CalcCoeff_BPF(vcf_t *pObj, vcf_coef_t *pCoeff, synth_float_t *pCV_f, sy
|
||||
cv = pObj->cv_f_bias + pCV_f[n];
|
||||
ks = VCF_LUT_get_sin(pObj, cv);
|
||||
kc = VCF_LUT_get_cos(pObj, cv);
|
||||
q = min(FILTER_Q_MAX, max(FILTER_Q_MIN, pObj->cv_q_bias + FILTER_Q_MAX*pCV_q[n]));
|
||||
q = jsy_min(FILTER_Q_MAX, jsy_max(FILTER_Q_MIN, pObj->cv_q_bias + FILTER_Q_MAX*pCV_q[n]));
|
||||
pObj->cv_q_last = q;
|
||||
if (pObj->order == 2)
|
||||
q *= q;
|
||||
|
||||
@@ -145,7 +145,7 @@ void Clamp_inplace_V(synth_float_t *pSrcDst, synth_float_t minimum, synth_float_
|
||||
{
|
||||
while(len--)
|
||||
{
|
||||
*(pSrcDst) = max(minimum, min(maximum, *(pSrcDst)));
|
||||
*(pSrcDst) = jsy_max(minimum, jsy_min(maximum, *(pSrcDst)));
|
||||
pSrcDst++;
|
||||
}
|
||||
}
|
||||
@@ -154,7 +154,7 @@ void Clamp_V(synth_float_t *pDst, synth_float_t *pSrc, synth_float_t minimum, sy
|
||||
{
|
||||
while(len--)
|
||||
{
|
||||
*(pDst++) = max(minimum, min(maximum, *(pSrc++)));
|
||||
*(pDst++) = jsy_max(minimum, jsy_min(maximum, *(pSrc++)));
|
||||
}
|
||||
}
|
||||
|
||||
@@ -162,7 +162,7 @@ void uMax_VS(synth_float_t *pDst, synth_float_t *pSrc1, synth_float_t src2, UINT
|
||||
{
|
||||
while(len--)
|
||||
{
|
||||
*(pDst++) = max(fabs(*(pSrc1++)), src2);
|
||||
*(pDst++) = jsy_max(fabs(*(pSrc1++)), src2);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -170,7 +170,7 @@ void uMax_VV(synth_float_t *pDst, synth_float_t *pSrc1, synth_float_t *pSrc2, UI
|
||||
{
|
||||
while(len--)
|
||||
{
|
||||
*(pDst++) = max(fabs(*(pSrc1++)), *(pSrc2++));
|
||||
*(pDst++) = jsy_max(fabs(*(pSrc1++)), *(pSrc2++));
|
||||
}
|
||||
}
|
||||
|
||||
@@ -178,7 +178,7 @@ void uMin_VS(synth_float_t *pDst, synth_float_t *pSrc1, synth_float_t src2, UINT
|
||||
{
|
||||
while(len--)
|
||||
{
|
||||
*(pDst++) = min(fabs(*(pSrc1++)), src2);
|
||||
*(pDst++) = jsy_min(fabs(*(pSrc1++)), src2);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -186,6 +186,6 @@ void uMin_VV(synth_float_t *pDst, synth_float_t *pSrc1, synth_float_t *pSrc2, UI
|
||||
{
|
||||
while(len--)
|
||||
{
|
||||
*(pDst++) = min(fabs(*(pSrc1++)), *(pSrc2++));
|
||||
*(pDst++) = jsy_min(fabs(*(pSrc1++)), *(pSrc2++));
|
||||
}
|
||||
}
|
||||
|
||||
@@ -324,7 +324,7 @@ void VoiceEvent(voice_t *pObj, UINT32 type)
|
||||
|
||||
synth_float_t getKeyFreq(voice_t *pObj, int key)
|
||||
{
|
||||
int index = max(0, min(NUM_FREQS-1, key));
|
||||
int index = jsy_max(0, jsy_min(NUM_FREQS-1, key));
|
||||
return pObj->pCom->freqTab[index];
|
||||
}
|
||||
|
||||
@@ -349,9 +349,9 @@ void VoiceParam2Set(voice_t *pObj, UINT32 type, synth_float_t value)
|
||||
{
|
||||
case VOICE_PARAM_VOICE_PAN:
|
||||
if (pObj->id % 2)
|
||||
pObj->param[type] = min(1, max(-1, -value/100));
|
||||
pObj->param[type] = jsy_min(1, jsy_max(-1, -value/100));
|
||||
else
|
||||
pObj->param[type] = min(1, max(-1, value/100));
|
||||
pObj->param[type] = jsy_min(1, jsy_max(-1, value/100));
|
||||
break;
|
||||
|
||||
case VOICE_PARAM_PORTAMENTO_TIME:
|
||||
@@ -1222,7 +1222,7 @@ void VoiceProcessDataV(voice_t *pObj, float *pOut1, float *pOut2, UINT32 len)
|
||||
}
|
||||
|
||||
// Amplifier envelope and voice panning
|
||||
env_gain = 0.25f*max(0, min(1, pObj->param[VOICE_PARAM_VCA_ENV_GAIN]));
|
||||
env_gain = 0.25f*jsy_max(0, jsy_min(1, pObj->param[VOICE_PARAM_VCA_ENV_GAIN]));
|
||||
|
||||
// VCA AM
|
||||
Mul_VS(vca_am, pModSrc[(int)pObj->param[VOICE_PARAM_VCA_AM_SRC_0]], pObj->param[VOICE_PARAM_VCA_AM_AMT_0], len);
|
||||
@@ -1241,7 +1241,7 @@ void VoiceProcessDataV(voice_t *pObj, float *pOut1, float *pOut2, UINT32 len)
|
||||
|
||||
for (j=0; j < (INT32)len; j++)
|
||||
{
|
||||
// env_gain = 0.25f*max(0, min(1, pObj->param_smoothed[VOICE_PARAM_VCA_ENV_GAIN][j]));
|
||||
// env_gain = 0.25f*jsy_max(0, jsy_min(1, pObj->param_smoothed[VOICE_PARAM_VCA_ENV_GAIN][j]));
|
||||
out = pBuf_Postvcf[j] * pBuf_ENV[VOICE_ENV_VCA][j] * env_gain * vca_am[j];
|
||||
(*pOut1++) += (float)((1+pObj->param[VOICE_PARAM_VOICE_PAN])*(1+vca_pan[j])*out);
|
||||
(*pOut2++) += (float)((1-pObj->param[VOICE_PARAM_VOICE_PAN])*(1-vca_pan[j])*out);
|
||||
|
||||
@@ -11,6 +11,8 @@
|
||||
|
||||
//#define WAVE_EXPORT_FILE
|
||||
|
||||
extern const wt_descr_t _g_wt_descr[WT_NUM_WAVETABLES];
|
||||
#if 0
|
||||
const wt_descr_t _g_wt_descr[WT_NUM_WAVETABLES] =
|
||||
{
|
||||
{8, 0, 101, 8, 69, 16, 70, 24, 71, 32, 72, 40, 73, 48, 74, 60, 75},
|
||||
@@ -55,6 +57,7 @@ const wt_descr_t _g_wt_descr[WT_NUM_WAVETABLES] =
|
||||
{22, 0, 400, 1, 401, 4, 402, 8, 403, 11, 404, 13, 405, 17, 406, 19, 407, 22, 408, 25, 409, 29, 410, 30, 411, 34, 412, 36, 413, 39, 414, 43, 415, 48, 416, 52, 417, 53, 418, 54, 419, 59, 420, 60, 421}
|
||||
|
||||
};
|
||||
#endif
|
||||
|
||||
void WT_ModInit(wt_common_t *pCom)
|
||||
{
|
||||
@@ -316,7 +319,7 @@ void WT_ProcessDataV(wt_t *pObj, synth_float_t *pPitch, synth_float_t *pCV_fm, s
|
||||
if (pObj->startup)
|
||||
pObj->x = 0;
|
||||
|
||||
pObj->wt_index = (WT_WAVETABLE_SIZE-1)*max(0, min(1, pObj->param[WT_PARAM2_WAVETABLE_ENTRY] + pCV_pwm[i]));
|
||||
pObj->wt_index = (WT_WAVETABLE_SIZE-1)*jsy_max(0, jsy_min(1, pObj->param[WT_PARAM2_WAVETABLE_ENTRY] + pCV_pwm[i]));
|
||||
pObj->wt_start = (UINT32)pObj->wt_index;
|
||||
|
||||
if (pCV_fm)
|
||||
@@ -328,7 +331,7 @@ void WT_ProcessDataV(wt_t *pObj, synth_float_t *pPitch, synth_float_t *pCV_fm, s
|
||||
ni = (UINT32)(pObj->x*(WT_WAVE_SIZE));
|
||||
|
||||
w1 = pObj->pCom->ppWavetables[wt_table][pObj->wt_start][ni];
|
||||
w2 = pObj->pCom->ppWavetables[wt_table][min((WT_WAVETABLE_SIZE-1), pObj->wt_start+1)][ni];
|
||||
w2 = pObj->pCom->ppWavetables[wt_table][jsy_min((WT_WAVETABLE_SIZE-1), pObj->wt_start+1)][ni];
|
||||
kmix = pObj->wt_index - (UINT32)pObj->wt_index;
|
||||
out = w1*(1-kmix) + w2*kmix;
|
||||
|
||||
@@ -350,7 +353,7 @@ void WT_ProcessDataV(wt_t *pObj, synth_float_t *pPitch, synth_float_t *pCV_fm, s
|
||||
if (pObj->startup)
|
||||
pObj->x = 0;
|
||||
|
||||
pObj->wt_index = (WT_WAVETABLE_SIZE-1)*max(0, min(1, pObj->param[WT_PARAM2_WAVETABLE_ENTRY] + pCV_pwm[i]));
|
||||
pObj->wt_index = (WT_WAVETABLE_SIZE-1)*jsy_max(0, jsy_min(1, pObj->param[WT_PARAM2_WAVETABLE_ENTRY] + pCV_pwm[i]));
|
||||
pObj->wt_start = (UINT32)pObj->wt_index;
|
||||
|
||||
if (pCV_fm)
|
||||
@@ -365,7 +368,7 @@ void WT_ProcessDataV(wt_t *pObj, synth_float_t *pPitch, synth_float_t *pCV_fm, s
|
||||
ni_next = (ni + 1)&(WT_WAVE_SIZE-1);
|
||||
|
||||
w1 = (pObj->pCom->ppWavetables[wt_table][pObj->wt_start][ni_next] - pObj->pCom->ppWavetables[wt_table][pObj->wt_start][ni])*nf + pObj->pCom->ppWavetables[wt_table][pObj->wt_start][ni];
|
||||
w2 = (pObj->pCom->ppWavetables[wt_table][min((WT_WAVETABLE_SIZE-1), pObj->wt_start+1)][ni_next] - pObj->pCom->ppWavetables[wt_table][min((WT_WAVETABLE_SIZE-1), pObj->wt_start+1)][ni])*nf + pObj->pCom->ppWavetables[wt_table][min((WT_WAVETABLE_SIZE-1), pObj->wt_start+1)][ni];
|
||||
w2 = (pObj->pCom->ppWavetables[wt_table][jsy_min((WT_WAVETABLE_SIZE-1), pObj->wt_start+1)][ni_next] - pObj->pCom->ppWavetables[wt_table][jsy_min((WT_WAVETABLE_SIZE-1), pObj->wt_start+1)][ni])*nf + pObj->pCom->ppWavetables[wt_table][jsy_min((WT_WAVETABLE_SIZE-1), pObj->wt_start+1)][ni];
|
||||
kmix = pObj->wt_index - (UINT32)pObj->wt_index;
|
||||
out = w1*(1-kmix) + w2*kmix;
|
||||
|
||||
|
||||
Reference in New Issue
Block a user