First test for sequencer-sync towards the audio interrupt.

pull/65/head
Holger Wirtz 3 years ago
parent e8772102b1
commit 09ff0cb755
  1. 30
      MicroDexed.ino
  2. 81
      sequencer.cpp
  3. 48
      sequencer.h
  4. 39
      sequencer_timer.cpp
  5. 27
      sequencer_timer.h

@ -36,6 +36,7 @@
#include "effect_modulated_delay.h"
#include "effect_stereo_mono.h"
#include "effect_mono_stereo.h"
#include "sequencer_timer.h"
#ifdef USE_PLATEREVERB
#include "effect_platervbstereo.h"
#else
@ -251,6 +252,9 @@ AudioConnection patchCord22(drum_mixer_l, 0, master_mixer_l, 2);
#endif
#endif
AudioSequencerTimer sequencer_timer;
AudioConnection patchCord25(reverb_mixer_r, sequencer_timer);
//
// Dynamic patching of MicroDexed objects
//
@ -400,6 +404,29 @@ extern LCDMenuLib2 LCDML;
extern void getNoteName(char* noteName, uint8_t noteNumber);
void testfunc(void)
{
static int8_t takt;
switch (takt % 4)
{
case 0:
Serial.println("EINS!");
break;
case 1:
Serial.println("ZWEI!");
break;
case 2:
Serial.println("DREI!");
break;
case 3:
Serial.println("VIER!");
takt = -1;
break;
}
takt++;
}
/***********************************************************************
SETUP
***********************************************************************/
@ -665,6 +692,9 @@ void setup()
audio_thru_mixer_l.gain(3, 0.0);
#endif
sequencer_timer.set_bpm(60);
sequencer_timer.step_function(&testfunc);
#ifdef DEBUG
Serial.println(F("<setup end>"));
#endif

@ -12,19 +12,22 @@ extern void handleNoteOff(byte , byte , byte );
extern void UI_func_sequencer(uint8_t);
extern const char* seq_find_shortname(uint8_t);
void sequencer(void)
{
if (seq_note_in > 0 && seq_note_in < 62 && seq_recording == false ) {
// handleNoteOff(configuration.dexed[0].midi_channel, seq_data[3][seq_step] + seq_transpose , 0);
// handleNoteOff(configuration.dexed[0].midi_channel, seq_data[3][seq_step - 1] + seq_transpose , 0);
// handleNoteOff(configuration.dexed[0].midi_channel, seq_data[3][seq_step] + seq_transpose , 0);
// handleNoteOff(configuration.dexed[0].midi_channel, seq_data[3][seq_step - 1] + seq_transpose , 0);
//if (seq_note_in>65)seq_note_in=seq_note_in-12;
//if (seq_note_in>65)seq_note_in=seq_note_in-12;
// seq_transpose = seq_note_in % 12 ;
// seq_transpose = seq_note_in % 12 ;
//seq_transpose=seq_transpose-12;
// seq_note_in = 0;
// seq_note_in = 0;
}
if (seq_millis_timer > seq_timer_previous + seq_tempo_ms)
@ -34,17 +37,17 @@ void sequencer(void)
if (LCDML.FUNC_getID() == LCDML.OTHER_getIDFromFunction(UI_func_sequencer)) {
//write to sequencer if in sequencer menu
//write to sequencer if in sequencer menu
if (seq_note_in > 0 && seq_recording == true) {
// if ( seq_content_type[ seq_patternchain[seq_chain_active_step][active_track] ] == 1) handleNoteOff(configuration.dexed[0].midi_channel, seq_data[active_track][seq_step] + seq_transpose , 0);
// if ( seq_content_type[ seq_patternchain[seq_chain_active_step][active_track] ] == 1) handleNoteOff(configuration.dexed[0].midi_channel, seq_data[active_track][seq_step] + seq_transpose , 0);
seq_data[seq_active_track][seq_step] = seq_note_in;
seq_vel[seq_active_track][seq_step] = seq_note_in_velocity;
seq_note_in = 0;
seq_note_in_velocity=0;
seq_note_in_velocity = 0;
}
lcd.setCursor(seq_step, 1);
lcd.setCursor(seq_step, 1);
lcd.print("X");
if (seq_step == 0) {
lcd.setCursor(15, 1);
@ -54,53 +57,53 @@ void sequencer(void)
{
lcd.setCursor(seq_step - 1, 1);
lcd.print(seq_find_shortname(seq_step - 1)[0]);
}
}
}
for (uint8_t d = 0; d < 4; d++)
{
if ( seq_track_type[d] == 0){// drum track
if (seq_data[ seq_patternchain[seq_chain_active_step][d] ][seq_step] > 0 && seq_vel[ seq_patternchain[seq_chain_active_step][d] ][seq_step] > 0)
{
handleNoteOn(DRUM_MIDI_CHANNEL, seq_data[ seq_patternchain[seq_chain_active_step][d] ][seq_step] , seq_vel[ seq_patternchain[seq_chain_active_step][d] ][seq_step]);
if ( seq_track_type[d] == 0) { // drum track
if (seq_data[ seq_patternchain[seq_chain_active_step][d] ][seq_step] > 0 && seq_vel[ seq_patternchain[seq_chain_active_step][d] ][seq_step] > 0)
{
handleNoteOn(DRUM_MIDI_CHANNEL, seq_data[ seq_patternchain[seq_chain_active_step][d] ][seq_step] , seq_vel[ seq_patternchain[seq_chain_active_step][d] ][seq_step]);
}
}
else {
if (seq_data[ seq_patternchain[seq_chain_active_step][d] ][seq_step] > 0 && seq_vel[ seq_patternchain[seq_chain_active_step][d] ][seq_step] > 0) // instrument track
{
handleNoteOn(configuration.dexed[0].midi_channel, seq_data[ seq_patternchain[seq_chain_active_step][d] ][seq_step] + seq_transpose , seq_vel[ seq_patternchain[seq_chain_active_step][d] ][seq_step]);
seq_prev_note[d] = seq_data[ seq_patternchain[seq_chain_active_step][d] ][seq_step] + seq_transpose;
}
}
seq_noteoffsent[d] = false;
}
else {
if (seq_data[ seq_patternchain[seq_chain_active_step][d] ][seq_step] > 0 && seq_vel[ seq_patternchain[seq_chain_active_step][d] ][seq_step] > 0) // instrument track
{
handleNoteOn(configuration.dexed[0].midi_channel, seq_data[ seq_patternchain[seq_chain_active_step][d] ][seq_step] + seq_transpose , seq_vel[ seq_patternchain[seq_chain_active_step][d] ][seq_step]);
seq_prev_note[d]=seq_data[ seq_patternchain[seq_chain_active_step][d] ][seq_step] + seq_transpose;
}
}
seq_noteoffsent[d] = false;
}
seq_step++;
if (seq_step > 15) {
seq_step = 0;
if (seq_chain_lenght>0){
seq_chain_active_step++;
if (seq_chain_active_step>seq_chain_lenght)
{
seq_chain_active_step=0;
}
}
if (seq_chain_lenght > 0) {
seq_chain_active_step++;
if (seq_chain_active_step > seq_chain_lenght)
{
seq_chain_active_step = 0;
}
}
}
}
if (seq_millis_timer > seq_timer_previous + 80 )
{
for (uint8_t d = 0; d < 4; d++)
for (uint8_t d = 0; d < 4; d++)
{
if( seq_noteoffsent[d] == false) {
if ( seq_noteoffsent[d] == false) {
if ( seq_prev_note[d] > 0) //test instrument sequencer Instance=0
{
handleNoteOff(configuration.dexed[0].midi_channel, seq_prev_note[d] , 0);
}
}
seq_noteoffsent[d] = true;
}
}
}
seq_noteoffsent[d] = true;
}
}
}

@ -2,7 +2,7 @@
uint8_t seq_active_track = 0;
uint8_t seq_menu;
bool seq_button_r = false;
bool seq_noteoffsent[4] = {false,false,false,false};
bool seq_noteoffsent[4] = {false, false, false, false};
elapsedMillis seq_millis_timer;
uint8_t seq_step = 0;
uint32_t seq_timer_previous = 0;
@ -11,39 +11,39 @@ bool seq_recording = false;
uint8_t seq_note_in;
uint8_t seq_note_in_velocity;
int seq_transpose;
int seq_tempo_ms=147;
int seq_bpm=102;
int seq_tempo_ms = 147;
int seq_bpm = 102;
uint8_t seq_temp_select_menu;
uint8_t seq_temp_active_menu = 99;
uint8_t seq_chain_active_chainstep;
uint8_t seq_chain_lenght = 3; // 0=16 steps, 1=32 Steps, 2=46 Steps, 3=64 Steps
uint8_t seq_chain_active_step = 0;
uint8_t seq_prev_note[4]; // note_offs for every (instr.) track
uint8_t seq_data[10][16] = {72 ,0 ,0 ,0 ,72 ,0 ,0 ,0 ,72 ,0 ,0 ,0 ,72 ,0 ,0 ,0 ,
78 ,78 ,78 ,78 ,78 ,78 ,78 ,78 ,78 ,78 ,78 ,78 ,78 ,78 ,78 ,78 ,
72 ,0 ,0 ,0 ,72 ,0 ,0 ,0 ,72 ,0 ,0 ,75 ,72 ,0 ,0 ,0 ,
60 ,61 ,62 ,63 ,64 ,65 ,66 ,0 ,0 ,0 ,0 ,0 ,0 ,0 ,0 ,0 ,
0 ,0 ,0 ,0 ,0 ,0 ,0 ,0 ,0 ,0 ,0 ,0 ,0 ,0 ,0 ,0 ,
55 ,0 ,0 ,0 ,0 ,0 ,52 ,0 ,0 ,0 ,0 ,0 ,0 ,0 ,0 ,0 ,
57 ,0 ,0 ,0 ,0 ,0 ,53 ,0 ,0 ,0 ,0 ,0 ,0 ,0 ,0 ,0 ,
74 ,0 ,0 ,72 ,0 ,0 ,74 ,0 ,0 ,0 ,76 ,0 ,0 ,0 ,0 ,0 ,
74 ,0 ,0 ,72 ,0 ,0 ,71 ,0 ,0 ,0 ,67 ,0 ,0 ,0 ,0 ,0 ,
69 ,0 ,0 ,76 ,0 ,0 ,69 ,0 ,0 ,0 ,0 ,0 ,0 ,0 ,0 ,0
uint8_t seq_data[10][16] = {72 , 0 , 0 , 0 , 72 , 0 , 0 , 0 , 72 , 0 , 0 , 0 , 72 , 0 , 0 , 0 ,
78 , 78 , 78 , 78 , 78 , 78 , 78 , 78 , 78 , 78 , 78 , 78 , 78 , 78 , 78 , 78 ,
72 , 0 , 0 , 0 , 72 , 0 , 0 , 0 , 72 , 0 , 0 , 75 , 72 , 0 , 0 , 0 ,
60 , 61 , 62 , 63 , 64 , 65 , 66 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 ,
0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 ,
55 , 0 , 0 , 0 , 0 , 0 , 52 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 ,
57 , 0 , 0 , 0 , 0 , 0 , 53 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 ,
74 , 0 , 0 , 72 , 0 , 0 , 74 , 0 , 0 , 0 , 76 , 0 , 0 , 0 , 0 , 0 ,
74 , 0 , 0 , 72 , 0 , 0 , 71 , 0 , 0 , 0 , 67 , 0 , 0 , 0 , 0 , 0 ,
69 , 0 , 0 , 76 , 0 , 0 , 69 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0
};
uint8_t seq_vel[10][16] = {120 ,0 ,0 ,0 ,120 ,0 ,0 ,0 ,120 ,0 ,0 ,0 ,120 ,0 ,0 ,0 ,
125 ,101 ,125 ,125 ,126 ,98 ,126 ,99 ,126 ,97 ,126 ,100 ,126 ,99 ,125 ,100 ,
120 ,0 ,0 ,0 ,120 ,0 ,0 ,0 ,120 ,0 ,120 ,120 ,120 ,120 ,0 ,0 ,
0 ,0 ,0 ,0 ,0 ,0 ,0 ,0 ,0 ,0 ,0 ,0 ,0 ,0 ,0 ,0 ,
0 ,0 ,0 ,0 ,0 ,0 ,0 ,0 ,0 ,0 ,0 ,0 ,0 ,0 ,0 ,0 ,
125 ,0 ,0 ,0 ,0 ,0 ,126 ,0 ,0 ,0 ,0 ,0 ,0 ,0 ,0 ,0 ,
78 ,120 ,0 ,0 ,0 ,0 ,84 ,120 ,0 ,0 ,0 ,0 ,0 ,0 ,0 ,0 ,
98 ,120 ,0 ,88 ,120 ,0 ,127 ,120 ,0 ,0 ,125 ,120 ,0 ,0 ,
0 ,0 ,124 ,120 ,0 ,115 ,0 ,0 ,126 ,120 ,0 ,120 ,127 ,120 ,0 ,0 ,
0 ,0 ,123 ,120 ,0 ,110 ,120 ,0 ,90 ,120 ,0 ,0 ,0 ,0 ,0 ,0 ,0 ,0
uint8_t seq_vel[10][16] = {120 , 0 , 0 , 0 , 120 , 0 , 0 , 0 , 120 , 0 , 0 , 0 , 120 , 0 , 0 , 0 ,
125 , 101 , 125 , 125 , 126 , 98 , 126 , 99 , 126 , 97 , 126 , 100 , 126 , 99 , 125 , 100 ,
120 , 0 , 0 , 0 , 120 , 0 , 0 , 0 , 120 , 0 , 120 , 120 , 120 , 120 , 0 , 0 ,
0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 ,
0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 ,
125 , 0 , 0 , 0 , 0 , 0 , 126 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 ,
78 , 120 , 0 , 0 , 0 , 0 , 84 , 120 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0 ,
98 , 120 , 0 , 88 , 120 , 0 , 127 , 120 , 0 , 0 , 125 , 120 , 0 , 0 ,
0 , 0 , 124 , 120 , 0 , 115 , 0 , 0 , 126 , 120 , 0 , 120 , 127 , 120 , 0 , 0 ,
0 , 0 , 123 , 120 , 0 , 110 , 120 , 0 , 90 , 120 , 0 , 0 , 0 , 0 , 0 , 0 , 0 , 0
};
uint8_t seq_patternchain[4][4] = { 0 ,1 ,6 ,9 ,0 ,1 ,5 ,8 ,0 ,1 ,6 ,9 ,2 ,1 ,5 ,7
uint8_t seq_patternchain[4][4] = { 0 , 1 , 6 , 9 , 0 , 1 , 5 , 8 , 0 , 1 , 6 , 9 , 2 , 1 , 5 , 7
};
uint8_t seq_content_type[10] = { 0, 0, 0, 0 , 1, 1, 1 , 1 , 1 , 1 }; // 0 = track is Drumtrack, 1= Instrumenttrack
uint8_t seq_track_type[4] = { 0, 0, 1, 1 }; // 0 = track is Drumtrack, 1= Instrumenttrack

@ -0,0 +1,39 @@
#include <Audio.h>
#include "config.h"
#include "sequencer_timer.h"
void AudioSequencerTimer::update(void)
{
audio_block_t *in;
in = receiveReadOnly(0);
if (in)
release(in);
tick++;
if (tick >= float(beat)*float(bpm) + 0.5)
{
if (sequencer_step_function != NULL)
(*sequencer_step_function)();
tick = 0;
}
}
uint32_t AudioSequencerTimer::get_tick(void)
{
return (tick);
}
void AudioSequencerTimer::set_bpm(uint8_t b)
{
bpm = b;
}
void AudioSequencerTimer::step_function(void(*func)())
{
if (func != NULL)
sequencer_step_function = func;
else
sequencer_step_function = NULL;
}

@ -0,0 +1,27 @@
#ifndef _SEQUENCER_TIMER_H_
#define _SEQUENCER_TIMER_H_
class AudioSequencerTimer : public AudioStream
{
public:
AudioSequencerTimer(void):
AudioStream(1, inputQueueArray)
{
tick = 0;
bpm = 60;
sequencer_step_function = NULL;
}
virtual uint32_t get_tick(void);
virtual void set_bpm(uint8_t b);
virtual void step_function(void(*func)());
virtual void update(void);
private:
audio_block_t *inputQueueArray[1];
uint8_t bpm;
void (*sequencer_step_function)();
volatile uint32_t tick;
const float beat = AUDIO_SAMPLE_RATE_EXACT / float(AUDIO_BLOCK_SAMPLES) / 60.0;
};
#endif
Loading…
Cancel
Save