Skip to main content

reflex-silverpoint-react

A Reflex custom component for silverpoint: charts drawn in the manner of a Renaissance silverpoint drawing, with a fine silver line on a prepared ground, tone built from hatching, and white heightening on the live value.

The hand-drawn irregularity lives only in the ornament. The data geometry is exact, and every chart has a precision mode that turns the inking off.

It wraps @silverpoint/react 0.1.1 and exposes all 33 charts, the SilverpointProvider, the interaction events, custom readouts and the imperative handle (SVG export and geometry) as Python.

The gallery of the demo app

Installation

pip install reflex-silverpoint-react
# or
uv add reflex-silverpoint-react

Nothing else to do on the JavaScript side: Reflex installs @silverpoint/react, @silverpoint/core, @silverpoint/grounds and @silverpoint/fonts, and every chart imports the two stylesheets it needs (@silverpoint/grounds/styles.css and the self-hosted EB Garamond of @silverpoint/fonts/fonts.css). No Tailwind, no CDN.

Requires Reflex 0.9.12 or later (React 19).

Quickstart

import reflex as rx
from reflex_silverpoint_react import line_chart

DATA = [
    {"hour": "00", "hits": 18},
    {"hour": "04", "hits": 11},
    {"hour": "08", "hits": 42},
    {"hour": "12", "hits": 64},
    {"hour": "16", "hits": 57},
    {"hour": "20", "hits": 30},
]


def index() -> rx.Component:
    return rx.box(
        line_chart(data=DATA, x_key="hour", value_key="hits", title="Hits per hour"),
        width="480px",
    )


app = rx.App()
app.add_page(index)

The chart takes the width of its container; height is the height of the drawing area (160 px by default). Omit data and a chart draws its own demo dataset.

Props are the React props in snake_case: xKey → x_key, hatchFill → hatch_fill, footerRight → footer_right, centerLabel → center_label, and so on. data and every prop can be a Reflex state var.

The 33 charts

Family Charts
Lines line_chart, step_chart, sparkline_rows, kpi_card
Bars bar_chart, stacked_bar_chart, composed_chart, waterfall_chart, funnel_chart, bullet_chart, pyramid_chart, candlestick_chart
Areas area_chart, range_band_chart, stream_chart
Points & grids scatter_chart, bubble_chart, heatmap_chart, treemap_chart, activity_grid
Flows sankey_chart, chord_ring
Radial donut_chart, radar_chart, polar_bar_chart, radial_arc_group, radial_rings, gauge_arc, meter_chart, coxcomb_chart, wind_rose, volvelle_chart, orbit_chart

Every factory has a class of the same name in PascalCase (LineChart, WindRose…). reflex_silverpoint_react.CHARTS is the whole catalog with each chart's family and the reference of its own props (COMMON_PROPS holds the shared ones), handy for galleries and documentation.

Props every chart shares

Prop Default
data demo dataset The rows to draw: a list of dicts.
ground / substrate / mode "silverpoint" / "cream" / "ink" Style. Substrates: cream, green, blue, ochre. mode="precision" turns the inking off.
seed, id derived, stable The hand drawing is deterministic: same props, same strokes.
height, width 160, container width Size of the drawing area in px.
chrome "card" "bare" draws only the plot.
title, badge, value, unit, footer_left, footer_right — The card's text.
label, description, data_table from title, —, "hidden" Accessibility.
locale, number_format environment Number formatting (number_format is a dict of Intl.NumberFormatOptions).
hatch_fill "tile" "per-shape" gives richer hatching at a much greater weight.
tooltip built-in readout A custom readout; see tooltip_template.
on_active_change, on_select — Events; see below.

One ground for the whole app

from reflex_silverpoint_react import bar_chart, donut_chart, silverpoint_provider

silverpoint_provider(
    bar_chart(data=sales, x_key="month", value_key="units", title="Units sold", unit="units"),
    donut_chart(data=channels, name_key="channel", value_key="share", title="Sales by channel", center_label="%"),
    ground="silverpoint",
    substrate="green",
    locale="en-GB",
)

A prop on a chart always wins over the provider. The provider's props can be state vars, so one select can re-ground a whole dashboard.

Interaction

class State(rx.State):
    active: str = "—"

    @rx.event
    def on_active(self, item: dict | None):
        self.active = "—" if item is None else f"{item['datum']['hour']}: {item['value']}"

    @rx.event
    def on_select(self, item: dict):
        print("selected", item["datum"])


line_chart(
    data=DATA,
    x_key="hour",
    value_key="hits",
    on_active_change=State.on_active,
    on_select=State.on_select,
    tooltip=tooltip_template("{datum.hour} h · {value} hits"),
)
  • on_active_change receives the item under the pointer or keyboard focus, and None when it leaves. on_select fires on click, Enter or Space. The item is {"seriesKey", "index", "datum", "value", "point": {"x", "y"}}.
  • tooltip_template(text) builds the tooltip render function from a format string. Placeholders: {heading}, {text} (the built-in readout's two lines), {announcement}, {value}, {index}, {series} and {datum.<field>}. {{ and }} print literal braces.

Export: the imperative handle

Give a chart an id and its ChartHandle is reachable from Python:

from reflex_silverpoint_react import download_svg, get_geometry, get_svg

line_chart(id="hits", data=DATA, x_key="hour", value_key="hits")

rx.button("Download SVG", on_click=download_svg("hits", "hits.svg"))  # in the browser
rx.button("SVG to Python", on_click=get_svg("hits", State.receive_svg))  # handler gets a str
rx.button("Geometry", on_click=get_geometry("hits", State.receive_geometry))  # handler gets a dict

The exported SVG carries its own ground colours, so it renders the same outside the app.

Notes

  • volvelle_chart: index_ring and index_value apply to your own rings, so pass data when you use them (the demo dataset keeps its own index).
  • gauge_arc and meter_chart take percent (0-100) instead of data.
  • Charts switch to precision by themselves under prefers-contrast: more or forced-colors: active; no prop overrides that.
  • Accessors are field names (strings). The JavaScript API also accepts functions; from Python, shape your rows instead.

Demo app

uv venv && uv pip install -e .
cd silverpoint_react_demo
uv run reflex run

Pages: Start (quickstart, provider, ink vs precision), Gallery (the 33 charts, ground controls, demo datasets vs data from Python state with a re-roll), Playground (one chart, every rendering choice and the Python that reproduces it), Interaction (events, custom readout, a volvelle that turns on click, live KPI/gauge/meter, SVG and geometry export) and one reference page per chart (/chart/<slug>) with its props.

Interaction page

Development

uv venv && uv pip install -e ".[dev]"
uv run pytest
uv run ruff check .
uv run reflex component build   # .pyi stubs + sdist and wheel in dist/

License

MIT. silverpoint is MIT; the EB Garamond typeface is under the SIL Open Font License.

Release files for reflex-silverpoint-react 0.1.0

For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.

Source distribution (sdist)

Source distribution for reflex-silverpoint-react 0.1.0
File Size Uploaded
reflex_silverpoint_react-0.1.0.tar.gz 29.4 kB Details

Built distribution (wheel)

Table of built distributions (wheels) for reflex-silverpoint-react 0.1.0
File Interpreter ABI Platform
reflex_silverpoint_react-0.1.0-py3-none-any.whl Python 3 none any Details

Total release size: 58.2 kB

Release files / reflex_silverpoint_react-0.1.0.tar.gz

Download URL reflex_silverpoint_react-0.1.0.tar.gz
Size 29.4 kB
Tags Source
SHA-256 checksum
How to use checksums
8516478dab73ba6e9fb882a0a5c29aeab7985090e0897857b754fcd685a6513e
BLAKE2b-256 checksum
How to use checksums
c31c33a5d1b18d67d9adab6e2f6d07c3d49839ea3185b256b2e4d3cb1e4197ee
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
Yes
Uploaded via twine/7.0.0 CPython/3.13.14

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 Sep 26, 2026.

Transparency log

Release files / reflex_silverpoint_react-0.1.0-py3-none-any.whl

Download URL reflex_silverpoint_react-0.1.0-py3-none-any.whl
Size 28.8 kB
Tags Python 3
SHA-256 checksum
How to use checksums
81b9c6304ebf0ebbbc7ece9a675c8bb686517946dc4fa04324ca187b719e24c5
BLAKE2b-256 checksum
How to use checksums
e970bd5091a999821fd9d442d14c162215630fc0f1396290f044607ea85e066e
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
Yes
Uploaded via twine/7.0.0 CPython/3.13.14

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 Sep 26, 2026.

Transparency log

Release history Release notifications | RSS feed

This release

0.1.0 This release

2 release files

Anthropic, PBC Visionary sponsor Bloomberg Visionary sponsor Hudson River Trading Visionary sponsor Meta Visionary sponsor NVIDIA Visionary sponsor Microsoft Sustainability sponsor Depot Continuous Integration AWS Cloud computing and Security Sponsor Datadog Monitoring Fastly CDN Google Download Analytics Sentry Error logging StatusPage Status page