mirror of
https://github.com/KevinMidboe/python-gpiozero.git
synced 2025-10-29 17:50:37 +00:00
Rework when_changed attribute to use weakrefs
Some fairly major changes to ensure that the Pin.when_changed property doesn't keep references to the objects owning the callbacks that are assigned. This is vaguely tricky given that ordinary weakref's can't be used with bound methods (which are ephemeral), so I've back-ported weakref.WeakMethod from Py3.4. This solves a whole pile of things like Button instances not disappearing when they're deleted, and makes composite devices containing Buttons much easier to construct as we don't need to worry about partially constructed things not getting deleted.
This commit is contained in:
@@ -438,23 +438,28 @@ class HoldThread(GPIOThread):
|
||||
device is active.
|
||||
"""
|
||||
def __init__(self, parent):
|
||||
super(HoldThread, self).__init__(target=self.held, args=(parent,))
|
||||
super(HoldThread, self).__init__(
|
||||
target=self.held, args=(weakref.proxy(parent),))
|
||||
self.holding = Event()
|
||||
self.start()
|
||||
|
||||
def held(self, parent):
|
||||
while not self.stopping.is_set():
|
||||
if self.holding.wait(0.1):
|
||||
self.holding.clear()
|
||||
while not (
|
||||
self.stopping.is_set() or
|
||||
parent._inactive_event.wait(parent.hold_time)
|
||||
):
|
||||
if parent._held_from is None:
|
||||
parent._held_from = time()
|
||||
parent._fire_held()
|
||||
if not parent.hold_repeat:
|
||||
break
|
||||
try:
|
||||
while not self.stopping.is_set():
|
||||
if self.holding.wait(0.1):
|
||||
self.holding.clear()
|
||||
while not (
|
||||
self.stopping.is_set() or
|
||||
parent._inactive_event.wait(parent.hold_time)
|
||||
):
|
||||
if parent._held_from is None:
|
||||
parent._held_from = time()
|
||||
parent._fire_held()
|
||||
if not parent.hold_repeat:
|
||||
break
|
||||
except ReferenceError:
|
||||
# Parent is dead; time to die!
|
||||
pass
|
||||
|
||||
|
||||
class GPIOQueue(GPIOThread):
|
||||
|
||||
Reference in New Issue
Block a user