Browse Source

namespacing, introduce globals.hh,

instr_abstract.hh
replace using namespace with ns aliases, etc..
main
heck 7 months ago
parent
commit
6dc14634b5
  1. 34
      src/globals.hh
  2. 28
      src/instr_abstract.hh
  3. 14
      src/instr_fm.cc
  4. 7
      src/instr_fm.hh
  5. 18
      src/instr_kick.cc
  6. 8
      src/instr_kick.hh
  7. 9
      src/instr_noise.cc
  8. 8
      src/instr_noise.hh
  9. 157
      src/main_perkons.cc
  10. 21
      src/perkons_instrument_interface.hh
  11. 19
      src/types.hh
  12. 2
      src/utils.hh

34
src/globals.hh

@ -0,0 +1,34 @@
#ifndef HECK_DAISY_GLOBALS_HH
#define HECK_DAISY_GLOBALS_HH
#include <cstdint>
namespace Constants {
constexpr int BUFFERSIZE = 4;
constexpr int SAMPLERATE = 48000;
constexpr int TRACK_COUNT = 4;
namespace MIDI_Mapping {
constexpr int TRACK_PITCH = 70;
constexpr int TRACK_DECAY = 71;
constexpr int TRACK_PARAM1 = 72;
constexpr int TRACK_PARAM2 = 73;
constexpr int TRACK_FILTER = 74;
constexpr int TRACK_DRIVE = 75;
constexpr int TRACK_VOLUME = 76;
} // namespace MIDI_Mapping
} // namespace Constants
// Types
using u8 = uint8_t;
using u16 = uint16_t;
using u32 = uint32_t;
using u64 = uint64_t;
using i8 = int8_t;
using i16 = int16_t;
using i32 = int32_t;
using i64 = int64_t;
using f32 = float;
using f64 = double;
#endif

28
src/instr_abstract.hh

@ -0,0 +1,28 @@
#ifndef HECK_DAISY_PERKONS_INSTR_ABSTRACT
#define HECK_DAISY_PERKONS_INSTR_ABSTRACT
#include "globals.hh"
namespace Heck {
namespace Instrument {
int samplerate = Constants::SAMPLERATE;
class AbstractInstrument {
public:
virtual void trigger() = 0;
// ctl-nr must be 0-3
// val must be 0-1
virtual void ctl(unsigned int ctl_nr, float val) = 0;
// pos must be either 0,1,2
virtual void switch_mode(unsigned int pos) = 0;
virtual void switch_variation(unsigned int pos) = 0;
virtual float nextsample() = 0;
private:
};
} // namespace Instruments
} // namespace Heck
#endif // HECK_DAISY_PERKONS_INSTR_ABSTRACT

14
src/instr_fm.cc

@ -1,13 +1,10 @@
#include "instr_fm.hh" #include "instr_fm.hh"
#include "daisysp.h" #include "daisysp.h"
using namespace daisysp;
namespace Heck { namespace Heck {
namespace Instrument { namespace Instrument {
void FM::init(float samplerate) void FM::init()
{ {
osc.Init(samplerate); osc.Init(samplerate);
osc.SetFrequency(100); osc.SetFrequency(100);
@ -15,17 +12,15 @@ namespace Heck {
osc.SetIndex(0.); osc.SetIndex(0.);
volEnv.Init(samplerate); volEnv.Init(samplerate);
volEnv.SetTime(ADENV_SEG_ATTACK, .0001); volEnv.SetTime(dsp::ADENV_SEG_ATTACK, .0001);
volEnv.SetTime(ADENV_SEG_DECAY, 1.); volEnv.SetTime(dsp::ADENV_SEG_DECAY, 1.);
volEnv.SetMax(1); volEnv.SetMax(1);
volEnv.SetMin(0); volEnv.SetMin(0);
} }
void FM::trigger() void FM::trigger()
{ {
volEnv.Trigger(); volEnv.Trigger();
return;
} }
void FM::ctl(unsigned int ctl_nr, float val) void FM::ctl(unsigned int ctl_nr, float val)
@ -35,7 +30,7 @@ namespace Heck {
osc.SetFrequency(val * 200.); osc.SetFrequency(val * 200.);
break; break;
case 1: case 1:
volEnv.SetTime(ADENV_SEG_DECAY, val * 2.); volEnv.SetTime(dsp::ADENV_SEG_DECAY, val * 2.);
break; break;
case 2: case 2:
osc.SetRatio(val * 1.); osc.SetRatio(val * 1.);
@ -52,7 +47,6 @@ namespace Heck {
void FM::switch_mode(unsigned int pos) {} void FM::switch_mode(unsigned int pos) {}
void FM::switch_variation(unsigned int pos) {} void FM::switch_variation(unsigned int pos) {}
void FM::switch_filter(unsigned int pos) {}
float FM::nextsample() float FM::nextsample()
{ {

7
src/instr_fm.hh

@ -1,7 +1,7 @@
#ifndef HECK_DAISY_INSTR_FM_HH #ifndef HECK_DAISY_INSTR_FM_HH
#define HECK_DAISY_INSTR_FM_HH #define HECK_DAISY_INSTR_FM_HH
#include "perkons_instrument_interface.hh" #include "instr_abstract.hh"
#include "daisy_seed.h" #include "daisy_seed.h"
#include "daisysp.h" #include "daisysp.h"
@ -11,15 +11,14 @@ namespace dsp = daisysp;
namespace Heck { namespace Heck {
namespace Instrument { namespace Instrument {
class FM : public PerkonsInstrumentInterface { class FM : public AbstractInstrument {
public: public:
void init(float samplerate); void init();
void trigger() override; void trigger() override;
void ctl(unsigned int ctl_nr, float val) override; void ctl(unsigned int ctl_nr, float val) override;
void switch_mode(unsigned int pos) override; void switch_mode(unsigned int pos) override;
void switch_variation(unsigned int pos) override; void switch_variation(unsigned int pos) override;
void switch_filter(unsigned int pos) override;
float nextsample() override; float nextsample() override;

18
src/instr_kick.cc

@ -1,44 +1,38 @@
#include "instr_kick.hh" #include "instr_kick.hh"
#include "daisysp.h" #include "daisysp.h"
using namespace daisysp;
namespace Heck { namespace Heck {
namespace Instrument { namespace Instrument {
void Kick::init(float samplerate) void Kick::init()
{ {
osc.Init(samplerate); osc.Init(samplerate);
osc.SetWaveform(Oscillator::WAVE_TRI); osc.SetWaveform(dsp::Oscillator::WAVE_TRI);
osc.SetAmp(1); osc.SetAmp(1);
pitchEnv.Init(samplerate); pitchEnv.Init(samplerate);
pitchEnv.SetTime(ADENV_SEG_ATTACK, .001); pitchEnv.SetTime(dsp::ADENV_SEG_ATTACK, .001);
pitchEnv.SetTime(ADENV_SEG_DECAY, .01); pitchEnv.SetTime(dsp::ADENV_SEG_DECAY, .01);
pitchEnv.SetMax(250); pitchEnv.SetMax(250);
pitchEnv.SetMin(20); pitchEnv.SetMin(20);
volEnv.Init(samplerate); volEnv.Init(samplerate);
volEnv.SetTime(ADENV_SEG_ATTACK, .0001); volEnv.SetTime(dsp::ADENV_SEG_ATTACK, .0001);
volEnv.SetTime(ADENV_SEG_DECAY, 0.1); volEnv.SetTime(dsp::ADENV_SEG_DECAY, 0.1);
volEnv.SetMax(1); volEnv.SetMax(1);
volEnv.SetMin(0); volEnv.SetMin(0);
} }
void Kick::trigger() void Kick::trigger()
{ {
volEnv.Trigger(); volEnv.Trigger();
pitchEnv.Trigger(); pitchEnv.Trigger();
return;
} }
void Kick::ctl(unsigned int ctl_nr, float val) {} void Kick::ctl(unsigned int ctl_nr, float val) {}
void Kick::switch_mode(unsigned int pos) {} void Kick::switch_mode(unsigned int pos) {}
void Kick::switch_variation(unsigned int pos) {} void Kick::switch_variation(unsigned int pos) {}
void Kick::switch_filter(unsigned int pos) {}
float Kick::nextsample() float Kick::nextsample()
{ {

8
src/instr_kick.hh

@ -1,7 +1,7 @@
#ifndef HECK_DAISY_INSTR_KICK_HH #ifndef HECK_DAISY_INSTR_KICK_HH
#define HECK_DAISY_INSTR_KICK_HH #define HECK_DAISY_INSTR_KICK_HH
#include "perkons_instrument_interface.hh" #include "instr_abstract.hh"
#include "daisy_seed.h" #include "daisy_seed.h"
#include "daisysp.h" #include "daisysp.h"
@ -11,18 +11,16 @@ namespace dsp = daisysp;
namespace Heck { namespace Heck {
namespace Instrument { namespace Instrument {
class Kick : public PerkonsInstrumentInterface { class Kick : public AbstractInstrument {
public: public:
void init(float samplerate); void init();
void trigger() override; void trigger() override;
void ctl(unsigned int ctl_nr, float val) override; void ctl(unsigned int ctl_nr, float val) override;
void switch_mode(unsigned int pos) override; void switch_mode(unsigned int pos) override;
void switch_variation(unsigned int pos) override; void switch_variation(unsigned int pos) override;
void switch_filter(unsigned int pos) override;
float nextsample() override; float nextsample() override;
private: private:
dsp::Oscillator osc; dsp::Oscillator osc;
dsp::AdEnv volEnv; dsp::AdEnv volEnv;

9
src/instr_noise.cc

@ -1,18 +1,16 @@
#include "instr_noise.hh" #include "instr_noise.hh"
#include "daisysp.h" #include "daisysp.h"
using namespace daisysp;
namespace Heck { namespace Heck {
namespace Instrument { namespace Instrument {
void Noise::init(float samplerate) void Noise::init()
{ {
noise.Init(); noise.Init();
env.Init(samplerate); env.Init(samplerate);
env.SetTime(ADENV_SEG_ATTACK, .0001); env.SetTime(dsp::ADENV_SEG_ATTACK, .0001);
env.SetTime(ADENV_SEG_DECAY, .01); env.SetTime(dsp::ADENV_SEG_DECAY, .01);
env.SetMax(1); env.SetMax(1);
env.SetMin(0); env.SetMin(0);
} }
@ -25,7 +23,6 @@ namespace Heck {
void Noise::ctl(unsigned int ctl_nr, float val) {} void Noise::ctl(unsigned int ctl_nr, float val) {}
void Noise::switch_mode(unsigned int pos) {} void Noise::switch_mode(unsigned int pos) {}
void Noise::switch_variation(unsigned int pos) {} void Noise::switch_variation(unsigned int pos) {}
void Noise::switch_filter(unsigned int pos) {}
float Noise::nextsample() float Noise::nextsample()
{ {

8
src/instr_noise.hh

@ -1,7 +1,7 @@
#ifndef HECK_DAISY_INSTR_NOISE_HH #ifndef HECK_DAISY_INSTR_NOISE_HH
#define HECK_DAISY_INSTR_NOISE_HH #define HECK_DAISY_INSTR_NOISE_HH
#include "perkons_instrument_interface.hh" #include "instr_abstract.hh"
#include "daisy_seed.h" #include "daisy_seed.h"
#include "daisysp.h" #include "daisysp.h"
@ -11,18 +11,16 @@ namespace dsp = daisysp;
namespace Heck { namespace Heck {
namespace Instrument { namespace Instrument {
class Noise : public PerkonsInstrumentInterface { class Noise : public AbstractInstrument {
public: public:
void init(float samplerate); void init();
void trigger() override; void trigger() override;
void ctl(unsigned int ctl_nr, float val) override; void ctl(unsigned int ctl_nr, float val) override;
void switch_mode(unsigned int pos) override; void switch_mode(unsigned int pos) override;
void switch_variation(unsigned int pos) override; void switch_variation(unsigned int pos) override;
void switch_filter(unsigned int pos) override;
float nextsample() override; float nextsample() override;
private: private:
dsp::WhiteNoise noise; dsp::WhiteNoise noise;
dsp::AdEnv env; dsp::AdEnv env;

157
src/main_perkons.cc

@ -1,42 +1,86 @@
// Hecks perkons extension // Hecks perkons extension
#include <map>
#include <array> #include <array>
#include <memory> #include <memory>
#include "daisy_seed.h" #include "daisy_seed.h"
#include "daisysp.h" #include "daisysp.h"
#include "types.hh" #include "globals.hh"
#include "utils.hh" #include "utils.hh"
#include "perkons_instrument_interface.hh" #include "instr_abstract.hh"
#include "instr_kick.hh" #include "instr_kick.hh"
#include "instr_noise.hh" #include "instr_noise.hh"
#include "instr_fm.hh" #include "instr_fm.hh"
#define TRACK_COUNT 4 namespace ld = daisy;
namespace dsp = daisysp;
namespace Heck { namespace Heck {
// ============================================================================================= // =============================================================================================
// INIT // INIT
// ============================================================================================= // =============================================================================================
using namespace daisy;
using namespace daisysp;
static DaisySeed hw{}; static ld::DaisySeed hw{};
static MidiUartHandler midi{}; static ld::MidiUartHandler midi{};
static FIFO<MidiEvent, 128> event_log{}; static ld::FIFO<ld::MidiEvent, 128> event_log{};
Instrument::Noise instrument0{}; Instrument::Noise instrument0{};
Instrument::FM instrument1{}; Instrument::FM instrument1{};
Instrument::FM instrument2{}; Instrument::FM instrument2{};
Instrument::Kick instrument3{}; Instrument::Kick instrument3{};
std::array<std::shared_ptr<PerkonsInstrumentInterface>, TRACK_COUNT> tracks{}; struct Track {
public:
void init(Instrument::AbstractInstrument& instrument)
{
instrument_.reset(&instrument);
ctl_volume_ = 1.;
// filter_.Init();
}
float nextsample()
{
float sig = instrument_->nextsample();
sig = vca_(sig, ctl_volume_);
// sig = filter_.Low();
return sig;
}
void trigger()
{
instrument_->trigger();
}
void volume(float vol)
{
ctl_volume_ = vol;
}
void filter(float freq)
{
filter_.SetFreq(freq);
}
void drive(float amt)
{
filter_.SetDrive(amt);
}
private:
std::shared_ptr<Instrument::AbstractInstrument> instrument_{};
dsp::LinearVCA vca_{};
dsp::Svf filter_{};
float ctl_volume_{};
};
std::array<Track, Constants::TRACK_COUNT> tracks;
// function prototypes // function prototypes
int create_tracks(float samplerate); int create_tracks();
void AudioCallback( void AudioCallback(
AudioHandle::InterleavingInputBuffer in, ld::AudioHandle::InterleavingInputBuffer in,
AudioHandle::InterleavingOutputBuffer out, ld::AudioHandle::InterleavingOutputBuffer out,
size_t size); size_t size);
@ -50,11 +94,35 @@ namespace Heck {
hw.StartLog(true); hw.StartLog(true);
// Start Audio // Start Audio
hw.SetAudioBlockSize(4); hw.PrintLine("Setting Blocksize: %i", Constants::BUFFERSIZE);
float samplerate = hw.AudioSampleRate(); hw.SetAudioBlockSize(Constants::BUFFERSIZE);
hw.PrintLine("Setting Samplerate: %i", Constants::SAMPLERATE);
switch (Constants::SAMPLERATE) {
case 8000:
hw.SetAudioSampleRate(daisy::SaiHandle::Config::SampleRate::SAI_8KHZ);
break;
case 16000:
hw.SetAudioSampleRate(daisy::SaiHandle::Config::SampleRate::SAI_16KHZ);
break;
case 32000:
hw.SetAudioSampleRate(daisy::SaiHandle::Config::SampleRate::SAI_32KHZ);
break;
case 48000:
hw.SetAudioSampleRate(daisy::SaiHandle::Config::SampleRate::SAI_48KHZ);
break;
case 96000:
hw.SetAudioSampleRate(daisy::SaiHandle::Config::SampleRate::SAI_48KHZ);
break;
default:
hw.PrintLine("Samplerate not supported, fallback to 48000");
hw.SetAudioSampleRate(daisy::SaiHandle::Config::SampleRate::SAI_48KHZ);
break;
}
hw.PrintLine("Creating Tracks"); hw.PrintLine("Creating Tracks");
create_tracks(samplerate); create_tracks();
hw.PrintLine("Starting Audio"); hw.PrintLine("Starting Audio");
hw.StartAudio(AudioCallback); hw.StartAudio(AudioCallback);
@ -62,11 +130,11 @@ namespace Heck {
// MIDI RX // MIDI RX
hw.PrintLine("Setting up MIDI"); hw.PrintLine("Setting up MIDI");
MidiUartHandler::Config midi_config; ld::MidiUartHandler::Config midi_config;
midi.Init(midi_config); midi.Init(midi_config);
u32 systick_last_rt_msg{}; u32 systick_last_rt_msg{};
midi.realtime_callback = [&systick_last_rt_msg](MidiEvent& msg) { midi.realtime_callback = [&systick_last_rt_msg](ld::MidiEvent& msg) {
u32 systick_now = System::GetNow(); u32 systick_now = ld::System::GetNow();
u32 systick_since_last = systick_now - systick_last_rt_msg; u32 systick_since_last = systick_now - systick_last_rt_msg;
systick_last_rt_msg = systick_now; systick_last_rt_msg = systick_now;
@ -90,17 +158,16 @@ namespace Heck {
hw.PrintLine("Entering MainLoop"); hw.PrintLine("Entering MainLoop");
} }
int create_tracks(float samplerate) int create_tracks()
{ {
instrument0.init(samplerate); instrument0.init();
tracks[0] = std::shared_ptr<PerkonsInstrumentInterface>(&instrument0); tracks[0].init(instrument0);
instrument1.init(samplerate); instrument1.init();
tracks[1] = std::shared_ptr<PerkonsInstrumentInterface>(&instrument1); tracks[1].init(instrument1);
instrument2.init(samplerate); instrument2.init();
tracks[2] = std::shared_ptr<PerkonsInstrumentInterface>(&instrument2); tracks[2].init(instrument2);
instrument3.init(samplerate); instrument3.init();
tracks[3] = std::shared_ptr<PerkonsInstrumentInterface>(&instrument3); tracks[3].init(instrument3);
return 0; return 0;
} }
@ -111,14 +178,14 @@ namespace Heck {
void AudioCallback( void AudioCallback(
AudioHandle::InterleavingInputBuffer in, ld::AudioHandle::InterleavingInputBuffer in,
AudioHandle::InterleavingOutputBuffer out, ld::AudioHandle::InterleavingOutputBuffer out,
size_t size) size_t size)
{ {
float sig_out{}; float sig_out{};
for (size_t i = 0; i < size; i += 2) { for (size_t i = 0; i < size; i += 2) {
for (int i = 0; i < TRACK_COUNT; i++) { for (int i = 0; i < Constants::TRACK_COUNT; i++) {
sig_out += tracks[i]->nextsample(); sig_out += tracks[i].nextsample();
} }
sig_out *= 0.1; sig_out *= 0.1;
@ -129,22 +196,30 @@ namespace Heck {
void mainloop() void mainloop()
{ {
u32 now = System::GetNow(); u32 now = ld::System::GetNow();
u32 log_time{}; u32 log_time{};
bool heartbeat_led_state{ false }; bool heartbeat_led_state{ false };
u32 heartbeat_time{}; u32 heartbeat_time{};
while (1) { while (1) {
now = System::GetNow(); now = ld::System::GetNow();
while (midi.HasEvents()) { while (midi.HasEvents()) {
MidiEvent msg = midi.PopEvent(); ld::MidiEvent msg = midi.PopEvent();
event_log.PushBack(msg); event_log.PushBack(msg);
if (msg.type == MidiMessageType::NoteOn) { if (msg.type == ld::MidiMessageType::NoteOn) {
if (msg.channel >= 0 && msg.channel < TRACK_COUNT) { if (msg.channel >= 0 && msg.channel < Constants::TRACK_COUNT) {
tracks[msg.channel]->trigger(); tracks[msg.channel].trigger();
}
} else if (msg.type == ld::MidiMessageType::ControlChange) {
ld::ControlChangeEvent cc = msg.AsControlChange();
switch (cc.control_number) {
case Constants::MIDI_Mapping::TRACK_VOLUME:
tracks[cc.channel].volume(cc.value);
break;
case Constants::MIDI_Mapping::TRACK_FILTER:
tracks[cc.channel].volume(cc.value);
break;
} }
} else if (msg.type == MidiMessageType::ControlChange) {
// ControlChangeEvent cc = msg.AsControlChange();
event_log.PushBack(msg); event_log.PushBack(msg);
} else { } else {
} }

21
src/perkons_instrument_interface.hh

@ -1,21 +0,0 @@
#ifndef HECK_DAISY_PERKONS_INSTRUMENT_INTERFACE
#define HECK_DAISY_PERKONS_INSTRUMENT_INTERFACE
class PerkonsInstrumentInterface {
public:
virtual void trigger() = 0;
// ctl-nr must be 0-5
// val must be 0-1
virtual void ctl(unsigned int ctl_nr, float val) = 0;
// pos must be either 0,1,2
virtual void switch_mode(unsigned int pos) = 0;
virtual void switch_variation(unsigned int pos) = 0;
virtual void switch_filter(unsigned int pos) = 0;
virtual float nextsample() = 0;
private:
};
#endif // HECK_DAISY_PERKONS_INSTRUMENT_INTERFACE

19
src/types.hh

@ -1,19 +0,0 @@
#ifndef HECK_DAISY_TYPES_HH
#define HECK_DAISY_TYPES_HH
#include <cstdint>
using u8 = uint8_t;
using u16 = uint16_t;
using u32 = uint32_t;
using u64 = uint64_t;
using i8 = int8_t;
using i16 = int16_t;
using i32 = int32_t;
using i64 = int64_t;
using f32 = float;
using f64 = double;
#endif

2
src/utils.hh

@ -2,7 +2,7 @@
#define HECK_DAISY_UTILS_HH #define HECK_DAISY_UTILS_HH
#include "daisy_seed.h" #include "daisy_seed.h"
#include "types.hh" #include "globals.hh"
void GetMidiTypeAsString(daisy::MidiEvent& msg, char* str); void GetMidiTypeAsString(daisy::MidiEvent& msg, char* str);
void GetMidiRTTypeAsString(daisy::MidiEvent& msg, char* str); void GetMidiRTTypeAsString(daisy::MidiEvent& msg, char* str);

Loading…
Cancel
Save