Button Shim hold issue

Looks like the code behind Button SHIM is some kind of eldritch horror that I’ve left in my wake. It makes no effort to differentiate between a “hold” and a “press”. Probably intentionally, but it’s very confusing to distill this behaviour into something that works.

Button presses consist of three parts- the Press, the Hold and the Release. They always happen in this order, and you cannot easily make something triggered by the “Press” contingent on whether or not you do something during the “Hold”. Not without time travel, anyway!

The key is to use the “Release” event to handle your “Press” action. And the “Press” event to reset the state of your system for the next interaction:

has_been_held = False
@buttonshim.on_press(buttonshim.BUTTON_A)
def handler(button, pressed):
    global has_been_held   # Required so that the line below doesn't just create a new  variable in this scope
    has_been_held = False  # Reset our basic state machine to the start

@buttonshim.on_release(buttonshim.BUTTON_A)
def handler(button, pressed):
    if not has_been_held:
        # Perform your "Press" action (lights on?) here

@buttonshim.on_hold(buttonshim.BUTTON_A, hold_time=2)
def handler(button):
    global has_been_held
    has_been_held = True
    # Perform your "Held" action (lights off?) here

Now the flow is as follows:

  1. has_been_held, which tracks if the button has been held, defaults to False
  2. pressing the button sets has_been_held to False starting a new interaction cycle
  3. upon releasing the button, it checks has_been_held and, if true, knows the button has been held down long enough to trigger a hold event, so can skip your release action
  4. if you hold the button, it triggers the hold event, but also sets has_been_held to True to indicate to your release handler that you can ignore the release event.

Whew! I think I confused myself explaining this. This use-case would make a really good example for Button SHIM though, so I’ve raised a ticket to remind us to write one - https://github.com/pimoroni/button-shim/issues/13