# qtlets
Automatic linking of data to qt widgets. MCV without the boilerplate.
`qtlets` provides a simple way to keep in sync Qt widgets and data, without
forcing a redesign of your data classes. The rule is: *if you like your class, you can
keep your class*.
Currently, bidirectional linking can be performed in a simple call<sup>1</sup>:
`instance.link_widget(my_widget, "name")`
The data displayed on `my_widget` will be updated whenever `instance.name` is
modified. Changing the value on `my_widget` will update `instance.name`.
Multiple widgets can be kept synchronized in this way.
This functionnality is provided by a lightweight Mixin class called `HasQtlets`.
To enable `qtlets` on an `Existing` class, simply do:
```
class Data(HasQtlets, Existing): pass
```
and then use `Data` as a drop-in replacement for `Existing`. To link widgets,
make calls to `link_widget`. The widget should be able to send and receive the
appropriate data type. A few basic types are availalbe in `qtlets.widgets`
This library is currently in early stages. The documentation is light, and
the API is changing quickly. All help is appreciated...
<sup>1</sup> Some conditions currently apply, see the Features section.
# Getting started
Requires an environment with python 3.8.
## Install dependencies
```
pip install -r requirements.txt
pip install -e .
```
## Run tests
`py.test`
# Features
The following features are currently supported:
- Linking of widgets and data. Currently, scalar data members are supported;
- Multiple widgets can be linked with the same data attribute;
- Compatibility with simple vanilla classes, as well as more complex
third-party libraries such as `traitlets` (Even `attrs`! Isn't inheritance
wonderful?);
- Support for `properties`;
- The signal and slots used to communicate with the widget can be specified
explicitly. For some widgets, a reasonable default is provided.
The following features are desired:
- Adding more data types and widgets.
- Streamlined type conversions and checks. For type conversion, we can pass
conversion functions to `link_widget`.
- Support for collections attributes (ex: `instance.values = []`)
- Support polling (`inst.link(widget, attrname, poll_interval=15)`)
- Leverage Qt's thread affinity when using signals and slots, for setting as
well as for getting.
- More dedicated widgets.
- Use either PySide6 or PyQt. See how pyqtgraph does it.
Raw data
{
"_id": null,
"home_page": null,
"name": "qtlets",
"maintainer": null,
"docs_url": null,
"requires_python": ">=3.8",
"maintainer_email": null,
"keywords": "qt, qtwidgets, pyside6, gui",
"author": null,
"author_email": "Samuel Palato <7659022+spalato@users.noreply.github.com>",
"download_url": "https://files.pythonhosted.org/packages/eb/e6/ea01182627277ee536af3adfd7ac9805b93c135421a0fedd9baa6a6c1aaa/qtlets-0.4.tar.gz",
"platform": null,
"description": "# qtlets\r\nAutomatic linking of data to qt widgets. MCV without the boilerplate.\r\n\r\n`qtlets` provides a simple way to keep in sync Qt widgets and data, without \r\nforcing a redesign of your data classes. The rule is: *if you like your class, you can\r\nkeep your class*. \r\n\r\nCurrently, bidirectional linking can be performed in a simple call<sup>1</sup>:\r\n`instance.link_widget(my_widget, \"name\")`\r\nThe data displayed on `my_widget` will be updated whenever `instance.name` is\r\nmodified. Changing the value on `my_widget` will update `instance.name`. \r\nMultiple widgets can be kept synchronized in this way.\r\n \r\nThis functionnality is provided by a lightweight Mixin class called `HasQtlets`.\r\nTo enable `qtlets` on an `Existing` class, simply do:\r\n```\r\nclass Data(HasQtlets, Existing): pass\r\n``` \r\nand then use `Data` as a drop-in replacement for `Existing`. To link widgets,\r\nmake calls to `link_widget`. The widget should be able to send and receive the\r\nappropriate data type. A few basic types are availalbe in `qtlets.widgets`\r\n\r\n\r\nThis library is currently in early stages. The documentation is light, and \r\nthe API is changing quickly. All help is appreciated...\r\n\r\n<sup>1</sup> Some conditions currently apply, see the Features section.\r\n\r\n# Getting started\r\n\r\nRequires an environment with python 3.8.\r\n\r\n## Install dependencies\r\n```\r\npip install -r requirements.txt\r\npip install -e .\r\n```\r\n\r\n## Run tests\r\n`py.test`\r\n\r\n# Features\r\n\r\nThe following features are currently supported:\r\n- Linking of widgets and data. Currently, scalar data members are supported;\r\n- Multiple widgets can be linked with the same data attribute;\r\n- Compatibility with simple vanilla classes, as well as more complex \r\n third-party libraries such as `traitlets` (Even `attrs`! Isn't inheritance \r\n wonderful?);\r\n- Support for `properties`;\r\n- The signal and slots used to communicate with the widget can be specified\r\n explicitly. For some widgets, a reasonable default is provided. \r\n\r\n\r\nThe following features are desired:\r\n- Adding more data types and widgets.\r\n- Streamlined type conversions and checks. For type conversion, we can pass\r\n conversion functions to `link_widget`.\r\n- Support for collections attributes (ex: `instance.values = []`)\r\n- Support polling (`inst.link(widget, attrname, poll_interval=15)`)\r\n- Leverage Qt's thread affinity when using signals and slots, for setting as \r\n well as for getting. \r\n- More dedicated widgets.\r\n- Use either PySide6 or PyQt. See how pyqtgraph does it.\r\n",
"bugtrack_url": null,
"license": null,
"summary": "Qt with less boilerplate",
"version": "0.4",
"project_urls": {
"Homepage": "https://github.com/spalato/qtlets",
"Source": "https://github.com/spalato/qtlets",
"Tracker": "https://github.com/spalato/qtlets/issues"
},
"split_keywords": [
"qt",
" qtwidgets",
" pyside6",
" gui"
],
"urls": [
{
"comment_text": "",
"digests": {
"blake2b_256": "5ee9c2214567eb58be76684bd27ecbd241cfc9ccf1c8978f2650e24f6bc60305",
"md5": "f5a85a614f4e4f7e5c085f5b2492461b",
"sha256": "27cf3da905e039ab8022ec8c7f990dc4cc6a62b7fe256b94fbcbd4442d00d469"
},
"downloads": -1,
"filename": "qtlets-0.4-py3-none-any.whl",
"has_sig": false,
"md5_digest": "f5a85a614f4e4f7e5c085f5b2492461b",
"packagetype": "bdist_wheel",
"python_version": "py3",
"requires_python": ">=3.8",
"size": 7230,
"upload_time": "2025-10-19T17:06:25",
"upload_time_iso_8601": "2025-10-19T17:06:25.855712Z",
"url": "https://files.pythonhosted.org/packages/5e/e9/c2214567eb58be76684bd27ecbd241cfc9ccf1c8978f2650e24f6bc60305/qtlets-0.4-py3-none-any.whl",
"yanked": false,
"yanked_reason": null
},
{
"comment_text": "",
"digests": {
"blake2b_256": "ebe6ea01182627277ee536af3adfd7ac9805b93c135421a0fedd9baa6a6c1aaa",
"md5": "2555fc2640a91979f17cde8d68375961",
"sha256": "a8cbd2f60fdf6f58431e7112d0006613f47fec880a8f6e98114e0c35ada29c41"
},
"downloads": -1,
"filename": "qtlets-0.4.tar.gz",
"has_sig": false,
"md5_digest": "2555fc2640a91979f17cde8d68375961",
"packagetype": "sdist",
"python_version": "source",
"requires_python": ">=3.8",
"size": 9869,
"upload_time": "2025-10-19T17:06:27",
"upload_time_iso_8601": "2025-10-19T17:06:27.298084Z",
"url": "https://files.pythonhosted.org/packages/eb/e6/ea01182627277ee536af3adfd7ac9805b93c135421a0fedd9baa6a6c1aaa/qtlets-0.4.tar.gz",
"yanked": false,
"yanked_reason": null
}
],
"upload_time": "2025-10-19 17:06:27",
"github": true,
"gitlab": false,
"bitbucket": false,
"codeberg": false,
"github_user": "spalato",
"github_project": "qtlets",
"travis_ci": false,
"coveralls": false,
"github_actions": false,
"requirements": [
{
"name": "PySide2",
"specs": []
}
],
"lcname": "qtlets"
}