Fixing learning drum notes via MIDI.

dev
Holger Wirtz 1 year ago
parent c5b3a4df5a
commit 167f5b0162
  1. 116
      MicroDexed.ino
  2. 18
      UI.hpp
  3. 6
      config.h

@ -824,7 +824,7 @@ void handleNoteOn(byte inChannel, byte inNumber, byte inVelocity) {
//
// MIDI learn mode
//
if (midi_learn_mode != MIDI_LEARN_MODE_OFF) {
if (midi_learn_mode > MIDI_LEARN_MODE_OFF) {
int8_t tmp_channel = handle_midi_learn(inNumber);
if (tmp_channel >= 0)
inChannel = tmp_channel;
@ -890,19 +890,22 @@ void handleNoteOn(byte inChannel, byte inNumber, byte inVelocity) {
if (drum_counter >= NUM_DRUMS)
drum_counter = 0;
if (!(midi_learn_mode & 0x80)) {
if (midi_learn_mode > MIDI_LEARN_MODE_OFF) {
inNumber = configuration.drums.midinote[active_sample];
} else {
inNumber = midi_learn_mode & 0x7f;
midi_learn_mode = MIDI_LEARN_MODE_DRUM_NOTE;
}
#ifdef DEBUG
char note_name[4];
getNoteName(note_name, inNumber);
if (midi_learn_mode > MIDI_LEARN_MODE_OFF) {
if (midi_learn_mode & 0x80)
Serial.printf_P(PSTR("MIDI LEARN MODE DRUM (%s) for note (%s)\n"), byte_to_binary(midi_learn_mode), note_name);
else
Serial.printf_P(PSTR("MIDI LEARN MODE NOTE (%s) for note (%s)\n"), byte_to_binary(midi_learn_mode), note_name);
}
Serial.print(F("Triggring Drum["));
Serial.print(drum_counter, DEC);
Serial.print(F("]: with note "));
Serial.print(F("] with note "));
Serial.print(note_name);
Serial.print(F("/"));
Serial.println(inNumber, DEC);
@ -918,43 +921,45 @@ void handleNoteOn(byte inChannel, byte inNumber, byte inVelocity) {
}
}
uint8_t slot = drum_get_slot(drum_config[use_drum].drum_class);
float pan = mapfloat(configuration.drums.pan[use_drum], DRUMS_PANORAMA_MIN, DRUMS_PANORAMA_MAX, 0.0, 1.0);
float reverb_send = configuration.drums.reverb_send[use_drum] / 100.0f;
float vol_min = configuration.drums.vol_min[use_drum] / 100.0f;
float vol_max = configuration.drums.vol_max[use_drum] / 100.0f;
drum_mixer_r.gain(slot, pan * volume_transform(mapfloat(inVelocity, 0, 127, vol_min, vol_max)));
drum_mixer_l.gain(slot, (1.0 - pan) * volume_transform(mapfloat(inVelocity, 0, 127, vol_min, vol_max)));
drum_reverb_send_mixer_r.gain(slot, pan * volume_transform(reverb_send));
drum_reverb_send_mixer_l.gain(slot, (1.0 - pan) * volume_transform(reverb_send));
if (drum_config[use_drum].drum_data != NULL && drum_config[use_drum].len > 0) {
if (configuration.drums.pitch[use_drum] != 0) {
Drum[slot]->enableInterpolation(true);
Drum[slot]->setPlaybackRate(pow(2, float(configuration.drums.pitch[use_drum]) / 120.0));
} else {
Drum[slot]->enableInterpolation(false);
Drum[slot]->setPlaybackRate(1.0);
}
Drum[slot]->playRaw((int16_t*)drum_config[use_drum].drum_data, drum_config[use_drum].len, 1);
#ifdef DEBUG
Serial.printf(PSTR("Playing sample [%s][%c%c] on slot [%d] main volume [%d]: drum_data=%p, len=%d\n"), drum_config[use_drum].name, slot, configuration.drums.main_vol, drum_config[use_drum].drum_data, drum_config[use_drum].len);
Serial.print(F("Drum Slot ["));
Serial.print(slot);
Serial.print(F("]: Velocity="));
Serial.print(mapfloat(inVelocity, 0, 127, vol_min, vol_max), 2);
Serial.print(F(" Pan="));
Serial.print(pan, 2);
Serial.print(F(" ReverbSend="));
Serial.print(reverb_send, 2);
Serial.print(F(" Pitch="));
Serial.print(configuration.drums.pitch[use_drum] / 10.0f, 1);
Serial.print(F(" Playback speed="));
Serial.println(pow(2, float(configuration.drums.pitch[use_drum]) / 120.0));
if (drum_config[use_drum].midinote > 0) {
uint8_t slot = drum_get_slot(drum_config[use_drum].drum_class);
float pan = mapfloat(configuration.drums.pan[use_drum], DRUMS_PANORAMA_MIN, DRUMS_PANORAMA_MAX, 0.0, 1.0);
float reverb_send = configuration.drums.reverb_send[use_drum] / 100.0f;
float vol_min = configuration.drums.vol_min[use_drum] / 100.0f;
float vol_max = configuration.drums.vol_max[use_drum] / 100.0f;
drum_mixer_r.gain(slot, pan * volume_transform(mapfloat(inVelocity, 0, 127, vol_min, vol_max)));
drum_mixer_l.gain(slot, (1.0 - pan) * volume_transform(mapfloat(inVelocity, 0, 127, vol_min, vol_max)));
drum_reverb_send_mixer_r.gain(slot, pan * volume_transform(reverb_send));
drum_reverb_send_mixer_l.gain(slot, (1.0 - pan) * volume_transform(reverb_send));
if (drum_config[use_drum].drum_data != NULL && drum_config[use_drum].len > 0) {
if (configuration.drums.pitch[use_drum] != 0) {
Drum[slot]->enableInterpolation(true);
Drum[slot]->setPlaybackRate(pow(2, float(configuration.drums.pitch[use_drum]) / 120.0));
} else {
Drum[slot]->enableInterpolation(false);
Drum[slot]->setPlaybackRate(1.0);
}
Drum[slot]->playRaw((int16_t*)drum_config[use_drum].drum_data, drum_config[use_drum].len, 1);
#ifdef DEBUG
Serial.printf_P(PSTR("Playing sample [%s] on slot [%d] main volume [%d]: drum_data=%p, len=%d\n"), drum_config[use_drum].name, slot, configuration.drums.main_vol, drum_config[use_drum].drum_data, drum_config[use_drum].len);
Serial.print(F("Drum Slot ["));
Serial.print(slot);
Serial.print(F("]: Velocity="));
Serial.print(mapfloat(inVelocity, 0, 127, vol_min, vol_max), 2);
Serial.print(F(" Pan="));
Serial.print(pan, 2);
Serial.print(F(" ReverbSend="));
Serial.print(reverb_send, 2);
Serial.print(F(" Pitch="));
Serial.print(configuration.drums.pitch[use_drum] / 10.0f, 1);
Serial.print(F(" Playback speed="));
Serial.println(pow(2, float(configuration.drums.pitch[use_drum]) / 120.0));
#endif
}
}
}
#endif
@ -964,7 +969,7 @@ void handleNoteOff(byte inChannel, byte inNumber, byte inVelocity) {
//
// MIDI learn mode
//
if (midi_learn_mode != MIDI_LEARN_MODE_OFF) {
if (midi_learn_mode > MIDI_LEARN_MODE_OFF) {
int8_t tmp_channel = handle_midi_learn(inNumber);
if (tmp_channel >= 0)
inChannel = tmp_channel;
@ -2215,7 +2220,7 @@ int8_t handle_midi_learn(int8_t note) {
int8_t ret_channel = -1;
#ifdef DEBUG
Serial.printf(PSTR("MIDI learning for %d with midi learn mode %d\n"), note, midi_learn_mode);
Serial.printf_P(PSTR("MIDI learning for note %d with midi learn mode %d\n"), note, midi_learn_mode);
#endif
if (LCDML.FUNC_getID() == LCDML.OTHER_getIDFromFunction(UI_func_drum_pan)) {
@ -2232,15 +2237,10 @@ int8_t handle_midi_learn(int8_t note) {
LCDML.OTHER_jumpToFunc(UI_func_drum_vol_min_max);
} else if (LCDML.FUNC_getID() == LCDML.OTHER_getIDFromFunction(UI_func_drum_midi_note)) {
ret_channel = configuration.drums.midi_channel;
if (midi_learn_mode != MIDI_LEARN_MODE_NOTE && midi_learn_mode != MIDI_LEARN_MODE_DRUM_NOTE)
if (midi_learn_mode & 0x80)
active_sample = get_drums_id_by_note(note);
else {
if (midi_learn_mode != MIDI_LEARN_MODE_DRUM_NOTE)
midi_learn_mode = note;
else
midi_learn_mode = note & 0x80;
LCDML.OTHER_jumpToFunc(UI_func_drum_midi_note);
}
midi_learn_mode |= note;
LCDML.OTHER_jumpToFunc(UI_func_drum_midi_note);
} else if (LCDML.FUNC_getID() == LCDML.OTHER_getIDFromFunction(UI_func_drum_pitch)) {
ret_channel = configuration.drums.midi_channel;
active_sample = get_drums_id_by_note(note);
@ -2889,6 +2889,18 @@ void SerialPrintFormatInt3(uint8_t num) {
Serial.print(buf);
}
const char* byte_to_binary(int x) {
static char b[9];
b[0] = '\0';
int z;
for (z = 128; z > 0; z >>= 1) {
strcat(b, ((x & z) == z) ? "1" : "0");
}
return b;
}
#if defined(ARDUINO_TEENSY36)
/* From: https://forum.pjrc.com/threads/33443-How-to-display-free-ram */
extern "C" char* sbrk(int incr);

@ -2909,7 +2909,7 @@ void UI_func_note_refresh(uint8_t param) {
MicroDexed[selected_instance_id]->setNoteRefreshMode(configuration.dexed[selected_instance_id].note_refresh);
#ifdef DEBUG
Serial.printf(PSTR("Note refresh: %d\n"), configuration.dexed[selected_instance_id].note_refresh);
Serial.printf_P(PSTR("Note refresh: %d\n"), configuration.dexed[selected_instance_id].note_refresh);
#endif
display.setCursor(0, 1);
@ -4440,8 +4440,8 @@ void UI_func_drum_midi_note(uint8_t param) {
for (uint8_t i = 0; i < NUM_DRUMSET_CONFIG; i++)
midinote_old[i] = configuration.drums.midinote[i];
if (!display_name)
midi_learn_mode = MIDI_LEARN_MODE_DRUM_NOTE;
if (display_name)
midi_learn_mode = MIDI_LEARN_MODE_ON| 0x80;
else
midi_learn_mode = MIDI_LEARN_MODE_ON;
@ -4476,8 +4476,8 @@ void UI_func_drum_midi_note(uint8_t param) {
}
}
if (midi_learn_mode >= DRUMS_MIDI_NOTE_MIN)
configuration.drums.midinote[active_sample] = midi_learn_mode & 0x7f;
// if (midi_learn_mode & 0x80)
// configuration.drums.midinote[active_sample] = midi_learn_mode & 0x7f;
if ((LCDML.BT_checkDown() && encoderDir[ENC_R].Down()) || (LCDML.BT_checkUp() && encoderDir[ENC_R].Up()) || (LCDML.BT_checkEnter() && encoderDir[ENC_R].ButtonShort())) {
if (LCDML.BT_checkDown()) {
@ -4526,8 +4526,8 @@ void UI_func_drum_midi_note(uint8_t param) {
} else if (ask_before_quit_mode == 0) { // BACK
ask_before_quit_mode = -1;
ask_before_quit = false;
if (!display_name)
midi_learn_mode = MIDI_LEARN_MODE_DRUM_NOTE;
if (display_name)
midi_learn_mode = MIDI_LEARN_MODE_ON | 0x80;
else
midi_learn_mode = MIDI_LEARN_MODE_ON;
LCDML.OTHER_updateFunc();
@ -4550,8 +4550,8 @@ void UI_func_drum_midi_note(uint8_t param) {
#endif
_check_display_name(display_name, 3);
if (!display_name)
midi_learn_mode = MIDI_LEARN_MODE_DRUM_NOTE;
if (display_name)
midi_learn_mode = MIDI_LEARN_MODE_ON | 0x80;
else
midi_learn_mode = MIDI_LEARN_MODE_ON;
}

@ -829,10 +829,8 @@ enum reverb_mixer_ports {
enum midi_learn_modes {
MIDI_LEARN_MODE_OFF,
MIDI_LEARN_MODE_ON,
MIDI_LEARN_MODE_NOTE,
MIDI_LEARN_MODE_DRUM_NOTE
};
MIDI_LEARN_MODE_ON
};
#ifndef _MAPFLOAT
#define _MAPFLOAT

Loading…
Cancel
Save