reflex-silverpoint-react 0.6.0__tar.gz → 0.7.1__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.
- {reflex_silverpoint_react-0.6.0 → reflex_silverpoint_react-0.7.1}/PKG-INFO +214 -14
- {reflex_silverpoint_react-0.6.0 → reflex_silverpoint_react-0.7.1}/README.md +208 -9
- {reflex_silverpoint_react-0.6.0 → reflex_silverpoint_react-0.7.1}/custom_components/reflex_silverpoint_react/__init__.py +137 -1
- reflex_silverpoint_react-0.7.1/custom_components/reflex_silverpoint_react/assets/trigger.jsx +63 -0
- {reflex_silverpoint_react-0.6.0 → reflex_silverpoint_react-0.7.1}/custom_components/reflex_silverpoint_react/base.py +67 -3
- reflex_silverpoint_react-0.7.1/custom_components/reflex_silverpoint_react/base.pyi +162 -0
- {reflex_silverpoint_react-0.6.0 → reflex_silverpoint_react-0.7.1}/custom_components/reflex_silverpoint_react/charts.pyi +125 -3596
- reflex_silverpoint_react-0.7.1/custom_components/reflex_silverpoint_react/composed.py +633 -0
- reflex_silverpoint_react-0.7.1/custom_components/reflex_silverpoint_react/composed.pyi +684 -0
- {reflex_silverpoint_react-0.6.0 → reflex_silverpoint_react-0.7.1}/custom_components/reflex_silverpoint_react/dashboard.py +8 -1
- reflex_silverpoint_react-0.7.1/custom_components/reflex_silverpoint_react/dashboard.pyi +179 -0
- reflex_silverpoint_react-0.7.1/custom_components/reflex_silverpoint_react/overlays.py +784 -0
- reflex_silverpoint_react-0.7.1/custom_components/reflex_silverpoint_react/overlays.pyi +674 -0
- reflex_silverpoint_react-0.7.1/custom_components/reflex_silverpoint_react/palette.py +377 -0
- reflex_silverpoint_react-0.7.1/custom_components/reflex_silverpoint_react/surfaces.py +235 -0
- reflex_silverpoint_react-0.7.1/custom_components/reflex_silverpoint_react/surfaces.pyi +288 -0
- reflex_silverpoint_react-0.7.1/custom_components/reflex_silverpoint_react/timeline.py +172 -0
- reflex_silverpoint_react-0.7.1/custom_components/reflex_silverpoint_react/timeline.pyi +100 -0
- {reflex_silverpoint_react-0.6.0 → reflex_silverpoint_react-0.7.1}/custom_components/reflex_silverpoint_react/ui.py +19 -0
- reflex_silverpoint_react-0.7.1/custom_components/reflex_silverpoint_react/ui.pyi +942 -0
- {reflex_silverpoint_react-0.6.0 → reflex_silverpoint_react-0.7.1}/custom_components/reflex_silverpoint_react.egg-info/PKG-INFO +214 -14
- {reflex_silverpoint_react-0.6.0 → reflex_silverpoint_react-0.7.1}/custom_components/reflex_silverpoint_react.egg-info/SOURCES.txt +12 -1
- {reflex_silverpoint_react-0.6.0 → reflex_silverpoint_react-0.7.1}/custom_components/reflex_silverpoint_react.egg-info/requires.txt +3 -1
- {reflex_silverpoint_react-0.6.0 → reflex_silverpoint_react-0.7.1}/pyproject.toml +14 -5
- {reflex_silverpoint_react-0.6.0 → reflex_silverpoint_react-0.7.1}/tests/test_components.py +3 -3
- reflex_silverpoint_react-0.7.1/tests/test_v07.py +322 -0
- reflex_silverpoint_react-0.6.0/custom_components/reflex_silverpoint_react/base.pyi +0 -274
- reflex_silverpoint_react-0.6.0/custom_components/reflex_silverpoint_react/dashboard.pyi +0 -314
- reflex_silverpoint_react-0.6.0/custom_components/reflex_silverpoint_react/ui.pyi +0 -1687
- {reflex_silverpoint_react-0.6.0 → reflex_silverpoint_react-0.7.1}/LICENSE +0 -0
- {reflex_silverpoint_react-0.6.0 → reflex_silverpoint_react-0.7.1}/custom_components/reflex_silverpoint_react/catalog.py +0 -0
- {reflex_silverpoint_react-0.6.0 → reflex_silverpoint_react-0.7.1}/custom_components/reflex_silverpoint_react/charts.py +0 -0
- {reflex_silverpoint_react-0.6.0 → reflex_silverpoint_react-0.7.1}/custom_components/reflex_silverpoint_react/helpers.py +0 -0
- {reflex_silverpoint_react-0.6.0 → reflex_silverpoint_react-0.7.1}/custom_components/reflex_silverpoint_react/ui_catalog.py +0 -0
- {reflex_silverpoint_react-0.6.0 → reflex_silverpoint_react-0.7.1}/custom_components/reflex_silverpoint_react.egg-info/dependency_links.txt +0 -0
- {reflex_silverpoint_react-0.6.0 → reflex_silverpoint_react-0.7.1}/custom_components/reflex_silverpoint_react.egg-info/top_level.txt +0 -0
- {reflex_silverpoint_react-0.6.0 → reflex_silverpoint_react-0.7.1}/setup.cfg +0 -0
- {reflex_silverpoint_react-0.6.0 → reflex_silverpoint_react-0.7.1}/tests/test_demo_data.py +0 -0
|
@@ -1,22 +1,23 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: reflex-silverpoint-react
|
|
3
|
-
Version: 0.
|
|
4
|
-
Summary: The 60 silverpoint charts, the
|
|
3
|
+
Version: 0.7.1
|
|
4
|
+
Summary: The 60 silverpoint charts, the Dashboard, 38 UI, composed and overlay components, palettes and a Knight Lab timeline (Renaissance silverpoint drawing style) for Reflex, wrapping @silverpoint/react 0.7
|
|
5
5
|
Author-email: Ernesto Crespo <ecrespo@gmail.com>
|
|
6
6
|
License: MIT
|
|
7
7
|
Project-URL: Homepage, https://github.com/ecrespo/reflex-silverpoint-react
|
|
8
8
|
Project-URL: Source, https://github.com/ecrespo/reflex-silverpoint-react
|
|
9
9
|
Project-URL: Issues, https://github.com/ecrespo/reflex-silverpoint-react/issues
|
|
10
10
|
Project-URL: Upstream, https://github.com/ecrespo/silverpoint
|
|
11
|
-
Keywords: reflex,reflex-custom-components,charts,silverpoint,data-visualization,svg,ui-components
|
|
11
|
+
Keywords: reflex,reflex-custom-components,charts,silverpoint,data-visualization,svg,ui-components,palette,timeline
|
|
12
12
|
Classifier: Development Status :: 4 - Beta
|
|
13
13
|
Classifier: License :: OSI Approved :: MIT License
|
|
14
14
|
Classifier: Programming Language :: Python :: 3
|
|
15
15
|
Classifier: Topic :: Scientific/Engineering :: Visualization
|
|
16
|
-
Requires-Python: >=3.
|
|
16
|
+
Requires-Python: >=3.11
|
|
17
17
|
Description-Content-Type: text/markdown
|
|
18
18
|
License-File: LICENSE
|
|
19
|
-
Requires-Dist: reflex>=0.
|
|
19
|
+
Requires-Dist: reflex>=0.10.0
|
|
20
|
+
Provides-Extra: timeline
|
|
20
21
|
Provides-Extra: dev
|
|
21
22
|
Requires-Dist: build; extra == "dev"
|
|
22
23
|
Requires-Dist: twine; extra == "dev"
|
|
@@ -33,11 +34,58 @@ prepared ground, tone built from hatching, and white heightening on the live val
|
|
|
33
34
|
The hand-drawn irregularity lives only in the ornament. The data geometry is exact, and every chart
|
|
34
35
|
has a `precision` mode that turns the inking off.
|
|
35
36
|
|
|
36
|
-
It wraps [`@silverpoint/react`](https://www.npmjs.com/package/@silverpoint/react) 0.
|
|
37
|
+
It wraps [`@silverpoint/react`](https://www.npmjs.com/package/@silverpoint/react) **0.7.0** and exposes
|
|
37
38
|
**all 60 charts**, the **`Dashboard`** (a laid-out, linkable grid of charts), the **17 UI
|
|
38
|
-
components** (buttons, inputs, tabs, cards, alerts…), the
|
|
39
|
-
|
|
40
|
-
|
|
39
|
+
components** (buttons, inputs, tabs, cards, alerts…), the **12 composed components** (table,
|
|
40
|
+
pagination, breadcrumb, avatar…), the **7 overlays** and the toaster (modal, drawer, popover,
|
|
41
|
+
tooltip, select, dropdown menu, toast), the **palettes**, the **Knight Lab timeline**, the
|
|
42
|
+
`SilverpointProvider`, both grounds (`silverpoint` and `cyanotype`), the interaction events, custom
|
|
43
|
+
readouts and the imperative handle (SVG export and geometry) as Python.
|
|
44
|
+
|
|
45
|
+
Everything it renders is an npm component of silverpoint, under its parity contract: the same
|
|
46
|
+
markup React, Vue and Angular render.
|
|
47
|
+
|
|
48
|
+
### New in 0.7.1
|
|
49
|
+
|
|
50
|
+
- Wraps **`@silverpoint/react` 0.7.0** (0.7.0 wrapped 0.6.0). silverpoint 0.7 took this package's
|
|
51
|
+
palettes, composed components, overlays and timeline into the library itself, so they are now the
|
|
52
|
+
npm components, not Reflex-composed copies: same Python builders, the library's markup.
|
|
53
|
+
- **Palettes** are the npm `palette` prop: they merge element → dashboard → provider field by field,
|
|
54
|
+
`silverpoint_provider(palette=...)` works, and `silverpoint_palette(...)` is a provider with a
|
|
55
|
+
palette. `check_palette()` measures the core's nine contrast pairs (the focus ring and the white
|
|
56
|
+
heightening included); `"ironGall"` names the `iron_gall` preset too.
|
|
57
|
+
- **Composed components and overlays read `silverpoint_provider`**, as the `Sp` components do.
|
|
58
|
+
Overlays are a native `<dialog>` and the Popover API (no Radix); they render in place, so a
|
|
59
|
+
section's palette reaches them.
|
|
60
|
+
- **Logical sides**: `side="start"`/`"end"` and `position="bottom-end"`…; `left`/`right` still work
|
|
61
|
+
with a `DeprecationWarning`. `sp_drawer(size=)` is `extent=`, `sp_popover(side_offset=)` is
|
|
62
|
+
`offset=`; `sp_modal` gains `label` and `dismissible`, `sp_result`/`sp_descriptions`
|
|
63
|
+
`heading_level`.
|
|
64
|
+
- `sp_textarea(textarea_id=)` and `sp_input_number(input_id=)` are `id=` (deprecated aliases kept);
|
|
65
|
+
`sp_textarea` has no `on_blur`. `sp_collapse_item(on_toggle=)` receives the new open state (a bool).
|
|
66
|
+
- **`sp_timeline`** is the npm `SpTimeline`: TimelineJS is an npm dependency of that component, so the
|
|
67
|
+
`[timeline]` extra pulls in nothing any more (it is kept so existing installs keep working).
|
|
68
|
+
- `sort_rows()` follows the core's `uiSortRows` order (numbers first, then text by code point).
|
|
69
|
+
|
|
70
|
+
### New in 0.7.0
|
|
71
|
+
|
|
72
|
+
- **Reflex 0.10.0**, and therefore **Python 3.11 or later** (Python 3.10 is no longer supported).
|
|
73
|
+
Reflex 0.10 removed `reflex component build`: stubs are regenerated with `scripts/make_stubs.py`.
|
|
74
|
+
- **Palettes** — `palette=` on every chart, UI component, dashboard and composed component,
|
|
75
|
+
`silverpoint_palette(...)` for a whole section, six presets named after drawing media
|
|
76
|
+
(`silverpoint`, `sanguine`, `sepia`, `iron_gall`, `verdigris`, `indigo`) and `check_palette()`
|
|
77
|
+
against the contrast thresholds of the data model. See [Palettes](#palettes).
|
|
78
|
+
- **Composed components, level A** (native markup): `sp_table` (+ `sort_rows`), `sp_pagination`,
|
|
79
|
+
`sp_breadcrumb`, `sp_avatar` (+ `sp_avatar_group`), `sp_statistic`, `sp_descriptions`,
|
|
80
|
+
`sp_timeline_list`, `sp_collapse` (+ `sp_collapse_item`), `sp_empty`, `sp_result`, `sp_textarea`
|
|
81
|
+
and `sp_input_number`.
|
|
82
|
+
- **Composed components, level B** (overlays on Radix primitives): `sp_modal`, `sp_drawer`,
|
|
83
|
+
`sp_popover`, `sp_tooltip`, `sp_select`, `sp_dropdown_menu` and `sp_toast` (+ `sp_toaster`), with
|
|
84
|
+
`sp_trigger` as their drawn button. See [Composed components](#composed-components).
|
|
85
|
+
- **`sp_timeline`** — Knight Lab TimelineJS drawn in silverpoint: a skin on the ground's colours and
|
|
86
|
+
type, plus the ground's own hand-inked frames and tone tiles on its markers, eras and buttons.
|
|
87
|
+
Optional extra (until 0.7.1): `pip install "reflex-silverpoint-react[timeline]"`. See [Timeline](#timeline).
|
|
88
|
+
- `sp_surface`, `sp_glyph`: the building blocks, for components of your own.
|
|
41
89
|
|
|
42
90
|
### New in 0.6
|
|
43
91
|
|
|
@@ -87,7 +135,7 @@ stylesheets it needs (`@silverpoint/grounds/styles.css` and the self-hosted EB G
|
|
|
87
135
|
`@silverpoint/fonts/fonts.css`); the UI components also import `@silverpoint/grounds/ui.css`. No
|
|
88
136
|
Tailwind, no CDN.
|
|
89
137
|
|
|
90
|
-
Requires Reflex 0.
|
|
138
|
+
Requires Reflex 0.10.0 or later (React 19) and Python 3.11 or later.
|
|
91
139
|
|
|
92
140
|
## Quickstart
|
|
93
141
|
|
|
@@ -350,6 +398,137 @@ rx.el.form(
|
|
|
350
398
|
- Text inputs controlled from state make a round trip per keystroke; for long text, prefer
|
|
351
399
|
`default_value` and read the value on submit.
|
|
352
400
|
|
|
401
|
+
## Palettes
|
|
402
|
+
|
|
403
|
+
silverpoint never writes a colour into its drawing: every stroke and fill is painted by CSS through
|
|
404
|
+
the ground's `--sp-` custom properties. A palette sets them, so it re-colours without re-rendering.
|
|
405
|
+
|
|
406
|
+
```python
|
|
407
|
+
from reflex_silverpoint_react import PALETTES, Palette, bar_chart, check_palette, silverpoint_palette, sp_button
|
|
408
|
+
|
|
409
|
+
bar_chart(title="Orders", palette="sanguine") # a preset
|
|
410
|
+
sp_button("Save", variant="primary", palette={"ink": "#2C6355"}) # a dict of fields
|
|
411
|
+
bar_chart(title="Orders", palette=State.palette) # a state var holding a dict
|
|
412
|
+
|
|
413
|
+
MINE = Palette(substrate="#F2E8DC", ink="#8A3A24", ink_secondary="#6A4A3A", text="#4A2216")
|
|
414
|
+
assert not check_palette(MINE) # [] when every field meets its contrast threshold
|
|
415
|
+
|
|
416
|
+
silverpoint_palette(dashboard(...), sp_card(...), palette="indigo") # a whole section
|
|
417
|
+
```
|
|
418
|
+
|
|
419
|
+
Fields: `substrate`, `ink`, `ink_secondary`, `heighten`, `rule`, `grid`, `text`, `text_muted` and
|
|
420
|
+
`focus` (the UI focus ring). Unset fields keep the ground's own. Palettes merge field by field,
|
|
421
|
+
element → dashboard → provider, so an element's own `palette` wins over its section's. A palette is
|
|
422
|
+
**monochrome by design**: tone is built from hatch density (Art. 6), so a chart has two inks (`ink`
|
|
423
|
+
for the main series, `ink_secondary` for the second), never a colour per series. `precision` mode and
|
|
424
|
+
the system's high-contrast modes still apply on top. `silverpoint_palette(...)` is
|
|
425
|
+
`silverpoint_provider(palette=...)` around the section.
|
|
426
|
+
|
|
427
|
+
## Composed components
|
|
428
|
+
|
|
429
|
+
silverpoint 0.7's composed components and overlays, the npm components of `@silverpoint/react/ui`:
|
|
430
|
+
native markup drawn by the core with the ground's hand-inked frames, hatched tones and
|
|
431
|
+
heightening, exactly as the `Sp` components are. Like them they read `silverpoint_provider` (and
|
|
432
|
+
the dashboard they sit in); a prop on the component always wins.
|
|
433
|
+
|
|
434
|
+
```python
|
|
435
|
+
from reflex_silverpoint_react import sort_rows, sp_pagination, sp_table
|
|
436
|
+
|
|
437
|
+
sp_table(
|
|
438
|
+
[
|
|
439
|
+
{"key": "team", "title": "Team", "sortable": True},
|
|
440
|
+
{"key": "load", "title": "Load", "align": "end", "sortable": True},
|
|
441
|
+
],
|
|
442
|
+
State.rows,
|
|
443
|
+
caption="On-call teams",
|
|
444
|
+
sort_key=State.sort_key,
|
|
445
|
+
sort_order=State.sort_order,
|
|
446
|
+
on_sort=State.sort, # receives the key; sort with sort_rows(rows, key, order)
|
|
447
|
+
striped=True,
|
|
448
|
+
)
|
|
449
|
+
sp_pagination(total=240, current=State.page, on_change=State.set_page, show_total=True)
|
|
450
|
+
```
|
|
451
|
+
|
|
452
|
+
| Composed (native markup) | |
|
|
453
|
+
|---|---|
|
|
454
|
+
| `sp_table` | Card-framed table: small-caps header, tabular figures, hatched striping, sortable headers with `aria-sort` |
|
|
455
|
+
| `sp_pagination` | Previous/next, first/last, a window around the current page (heightened); `on_change(page)` |
|
|
456
|
+
| `sp_breadcrumb` | `<nav>` of links; the last item is the current page |
|
|
457
|
+
| `sp_avatar`, `sp_avatar_group` | Portrait or initials in a drawn round (or square) frame |
|
|
458
|
+
| `sp_statistic` | Small-caps title, large tabular figure, prefix/suffix, trend arrow |
|
|
459
|
+
| `sp_descriptions` | Label–value grid (`<dl>`), optionally card-framed |
|
|
460
|
+
| `sp_timeline_list` | Vertical list: `done` (hatched), `current` (heightened), `pending`, `error` |
|
|
461
|
+
| `sp_collapse`, `sp_collapse_item` | Native `<details>`; `accordion=True` keeps one open |
|
|
462
|
+
| `sp_empty`, `sp_result` | Empty state; outcome with a drawn round mark |
|
|
463
|
+
| `sp_textarea`, `sp_input_number` | On the `SpInput` contract; `on_change` receives the value (text or number) |
|
|
464
|
+
|
|
465
|
+
| Overlays (`<dialog>`, Popover API) | |
|
|
466
|
+
|---|---|
|
|
467
|
+
| `sp_modal`, `sp_drawer` | Dialog on a card frame over a hatched backdrop; drawer from any edge |
|
|
468
|
+
| `sp_popover`, `sp_tooltip` | Anchored content; tooltip on hover or keyboard focus |
|
|
469
|
+
| `sp_select` | Single choice with typeahead; the chosen option ticked, the highlighted one heightened |
|
|
470
|
+
| `sp_dropdown_menu` | Commands with shortcuts, separators and labels; `on_select(key)` |
|
|
471
|
+
| `sp_toast`, `sp_toaster` | Notices that stack in a corner; `error`/`warning` are announced assertively |
|
|
472
|
+
|
|
473
|
+
Behaviour is the platform's: `showModal()` for the modal and the drawer (focus stays inside, Escape
|
|
474
|
+
and the backdrop close it unless `dismissible=False`), the Popover API for the rest (light
|
|
475
|
+
dismiss), keyboard and placement from `@silverpoint/core` (APG listbox and menu, typeahead, flip and
|
|
476
|
+
shift). Overlays render in place (the top layer, no portal), so a section's palette reaches them.
|
|
477
|
+
Sides are logical (`start`/`end`) and mirror in right-to-left text. An overlay clones its `trigger`
|
|
478
|
+
with its ARIA and a toggling click, so the trigger must keep the props it is given: a native
|
|
479
|
+
`rx.el.button`, or `sp_trigger(...)`, the drawn button strings become (`sp_button` drops them in
|
|
480
|
+
silverpoint 0.7.0). `sp_trigger` does not read the provider: give it `ground`, `substrate`, `mode`
|
|
481
|
+
and `palette`.
|
|
482
|
+
|
|
483
|
+
```python
|
|
484
|
+
sp_modal(
|
|
485
|
+
rx.el.p("Apply the new ground?"),
|
|
486
|
+
trigger="Open",
|
|
487
|
+
title="Apply changes",
|
|
488
|
+
footer=sp_trigger("Apply", variant="primary", on_click=State.confirm),
|
|
489
|
+
open=State.modal_open,
|
|
490
|
+
on_open_change=State.set_modal_open,
|
|
491
|
+
)
|
|
492
|
+
sp_select(["North", "East", "South", "West"], value=State.region, on_change=State.set_region)
|
|
493
|
+
sp_toaster(sp_toast("Saved", State.text, kind="success", open=State.toast_open, on_open_change=State.set_toast_open))
|
|
494
|
+
```
|
|
495
|
+
|
|
496
|
+

|
|
497
|
+
|
|
498
|
+
## Timeline
|
|
499
|
+
|
|
500
|
+
The npm `SpTimeline` of `@silverpoint/react/timeline`. TimelineJS (`@knight-lab/timelinejs` 3.9.13)
|
|
501
|
+
is an npm dependency of this component: Reflex installs it when a page uses `sp_timeline`, and no
|
|
502
|
+
Python extra is needed. If it cannot be loaded, the component warns `SP025` and renders `fallback`.
|
|
503
|
+
|
|
504
|
+
```python
|
|
505
|
+
from reflex_silverpoint_react import sp_timeline
|
|
506
|
+
|
|
507
|
+
sp_timeline(
|
|
508
|
+
DATA, # TimelineJS data: title, events, eras (or any object with to_dict())
|
|
509
|
+
height=560,
|
|
510
|
+
ground="silverpoint",
|
|
511
|
+
substrate="cream",
|
|
512
|
+
mode="ink",
|
|
513
|
+
palette="sepia",
|
|
514
|
+
inked_frames=True, # the ground's hand-drawn frames and tone tiles
|
|
515
|
+
on_change=State.on_change, # the unique_id of the slide shown
|
|
516
|
+
)
|
|
517
|
+
```
|
|
518
|
+
|
|
519
|
+
It works in two layers. The **skin** replaces TimelineJS's colours, type and rules with the
|
|
520
|
+
ground's `--sp-` properties: substrate, inks, EB Garamond, hairline rules, eras hatched by density,
|
|
521
|
+
the current marker heightened. The **hand** reads the ground's own frame and tone masks from hidden
|
|
522
|
+
probes and lays them on the markers, eras and menubar, so they are drawn with the same pieces as
|
|
523
|
+
the `Sp` components; `inked_frames=False` keeps the skin only, and `precision`, `cyanotype` and
|
|
524
|
+
forced colours fall back to exact rules by themselves. Note that TimelineJS requests its icon font
|
|
525
|
+
from a relative path (`/css/icons/tl-icons.*`); the Reflex dev server answers it with HTML, so the
|
|
526
|
+
browser logs font-decoding warnings. They come from TimelineJS, not from this package.
|
|
527
|
+
|
|
528
|
+

|
|
529
|
+
|
|
530
|
+

|
|
531
|
+
|
|
353
532
|
## Interaction
|
|
354
533
|
|
|
355
534
|
```python
|
|
@@ -419,24 +598,45 @@ uv run reflex run
|
|
|
419
598
|
Pages: **Start** (quickstart, provider, ink vs precision), **Gallery** (the 60 charts, ground
|
|
420
599
|
controls, demo datasets vs data from Python state with a re-roll), **Playground** (one chart, every
|
|
421
600
|
rendering choice and the Python that reproduces it), **Interaction** (events, custom readout, a
|
|
422
|
-
volvelle that turns on click, a treemap and a sunburst that drill down together, live
|
|
601
|
+
volvelle that turns on click, a treemap and a sunburst that drill down together, live
|
|
602
|
+
KPI/gauge/meter, SVG and geometry export), **Dashboard** (a
|
|
423
603
|
linked operations dashboard fed from Python state with ground, substrate, mode and column controls, a
|
|
424
604
|
KPI strip, and `dashboard_link` on its own), **UI components** (`/ui`: the components controlled from
|
|
425
605
|
Python state with a native form submit, and the three reference panels of the upstream example apps
|
|
426
606
|
in silverpoint ink, precision and cyanotype), one **reference page per chart** (`/chart/<slug>`) and
|
|
427
|
-
one per UI component (`/ui/<slug>`: every declared state on both grounds, usage and props). The
|
|
607
|
+
one per UI component (`/ui/<slug>`: every declared state on both grounds, usage and props). The
|
|
608
|
+
Gallery and Playground also get a ground control, for `cyanotype`, and a palette control.
|
|
609
|
+
New in 0.7: **More components** (`/components`: the 20 composed components wired to Python, with
|
|
610
|
+
ground, substrate, mode and palette controls and an event log), **Palettes** (`/palettes`: the
|
|
611
|
+
presets, a palette builder with colour pickers and `check_palette`, a coloured section) and
|
|
612
|
+
**Timeline** (`/timeline`: the Knight Lab timeline on every ground, mode and palette).
|
|
428
613
|
|
|
429
614
|

|
|
430
615
|
|
|
431
616
|
## Development
|
|
432
617
|
|
|
433
618
|
```bash
|
|
434
|
-
uv
|
|
619
|
+
uv sync --extra dev
|
|
435
620
|
uv run pytest
|
|
436
621
|
uv run ruff check .
|
|
437
|
-
|
|
622
|
+
# Reflex 0.10 removed `reflex component build`: regenerate the .pyi stubs with the generator
|
|
623
|
+
# Reflex itself uses (plus this package's fixes), then build the sdist and wheel.
|
|
624
|
+
uv run python scripts/make_stubs.py
|
|
625
|
+
uv build
|
|
438
626
|
```
|
|
439
627
|
|
|
628
|
+
Before committing, run the hooks of [`.pre-commit-config.yaml`](.pre-commit-config.yaml) (ruff check
|
|
629
|
+
and format — including the Python blocks of this README — file hygiene and `uv lock --check`):
|
|
630
|
+
|
|
631
|
+
```bash
|
|
632
|
+
pre-commit install
|
|
633
|
+
pre-commit run --all-files
|
|
634
|
+
```
|
|
635
|
+
|
|
636
|
+
Changes per version are in [CHANGELOG.md](CHANGELOG.md); the guide for coding agents is
|
|
637
|
+
[AGENTS.md](AGENTS.md). Releases are published to PyPI by pushing a `vX.Y.Z` tag on `main` that
|
|
638
|
+
matches `version` in `pyproject.toml`.
|
|
639
|
+
|
|
440
640
|
## License
|
|
441
641
|
|
|
442
642
|
MIT. silverpoint is MIT; the EB Garamond typeface is under the SIL Open Font License.
|
|
@@ -7,11 +7,58 @@ prepared ground, tone built from hatching, and white heightening on the live val
|
|
|
7
7
|
The hand-drawn irregularity lives only in the ornament. The data geometry is exact, and every chart
|
|
8
8
|
has a `precision` mode that turns the inking off.
|
|
9
9
|
|
|
10
|
-
It wraps [`@silverpoint/react`](https://www.npmjs.com/package/@silverpoint/react) 0.
|
|
10
|
+
It wraps [`@silverpoint/react`](https://www.npmjs.com/package/@silverpoint/react) **0.7.0** and exposes
|
|
11
11
|
**all 60 charts**, the **`Dashboard`** (a laid-out, linkable grid of charts), the **17 UI
|
|
12
|
-
components** (buttons, inputs, tabs, cards, alerts…), the
|
|
13
|
-
|
|
14
|
-
|
|
12
|
+
components** (buttons, inputs, tabs, cards, alerts…), the **12 composed components** (table,
|
|
13
|
+
pagination, breadcrumb, avatar…), the **7 overlays** and the toaster (modal, drawer, popover,
|
|
14
|
+
tooltip, select, dropdown menu, toast), the **palettes**, the **Knight Lab timeline**, the
|
|
15
|
+
`SilverpointProvider`, both grounds (`silverpoint` and `cyanotype`), the interaction events, custom
|
|
16
|
+
readouts and the imperative handle (SVG export and geometry) as Python.
|
|
17
|
+
|
|
18
|
+
Everything it renders is an npm component of silverpoint, under its parity contract: the same
|
|
19
|
+
markup React, Vue and Angular render.
|
|
20
|
+
|
|
21
|
+
### New in 0.7.1
|
|
22
|
+
|
|
23
|
+
- Wraps **`@silverpoint/react` 0.7.0** (0.7.0 wrapped 0.6.0). silverpoint 0.7 took this package's
|
|
24
|
+
palettes, composed components, overlays and timeline into the library itself, so they are now the
|
|
25
|
+
npm components, not Reflex-composed copies: same Python builders, the library's markup.
|
|
26
|
+
- **Palettes** are the npm `palette` prop: they merge element → dashboard → provider field by field,
|
|
27
|
+
`silverpoint_provider(palette=...)` works, and `silverpoint_palette(...)` is a provider with a
|
|
28
|
+
palette. `check_palette()` measures the core's nine contrast pairs (the focus ring and the white
|
|
29
|
+
heightening included); `"ironGall"` names the `iron_gall` preset too.
|
|
30
|
+
- **Composed components and overlays read `silverpoint_provider`**, as the `Sp` components do.
|
|
31
|
+
Overlays are a native `<dialog>` and the Popover API (no Radix); they render in place, so a
|
|
32
|
+
section's palette reaches them.
|
|
33
|
+
- **Logical sides**: `side="start"`/`"end"` and `position="bottom-end"`…; `left`/`right` still work
|
|
34
|
+
with a `DeprecationWarning`. `sp_drawer(size=)` is `extent=`, `sp_popover(side_offset=)` is
|
|
35
|
+
`offset=`; `sp_modal` gains `label` and `dismissible`, `sp_result`/`sp_descriptions`
|
|
36
|
+
`heading_level`.
|
|
37
|
+
- `sp_textarea(textarea_id=)` and `sp_input_number(input_id=)` are `id=` (deprecated aliases kept);
|
|
38
|
+
`sp_textarea` has no `on_blur`. `sp_collapse_item(on_toggle=)` receives the new open state (a bool).
|
|
39
|
+
- **`sp_timeline`** is the npm `SpTimeline`: TimelineJS is an npm dependency of that component, so the
|
|
40
|
+
`[timeline]` extra pulls in nothing any more (it is kept so existing installs keep working).
|
|
41
|
+
- `sort_rows()` follows the core's `uiSortRows` order (numbers first, then text by code point).
|
|
42
|
+
|
|
43
|
+
### New in 0.7.0
|
|
44
|
+
|
|
45
|
+
- **Reflex 0.10.0**, and therefore **Python 3.11 or later** (Python 3.10 is no longer supported).
|
|
46
|
+
Reflex 0.10 removed `reflex component build`: stubs are regenerated with `scripts/make_stubs.py`.
|
|
47
|
+
- **Palettes** — `palette=` on every chart, UI component, dashboard and composed component,
|
|
48
|
+
`silverpoint_palette(...)` for a whole section, six presets named after drawing media
|
|
49
|
+
(`silverpoint`, `sanguine`, `sepia`, `iron_gall`, `verdigris`, `indigo`) and `check_palette()`
|
|
50
|
+
against the contrast thresholds of the data model. See [Palettes](#palettes).
|
|
51
|
+
- **Composed components, level A** (native markup): `sp_table` (+ `sort_rows`), `sp_pagination`,
|
|
52
|
+
`sp_breadcrumb`, `sp_avatar` (+ `sp_avatar_group`), `sp_statistic`, `sp_descriptions`,
|
|
53
|
+
`sp_timeline_list`, `sp_collapse` (+ `sp_collapse_item`), `sp_empty`, `sp_result`, `sp_textarea`
|
|
54
|
+
and `sp_input_number`.
|
|
55
|
+
- **Composed components, level B** (overlays on Radix primitives): `sp_modal`, `sp_drawer`,
|
|
56
|
+
`sp_popover`, `sp_tooltip`, `sp_select`, `sp_dropdown_menu` and `sp_toast` (+ `sp_toaster`), with
|
|
57
|
+
`sp_trigger` as their drawn button. See [Composed components](#composed-components).
|
|
58
|
+
- **`sp_timeline`** — Knight Lab TimelineJS drawn in silverpoint: a skin on the ground's colours and
|
|
59
|
+
type, plus the ground's own hand-inked frames and tone tiles on its markers, eras and buttons.
|
|
60
|
+
Optional extra (until 0.7.1): `pip install "reflex-silverpoint-react[timeline]"`. See [Timeline](#timeline).
|
|
61
|
+
- `sp_surface`, `sp_glyph`: the building blocks, for components of your own.
|
|
15
62
|
|
|
16
63
|
### New in 0.6
|
|
17
64
|
|
|
@@ -61,7 +108,7 @@ stylesheets it needs (`@silverpoint/grounds/styles.css` and the self-hosted EB G
|
|
|
61
108
|
`@silverpoint/fonts/fonts.css`); the UI components also import `@silverpoint/grounds/ui.css`. No
|
|
62
109
|
Tailwind, no CDN.
|
|
63
110
|
|
|
64
|
-
Requires Reflex 0.
|
|
111
|
+
Requires Reflex 0.10.0 or later (React 19) and Python 3.11 or later.
|
|
65
112
|
|
|
66
113
|
## Quickstart
|
|
67
114
|
|
|
@@ -324,6 +371,137 @@ rx.el.form(
|
|
|
324
371
|
- Text inputs controlled from state make a round trip per keystroke; for long text, prefer
|
|
325
372
|
`default_value` and read the value on submit.
|
|
326
373
|
|
|
374
|
+
## Palettes
|
|
375
|
+
|
|
376
|
+
silverpoint never writes a colour into its drawing: every stroke and fill is painted by CSS through
|
|
377
|
+
the ground's `--sp-` custom properties. A palette sets them, so it re-colours without re-rendering.
|
|
378
|
+
|
|
379
|
+
```python
|
|
380
|
+
from reflex_silverpoint_react import PALETTES, Palette, bar_chart, check_palette, silverpoint_palette, sp_button
|
|
381
|
+
|
|
382
|
+
bar_chart(title="Orders", palette="sanguine") # a preset
|
|
383
|
+
sp_button("Save", variant="primary", palette={"ink": "#2C6355"}) # a dict of fields
|
|
384
|
+
bar_chart(title="Orders", palette=State.palette) # a state var holding a dict
|
|
385
|
+
|
|
386
|
+
MINE = Palette(substrate="#F2E8DC", ink="#8A3A24", ink_secondary="#6A4A3A", text="#4A2216")
|
|
387
|
+
assert not check_palette(MINE) # [] when every field meets its contrast threshold
|
|
388
|
+
|
|
389
|
+
silverpoint_palette(dashboard(...), sp_card(...), palette="indigo") # a whole section
|
|
390
|
+
```
|
|
391
|
+
|
|
392
|
+
Fields: `substrate`, `ink`, `ink_secondary`, `heighten`, `rule`, `grid`, `text`, `text_muted` and
|
|
393
|
+
`focus` (the UI focus ring). Unset fields keep the ground's own. Palettes merge field by field,
|
|
394
|
+
element → dashboard → provider, so an element's own `palette` wins over its section's. A palette is
|
|
395
|
+
**monochrome by design**: tone is built from hatch density (Art. 6), so a chart has two inks (`ink`
|
|
396
|
+
for the main series, `ink_secondary` for the second), never a colour per series. `precision` mode and
|
|
397
|
+
the system's high-contrast modes still apply on top. `silverpoint_palette(...)` is
|
|
398
|
+
`silverpoint_provider(palette=...)` around the section.
|
|
399
|
+
|
|
400
|
+
## Composed components
|
|
401
|
+
|
|
402
|
+
silverpoint 0.7's composed components and overlays, the npm components of `@silverpoint/react/ui`:
|
|
403
|
+
native markup drawn by the core with the ground's hand-inked frames, hatched tones and
|
|
404
|
+
heightening, exactly as the `Sp` components are. Like them they read `silverpoint_provider` (and
|
|
405
|
+
the dashboard they sit in); a prop on the component always wins.
|
|
406
|
+
|
|
407
|
+
```python
|
|
408
|
+
from reflex_silverpoint_react import sort_rows, sp_pagination, sp_table
|
|
409
|
+
|
|
410
|
+
sp_table(
|
|
411
|
+
[
|
|
412
|
+
{"key": "team", "title": "Team", "sortable": True},
|
|
413
|
+
{"key": "load", "title": "Load", "align": "end", "sortable": True},
|
|
414
|
+
],
|
|
415
|
+
State.rows,
|
|
416
|
+
caption="On-call teams",
|
|
417
|
+
sort_key=State.sort_key,
|
|
418
|
+
sort_order=State.sort_order,
|
|
419
|
+
on_sort=State.sort, # receives the key; sort with sort_rows(rows, key, order)
|
|
420
|
+
striped=True,
|
|
421
|
+
)
|
|
422
|
+
sp_pagination(total=240, current=State.page, on_change=State.set_page, show_total=True)
|
|
423
|
+
```
|
|
424
|
+
|
|
425
|
+
| Composed (native markup) | |
|
|
426
|
+
|---|---|
|
|
427
|
+
| `sp_table` | Card-framed table: small-caps header, tabular figures, hatched striping, sortable headers with `aria-sort` |
|
|
428
|
+
| `sp_pagination` | Previous/next, first/last, a window around the current page (heightened); `on_change(page)` |
|
|
429
|
+
| `sp_breadcrumb` | `<nav>` of links; the last item is the current page |
|
|
430
|
+
| `sp_avatar`, `sp_avatar_group` | Portrait or initials in a drawn round (or square) frame |
|
|
431
|
+
| `sp_statistic` | Small-caps title, large tabular figure, prefix/suffix, trend arrow |
|
|
432
|
+
| `sp_descriptions` | Label–value grid (`<dl>`), optionally card-framed |
|
|
433
|
+
| `sp_timeline_list` | Vertical list: `done` (hatched), `current` (heightened), `pending`, `error` |
|
|
434
|
+
| `sp_collapse`, `sp_collapse_item` | Native `<details>`; `accordion=True` keeps one open |
|
|
435
|
+
| `sp_empty`, `sp_result` | Empty state; outcome with a drawn round mark |
|
|
436
|
+
| `sp_textarea`, `sp_input_number` | On the `SpInput` contract; `on_change` receives the value (text or number) |
|
|
437
|
+
|
|
438
|
+
| Overlays (`<dialog>`, Popover API) | |
|
|
439
|
+
|---|---|
|
|
440
|
+
| `sp_modal`, `sp_drawer` | Dialog on a card frame over a hatched backdrop; drawer from any edge |
|
|
441
|
+
| `sp_popover`, `sp_tooltip` | Anchored content; tooltip on hover or keyboard focus |
|
|
442
|
+
| `sp_select` | Single choice with typeahead; the chosen option ticked, the highlighted one heightened |
|
|
443
|
+
| `sp_dropdown_menu` | Commands with shortcuts, separators and labels; `on_select(key)` |
|
|
444
|
+
| `sp_toast`, `sp_toaster` | Notices that stack in a corner; `error`/`warning` are announced assertively |
|
|
445
|
+
|
|
446
|
+
Behaviour is the platform's: `showModal()` for the modal and the drawer (focus stays inside, Escape
|
|
447
|
+
and the backdrop close it unless `dismissible=False`), the Popover API for the rest (light
|
|
448
|
+
dismiss), keyboard and placement from `@silverpoint/core` (APG listbox and menu, typeahead, flip and
|
|
449
|
+
shift). Overlays render in place (the top layer, no portal), so a section's palette reaches them.
|
|
450
|
+
Sides are logical (`start`/`end`) and mirror in right-to-left text. An overlay clones its `trigger`
|
|
451
|
+
with its ARIA and a toggling click, so the trigger must keep the props it is given: a native
|
|
452
|
+
`rx.el.button`, or `sp_trigger(...)`, the drawn button strings become (`sp_button` drops them in
|
|
453
|
+
silverpoint 0.7.0). `sp_trigger` does not read the provider: give it `ground`, `substrate`, `mode`
|
|
454
|
+
and `palette`.
|
|
455
|
+
|
|
456
|
+
```python
|
|
457
|
+
sp_modal(
|
|
458
|
+
rx.el.p("Apply the new ground?"),
|
|
459
|
+
trigger="Open",
|
|
460
|
+
title="Apply changes",
|
|
461
|
+
footer=sp_trigger("Apply", variant="primary", on_click=State.confirm),
|
|
462
|
+
open=State.modal_open,
|
|
463
|
+
on_open_change=State.set_modal_open,
|
|
464
|
+
)
|
|
465
|
+
sp_select(["North", "East", "South", "West"], value=State.region, on_change=State.set_region)
|
|
466
|
+
sp_toaster(sp_toast("Saved", State.text, kind="success", open=State.toast_open, on_open_change=State.set_toast_open))
|
|
467
|
+
```
|
|
468
|
+
|
|
469
|
+

|
|
470
|
+
|
|
471
|
+
## Timeline
|
|
472
|
+
|
|
473
|
+
The npm `SpTimeline` of `@silverpoint/react/timeline`. TimelineJS (`@knight-lab/timelinejs` 3.9.13)
|
|
474
|
+
is an npm dependency of this component: Reflex installs it when a page uses `sp_timeline`, and no
|
|
475
|
+
Python extra is needed. If it cannot be loaded, the component warns `SP025` and renders `fallback`.
|
|
476
|
+
|
|
477
|
+
```python
|
|
478
|
+
from reflex_silverpoint_react import sp_timeline
|
|
479
|
+
|
|
480
|
+
sp_timeline(
|
|
481
|
+
DATA, # TimelineJS data: title, events, eras (or any object with to_dict())
|
|
482
|
+
height=560,
|
|
483
|
+
ground="silverpoint",
|
|
484
|
+
substrate="cream",
|
|
485
|
+
mode="ink",
|
|
486
|
+
palette="sepia",
|
|
487
|
+
inked_frames=True, # the ground's hand-drawn frames and tone tiles
|
|
488
|
+
on_change=State.on_change, # the unique_id of the slide shown
|
|
489
|
+
)
|
|
490
|
+
```
|
|
491
|
+
|
|
492
|
+
It works in two layers. The **skin** replaces TimelineJS's colours, type and rules with the
|
|
493
|
+
ground's `--sp-` properties: substrate, inks, EB Garamond, hairline rules, eras hatched by density,
|
|
494
|
+
the current marker heightened. The **hand** reads the ground's own frame and tone masks from hidden
|
|
495
|
+
probes and lays them on the markers, eras and menubar, so they are drawn with the same pieces as
|
|
496
|
+
the `Sp` components; `inked_frames=False` keeps the skin only, and `precision`, `cyanotype` and
|
|
497
|
+
forced colours fall back to exact rules by themselves. Note that TimelineJS requests its icon font
|
|
498
|
+
from a relative path (`/css/icons/tl-icons.*`); the Reflex dev server answers it with HTML, so the
|
|
499
|
+
browser logs font-decoding warnings. They come from TimelineJS, not from this package.
|
|
500
|
+
|
|
501
|
+

|
|
502
|
+
|
|
503
|
+

|
|
504
|
+
|
|
327
505
|
## Interaction
|
|
328
506
|
|
|
329
507
|
```python
|
|
@@ -393,24 +571,45 @@ uv run reflex run
|
|
|
393
571
|
Pages: **Start** (quickstart, provider, ink vs precision), **Gallery** (the 60 charts, ground
|
|
394
572
|
controls, demo datasets vs data from Python state with a re-roll), **Playground** (one chart, every
|
|
395
573
|
rendering choice and the Python that reproduces it), **Interaction** (events, custom readout, a
|
|
396
|
-
volvelle that turns on click, a treemap and a sunburst that drill down together, live
|
|
574
|
+
volvelle that turns on click, a treemap and a sunburst that drill down together, live
|
|
575
|
+
KPI/gauge/meter, SVG and geometry export), **Dashboard** (a
|
|
397
576
|
linked operations dashboard fed from Python state with ground, substrate, mode and column controls, a
|
|
398
577
|
KPI strip, and `dashboard_link` on its own), **UI components** (`/ui`: the components controlled from
|
|
399
578
|
Python state with a native form submit, and the three reference panels of the upstream example apps
|
|
400
579
|
in silverpoint ink, precision and cyanotype), one **reference page per chart** (`/chart/<slug>`) and
|
|
401
|
-
one per UI component (`/ui/<slug>`: every declared state on both grounds, usage and props). The
|
|
580
|
+
one per UI component (`/ui/<slug>`: every declared state on both grounds, usage and props). The
|
|
581
|
+
Gallery and Playground also get a ground control, for `cyanotype`, and a palette control.
|
|
582
|
+
New in 0.7: **More components** (`/components`: the 20 composed components wired to Python, with
|
|
583
|
+
ground, substrate, mode and palette controls and an event log), **Palettes** (`/palettes`: the
|
|
584
|
+
presets, a palette builder with colour pickers and `check_palette`, a coloured section) and
|
|
585
|
+
**Timeline** (`/timeline`: the Knight Lab timeline on every ground, mode and palette).
|
|
402
586
|
|
|
403
587
|

|
|
404
588
|
|
|
405
589
|
## Development
|
|
406
590
|
|
|
407
591
|
```bash
|
|
408
|
-
uv
|
|
592
|
+
uv sync --extra dev
|
|
409
593
|
uv run pytest
|
|
410
594
|
uv run ruff check .
|
|
411
|
-
|
|
595
|
+
# Reflex 0.10 removed `reflex component build`: regenerate the .pyi stubs with the generator
|
|
596
|
+
# Reflex itself uses (plus this package's fixes), then build the sdist and wheel.
|
|
597
|
+
uv run python scripts/make_stubs.py
|
|
598
|
+
uv build
|
|
412
599
|
```
|
|
413
600
|
|
|
601
|
+
Before committing, run the hooks of [`.pre-commit-config.yaml`](.pre-commit-config.yaml) (ruff check
|
|
602
|
+
and format — including the Python blocks of this README — file hygiene and `uv lock --check`):
|
|
603
|
+
|
|
604
|
+
```bash
|
|
605
|
+
pre-commit install
|
|
606
|
+
pre-commit run --all-files
|
|
607
|
+
```
|
|
608
|
+
|
|
609
|
+
Changes per version are in [CHANGELOG.md](CHANGELOG.md); the guide for coding agents is
|
|
610
|
+
[AGENTS.md](AGENTS.md). Releases are published to PyPI by pushing a `vX.Y.Z` tag on `main` that
|
|
611
|
+
matches `version` in `pyproject.toml`.
|
|
612
|
+
|
|
414
613
|
## License
|
|
415
614
|
|
|
416
615
|
MIT. silverpoint is MIT; the EB Garamond typeface is under the SIL Open Font License.
|