Gizeh — Cairo for tourists
Gizeh is a Python library for vector graphics, built on top of cairocffi (Cairo bindings for Python). Cairo is powerful but low-level; Gizeh adds a small set of intuitive primitives to make drawing easier.
# Let's draw a red circle!
import gizeh
surface = gizeh.Surface(width=320, height=260) # pixels
circle = gizeh.circle(r=30, xy=[40, 40], fill=(1, 0, 0))
circle.draw(surface) # draw the circle on the surface
surface.write_to_png("circle.png") # export as PNG
See Gizeh in action (combined with MoviePy for animations) in this blog post.
Gizeh supports Python 3.7+.
Installation
Gizeh requires the Cairo graphics library to be installed on your system.
- macOS (Homebrew):
brew install cairo pkg-config
- Debian/Ubuntu:
sudo apt-get install -y libcairo2-dev pkg-config
Then install the Python package:
pip install gizeh
Alternatively, from source (editable/development install):
pip install -e .
User Guide
This guide, along with the examples in gizeh/examples, should give you everything you need to get started. Check docstrings for details.
Surfaces
A Surface is a rectangle of fixed dimensions (in pixels) on which you draw elements, and which you can save/export as an image:
import gizeh
# initialize surface
surface = gizeh.Surface(width=320, height=260) # in pixels
# make a shape and draw it on the surface
circle = gizeh.circle(r=30, xy=[40, 40], fill=(1, 1, 1))
circle.draw(surface)
# export the surface
surface.get_npimage() # returns a (width x height x 3) numpy array
surface.write_to_png("circle.png")
Elements
Basic elements are circles, rectangles, lines, text, etc., that you draw on a surface using my_element.draw(surface). Common parameters:
xy: center coordinates of the object. At render time (surface.write_to_png) you can sety_originto"top"(default) or"bottom". With"top",(0, 0)is the upper-left of the final image; the bottom-right is(width, height). With"bottom",(0, 0)is the bottom-left (like plots), and(width, height)is the top-right.angle: rotation (radians) aroundxy.fill: interior fill (default: none). Can be a color(R, G, B), gradient, image pattern, etc.stroke: contour fill; same rules asfill.stroke_width: contour width (pixels). Default is0(no stroke).
Examples:
import numpy as np
Pi = np.pi
circ = gizeh.circle(r=30, xy=(50, 50), fill=(1, 1, 1))
rect = gizeh.rectangle(lx=60.3, ly=45, xy=(60, 70), fill=(0, 1, 0), angle=Pi/8)
sqr = gizeh.square(l=20, stroke=(1, 1, 1), stroke_width=1.5)
arc = gizeh.arc(r=20, a1=Pi/4, a2=3*Pi/4, fill=(1, 1, 1))
text = gizeh.text("Hello world", fontfamily="Impact", fontsize=40,
fill=(1, 1, 1), xy=(100, 100), angle=Pi/12)
poly = gizeh.regular_polygon(r=40, n=5, angle=np.pi/4, xy=[40, 50], fill=(1, 0, 1))
line = gizeh.polyline(points=[(0, 0), (20, 30), (40, 40), (0, 10)],
stroke_width=3, stroke=(1, 0, 0), fill=(0, 1, 0))
Fill and stroke
fill and stroke can be:
- RGB
(r, g, b)with values in[0, 1] - RGBA
(r, g, b, a)withain[0, 1] gizeh.ColorGradientgizeh.ImagePattern(an image)- A NumPy RGB/RGBA image array (where implemented)
Transformations
Elements can be transformed (translated, rotated, scaled). All transformations are out-of-place: they return a modified copy.
square_1 = gizeh.square(l=20, xy=[30, 35], fill=(1, 0, 0))
square_2 = square_1.rotate(np.pi/8) # rotation around [0, 0] by default
square_3 = square_2.rotate(np.pi/4, center=[10, 15]) # rotation around a center
square_4 = square_1.scale(2) # two times bigger
square_5 = square_1.scale(sx=2, sy=3) # width x2, height x3
square_6 = square_1.scale(2, center=[30, 30]) # zoom around a center
square_7 = square_1.translate(xy=[5, 15]) # translation
Groups
A Group is a collection of elements (including nested groups) transformed and drawn together:
square = gizeh.square(l=20, fill=(1, 0, 0), xy=(40, 40))
circle = gizeh.circle(r=20, fill=(1, 1, 0), xy=(50, 30))
group_1 = gizeh.Group([square, circle])
group_2 = group_1.translate(xy=[30, 30]).rotate(np.pi/4)
group_3 = gizeh.Group([circle, group_1])
surface = gizeh.Surface(width=300, height=200)
group_1.draw(surface)
group_2.draw(surface)
group_3.draw(surface)
surface.write_to_png("my_masterwork.png")
Troubleshooting installation
If pip installation fails, ensure you have the system Cairo development packages and pkg-config installed (see “Installation” above).
- macOS (Homebrew):
brew install cairo pkg-config - Debian/Ubuntu:
sudo apt-get install -y libcairo2-dev pkg-config
Developers
Development uses uv for fast Python packaging and workflows.
Prerequisites:
- Install system packages
- macOS:
brew install uv cairo pkg-config - Debian/Ubuntu:
sudo apt-get install -y libcairo2-dev pkg-configand installuvfrom its docs
- macOS:
Setup and install deps:
uv python install 3.12
uv venv --python 3.12
uv sync --group dev
Run tests:
uv run pytest -q
Run a specific test:
uv run pytest -q tests/test_samples.py::test_random_squares
Quick import check:
uv run python -c "import gizeh, numpy, cairocffi; print('ok')"
Install and run pre-commit hooks:
uv run pre-commit install
uv run pre-commit run --all-files
Contributing
Gizeh is open-source (MIT) by Zulko. Contributions are welcome—issues and pull requests on GitHub.
Metadata
Release files for gizeh 0.1.12
For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.
Source distribution (sdist)
| File | Size | Uploaded | |
|---|---|---|---|
| gizeh-0.1.12.tar.gz | 18.2 kB | Details |
Built distribution (wheel)
| File | Interpreter | ABI | Platform | Reset |
|---|---|---|---|---|
| gizeh-0.1.12-py3-none-any.whl | Python 3 | none | any | Details |
Total release size: 34.8 kB
Release files / gizeh-0.1.12.tar.gz
| Download URL | gizeh-0.1.12.tar.gz |
|---|---|
| Size | 18.2 kB |
| Tags | Source |
|
SHA-256 checksum How to use checksums |
f028d8a12fcea7b8cd21d0f9e7bcc4f24536c110577bdae44560f4d90176c4cb
|
|
BLAKE2b-256 checksum How to use checksums |
339fe32ed103aa7cb2a6b515b1ad80f12740ec6c3b4779478a3412eda291bf8e
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
Yes |
| Uploaded via |
twine/6.1.0 CPython/3.13.7
|
Provenance
Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.
PyPI Publish Attestation
PyPI verified that this artifact, at this checksum, originated from the publisher listed below.
Signed by GitHub Actions, verified by PyPI on Nov 18, 2025.
Transparency logRelease files / gizeh-0.1.12-py3-none-any.whl
| Download URL | gizeh-0.1.12-py3-none-any.whl |
|---|---|
| Size | 16.6 kB |
| Tags | Python 3 |
|
SHA-256 checksum How to use checksums |
e9dbc80a7d0777100269e930a8bbf9af9d614ef4ec3887c90638eb58754f8400
|
|
BLAKE2b-256 checksum How to use checksums |
3a5baab49edc13265788db575539f9e19d0c3fedd279f8206925cd7f00cdae48
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
Yes |
| Uploaded via |
twine/6.1.0 CPython/3.13.7
|
Provenance
Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.
PyPI Publish Attestation
PyPI verified that this artifact, at this checksum, originated from the publisher listed below.
Signed by GitHub Actions, verified by PyPI on Nov 18, 2025.
Transparency log