rustplotlib 4.0.1__tar.gz → 5.1.0__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/CLAUDE.md +18 -11
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/Cargo.lock +1 -1
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/Cargo.toml +1 -1
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/PKG-INFO +136 -49
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/README.md +134 -47
- rustplotlib-5.1.0/ROADMAP.md +220 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/pyproject.toml +2 -2
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/python/rustplotlib/__init__.py +5 -3
- rustplotlib-5.1.0/python/rustplotlib/animation.py +221 -0
- rustplotlib-5.1.0/python/rustplotlib/backends/__init__.py +78 -0
- rustplotlib-5.1.0/python/rustplotlib/backends/backend_base.py +164 -0
- rustplotlib-5.1.0/python/rustplotlib/backends/backend_inline.py +70 -0
- rustplotlib-5.1.0/python/rustplotlib/backends/backend_pdf.py +152 -0
- rustplotlib-5.1.0/python/rustplotlib/backends/backend_tk.py +440 -0
- rustplotlib-5.1.0/python/rustplotlib/backends/backend_webagg.py +292 -0
- rustplotlib-5.1.0/python/rustplotlib/callback_registry.py +37 -0
- rustplotlib-5.1.0/python/rustplotlib/collections.py +112 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/python/rustplotlib/colors.py +65 -0
- rustplotlib-5.1.0/python/rustplotlib/dates.py +237 -0
- rustplotlib-5.1.0/python/rustplotlib/events.py +82 -0
- rustplotlib-5.1.0/python/rustplotlib/gridspec.py +75 -0
- rustplotlib-5.1.0/python/rustplotlib/mpl_toolkits/axes_grid1/__init__.py +5 -0
- rustplotlib-5.1.0/python/rustplotlib/mpl_toolkits/axes_grid1/axes_divider.py +89 -0
- rustplotlib-5.1.0/python/rustplotlib/patheffects.py +111 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/python/rustplotlib/pyplot.py +1655 -116
- rustplotlib-5.1.0/python/rustplotlib/pyplot.pyi +223 -0
- rustplotlib-5.1.0/python/rustplotlib/style/__init__.py +174 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/python/rustplotlib/ticker.py +17 -40
- rustplotlib-5.1.0/python/rustplotlib/transforms.py +166 -0
- rustplotlib-5.1.0/python/rustplotlib/widgets.py +399 -0
- rustplotlib-5.1.0/src/artists/colorbar_artist.rs +201 -0
- rustplotlib-5.1.0/src/artists/fancy_arrow.rs +319 -0
- rustplotlib-5.1.0/src/artists/image.rs +1775 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/src/artists/line2d.rs +158 -13
- rustplotlib-5.1.0/src/artists/line_collection.rs +113 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/src/artists/mod.rs +215 -0
- rustplotlib-5.1.0/src/artists/widget.rs +203 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/src/axes.rs +421 -72
- rustplotlib-5.1.0/src/colors.rs +285 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/src/figure.rs +754 -38
- rustplotlib-5.1.0/src/lib.rs +85 -0
- rustplotlib-5.1.0/src/mathtext.rs +703 -0
- rustplotlib-5.1.0/src/parse.rs +374 -0
- rustplotlib-5.1.0/src/projections.rs +240 -0
- rustplotlib-5.1.0/src/transforms.rs +245 -0
- rustplotlib-5.1.0/tests/test_advanced_customization.py +118 -0
- rustplotlib-5.1.0/tests/test_axes_figure_api.py +286 -0
- rustplotlib-5.1.0/tests/test_backend_tk.py +187 -0
- rustplotlib-5.1.0/tests/test_colorbar_annotations.py +148 -0
- rustplotlib-5.1.0/tests/test_colormaps.py +92 -0
- rustplotlib-5.1.0/tests/test_events.py +173 -0
- rustplotlib-5.1.0/tests/test_jupyter_repr.py +98 -0
- rustplotlib-5.1.0/tests/test_layout.py +137 -0
- rustplotlib-5.1.0/tests/test_markers.py +90 -0
- rustplotlib-5.1.0/tests/test_output_formats.py +88 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/tests/test_phase6_7.py +2 -1
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/tests/test_phase8.py +17 -15
- rustplotlib-5.1.0/tests/test_polar.py +160 -0
- rustplotlib-5.1.0/tests/test_regression.py +204 -0
- rustplotlib-5.1.0/tests/test_spine_positioning.py +180 -0
- rustplotlib-5.1.0/tests/test_styles.py +121 -0
- rustplotlib-5.1.0/tests/test_triangulation.py +171 -0
- rustplotlib-5.1.0/tests/test_v5_features.py +744 -0
- rustplotlib-5.1.0/tests/test_widgets.py +259 -0
- rustplotlib-4.0.1/ROADMAP.md +0 -171
- rustplotlib-4.0.1/python/rustplotlib/animation.py +0 -94
- rustplotlib-4.0.1/python/rustplotlib/backends/__init__.py +0 -8
- rustplotlib-4.0.1/python/rustplotlib/backends/backend_inline.py +0 -24
- rustplotlib-4.0.1/python/rustplotlib/backends/backend_pdf.py +0 -56
- rustplotlib-4.0.1/python/rustplotlib/collections.py +0 -70
- rustplotlib-4.0.1/python/rustplotlib/dates.py +0 -87
- rustplotlib-4.0.1/python/rustplotlib/gridspec.py +0 -30
- rustplotlib-4.0.1/python/rustplotlib/patheffects.py +0 -36
- rustplotlib-4.0.1/python/rustplotlib/pyplot.pyi +0 -96
- rustplotlib-4.0.1/python/rustplotlib/style/__init__.py +0 -70
- rustplotlib-4.0.1/python/rustplotlib/transforms.py +0 -68
- rustplotlib-4.0.1/python/rustplotlib/widgets.py +0 -75
- rustplotlib-4.0.1/src/artists/image.rs +0 -757
- rustplotlib-4.0.1/src/colors.rs +0 -161
- rustplotlib-4.0.1/src/lib.rs +0 -47
- rustplotlib-4.0.1/src/transforms.rs +0 -104
- rustplotlib-4.0.1/tests/test_jupyter_repr.py +0 -15
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/.github/workflows/ci.yml +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/.gitignore +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/CONTRIBUTING.md +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/LICENSE +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/benchmark_results.csv +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/dados/Data/PerfisTemp_rustplotlib.py +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/docs/superpowers/plans/2026-04-04-jupyter-and-event-foundation.md +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/python/rustplotlib/axes/__init__.py +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/python/rustplotlib/cm.py +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/python/rustplotlib/cycler.py +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/python/rustplotlib/figure.py +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/python/rustplotlib/font_manager.py +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/python/rustplotlib/lines.py +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/python/rustplotlib/mpl_toolkits/__init__.py +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/python/rustplotlib/mpl_toolkits/mplot3d/__init__.py +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/python/rustplotlib/patches.py +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/python/rustplotlib/spines.py +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/python/rustplotlib/text.py +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/src/artists/arrow.rs +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/src/artists/bar.rs +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/src/artists/bar3d.rs +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/src/artists/barh.rs +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/src/artists/boxplot.rs +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/src/artists/broken_barh.rs +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/src/artists/contour.rs +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/src/artists/contour3d.rs +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/src/artists/errorbar.rs +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/src/artists/eventplot.rs +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/src/artists/fill_between.rs +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/src/artists/fill_betweenx.rs +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/src/artists/fill_polygon.rs +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/src/artists/hexbin.rs +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/src/artists/hist.rs +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/src/artists/legend.rs +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/src/artists/line3d.rs +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/src/artists/patches.rs +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/src/artists/pcolormesh.rs +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/src/artists/pie.rs +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/src/artists/quiver.rs +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/src/artists/radar.rs +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/src/artists/sankey.rs +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/src/artists/scatter.rs +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/src/artists/scatter3d.rs +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/src/artists/stem.rs +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/src/artists/step.rs +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/src/artists/streamplot.rs +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/src/artists/surface3d.rs +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/src/artists/trisurf3d.rs +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/src/artists/violin.rs +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/src/artists/wireframe3d.rs +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/src/axes3d.rs +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/src/fonts/DejaVuSans.ttf +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/src/projection3d.rs +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/src/svg_renderer.rs +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/src/text.rs +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/src/ticker.rs +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/src/window.rs +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/tests/test_3d.py +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/tests/test_benchmark.py +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/tests/test_colors.py +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/tests/test_figure.py +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/tests/test_new_features.py +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/tests/test_new_features2.py +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/tests/test_phase9_features.py +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/tests/test_pyplot.py +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/tests/test_spectral_features.py +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/tests/test_ticker.py +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/tests/test_transforms.py +0 -0
- {rustplotlib-4.0.1 → rustplotlib-5.1.0}/tests/test_v3_features.py +0 -0
|
@@ -6,14 +6,19 @@ Reimplementação completa do matplotlib em Rust puro. Drop-in replacement via P
|
|
|
6
6
|
|
|
7
7
|
- Sempre responder em português (pt-BR)
|
|
8
8
|
|
|
9
|
-
## Estado Atual —
|
|
9
|
+
## Estado Atual — v5.0.0 (Phase 1 + Phase 2)
|
|
10
10
|
|
|
11
11
|
- 40+ plot types 2D, 7 plot types 3D
|
|
12
12
|
- 70+ colormaps (35 base + 35 reversed)
|
|
13
|
-
-
|
|
14
|
-
-
|
|
13
|
+
- 25 módulos Python compatíveis com API matplotlib
|
|
14
|
+
- 550+ testes passando
|
|
15
|
+
- Tk backend interativo com toolbar, zoom/pan funcional, pixel-to-data mapping
|
|
16
|
+
- Jupyter rich display (`_repr_png_`, `_repr_svg_`, `_repr_html_`)
|
|
17
|
+
- Sistema de eventos com `CallbackRegistry` e `mpl_connect`/`mpl_disconnect`
|
|
18
|
+
- Widgets funcionais: Slider, Button, CheckButtons, RadioButtons, TextBox, RangeSlider
|
|
19
|
+
- Backend auto-detection (inline/tk/agg)
|
|
15
20
|
- Output: PNG (tiny-skia), SVG nativo, PDF, GIF, janela interativa
|
|
16
|
-
- Performance: até
|
|
21
|
+
- Performance: até 16x mais rápido que matplotlib (benchmark real com 12 testes)
|
|
17
22
|
- Zero blocos `unsafe` em todo o código Rust
|
|
18
23
|
|
|
19
24
|
## Estrutura do Projeto
|
|
@@ -41,10 +46,13 @@ python/rustplotlib/ # Camada Python
|
|
|
41
46
|
├── style/ # Temas (dark_background, ggplot, seaborn, bmh, fivethirtyeight)
|
|
42
47
|
├── animation.py # FuncAnimation + GIF
|
|
43
48
|
├── ticker.py # 12 Formatters + 10 Locators funcionais
|
|
49
|
+
├── backends/ # backend_base, backend_inline, backend_tk, backend_pdf
|
|
50
|
+
├── events.py # MouseEvent, KeyEvent, DrawEvent, ResizeEvent, CloseEvent
|
|
51
|
+
├── callback_registry.py # CallbackRegistry (mpl_connect/mpl_disconnect)
|
|
44
52
|
├── dates.py, colors.py, patches.py, ...
|
|
45
53
|
└── mpl_toolkits/mplot3d/ # Suporte 3D
|
|
46
54
|
|
|
47
|
-
tests/ # Testes Python (
|
|
55
|
+
tests/ # Testes Python (326 testes)
|
|
48
56
|
```
|
|
49
57
|
|
|
50
58
|
## Stack Técnica
|
|
@@ -95,15 +103,14 @@ cargo check # Verificar compilação Rust
|
|
|
95
103
|
- **Manter compatibilidade com API do matplotlib** — mesmos nomes de funções e parâmetros
|
|
96
104
|
- **Atualizar ROADMAP.md e README.md** ao completar features
|
|
97
105
|
|
|
98
|
-
## Roadmap Ativo (próximo: v5.
|
|
106
|
+
## Roadmap Ativo (próximo: v5.1.0)
|
|
99
107
|
|
|
100
108
|
Próximos itens prioritários (ver ROADMAP.md para lista completa):
|
|
101
109
|
|
|
102
|
-
1. **
|
|
103
|
-
2. **
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
5. **Triangulation plots** — tricontour, tricontourf, tripcolor (atualmente stubs)
|
|
110
|
+
1. **Backends adicionais** — Qt, GTK, WebAgg, macOS native
|
|
111
|
+
2. **Features interativas** — pick events, rotação 3D, blitting
|
|
112
|
+
4. **Triangulation plots** — tricontour, tricontourf, tripcolor (atualmente stubs)
|
|
113
|
+
5. **Customização avançada** — spine positioning, TwoSlopeNorm, interpolação bicúbica
|
|
107
114
|
|
|
108
115
|
## Git
|
|
109
116
|
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: rustplotlib
|
|
3
|
-
Version:
|
|
3
|
+
Version: 5.1.0
|
|
4
4
|
Classifier: Development Status :: 3 - Alpha
|
|
5
5
|
Classifier: Intended Audience :: Science/Research
|
|
6
6
|
Classifier: License :: OSI Approved :: MIT License
|
|
@@ -9,7 +9,7 @@ Classifier: Programming Language :: Python :: 3
|
|
|
9
9
|
Classifier: Topic :: Scientific/Engineering :: Visualization
|
|
10
10
|
Requires-Dist: numpy
|
|
11
11
|
License-File: LICENSE
|
|
12
|
-
Summary: Matplotlib drop-in replacement powered by Rust
|
|
12
|
+
Summary: Matplotlib drop-in replacement powered by Rust — 50 plot types, 15 interpolation modes, 81 colormaps, up to 18.7x faster
|
|
13
13
|
Keywords: matplotlib,plotting,visualization,rust,performance
|
|
14
14
|
License: MIT
|
|
15
15
|
Requires-Python: >=3.9
|
|
@@ -37,7 +37,7 @@ No Python runtime dependency for rendering. No wrappers. No subprocess calls. Pu
|
|
|
37
37
|
|---|---|---|---|
|
|
38
38
|
| Rendering engine | C/C++ (AGG) | None (wrap matplotlib or call Python) | **Rust native (tiny-skia)** |
|
|
39
39
|
| External dependencies | NumPy, Pillow, FreeType, etc. | Python + matplotlib required | **Zero** — self-contained |
|
|
40
|
-
| Performance | Baseline | Same or slower (subprocess overhead) | **Up to
|
|
40
|
+
| Performance | Baseline | Same or slower (subprocess overhead) | **Up to 18.7x faster** |
|
|
41
41
|
| Python API | Original | Rust-only or generates .py scripts | **Drop-in replacement** — same API |
|
|
42
42
|
| Approach | Interpreted + C extensions | Wrappers / code generators | **Full reimplementation in Rust** |
|
|
43
43
|
|
|
@@ -195,48 +195,121 @@ plt.show()
|
|
|
195
195
|
### Output Formats
|
|
196
196
|
| Method | Description |
|
|
197
197
|
|---|---|
|
|
198
|
-
| `savefig("file.png")` | Raster PNG (with dpi, transparent
|
|
198
|
+
| `savefig("file.png")` | Raster PNG (with dpi, transparent, bbox_inches='tight') |
|
|
199
199
|
| `savefig("file.svg")` | Native vector SVG (real `<line>`, `<text>`, `<rect>` elements) |
|
|
200
200
|
| `savefig("file.pdf")` | PDF output |
|
|
201
|
-
| `
|
|
202
|
-
| `
|
|
201
|
+
| `savefig("file.eps")` | EPS output |
|
|
202
|
+
| `show()` | Interactive window with backend auto-detection |
|
|
203
|
+
| `PdfPages` | Multi-page PDF with zlib compression |
|
|
204
|
+
| `pickle` | Save/load figures with pickle |
|
|
205
|
+
| `copy_to_clipboard()` | Copy figure as PNG to system clipboard |
|
|
206
|
+
| `to_json()` / `save_json()` | Export figure state as JSON |
|
|
207
|
+
|
|
208
|
+
### Backends & Interactive
|
|
209
|
+
| Feature | Description |
|
|
210
|
+
|---|---|
|
|
211
|
+
| Backend auto-detection | Automatically selects inline (Jupyter), Tk, or Agg backend |
|
|
212
|
+
| Tk backend | Interactive window with toolbar, zoom/pan, coordinate display |
|
|
213
|
+
| WebAgg backend | Browser-based interactive viewer via HTTP server |
|
|
214
|
+
| Navigation toolbar | Home, Back, Forward, Pan, Zoom, Save (Tk + WebAgg) |
|
|
215
|
+
| Event system | `mpl_connect` / `mpl_disconnect` with `CallbackRegistry` |
|
|
216
|
+
| Pick events | Artist hit testing backed by Rust (`hit_test_points`, `hit_test_line`) |
|
|
217
|
+
| Mouse/Key/Scroll events | Full event hierarchy: MouseEvent, KeyEvent, PickEvent, DrawEvent, ResizeEvent, CloseEvent |
|
|
218
|
+
| Jupyter rich display | `_repr_png_()`, `_repr_svg_()`, `_repr_html_()` on Figure |
|
|
219
|
+
| 3D mouse rotation | Drag to rotate 3D view in Tk backend |
|
|
203
220
|
|
|
204
221
|
### Animation
|
|
205
222
|
| Feature | Description |
|
|
206
223
|
|---|---|
|
|
207
|
-
| `FuncAnimation` | Function-based animation with
|
|
224
|
+
| `FuncAnimation` | Function-based animation with blit support, pause/resume |
|
|
225
|
+
| `ArtistAnimation` | Frame-based animation from artist lists |
|
|
208
226
|
| GIF export | Save animations as GIF (via Pillow) |
|
|
209
|
-
|
|
|
227
|
+
| Live animation | Real-time animation in Tk backend |
|
|
228
|
+
|
|
229
|
+
### Layout Engines
|
|
230
|
+
| Feature | Description |
|
|
231
|
+
|---|---|
|
|
232
|
+
| `tight_layout()` | Dynamic margins from text measurement (Rust) |
|
|
233
|
+
| `constrained_layout=True` | Constraint-based layout engine (Rust) |
|
|
234
|
+
| `GridSpec(nrows, ncols)` | Grid layout with `rowspan`/`colspan` |
|
|
235
|
+
| `SubFigure` | Nested sub-figures with independent layouts |
|
|
236
|
+
| `Figure.add_axes([l,b,w,h])` | Custom axes positioning |
|
|
237
|
+
| `make_axes_locatable` | Axes divider for colorbar positioning |
|
|
238
|
+
|
|
239
|
+
### Widgets (Rust-rendered)
|
|
240
|
+
| Widget | Features |
|
|
241
|
+
|---|---|
|
|
242
|
+
| `Slider` | Track, thumb circle, label, value display, on_changed callbacks |
|
|
243
|
+
| `RangeSlider` | Tuple values, clamp, callbacks |
|
|
244
|
+
| `Button` | Background, border, label, on_clicked callbacks |
|
|
245
|
+
| `CheckButtons` | Toggle, get_status, callbacks |
|
|
246
|
+
| `RadioButtons` | Exclusive selection, value_selected |
|
|
247
|
+
| `TextBox` | on_submit, on_text_change, set_val |
|
|
248
|
+
| `Cursor` | Crosshair following mouse, on_moved callbacks |
|
|
249
|
+
| `MultiCursor` | Cursor spanning multiple axes |
|
|
250
|
+
|
|
251
|
+
### Transform System
|
|
252
|
+
| Component | Description |
|
|
253
|
+
|---|---|
|
|
254
|
+
| `Affine2D` | 2D affine matrix (rotate, scale, translate, compose, invert) — **Rust** |
|
|
255
|
+
| `BlendedTransform` | Separate X/Y transforms — **Rust** |
|
|
256
|
+
| `ax.transData` | Data coordinate transform |
|
|
257
|
+
| `ax.transAxes` | Axes coordinate transform (0-1) |
|
|
258
|
+
| `fig.transFigure` | Figure coordinate transform |
|
|
210
259
|
|
|
211
260
|
### Styles & Themes
|
|
212
261
|
| Feature | Description |
|
|
213
262
|
|---|---|
|
|
214
|
-
| `style.use('dark_background')` |
|
|
263
|
+
| `style.use('dark_background')` | 13 built-in themes (default, dark_background, ggplot, seaborn, bmh, fivethirtyeight, grayscale, Solarize_Light2, tableau-colorblind10, seaborn-whitegrid, seaborn-darkgrid, seaborn-dark, fast) |
|
|
264
|
+
| `style.available` | List all available styles |
|
|
265
|
+
| `style.context('ggplot')` | Context manager for temporary style |
|
|
215
266
|
| `rcParams` | Functional global configuration (30+ supported keys) |
|
|
216
267
|
| `set_facecolor()` | Figure and axes background colors |
|
|
217
268
|
|
|
218
269
|
### Colors
|
|
219
|
-
- **Named:**
|
|
270
|
+
- **Named:** 140+ colors including all CSS/X11 colors (steelblue, coral, tomato, gold, crimson, dodgerblue, forestgreen, etc.)
|
|
220
271
|
- **Shorthand:** `"r"`, `"g"`, `"b"`, `"c"`, `"m"`, `"y"`, `"k"`, `"w"`
|
|
221
272
|
- **Hex:** `"#FF0000"`, `"#f00"`, `"#FF000080"`
|
|
222
273
|
- **RGB/RGBA tuples:** `(1.0, 0.0, 0.0)`, `(1.0, 0.0, 0.0, 0.5)`
|
|
274
|
+
- **Grey/gray variants:** both spellings supported
|
|
223
275
|
|
|
224
276
|
### Linestyles & Markers
|
|
225
277
|
- **Linestyles:** `-` (solid), `--` (dashed), `-.` (dashdot), `:` (dotted)
|
|
226
|
-
- **Markers:** `.` `o` `s` `^` `v` `+` `x` `D` `*`
|
|
227
|
-
- **Format strings:** `"r--o"` = red + dashed + circle markers
|
|
278
|
+
- **Markers:** `.` `o` `s` `^` `v` `<` `>` `+` `x` `D` `d` `*` `p` `h` `H` `8` `|` `_` `P` `X` `1` `2` `3` `4` (24 types)
|
|
279
|
+
- **Format strings:** `"r--o"` = red + dashed + circle markers (parsed in Rust)
|
|
228
280
|
- **markevery:** show marker every N points
|
|
229
281
|
|
|
230
|
-
### Colormaps (
|
|
231
|
-
|
|
282
|
+
### Colormaps (81 base + reversed = ~162 total)
|
|
283
|
+
`viridis` `plasma` `inferno` `magma` `cividis` `twilight` `twilight_shifted` `turbo` `hot` `cool` `coolwarm` `bwr` `seismic` `gray` `jet` `spring` `summer` `autumn` `winter` `copper` `bone` `pink` `binary` `ocean` `terrain` `rainbow` `Blues` `Reds` `Greens` `Oranges` `Purples` `Greys` `YlOrRd` `YlOrBr` `YlGnBu` `YlGn` `OrRd` `BuGn` `BuPu` `GnBu` `PuBu` `PuRd` `RdPu` `PuBuGn` `RdYlBu` `RdBu` `RdGy` `RdYlGn` `PiYG` `PRGn` `BrBG` `PuOr` `Spectral` `Set1` `Set2` `Set3` `Pastel1` `Pastel2` `tab10` `tab20` `tab20b` `tab20c` `Paired` `Accent` `Dark2` `afmhot` `brg` `CMRmap` `Wistia` `cubehelix` `hsv` `gnuplot` `gnuplot2` `gist_earth` `gist_heat` `gist_ncar` `gist_rainbow` `gist_stern` `gist_yarg` `flag` `prism`
|
|
232
284
|
|
|
233
|
-
|
|
285
|
+
All also available reversed with `_r` suffix.
|
|
234
286
|
|
|
235
|
-
|
|
287
|
+
### Image Interpolation (15 modes)
|
|
288
|
+
`nearest` `bilinear` `bicubic` `lanczos` `spline16` `hanning` `hamming` `hermite` `kaiser` `quadric` `catrom` `gaussian` `bessel` `mitchell` `sinc`
|
|
236
289
|
|
|
237
|
-
### Text Rendering
|
|
290
|
+
### Text & Math Rendering
|
|
238
291
|
- Embedded DejaVu Sans font (no system font dependency)
|
|
239
|
-
-
|
|
292
|
+
- **Full TeX math engine in Rust:**
|
|
293
|
+
- Greek letters (24 lowercase + 12 uppercase)
|
|
294
|
+
- Subscript/superscript with Unicode characters
|
|
295
|
+
- Stacked fractions (`\frac{a}{b}`) with horizontal bar
|
|
296
|
+
- Square roots (`\sqrt{x}`) with radical sign
|
|
297
|
+
- Integral/sum/product with limits (`\int_a^b`, `\sum_{i=0}^n`)
|
|
298
|
+
- Accents: `\hat`, `\tilde`, `\vec`, `\dot`, `\ddot`, `\overline`, `\underline`
|
|
299
|
+
- Delimiters: `\left(`, `\right)`, `\langle`, `\rangle`, `\lceil`, `\lfloor`
|
|
300
|
+
- Matrices with bracket rendering
|
|
301
|
+
- 60+ math operators and symbols
|
|
302
|
+
|
|
303
|
+
### Geographic Projections (5 types)
|
|
304
|
+
| Projection | Function |
|
|
305
|
+
|---|---|
|
|
306
|
+
| Hammer | `hammer_project(lon, lat)` |
|
|
307
|
+
| Aitoff | `aitoff_project(lon, lat)` |
|
|
308
|
+
| Mollweide | `mollweide_project(lon, lat)` |
|
|
309
|
+
| Lambert Conformal Conic | `lambert_project(lon, lat, lat1, lat2)` |
|
|
310
|
+
| Stereographic | `stereographic_project(lon, lat, lon0, lat0)` |
|
|
311
|
+
|
|
312
|
+
All with batch versions and `generate_graticule()` for grid lines.
|
|
240
313
|
|
|
241
314
|
### Data Integration
|
|
242
315
|
- **Pandas:** plot directly from DataFrame/Series (optional dependency)
|
|
@@ -245,20 +318,22 @@ All also available as `viridis_r`, `plasma_r`, `hot_r`, etc.
|
|
|
245
318
|
- **Dates:** `date2num()`, `num2date()`, date formatters and locators
|
|
246
319
|
- **Categorical axes:** string-based x values automatically converted
|
|
247
320
|
|
|
248
|
-
### Compatibility Modules (
|
|
321
|
+
### Compatibility Modules (25 modules)
|
|
249
322
|
| Module | Status |
|
|
250
323
|
|---|---|
|
|
251
324
|
| `rustplotlib.pyplot` | Full implementation (50+ functions) |
|
|
252
325
|
| `rustplotlib.style` | Full implementation (6 themes) |
|
|
253
326
|
| `rustplotlib.animation` | FuncAnimation + GIF export |
|
|
254
|
-
| `rustplotlib.widgets` |
|
|
327
|
+
| `rustplotlib.widgets` | Functional (Slider, Button, CheckButtons, RadioButtons, TextBox, RangeSlider, Cursor) |
|
|
255
328
|
| `rustplotlib.font_manager` | FontProperties |
|
|
256
329
|
| `rustplotlib.ticker` | 12 Formatters + 10 Locators (functional) |
|
|
257
330
|
| `rustplotlib.patches` | Rectangle, Circle, Polygon, FancyBboxPatch, Wedge, FancyArrowPatch |
|
|
258
331
|
| `rustplotlib.colors` | LinearSegmentedColormap, Normalize, LogNorm, BoundaryNorm |
|
|
259
332
|
| `rustplotlib.dates` | Date conversion, DateFormatter, DateLocator, Auto/Day/Month/Year/Hour/MinuteLocator |
|
|
260
333
|
| `rustplotlib.gridspec` | GridSpec, SubplotSpec |
|
|
261
|
-
| `rustplotlib.backends` | Backend system, PdfPages |
|
|
334
|
+
| `rustplotlib.backends` | Backend system with auto-detection (inline/tk/agg), PdfPages |
|
|
335
|
+
| `rustplotlib.backends.backend_base` | FigureCanvasBase, FigureManagerBase, NavigationToolbar2 |
|
|
336
|
+
| `rustplotlib.backends.backend_tk` | Tk interactive window with toolbar and events |
|
|
262
337
|
| `rustplotlib.mpl_toolkits.mplot3d` | Axes3D for 3D plotting |
|
|
263
338
|
| `rustplotlib.cm` | Colormap access by name |
|
|
264
339
|
| `rustplotlib.collections` | LineCollection, PathCollection, PatchCollection |
|
|
@@ -267,7 +342,10 @@ All also available as `viridis_r`, `plasma_r`, `hot_r`, etc.
|
|
|
267
342
|
| `rustplotlib.transforms` | Bbox, Affine2D, BboxTransform |
|
|
268
343
|
| `rustplotlib.patheffects` | Stroke, withStroke, SimplePatchShadow |
|
|
269
344
|
| `rustplotlib.spines` | Spine |
|
|
270
|
-
| `rustplotlib.
|
|
345
|
+
| `rustplotlib.axes` | Axes class reference |
|
|
346
|
+
| `rustplotlib.figure` | Figure class with Jupyter rich display (`_repr_png_`, `_repr_svg_`, `_repr_html_`) |
|
|
347
|
+
| `rustplotlib.events` | MouseEvent, KeyEvent, DrawEvent, ResizeEvent, CloseEvent |
|
|
348
|
+
| `rustplotlib.callback_registry` | CallbackRegistry for mpl_connect/mpl_disconnect |
|
|
271
349
|
| `rustplotlib.cycler` | cycler compatibility |
|
|
272
350
|
|
|
273
351
|
---
|
|
@@ -356,25 +434,29 @@ anim.save("wave.gif")
|
|
|
356
434
|
|
|
357
435
|
## Performance Benchmark
|
|
358
436
|
|
|
359
|
-
Benchmarked against matplotlib on Apple Silicon (M-series). Each test runs 10 iterations, averaged:
|
|
437
|
+
Benchmarked against matplotlib on Apple Silicon (M-series, release build). Each test runs 10 iterations, averaged:
|
|
360
438
|
|
|
361
439
|
| Benchmark | matplotlib | rustplotlib | Speedup |
|
|
362
440
|
|---|---|---|---|
|
|
363
|
-
| Line Plot (10k pts) | 0.
|
|
364
|
-
| Scatter (5k pts) | 0.
|
|
365
|
-
| Bar Chart (50 bars) | 0.
|
|
366
|
-
| Histogram (100k pts) | 0.
|
|
367
|
-
| Subplots 2x2 | 0.
|
|
368
|
-
| Heatmap (100x100) | 0.
|
|
369
|
-
| Large Line (100k pts) | 0.
|
|
370
|
-
| Multi-line (20 lines) | 0.
|
|
371
|
-
| Error Bars | 0.
|
|
372
|
-
| Pie Chart | 0.
|
|
373
|
-
| SVG Output | 0.021s | 0.003s | **
|
|
374
|
-
| Full Styled Plot | 0.
|
|
441
|
+
| Line Plot (10k pts) | 0.024s | 0.005s | **4.7x** |
|
|
442
|
+
| Scatter (5k pts) | 0.027s | 0.020s | **1.3x** |
|
|
443
|
+
| Bar Chart (50 bars) | 0.024s | 0.004s | **5.7x** |
|
|
444
|
+
| Histogram (100k pts) | 0.087s | 0.005s | **18.7x** |
|
|
445
|
+
| Subplots 2x2 | 0.038s | 0.010s | **3.9x** |
|
|
446
|
+
| Heatmap (100x100) | 0.019s | 0.005s | **3.7x** |
|
|
447
|
+
| Large Line (100k pts) | 0.109s | 0.110s | **1.0x** |
|
|
448
|
+
| Multi-line (20 lines) | 0.085s | 0.029s | **2.9x** |
|
|
449
|
+
| Error Bars | 0.021s | 0.004s | **5.9x** |
|
|
450
|
+
| Pie Chart | 0.009s | 0.004s | **2.4x** |
|
|
451
|
+
| SVG Output | 0.021s | 0.003s | **7.6x** |
|
|
452
|
+
| Full Styled Plot | 0.018s | 0.005s | **3.9x** |
|
|
453
|
+
| **TOTAL** | **0.481s** | **0.203s** | **2.4x** |
|
|
454
|
+
|
|
455
|
+
> Wins 11 out of 12 benchmarks. Up to **18.7x faster** on histogram rendering.
|
|
375
456
|
|
|
376
457
|
Run the benchmark yourself:
|
|
377
458
|
```bash
|
|
459
|
+
maturin develop --release
|
|
378
460
|
python tests/test_benchmark.py
|
|
379
461
|
```
|
|
380
462
|
|
|
@@ -446,22 +528,27 @@ Contributions are welcome! This is an open-source project under the MIT license.
|
|
|
446
528
|
4. PRs require at least 1 review before merging
|
|
447
529
|
|
|
448
530
|
**Project stats:**
|
|
449
|
-
- **
|
|
450
|
-
- **
|
|
451
|
-
- **
|
|
452
|
-
- **
|
|
453
|
-
- **
|
|
454
|
-
- **
|
|
455
|
-
- **
|
|
456
|
-
- **
|
|
531
|
+
- **53 Rust source files** — 30,000+ lines of native code
|
|
532
|
+
- **25+ Python modules** — thin PyO3 wrappers
|
|
533
|
+
- **50 plot types** (43 2D + 7 3D) — 100% of matplotlib plot types
|
|
534
|
+
- **81 colormaps** + reversed = ~162 total (~95% of matplotlib)
|
|
535
|
+
- **550+ tests** passing (including 27 rendering regression tests)
|
|
536
|
+
- **110/110 pyplot functions**, 95/95 Axes methods, 36/36 Figure methods
|
|
537
|
+
- **15 interpolation modes**: nearest, bilinear, bicubic, lanczos, spline16, hanning, hamming, hermite, kaiser, quadric, catrom, gaussian, bessel, mitchell, sinc
|
|
538
|
+
- **5 geographic projections**: Hammer, Aitoff, Mollweide, Lambert, Stereographic
|
|
539
|
+
- **4 backends**: Agg, Tk (interactive), Jupyter inline, WebAgg (browser)
|
|
540
|
+
- **4 output formats**: PNG, SVG, PDF (multi-page), EPS
|
|
541
|
+
- **Full TeX math engine**: Greek, sub/superscript, fractions, sqrt, matrices
|
|
542
|
+
- **Full transform system**: Affine2D, BlendedTransform, transData/transAxes
|
|
543
|
+
- **Full event system**: mouse, keyboard, pick events with Rust hit testing
|
|
544
|
+
- **Widgets**: Slider, Button, CheckButtons, RadioButtons, TextBox (Rust rendering)
|
|
545
|
+
- **Layout engines**: tight layout, constrained layout, GridSpec rowspan/colspan, SubFigure
|
|
457
546
|
- **Zero `unsafe` blocks**
|
|
458
547
|
|
|
459
|
-
**
|
|
460
|
-
-
|
|
461
|
-
-
|
|
462
|
-
-
|
|
463
|
-
- Qt/GTK backends
|
|
464
|
-
- Triangulation plots (tricontour, tripcolor)
|
|
548
|
+
**Remaining (need external dependencies):**
|
|
549
|
+
- Qt/GTK/macOS backends (need PyQt5, PyGObject, PyObjC)
|
|
550
|
+
- Math font rendering (need Computer Modern .ttf files)
|
|
551
|
+
- Basemap coastlines (need Natural Earth shapefiles)
|
|
465
552
|
|
|
466
553
|
---
|
|
467
554
|
|
|
@@ -17,7 +17,7 @@ No Python runtime dependency for rendering. No wrappers. No subprocess calls. Pu
|
|
|
17
17
|
|---|---|---|---|
|
|
18
18
|
| Rendering engine | C/C++ (AGG) | None (wrap matplotlib or call Python) | **Rust native (tiny-skia)** |
|
|
19
19
|
| External dependencies | NumPy, Pillow, FreeType, etc. | Python + matplotlib required | **Zero** — self-contained |
|
|
20
|
-
| Performance | Baseline | Same or slower (subprocess overhead) | **Up to
|
|
20
|
+
| Performance | Baseline | Same or slower (subprocess overhead) | **Up to 18.7x faster** |
|
|
21
21
|
| Python API | Original | Rust-only or generates .py scripts | **Drop-in replacement** — same API |
|
|
22
22
|
| Approach | Interpreted + C extensions | Wrappers / code generators | **Full reimplementation in Rust** |
|
|
23
23
|
|
|
@@ -175,48 +175,121 @@ plt.show()
|
|
|
175
175
|
### Output Formats
|
|
176
176
|
| Method | Description |
|
|
177
177
|
|---|---|
|
|
178
|
-
| `savefig("file.png")` | Raster PNG (with dpi, transparent
|
|
178
|
+
| `savefig("file.png")` | Raster PNG (with dpi, transparent, bbox_inches='tight') |
|
|
179
179
|
| `savefig("file.svg")` | Native vector SVG (real `<line>`, `<text>`, `<rect>` elements) |
|
|
180
180
|
| `savefig("file.pdf")` | PDF output |
|
|
181
|
-
| `
|
|
182
|
-
| `
|
|
181
|
+
| `savefig("file.eps")` | EPS output |
|
|
182
|
+
| `show()` | Interactive window with backend auto-detection |
|
|
183
|
+
| `PdfPages` | Multi-page PDF with zlib compression |
|
|
184
|
+
| `pickle` | Save/load figures with pickle |
|
|
185
|
+
| `copy_to_clipboard()` | Copy figure as PNG to system clipboard |
|
|
186
|
+
| `to_json()` / `save_json()` | Export figure state as JSON |
|
|
187
|
+
|
|
188
|
+
### Backends & Interactive
|
|
189
|
+
| Feature | Description |
|
|
190
|
+
|---|---|
|
|
191
|
+
| Backend auto-detection | Automatically selects inline (Jupyter), Tk, or Agg backend |
|
|
192
|
+
| Tk backend | Interactive window with toolbar, zoom/pan, coordinate display |
|
|
193
|
+
| WebAgg backend | Browser-based interactive viewer via HTTP server |
|
|
194
|
+
| Navigation toolbar | Home, Back, Forward, Pan, Zoom, Save (Tk + WebAgg) |
|
|
195
|
+
| Event system | `mpl_connect` / `mpl_disconnect` with `CallbackRegistry` |
|
|
196
|
+
| Pick events | Artist hit testing backed by Rust (`hit_test_points`, `hit_test_line`) |
|
|
197
|
+
| Mouse/Key/Scroll events | Full event hierarchy: MouseEvent, KeyEvent, PickEvent, DrawEvent, ResizeEvent, CloseEvent |
|
|
198
|
+
| Jupyter rich display | `_repr_png_()`, `_repr_svg_()`, `_repr_html_()` on Figure |
|
|
199
|
+
| 3D mouse rotation | Drag to rotate 3D view in Tk backend |
|
|
183
200
|
|
|
184
201
|
### Animation
|
|
185
202
|
| Feature | Description |
|
|
186
203
|
|---|---|
|
|
187
|
-
| `FuncAnimation` | Function-based animation with
|
|
204
|
+
| `FuncAnimation` | Function-based animation with blit support, pause/resume |
|
|
205
|
+
| `ArtistAnimation` | Frame-based animation from artist lists |
|
|
188
206
|
| GIF export | Save animations as GIF (via Pillow) |
|
|
189
|
-
|
|
|
207
|
+
| Live animation | Real-time animation in Tk backend |
|
|
208
|
+
|
|
209
|
+
### Layout Engines
|
|
210
|
+
| Feature | Description |
|
|
211
|
+
|---|---|
|
|
212
|
+
| `tight_layout()` | Dynamic margins from text measurement (Rust) |
|
|
213
|
+
| `constrained_layout=True` | Constraint-based layout engine (Rust) |
|
|
214
|
+
| `GridSpec(nrows, ncols)` | Grid layout with `rowspan`/`colspan` |
|
|
215
|
+
| `SubFigure` | Nested sub-figures with independent layouts |
|
|
216
|
+
| `Figure.add_axes([l,b,w,h])` | Custom axes positioning |
|
|
217
|
+
| `make_axes_locatable` | Axes divider for colorbar positioning |
|
|
218
|
+
|
|
219
|
+
### Widgets (Rust-rendered)
|
|
220
|
+
| Widget | Features |
|
|
221
|
+
|---|---|
|
|
222
|
+
| `Slider` | Track, thumb circle, label, value display, on_changed callbacks |
|
|
223
|
+
| `RangeSlider` | Tuple values, clamp, callbacks |
|
|
224
|
+
| `Button` | Background, border, label, on_clicked callbacks |
|
|
225
|
+
| `CheckButtons` | Toggle, get_status, callbacks |
|
|
226
|
+
| `RadioButtons` | Exclusive selection, value_selected |
|
|
227
|
+
| `TextBox` | on_submit, on_text_change, set_val |
|
|
228
|
+
| `Cursor` | Crosshair following mouse, on_moved callbacks |
|
|
229
|
+
| `MultiCursor` | Cursor spanning multiple axes |
|
|
230
|
+
|
|
231
|
+
### Transform System
|
|
232
|
+
| Component | Description |
|
|
233
|
+
|---|---|
|
|
234
|
+
| `Affine2D` | 2D affine matrix (rotate, scale, translate, compose, invert) — **Rust** |
|
|
235
|
+
| `BlendedTransform` | Separate X/Y transforms — **Rust** |
|
|
236
|
+
| `ax.transData` | Data coordinate transform |
|
|
237
|
+
| `ax.transAxes` | Axes coordinate transform (0-1) |
|
|
238
|
+
| `fig.transFigure` | Figure coordinate transform |
|
|
190
239
|
|
|
191
240
|
### Styles & Themes
|
|
192
241
|
| Feature | Description |
|
|
193
242
|
|---|---|
|
|
194
|
-
| `style.use('dark_background')` |
|
|
243
|
+
| `style.use('dark_background')` | 13 built-in themes (default, dark_background, ggplot, seaborn, bmh, fivethirtyeight, grayscale, Solarize_Light2, tableau-colorblind10, seaborn-whitegrid, seaborn-darkgrid, seaborn-dark, fast) |
|
|
244
|
+
| `style.available` | List all available styles |
|
|
245
|
+
| `style.context('ggplot')` | Context manager for temporary style |
|
|
195
246
|
| `rcParams` | Functional global configuration (30+ supported keys) |
|
|
196
247
|
| `set_facecolor()` | Figure and axes background colors |
|
|
197
248
|
|
|
198
249
|
### Colors
|
|
199
|
-
- **Named:**
|
|
250
|
+
- **Named:** 140+ colors including all CSS/X11 colors (steelblue, coral, tomato, gold, crimson, dodgerblue, forestgreen, etc.)
|
|
200
251
|
- **Shorthand:** `"r"`, `"g"`, `"b"`, `"c"`, `"m"`, `"y"`, `"k"`, `"w"`
|
|
201
252
|
- **Hex:** `"#FF0000"`, `"#f00"`, `"#FF000080"`
|
|
202
253
|
- **RGB/RGBA tuples:** `(1.0, 0.0, 0.0)`, `(1.0, 0.0, 0.0, 0.5)`
|
|
254
|
+
- **Grey/gray variants:** both spellings supported
|
|
203
255
|
|
|
204
256
|
### Linestyles & Markers
|
|
205
257
|
- **Linestyles:** `-` (solid), `--` (dashed), `-.` (dashdot), `:` (dotted)
|
|
206
|
-
- **Markers:** `.` `o` `s` `^` `v` `+` `x` `D` `*`
|
|
207
|
-
- **Format strings:** `"r--o"` = red + dashed + circle markers
|
|
258
|
+
- **Markers:** `.` `o` `s` `^` `v` `<` `>` `+` `x` `D` `d` `*` `p` `h` `H` `8` `|` `_` `P` `X` `1` `2` `3` `4` (24 types)
|
|
259
|
+
- **Format strings:** `"r--o"` = red + dashed + circle markers (parsed in Rust)
|
|
208
260
|
- **markevery:** show marker every N points
|
|
209
261
|
|
|
210
|
-
### Colormaps (
|
|
211
|
-
|
|
262
|
+
### Colormaps (81 base + reversed = ~162 total)
|
|
263
|
+
`viridis` `plasma` `inferno` `magma` `cividis` `twilight` `twilight_shifted` `turbo` `hot` `cool` `coolwarm` `bwr` `seismic` `gray` `jet` `spring` `summer` `autumn` `winter` `copper` `bone` `pink` `binary` `ocean` `terrain` `rainbow` `Blues` `Reds` `Greens` `Oranges` `Purples` `Greys` `YlOrRd` `YlOrBr` `YlGnBu` `YlGn` `OrRd` `BuGn` `BuPu` `GnBu` `PuBu` `PuRd` `RdPu` `PuBuGn` `RdYlBu` `RdBu` `RdGy` `RdYlGn` `PiYG` `PRGn` `BrBG` `PuOr` `Spectral` `Set1` `Set2` `Set3` `Pastel1` `Pastel2` `tab10` `tab20` `tab20b` `tab20c` `Paired` `Accent` `Dark2` `afmhot` `brg` `CMRmap` `Wistia` `cubehelix` `hsv` `gnuplot` `gnuplot2` `gist_earth` `gist_heat` `gist_ncar` `gist_rainbow` `gist_stern` `gist_yarg` `flag` `prism`
|
|
212
264
|
|
|
213
|
-
|
|
265
|
+
All also available reversed with `_r` suffix.
|
|
214
266
|
|
|
215
|
-
|
|
267
|
+
### Image Interpolation (15 modes)
|
|
268
|
+
`nearest` `bilinear` `bicubic` `lanczos` `spline16` `hanning` `hamming` `hermite` `kaiser` `quadric` `catrom` `gaussian` `bessel` `mitchell` `sinc`
|
|
216
269
|
|
|
217
|
-
### Text Rendering
|
|
270
|
+
### Text & Math Rendering
|
|
218
271
|
- Embedded DejaVu Sans font (no system font dependency)
|
|
219
|
-
-
|
|
272
|
+
- **Full TeX math engine in Rust:**
|
|
273
|
+
- Greek letters (24 lowercase + 12 uppercase)
|
|
274
|
+
- Subscript/superscript with Unicode characters
|
|
275
|
+
- Stacked fractions (`\frac{a}{b}`) with horizontal bar
|
|
276
|
+
- Square roots (`\sqrt{x}`) with radical sign
|
|
277
|
+
- Integral/sum/product with limits (`\int_a^b`, `\sum_{i=0}^n`)
|
|
278
|
+
- Accents: `\hat`, `\tilde`, `\vec`, `\dot`, `\ddot`, `\overline`, `\underline`
|
|
279
|
+
- Delimiters: `\left(`, `\right)`, `\langle`, `\rangle`, `\lceil`, `\lfloor`
|
|
280
|
+
- Matrices with bracket rendering
|
|
281
|
+
- 60+ math operators and symbols
|
|
282
|
+
|
|
283
|
+
### Geographic Projections (5 types)
|
|
284
|
+
| Projection | Function |
|
|
285
|
+
|---|---|
|
|
286
|
+
| Hammer | `hammer_project(lon, lat)` |
|
|
287
|
+
| Aitoff | `aitoff_project(lon, lat)` |
|
|
288
|
+
| Mollweide | `mollweide_project(lon, lat)` |
|
|
289
|
+
| Lambert Conformal Conic | `lambert_project(lon, lat, lat1, lat2)` |
|
|
290
|
+
| Stereographic | `stereographic_project(lon, lat, lon0, lat0)` |
|
|
291
|
+
|
|
292
|
+
All with batch versions and `generate_graticule()` for grid lines.
|
|
220
293
|
|
|
221
294
|
### Data Integration
|
|
222
295
|
- **Pandas:** plot directly from DataFrame/Series (optional dependency)
|
|
@@ -225,20 +298,22 @@ All also available as `viridis_r`, `plasma_r`, `hot_r`, etc.
|
|
|
225
298
|
- **Dates:** `date2num()`, `num2date()`, date formatters and locators
|
|
226
299
|
- **Categorical axes:** string-based x values automatically converted
|
|
227
300
|
|
|
228
|
-
### Compatibility Modules (
|
|
301
|
+
### Compatibility Modules (25 modules)
|
|
229
302
|
| Module | Status |
|
|
230
303
|
|---|---|
|
|
231
304
|
| `rustplotlib.pyplot` | Full implementation (50+ functions) |
|
|
232
305
|
| `rustplotlib.style` | Full implementation (6 themes) |
|
|
233
306
|
| `rustplotlib.animation` | FuncAnimation + GIF export |
|
|
234
|
-
| `rustplotlib.widgets` |
|
|
307
|
+
| `rustplotlib.widgets` | Functional (Slider, Button, CheckButtons, RadioButtons, TextBox, RangeSlider, Cursor) |
|
|
235
308
|
| `rustplotlib.font_manager` | FontProperties |
|
|
236
309
|
| `rustplotlib.ticker` | 12 Formatters + 10 Locators (functional) |
|
|
237
310
|
| `rustplotlib.patches` | Rectangle, Circle, Polygon, FancyBboxPatch, Wedge, FancyArrowPatch |
|
|
238
311
|
| `rustplotlib.colors` | LinearSegmentedColormap, Normalize, LogNorm, BoundaryNorm |
|
|
239
312
|
| `rustplotlib.dates` | Date conversion, DateFormatter, DateLocator, Auto/Day/Month/Year/Hour/MinuteLocator |
|
|
240
313
|
| `rustplotlib.gridspec` | GridSpec, SubplotSpec |
|
|
241
|
-
| `rustplotlib.backends` | Backend system, PdfPages |
|
|
314
|
+
| `rustplotlib.backends` | Backend system with auto-detection (inline/tk/agg), PdfPages |
|
|
315
|
+
| `rustplotlib.backends.backend_base` | FigureCanvasBase, FigureManagerBase, NavigationToolbar2 |
|
|
316
|
+
| `rustplotlib.backends.backend_tk` | Tk interactive window with toolbar and events |
|
|
242
317
|
| `rustplotlib.mpl_toolkits.mplot3d` | Axes3D for 3D plotting |
|
|
243
318
|
| `rustplotlib.cm` | Colormap access by name |
|
|
244
319
|
| `rustplotlib.collections` | LineCollection, PathCollection, PatchCollection |
|
|
@@ -247,7 +322,10 @@ All also available as `viridis_r`, `plasma_r`, `hot_r`, etc.
|
|
|
247
322
|
| `rustplotlib.transforms` | Bbox, Affine2D, BboxTransform |
|
|
248
323
|
| `rustplotlib.patheffects` | Stroke, withStroke, SimplePatchShadow |
|
|
249
324
|
| `rustplotlib.spines` | Spine |
|
|
250
|
-
| `rustplotlib.
|
|
325
|
+
| `rustplotlib.axes` | Axes class reference |
|
|
326
|
+
| `rustplotlib.figure` | Figure class with Jupyter rich display (`_repr_png_`, `_repr_svg_`, `_repr_html_`) |
|
|
327
|
+
| `rustplotlib.events` | MouseEvent, KeyEvent, DrawEvent, ResizeEvent, CloseEvent |
|
|
328
|
+
| `rustplotlib.callback_registry` | CallbackRegistry for mpl_connect/mpl_disconnect |
|
|
251
329
|
| `rustplotlib.cycler` | cycler compatibility |
|
|
252
330
|
|
|
253
331
|
---
|
|
@@ -336,25 +414,29 @@ anim.save("wave.gif")
|
|
|
336
414
|
|
|
337
415
|
## Performance Benchmark
|
|
338
416
|
|
|
339
|
-
Benchmarked against matplotlib on Apple Silicon (M-series). Each test runs 10 iterations, averaged:
|
|
417
|
+
Benchmarked against matplotlib on Apple Silicon (M-series, release build). Each test runs 10 iterations, averaged:
|
|
340
418
|
|
|
341
419
|
| Benchmark | matplotlib | rustplotlib | Speedup |
|
|
342
420
|
|---|---|---|---|
|
|
343
|
-
| Line Plot (10k pts) | 0.
|
|
344
|
-
| Scatter (5k pts) | 0.
|
|
345
|
-
| Bar Chart (50 bars) | 0.
|
|
346
|
-
| Histogram (100k pts) | 0.
|
|
347
|
-
| Subplots 2x2 | 0.
|
|
348
|
-
| Heatmap (100x100) | 0.
|
|
349
|
-
| Large Line (100k pts) | 0.
|
|
350
|
-
| Multi-line (20 lines) | 0.
|
|
351
|
-
| Error Bars | 0.
|
|
352
|
-
| Pie Chart | 0.
|
|
353
|
-
| SVG Output | 0.021s | 0.003s | **
|
|
354
|
-
| Full Styled Plot | 0.
|
|
421
|
+
| Line Plot (10k pts) | 0.024s | 0.005s | **4.7x** |
|
|
422
|
+
| Scatter (5k pts) | 0.027s | 0.020s | **1.3x** |
|
|
423
|
+
| Bar Chart (50 bars) | 0.024s | 0.004s | **5.7x** |
|
|
424
|
+
| Histogram (100k pts) | 0.087s | 0.005s | **18.7x** |
|
|
425
|
+
| Subplots 2x2 | 0.038s | 0.010s | **3.9x** |
|
|
426
|
+
| Heatmap (100x100) | 0.019s | 0.005s | **3.7x** |
|
|
427
|
+
| Large Line (100k pts) | 0.109s | 0.110s | **1.0x** |
|
|
428
|
+
| Multi-line (20 lines) | 0.085s | 0.029s | **2.9x** |
|
|
429
|
+
| Error Bars | 0.021s | 0.004s | **5.9x** |
|
|
430
|
+
| Pie Chart | 0.009s | 0.004s | **2.4x** |
|
|
431
|
+
| SVG Output | 0.021s | 0.003s | **7.6x** |
|
|
432
|
+
| Full Styled Plot | 0.018s | 0.005s | **3.9x** |
|
|
433
|
+
| **TOTAL** | **0.481s** | **0.203s** | **2.4x** |
|
|
434
|
+
|
|
435
|
+
> Wins 11 out of 12 benchmarks. Up to **18.7x faster** on histogram rendering.
|
|
355
436
|
|
|
356
437
|
Run the benchmark yourself:
|
|
357
438
|
```bash
|
|
439
|
+
maturin develop --release
|
|
358
440
|
python tests/test_benchmark.py
|
|
359
441
|
```
|
|
360
442
|
|
|
@@ -426,22 +508,27 @@ Contributions are welcome! This is an open-source project under the MIT license.
|
|
|
426
508
|
4. PRs require at least 1 review before merging
|
|
427
509
|
|
|
428
510
|
**Project stats:**
|
|
429
|
-
- **
|
|
430
|
-
- **
|
|
431
|
-
- **
|
|
432
|
-
- **
|
|
433
|
-
- **
|
|
434
|
-
- **
|
|
435
|
-
- **
|
|
436
|
-
- **
|
|
511
|
+
- **53 Rust source files** — 30,000+ lines of native code
|
|
512
|
+
- **25+ Python modules** — thin PyO3 wrappers
|
|
513
|
+
- **50 plot types** (43 2D + 7 3D) — 100% of matplotlib plot types
|
|
514
|
+
- **81 colormaps** + reversed = ~162 total (~95% of matplotlib)
|
|
515
|
+
- **550+ tests** passing (including 27 rendering regression tests)
|
|
516
|
+
- **110/110 pyplot functions**, 95/95 Axes methods, 36/36 Figure methods
|
|
517
|
+
- **15 interpolation modes**: nearest, bilinear, bicubic, lanczos, spline16, hanning, hamming, hermite, kaiser, quadric, catrom, gaussian, bessel, mitchell, sinc
|
|
518
|
+
- **5 geographic projections**: Hammer, Aitoff, Mollweide, Lambert, Stereographic
|
|
519
|
+
- **4 backends**: Agg, Tk (interactive), Jupyter inline, WebAgg (browser)
|
|
520
|
+
- **4 output formats**: PNG, SVG, PDF (multi-page), EPS
|
|
521
|
+
- **Full TeX math engine**: Greek, sub/superscript, fractions, sqrt, matrices
|
|
522
|
+
- **Full transform system**: Affine2D, BlendedTransform, transData/transAxes
|
|
523
|
+
- **Full event system**: mouse, keyboard, pick events with Rust hit testing
|
|
524
|
+
- **Widgets**: Slider, Button, CheckButtons, RadioButtons, TextBox (Rust rendering)
|
|
525
|
+
- **Layout engines**: tight layout, constrained layout, GridSpec rowspan/colspan, SubFigure
|
|
437
526
|
- **Zero `unsafe` blocks**
|
|
438
527
|
|
|
439
|
-
**
|
|
440
|
-
-
|
|
441
|
-
-
|
|
442
|
-
-
|
|
443
|
-
- Qt/GTK backends
|
|
444
|
-
- Triangulation plots (tricontour, tripcolor)
|
|
528
|
+
**Remaining (need external dependencies):**
|
|
529
|
+
- Qt/GTK/macOS backends (need PyQt5, PyGObject, PyObjC)
|
|
530
|
+
- Math font rendering (need Computer Modern .ttf files)
|
|
531
|
+
- Basemap coastlines (need Natural Earth shapefiles)
|
|
445
532
|
|
|
446
533
|
---
|
|
447
534
|
|