Releasing a button used as a KeyIsDown modifier sends a single-element
MOUSE_GESTURE notification (Noop) that can incorrectly match MouseGesture
rules bound to the same button.
Track the state across notifications with three module-level variables:
- keys_used_while_held: buttons where a KeyIsDown rule fired during hold
- suppress_noop_for_buttons: buttons whose next Noop should be swallowed
- _suppress_current_noop: per-notification flag checked by MouseGesture.evaluate
KeyIsDown.evaluate records the button when a non-button notification
co-fires (e.g. scroll, gesture). On key-up, process_notification moves it
to suppress_noop_for_buttons. evaluate_rules sets _suppress_current_noop
when the incoming Noop matches. MouseGesture.evaluate returns False.
Re-pressing the button before release clears any pending suppression.