Virtual-keyboard: allow octave switches while hand-pedaling

This commit is contained in:
Robin Gareus 2019-10-27 13:54:47 +01:00
parent b53431a089
commit 474a3c5f69
Signed by: rgareus
GPG Key ID: A090BCE02CF57F04
2 changed files with 33 additions and 30 deletions

View File

@ -293,7 +293,7 @@ APianoKeyboard::stop_sustained_notes ()
int int
APianoKeyboard::key_binding (const char* key) const APianoKeyboard::key_binding (const char* key) const
{ {
if (_key_bindings.find (key) != _key_bindings.end ()) { if (key && _key_bindings.find (key) != _key_bindings.end ()) {
return _key_bindings.at (key); return _key_bindings.at (key);
} }
return -1; return -1;
@ -520,14 +520,9 @@ APianoKeyboard::bind_keys_basic_qwertz ()
bind_key ("apostrophe", 29); bind_key ("apostrophe", 29);
} }
static char*
bool get_keycode (GdkEventKey* event)
APianoKeyboard::on_key_press_event (GdkEventKey* event)
{ {
int note;
char* key;
guint keyval;
GdkKeymapKey kk; GdkKeymapKey kk;
/* We're not using event->keyval, because we need keyval with level set to 0. /* We're not using event->keyval, because we need keyval with level set to 0.
@ -536,45 +531,56 @@ APianoKeyboard::on_key_press_event (GdkEventKey* event)
kk.level = 0; kk.level = 0;
kk.group = 0; kk.group = 0;
keyval = gdk_keymap_lookup_key (NULL, &kk); guint keyval = gdk_keymap_lookup_key (NULL, &kk);
return gdk_keyval_name (gdk_keyval_to_lower (keyval));
}
key = gdk_keyval_name (gdk_keyval_to_lower (keyval)); bool
APianoKeyboard::on_key_press_event (GdkEventKey* event)
if (key == NULL) { {
return false; char* key = get_keycode (event);
} int note = key_binding (key);
note = key_binding (key);
if (note < 0) { if (note < 0) {
return false; return false;
} }
if (note == 128) { if (note == 128) {
if (event->type == GDK_KEY_RELEASE) { /* Rest is used on release */
Rest (); /* EMIT SIGNAL */
return true;
}
return false; return false;
} }
note += _octave * 12; note += _octave * 12;
assert (key);
assert (note >= 0); assert (note >= 0);
assert (note < NNOTES); assert (note < NNOTES);
if (event->type == GDK_KEY_PRESS) { _note_stack[key] = note;
press_key (note, _key_velocity);
} else if (event->type == GDK_KEY_RELEASE) { press_key (note, _key_velocity);
release_key (note);
}
return true; return true;
} }
bool bool
APianoKeyboard::on_key_release_event (GdkEventKey* event) APianoKeyboard::on_key_release_event (GdkEventKey* event)
{ {
return on_key_press_event (event); char* key = get_keycode (event);
if (key_binding (key) == 128) {
Rest (); /* EMIT SIGNAL */
return true;
}
if (_note_stack.find (key) == _note_stack.end ()) {
return key_binding (key) != -1;
}
release_key (_note_stack.at(key));
_note_stack.erase (key);
return true;
} }
int int
@ -946,8 +952,6 @@ APianoKeyboard::set_note_off (int note)
void void
APianoKeyboard::set_octave (int octave) APianoKeyboard::set_octave (int octave)
{ {
stop_unsustained_notes ();
if (octave < -1) { if (octave < -1) {
octave = -1; octave = -1;
} else if (octave > 7) { } else if (octave > 7) {
@ -961,8 +965,6 @@ APianoKeyboard::set_octave (int octave)
void void
APianoKeyboard::set_octave_range (int octave_range) APianoKeyboard::set_octave_range (int octave_range)
{ {
stop_unsustained_notes ();
if (octave_range < 2) { if (octave_range < 2) {
octave_range = 2; octave_range = 2;
} }

View File

@ -141,6 +141,7 @@ private:
std::map<std::string, int> _key_bindings; /**< Table used to translate from PC keyboard character to MIDI note number. */ std::map<std::string, int> _key_bindings; /**< Table used to translate from PC keyboard character to MIDI note number. */
std::map<int, std::string> _note_bindings; /**< Table to translate from MIDI note number to PC keyboard character. */ std::map<int, std::string> _note_bindings; /**< Table to translate from MIDI note number to PC keyboard character. */
std::map<std::string, int> _note_stack;
/* these are only valid during expose/draw */ /* these are only valid during expose/draw */
PangoFontDescription* _font_cue; PangoFontDescription* _font_cue;