kivy-garden-pyle
pyle is an experimental library aimed at reducing the boilerplate needed to create Kivy bindings without using the Kv language.
For example, suppose you want a function that adds a solid-color background to a specific Widget instance and provides a way to revert it.
Your code might look like this:
from contextlib import ExitStack
from kivy.graphics import Color, Rectangle
from kivy.clock import Clock
def add_solid_background(widget, *, color=(1., 1. , 1., .3)):
'''
Adds a solid-color background to widget and returns a function that reverts it.
'''
with ExitStack() as stack:
defer = stack.callback
before = widget.canvas.before
with before:
defer(before.remove, Color(*color))
defer(before.remove, rect := Rectangle(pos=widget.pos, size=widget.size))
def sync_graphics(dt, rect=rect, w=widget):
rect.pos = w.pos
rect.size = w.size
t = Clock.create_trigger(sync_graphics, -1)
defer(t.cancel)
widget.bind(pos=t, size=t)
defer(widget.unbind, pos=t, size=t)
return stack.pop_all().close
revert = add_solid_background(widget)
...
revert()
Now, here is what an equivalent implementation looks like with pyle:
from contextlib import ExitStack
from kivy.graphics import Color, Rectangle
from kivy_garden import pyle
def add_solid_background(widget, *, color=(1., 1. , 1., .3)):
with ExitStack() as stack:
defer = stack.callback
before = widget.canvas.before
with before:
defer(before.remove, Color(*color))
defer(before.remove, rect := Rectangle(pos=widget.pos, size=widget.size))
@pyle.throttle_rule
def sync_graphics(dt, rect=rect, w=widget):
rect.pos = w.pos
rect.size = w.size
stack.enter_context(sync_graphics)
return stack.pop_all().close
As you can see, the binding code becomes much cleaner. And of course, if you are using an async library, you may want to implement the feature as an async function, tying the background's lifetime to the coroutine it returns:
from contextlib import ExitStack
import asynckivy as ak
from kivy.graphics import Color, Rectangle
from kivy_garden import pyle
async def enable_solid_background(widget, *, color=(1., 1. , 1., .3)):
'''
Enables a solid-color background for a widget until the returned coroutine is cancelled.
'''
with ExitStack() as stack:
defer = stack.callback
before = widget.canvas.before
with before:
defer(before.remove, Color(*color))
defer(before.remove, rect := Rectangle(pos=widget.pos, size=widget.size))
@pyle.throttle_rule
def sync_graphics(dt, rect=rect, w=widget):
rect.pos = w.pos
rect.size = w.size
stack.enter_context(sync_graphics)
await ak.sleep_forever()
In the examples above, the @pyle.throttle_rule decorator turns sync_graphics into a context manager.
At this point, bindings are not yet enabled; they are enabled only while the context manager is active.
The context manager is not reentrant, but it is reusable:
# error
with sync_graphics:
with sync_graphics:
...
# fine
with sync_graphics:
...
with sync_graphics:
...
How does it know which Kivy properties should be observed?
It analyzes the signature and bytecode of the given function.
When the function has a pre-filled argument that is an instance of EventDispatcher,
any of its Kivy properties accessed via LOAD_ATTR will be observed.
Only the following types of "pre-filled" arguments are subjected to observation:
- default values like in the
sync_graphicsexample (w=widget) - values bound with
functools.partial selfarguments bound viaobj.instance_method
Any other way of filling arguments will not create bindings. For more details, please see test_detect_dependencies.py.
Tested on
- CPython 3.11 + Kivy 2.3.1
- CPython 3.12 + Kivy 2.3.1
- CPython 3.13 + Kivy 2.3.1
- CPython 3.14 + Kivy
be90b9f
Download files
Download the file for your platform. If you're not sure which to choose, learn more about installing packages.
Source Distribution
Built Distribution
Filter files by name, interpreter, ABI, and platform.
If you're not sure about the file name format, learn more about wheel file names.
Copy a direct link to the current filters
File details
Details for the file kivy_garden_pyle-0.1.0.tar.gz.
File metadata
- Download URL: kivy_garden_pyle-0.1.0.tar.gz
- Upload date:
- Size: 4.1 kB
- Tags: Source
- Uploaded using Trusted Publishing? Yes
- Uploaded via:
twine/6.1.0 CPython/3.13.7
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
3a66d1fdef225ad4f5e0d3642b231137ba2ffaddaca0b00853c58606c4baee16
|
|
| MD5 |
55e426f10285ab969abedcbf034dd9c0
|
|
| BLAKE2b-256 |
1635b1ece23ae3315408b05986297be1ee9f37fb009830a38265c564dda834c5
|
Provenance
The following attestation bundles were made for kivy_garden_pyle-0.1.0.tar.gz:
Publisher:
release.yml on gottadiveintopython/kivy-garden-pyle
-
Statement:
-
Statement type:
https://in-toto.io/Statement/v1 -
Predicate type:
https://docs.pypi.org/attestations/publish/v1 -
Subject name:
kivy_garden_pyle-0.1.0.tar.gz -
Subject digest:
3a66d1fdef225ad4f5e0d3642b231137ba2ffaddaca0b00853c58606c4baee16 - Sigstore transparency entry: 2374870488
- Sigstore integration time:
-
Permalink:
gottadiveintopython/kivy-garden-pyle@c0fa6e2357626e283d1d6dd7a064764a09f0590c -
Branch / Tag:
refs/tags/v0.1.0 - Owner: https://github.com/gottadiveintopython
-
Access:
public
-
Token Issuer:
https://token.actions.githubusercontent.com -
Runner Environment:
github-hosted -
Publication workflow:
release.yml@c0fa6e2357626e283d1d6dd7a064764a09f0590c -
Trigger Event:
push
-
Statement type:
File details
Details for the file kivy_garden_pyle-0.1.0-py3-none-any.whl.
File metadata
- Download URL: kivy_garden_pyle-0.1.0-py3-none-any.whl
- Upload date:
- Size: 4.8 kB
- Tags: Python 3
- Uploaded using Trusted Publishing? Yes
- Uploaded via:
twine/6.1.0 CPython/3.13.7
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
b8a3118434125b93c93f795cd2e376f54b9905c16d46ad0ee68602e51c04684d
|
|
| MD5 |
241cbef651a7243664ef628885d6cb4b
|
|
| BLAKE2b-256 |
fd45b5fd9e6df43b9062043608dbc710dbfa2dc23fa3597a251e2d849a580fac
|
Provenance
The following attestation bundles were made for kivy_garden_pyle-0.1.0-py3-none-any.whl:
Publisher:
release.yml on gottadiveintopython/kivy-garden-pyle
-
Statement:
-
Statement type:
https://in-toto.io/Statement/v1 -
Predicate type:
https://docs.pypi.org/attestations/publish/v1 -
Subject name:
kivy_garden_pyle-0.1.0-py3-none-any.whl -
Subject digest:
b8a3118434125b93c93f795cd2e376f54b9905c16d46ad0ee68602e51c04684d - Sigstore transparency entry: 2374870528
- Sigstore integration time:
-
Permalink:
gottadiveintopython/kivy-garden-pyle@c0fa6e2357626e283d1d6dd7a064764a09f0590c -
Branch / Tag:
refs/tags/v0.1.0 - Owner: https://github.com/gottadiveintopython
-
Access:
public
-
Token Issuer:
https://token.actions.githubusercontent.com -
Runner Environment:
github-hosted -
Publication workflow:
release.yml@c0fa6e2357626e283d1d6dd7a064764a09f0590c -
Trigger Event:
push
-
Statement type: