Added USE_F32 for switching to float precission (not working yet).

master
Holger Wirtz 6 years ago
parent e7f87f5209
commit 94c5d375df
  1. 63
      MicroMDAEPiano.ino
  2. 8
      config.h
  3. 17
      mdaEPiano.cpp
  4. 96
      mdaEPiano.h

@ -22,7 +22,11 @@
*/
#include "config.h"
#ifdef USE_F32
#include <OpenAudio_ArduinoLibrary.h> //for AudioConvert_I16toF32, AudioConvert_F32toI16, and AudioEffectGain_F32
#else
#include <Audio.h>
#endif
#include <Wire.h>
#include <SPI.h>
#include <MIDI.h>
@ -43,7 +47,6 @@
#include <Bounce.h>
#include <Encoder.h>
#include "LiquidCrystalPlus_I2C.h"
#include <OpenAudio_ArduinoLibrary.h> //for AudioConvert_I16toF32, AudioConvert_F32toI16, and AudioEffectGain_F32
// [I2C] SCL: Pin 19, SDA: Pin 18 (https://www.pjrc.com/teensy/td_libs_Wire.html)
#define LCD_I2C_ADDRESS 0x27
@ -54,31 +57,55 @@ Encoder enc1(ENC1_PIN_A, ENC1_PIN_B);
Bounce but1 = Bounce(BUT1_PIN, 10); // 10 ms debounce
// GUItool: begin automatically generated code
#ifdef USE_F32
AudioPlayQueue_F32 queue_r; //xy=494,404
AudioPlayQueue_F32 queue_l; //xy=494,404
AudioEffectCompressor_F32 comp_r;
AudioEffectCompressor_F32 comp_l;
AudioConvert_F32toI16 float2Int_r;
AudioConvert_F32toI16 float2Int_l;
AudioConvert_F32toI16 float2Int_r;
AudioConvert_F32toI16 float2Int_l;
#else
AudioPlayQueue queue_r; //xy=494,404
AudioPlayQueue queue_l; //xy=494,404
#endif
AudioAnalyzePeak peak_r; //xy=695,491
AudioAnalyzePeak peak_l; //xy=695,491
#ifdef USE_F32
#ifdef USE_COMP_F32
AudioEffectCompressor_F32 comp_r;
AudioEffectCompressor_F32 comp_l;
AudioConnection_F32 patchCord0(queue_r, comp_r);
AudioConnection_F32 patchCord1(queue_l, comp_l);
AudioConnection_F32 patchCord2(comp_r, float2Int_r);
AudioConnection_F32 patchCord3(comp_l, float2Int_l);
#else
AudioConnection_F32 patchCord0(queue_r, float2Int_r);
AudioConnection_F32 patchCord1(queue_l, float2Int_l);
#endif
#endif
#ifdef TEENSY_AUDIO_BOARD
AudioOutputI2S i2s1; //xy=1072,364
#ifdef USE_F32
AudioConnection patchCord4(float2Int_r, peak_r);
AudioConnection patchCord5(float2Int_l, peak_l);
AudioConnection patchCord6(float2Int_r, 0, i2s1, 0);
AudioConnection patchCord7(float2Int_l, 0, i2s1, 1);
#else
AudioConnection patchCord4(queue_r, peak_r);
AudioConnection patchCord5(queue_l, peak_l);
AudioConnection patchCord6(queue_r, 0, i2s1, 0);
AudioConnection patchCord7(queue_l, 0, i2s1, 1);
#endif
AudioControlSGTL5000 sgtl5000_1; //xy=700,536
#else
AudioOutputPT8211 pt8211_1; //xy=1079,320
AudioAmplifier volume_r; //xy=818,370
AudioAmplifier volume_l; //xy=818,411
#ifdef USE_F32
AudioConnection patchCord4(float2Int_r, volume_r);
AudioConnection patchCord5(float2Int_l, volume_l);
#else
AudioConnection patchCord4(queue_r, volume_r);
AudioConnection patchCord5(queue_l, volume_l);
#endif
AudioConnection patchCord6(volume_r, peak_r);
AudioConnection patchCord7(volume_l, peak_l);
AudioConnection patchCord8(volume_r, 0, pt8211_1, 1);
@ -91,6 +118,7 @@ uint8_t midi_channel = DEFAULT_MIDI_CHANNEL;
uint32_t xrun = 0;
uint32_t overload = 0;
uint32_t peak = 0;
uint32_t audio_buffer_problem = 0;
uint16_t render_time_max = 0;
float vol = VOLUME;
float vol_right = 1.0;
@ -173,7 +201,9 @@ void setup()
// start audio card
AudioMemory(AUDIO_MEM);
#ifdef USE_F32
AudioMemory_F32(AUDIO_MEM_F32);
#endif
#ifdef TEENSY_AUDIO_BOARD
sgtl5000_1.enable();
@ -185,7 +215,8 @@ void setup()
sgtl5000_1.volume(1.0, 1.0);
#endif
set_volume(vol, vol_left, vol_right);
//set_volume(vol, vol_left, vol_right);
set_volume(1.0, 1.0, 1.0);
#if defined (DEBUG) && defined (SHOW_CPU_LOAD_MSEC)
// Initialize processor and memory measurements
@ -215,10 +246,14 @@ void setup()
// DECAY,RELEASE,HARDNESS,TREBLE,PAN_TREM,LFO_RATE,VELOCITY_SENSE,STEREO,MAX_POLY,TUNE,DETUNE,OVERDRIVE
#if defined(USE_F32) && defined(USE_COMP_F32)
// setup compressor as limiter
setup_compressor(true, -15.0f, 5.0f, 0.005f, 0.200f);
// setup compressor like an automatic volume control
//setup_compressor(true,-50.0,5.0,1.0,2.0);
comp_r.setPreGain_dB(0.0);
comp_l.setPreGain_dB(0.0);
#endif
Serial.println(F("<setup end>"));
@ -230,8 +265,13 @@ void setup()
void loop()
{
#if defined(USE_F32)
float* audio_buffer_r; // pointer to AUDIO_BLOCK_SAMPLES * sizeof(float)
float* audio_buffer_l; // pointer to AUDIO_BLOCK_SAMPLES * sizeof(float)
#else
int16_t* audio_buffer_r; // pointer to AUDIO_BLOCK_SAMPLES * sizeof(int16_t)
int16_t* audio_buffer_l; // pointer to AUDIO_BLOCK_SAMPLES * sizeof(int16_t)
#endif
const uint16_t audio_block_time_ms = 1000000 / (SAMPLE_RATE / AUDIO_BLOCK_SAMPLES);
// Main sound calculation
@ -239,9 +279,6 @@ void loop()
{
fill_audio_buffer = 0;
audio_buffer_r = queue_r.getBuffer();
audio_buffer_l = queue_l.getBuffer();
#if defined (DEBUG) && defined (SHOW_CPU_LOAD_MSEC)
if (cpu_mem_millis > SHOW_CPU_LOAD_MSEC)
{
@ -289,10 +326,15 @@ void loop()
queue_r.playBuffer();
queue_l.playBuffer();
}
else
{
audio_buffer_problem++;
}
handle_input();
}
#if defined(USE_F32) && defined(USE_COMP_F32)
void setup_compressor(boolean use_HP_filter, float knee_dBFS, float comp_ratio, float attack_sec, float release_sec)
{
comp_r.enableHPFilter(use_HP_filter); comp_l.enableHPFilter(use_HP_filter);
@ -303,6 +345,7 @@ void setup_compressor(boolean use_HP_filter, float knee_dBFS, float comp_ratio,
comp_r.setAttack_sec(attack_sec, fs_Hz); comp_l.setAttack_sec(attack_sec, fs_Hz);
comp_r.setRelease_sec(release_sec, fs_Hz); comp_l.setRelease_sec(release_sec, fs_Hz);
}
#endif
void handle_input(void)
{
@ -536,6 +579,8 @@ void show_cpu_and_mem_usage(void)
Serial.print(overload, DEC);
Serial.print(F(" PEAK: "));
Serial.print(peak, DEC);
Serial.print(F(" AUDIO_BUF_ERR: "));
Serial.print(audio_buffer_problem, DEC);
Serial.println();
AudioProcessorUsageMaxReset();
AudioMemoryUsageMaxReset();

@ -31,12 +31,12 @@
//#define TEENSY_AUDIO_BOARD 1
#define VOLUME 0.8
#define DEFAULT_MIDI_CHANNEL MIDI_CHANNEL_OMNI
#define AUDIO_MEM 300
#define AUDIO_MEM_F32 10
#define AUDIO_MEM 16
#define AUDIO_MEM_F32 16
#define SAMPLE_RATE 44100
#define REDUCE_LOUDNESS 0
#define REDUCE_LOUDNESS 1
#define USE_XFADE_DATA 1
//#define USE_COMP_F32 1
#if !defined(__MK66FX1M0__) // check for Teensy-3.6
#undef USE_ONBOARD_USB_HOST
#define NVOICES 32

@ -3,7 +3,7 @@
MicroMDAEPiano is a port of the MDA-EPiano sound engine
(https://sourceforge.net/projects/mda-vst/) for the Teensy-3.5/3.6 with audio shield.
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 3 of the License, or
@ -49,7 +49,7 @@ mdaEPiano::mdaEPiano() // mdaEPiano::mdaEPiano(audioMasterCallback audioMaster)
fillpatch(i++, "(default)", 0.500f, 0.500f, 0.500f, 0.500f, 0.500f, 0.650f, 0.250f, 0.500f, 0.50f, 0.500f, 0.146f, 0.000f);
setProgram(0);
}
waves = (short*)epianoDataXfade;
//Waveform data and keymapping
@ -194,7 +194,11 @@ float mdaEPiano::getParameter(int32_t index) {
return programs[curProgram].param[index];
}
void mdaEPiano::process(float *outputs_r, float *outputs_l)
#ifdef USE_F32
void mdaEPiano::process(float* outputs_r, float* outputs_l)
#else
void mdaEPiano::process(int16_t* outputs_r, int16_t* outputs_l)
#endif
{
int16_t v;
float x, l, r, od = overdrive;
@ -223,7 +227,7 @@ void mdaEPiano::process(float *outputs_r, float *outputs_l)
}
l += V->outl * x;
r += V->outr * x;
V++;
}
@ -237,8 +241,13 @@ void mdaEPiano::process(float *outputs_r, float *outputs_l)
l += l * lmod * lfo1;
r += r * rmod * lfo1; //worth making all these local variables?
#ifdef USE_F32
outputs_l[frame] += l;
outputs_r[frame] += r;
#else
outputs_l[frame] = static_cast<int16_t>(l * 0x7fff) >> REDUCE_LOUDNESS;
outputs_r[frame] = static_cast<int16_t>(r * 0x7fff) >> REDUCE_LOUDNESS;
#endif
}
if (fabs(tl) < 1.0e-10) tl = 0.0f; //anti-denormal

@ -3,7 +3,7 @@
MicroMDAEPiano is a port of the MDA-EPiano sound engine
(https://sourceforge.net/projects/mda-vst/) for the Teensy-3.5/3.6 with audio shield.
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 3 of the License, or
@ -37,10 +37,10 @@
class mdaEPianoProgram
{
friend class mdaEPiano;
private:
float param[NPARAMS];
char name[24];
friend class mdaEPiano;
private:
float param[NPARAMS];
char name[24];
};
struct VOICE //voice state
@ -50,7 +50,7 @@ struct VOICE //voice state
int32_t pos;
int32_t end;
int32_t loop;
float env; //envelope
float dec;
@ -75,46 +75,50 @@ struct KGRP //keygroup
class mdaEPiano //: public AudioEffectX
{
public:
mdaEPiano(); // mdaEPiano(audioMasterCallback audioMaster);
~mdaEPiano();
virtual void process(float *outputs_r, float *outputs_l);
virtual bool processMidiMessage(uint8_t type, uint8_t data1, uint8_t data2);
virtual void setProgram(int32_t program);
virtual void setParameter(int32_t index, float value);
virtual float getParameter(int32_t index);
virtual void resume();
int32_t guiUpdate;
void guiGetDisplay(int32_t index, char *label);
private:
void update(); //my parameter update
void noteOn(int32_t note, int32_t velocity);
void fillpatch(int32_t p, char *name, float p0, float p1, float p2, float p3, float p4,
float p5, float p6, float p7, float p8, float p9, float p10,float p11);
mdaEPianoProgram* programs;
float Fs, iFs;
#define EVENTBUFFER 120
#define EVENTS_DONE 99999999
int32_t notes[EVENTBUFFER + 8]; //list of delta|note|velocity for current block
///global internal variables
KGRP kgrp[34];
VOICE voice[NVOICES];
int32_t activevoices, poly;
short *waves;
float width;
int32_t size, sustain;
float lfo0, lfo1, dlfo, lmod, rmod;
float treb, tfrq, tl, tr;
float tune, fine, random, stretch, overdrive;
float muff, muffvel, sizevel, velsens, volume, modwhl;
uint8_t curProgram;
public:
mdaEPiano(); // mdaEPiano(audioMasterCallback audioMaster);
~mdaEPiano();
#ifdef USE_F32
virtual void process(float *outputs_r, float *outputs_l);
#else
virtual void process(int16_t *outputs_r, int16_t *outputs_l);
#endif
virtual bool processMidiMessage(uint8_t type, uint8_t data1, uint8_t data2);
virtual void setProgram(int32_t program);
virtual void setParameter(int32_t index, float value);
virtual float getParameter(int32_t index);
virtual void resume();
int32_t guiUpdate;
void guiGetDisplay(int32_t index, char *label);
private:
void update(); //my parameter update
void noteOn(int32_t note, int32_t velocity);
void fillpatch(int32_t p, char *name, float p0, float p1, float p2, float p3, float p4,
float p5, float p6, float p7, float p8, float p9, float p10, float p11);
mdaEPianoProgram* programs;
float Fs, iFs;
#define EVENTBUFFER 120
#define EVENTS_DONE 99999999
int32_t notes[EVENTBUFFER + 8]; //list of delta|note|velocity for current block
///global internal variables
KGRP kgrp[34];
VOICE voice[NVOICES];
int32_t activevoices, poly;
short *waves;
float width;
int32_t size, sustain;
float lfo0, lfo1, dlfo, lmod, rmod;
float treb, tfrq, tl, tr;
float tune, fine, random, stretch, overdrive;
float muff, muffvel, sizevel, velsens, volume, modwhl;
uint8_t curProgram;
};
#endif

Loading…
Cancel
Save