Skip to content

Contributing to pymmcore-widgets

Thanks for thinking of a way to help improve this library!

Remember that contributions come in all shapes and sizes beyond writing bug fixes. Contributing to documentation, opening new issues for bugs, asking for clarification on things you find unclear or requesting new features, are all super valuable contributions.

You can do any of the above by opening a new issue or by submitting a pull request on the GitHub repository for this project. The contributing guide has the parts that are the same for every package (and the ways to reach us); this page has the parts that are specific to the widgets.

Development setup

We use uv. uv sync installs the package with its dev dependency group, which includes PyQt6:

git clone <your-fork>
cd pymmcore-widgets
uv sync
uv run mmcore install  # the demo device adapters, used by most tests

Running the tests

uv run pytest

Some of the tests show real windows. To run them without any windows (on a machine without a display, or just to keep your screen quiet), use Qt's offscreen platform:

QT_QPA_PLATFORM=offscreen uv run pytest

(On Windows PowerShell: $env:QT_QPA_PLATFORM = "offscreen" first.) CI runs the tests on macOS and Windows, with both PyQt6 and PySide6.

Widget pages and screenshots

Each widget's documentation page, its screenshots and its card in the widget gallery are generated by docs/_gen.py:

  • docs/widget_list.json lists the widgets, by gallery section.
  • examples/<snake_case_name>.py is the example for each one (e.g. examples/mda_widget.py for MDAWidget). _gen.py runs it offscreen, grabs the window it shows (in light and dark mode), and puts the code on the widget's page.
  • The widget's docstring becomes the rest of the page, and its first line is the description on the gallery card.

So, to add a widget to the docs, export it from pymmcore_widgets, add it to widget_list.json, and write an example that shows it with the demo configuration. _gen.py warns about exported widgets that are missing from the list. You can run it yourself to check that the example works:

uv run python docs/_gen.py          # only redoes screenshots whose example changed
uv run python docs/_gen.py --force  # redo them all

The output (docs/api/, docs/_generated/, docs/images/generated/) is not committed. The docs themselves are built as part of the unified pymmcore-plus site: see How These Docs Work to preview them.