Summary
Closing the Music Keyboard widget can restore stale global keyboard handlers and break keyboard behavior in other widgets that are still open.
Affected area
js/widgets/musickeyboard.js
Reproduction
- Open the Music Keyboard widget.
- Open the Help widget while Music Keyboard is still open.
- Use the Help widget once so its arrow-key navigation handler is active.
- Close the Music Keyboard widget.
- Try using the Help widget keyboard navigation again.
Actual result
The Help widget's document.onkeydown / document.onkeyup handlers can stop working after Music Keyboard closes, because Music Keyboard restores an older global handler snapshot.
Expected result
Closing Music Keyboard should restore the keyboard handlers that were active immediately before Music Keyboard installed its own handlers, without clobbering newer widget-level handlers from other open widgets.
Root cause
MusicKeyboard captures document.onkeydown and document.onkeyup once in the constructor:
const saveOnKeyDown = document.onkeydown;
const saveOnKeyUp = document.onkeyup;
Later, widgetWindow.onclose restores those captured values.
Because the snapshot is taken at construction time instead of right before Music Keyboard overwrites the handlers, it can become stale. If another widget changes the global keyboard handlers afterward, closing Music Keyboard restores the old snapshot and overwrites the newer handler.
Suggested fix
Store the previous document.onkeydown / document.onkeyup handlers immediately before Music Keyboard overrides them, and restore that per-open snapshot on close. An even safer follow-up would be to avoid direct document.onkeydown replacement entirely and use scoped addEventListener / removeEventListener handlers instead.
Summary
Closing the Music Keyboard widget can restore stale global keyboard handlers and break keyboard behavior in other widgets that are still open.
Affected area
js/widgets/musickeyboard.jsReproduction
Actual result
The Help widget's
document.onkeydown/document.onkeyuphandlers can stop working after Music Keyboard closes, because Music Keyboard restores an older global handler snapshot.Expected result
Closing Music Keyboard should restore the keyboard handlers that were active immediately before Music Keyboard installed its own handlers, without clobbering newer widget-level handlers from other open widgets.
Root cause
MusicKeyboardcapturesdocument.onkeydownanddocument.onkeyuponce in the constructor:const saveOnKeyDown = document.onkeydown;const saveOnKeyUp = document.onkeyup;Later,
widgetWindow.oncloserestores those captured values.Because the snapshot is taken at construction time instead of right before Music Keyboard overwrites the handlers, it can become stale. If another widget changes the global keyboard handlers afterward, closing Music Keyboard restores the old snapshot and overwrites the newer handler.
Suggested fix
Store the previous
document.onkeydown/document.onkeyuphandlers immediately before Music Keyboard overrides them, and restore that per-open snapshot on close. An even safer follow-up would be to avoid directdocument.onkeydownreplacement entirely and use scopedaddEventListener/removeEventListenerhandlers instead.