painting library

Drafter's extension API — import this alongside package:drafter/drafter.dart when you write a custom ChartRenderer or draw directly into a chart Canvas.

The everyday chart widgets, data models and theming live in the main package:drafter/drafter.dart entrypoint. This secondary entrypoint exposes the lower-level building blocks so they don't clutter the primary namespace:

Classes

AccessibilityFormat
Shared formatting so every renderer's ChartRenderer.accessibilityValue reads consistently. Trims trailing zeros so 40.0 announces as "40".
CartesianScale
The reversible data↔pixel mapping for an index-based cartesian chart (line/area/bar/candlestick). Renderers compute this once and use it for both painting (xForIndex/yForValue) and hit-testing (valueForY/nearestIndex), so paint geometry and interaction geometry can never drift apart.
ChartAxis
Cross-chart math & layout helpers so no chart re-implements them: axis tick steps, cartesian/radial bounds, and text-alignment offsets. Pure value math.
ChartBounds
The inset plotting rectangle for a cartesian chart (line/bar/scatter).
ChartCanvas
A thin, reusable widget that hosts any ChartRenderer in a CustomPaint, reads the theme from the environment, and traces the chart in with the shared reveal animation. Every concrete chart widget wraps this — so the animation/theming plumbing lives in exactly one place.
ChartFormatting
Deterministic, platform-independent number formatting for axis labels and value read-outs. Integer arithmetic avoids float-precision drift and drops trailing zeros (3.0 -> "3", 3.10 -> "3.1").
ChartHitTest
Pure hit-testing over a ChartScene. No Flutter painting — every function here is a deterministic query so the interaction layer (and tests) can reason about gestures without a canvas.
ChartRenderer
Draws one chart into a Canvas. Implementations hold immutable data + style, mirroring the Compose/SwiftUI renderer pattern: a renderer is a pure value that, given a canvas, size, theme, and reveal progress, draws itself.
ChartText
Text-alignment offset math: converts an HAlign/VAlign into the pixel delta to apply to a draw origin so a label of a given size anchors correctly.
InteractiveRenderer
An opt-in capability a ChartRenderer can also implement to expose the geometry it drew, so the interaction layer can hit-test it. InteractiveChart checks renderer is InteractiveRenderer; renderers that don't implement it still render normally, just without tooltips/selection (graceful degrade).
LabelLayout
One-dimensional label de-collision used wherever chart labels would overlap: axis ticks (drop overlapping labels) and trackball value rows (nudge them apart). Pure value math — no canvas, fully unit-testable.
RadialLayout
Center + radius for a radial chart (pie/gauge/radar/polar/sunburst).
TooltipRow
One row of a tooltip: a text line with an optional color swatch.

Enums

HAlign
Horizontal anchor for a label drawn at an origin x.
VAlign
Vertical anchor for a label drawn at an origin y.

Functions

areaGradientShader(Color color, {required double top, required double bottom, double topAlpha = 0.32}) Gradient
A soft vertical gradient shader fading from color near top to transparent at bottom. Mirrors areaGradient in the Compose library.
drafterFinite(double value, [double fallback = 0]) double
Returns value when it is finite, otherwise fallback (0 by default).
drafterFiniteOrNull(double value) double?
Returns value when it is finite, otherwise null.
drawChartText(Canvas canvas, String text, Offset at, {required Color color, double fontSize = 9, FontWeight weight = FontWeight.normal, HAlign h = HAlign.start, VAlign v = VAlign.top}) → void
Draws text anchored at at by h/v. The shared label helper every chart uses (the equivalent of SwiftUI's context.draw(Text…, at:, anchor:)).
drawHighlightRing(Canvas canvas, Offset center, Color color, {double radius = 6}) → void
A white-haloed ring marking a highlighted/selected datum.
drawSelectionBand(Canvas canvas, Rect rect, {required Color fill, required Color border}) → void
A translucent drag range-selection band over rect.
drawSmoothLine(Canvas canvas, {required List<Offset> points, required Color color, required double baseline, required double progress, double strokeWidth = 6, bool fill = true, bool endDot = true, bool smooth = true}) → void
Draws a single smooth line series with an optional gradient area fill, a tracing left-to-right reveal animation, and an optional highlighted end dot. The Flutter equivalent of DrawScope.drawSmoothLine.
drawTooltip(Canvas canvas, {required Offset anchor, required Size container, required List<TooltipRow> rows, required Color background, required Color textColor, required Color mutedTextColor, String? title}) → void
Draws a rounded tooltip panel near anchor, laying out an optional title above rows. The panel is kept fully inside container (flipped to the other side of the anchor and clamped to the edges as needed), so it never clips off-screen. Reuses the shared text cache via drawChartText.
drawTrackball(Canvas canvas, {required double x, required double top, required double bottom, required Color lineColor, List<Offset> markers = const [], List<Color> markerColors = const []}) → void
A vertical trackball line at x spanning top..bottom, with optional ring markers (one per series value at the active column) in markerColors.
drawVertexDot(Canvas canvas, Offset center, Color color, double radius) → void
Draws a small filled dot with a white halo — used to mark line vertices.
measureChartText(String text, {double fontSize = 9, FontWeight weight = FontWeight.normal, Color color = const Color(0xFF000000)}) double
The laid-out pixel width of text in the chart label style, using the same cache as drawChartText. Lets renderers de-overlap axis labels by measured width (via LabelLayout.thin) instead of guessing a stride.
normalizedLabels(List<String> labels, int count) List<String>
Pads or truncates labels to exactly count entries, so a mismatched label array can never drive a different number of columns than the data. Missing labels become empty strings; extra labels are dropped.
polylinePath(List<Offset> points) Path
A straight-segment polyline path, used when a series opts out of smoothing.
smoothPath(List<Offset> points) Path
Builds a smooth cubic-bezier Path that passes through every vertex in points using a Catmull-Rom spline (tension 0.5). Falls back to straight segments below three points, where a curve is undefined.
trimPath(Path path, double t) Path
Returns the sub-path of path from its start up to fraction t in 0..1, the Flutter equivalent of SwiftUI's Path.trimmedPath(from:to:).