Painting Typography
The typography resolver reads a text role or utility class as a TypeSpec: font, size, weight, paint, and optional stroke. Apply it to custom text, or convert it for Highcharts labels.
Typography
Every resolver takes an optional { el }: the id
or element whose nearest .screen ancestor
supplies the paint. The probe technique is documented on
Paint API
Paint API
TRMNLPaint: read the live CSS cascade from JavaScript to resolve framework colors and tile patterns
TRMNLPaint is the framework's public JavaScript paint API. It reads the live CSS cascade (bit depth, dark mode, theme, limited palette, and tiles all resolved) and hands back a canonical Fill, so token mappings are never duplicated in JavaScript. Charts are just one consumer; any plugin can resolve framework colors from JS for any purpose.
.
-
type(classOrRole, { el, stroke }): the resolved typography of a role or class as aTypeSpec. The role'chart-label'maps totext--small;'value','label','title'and'description'map to their own classes; any other string passes through as a literal class list (e.g.'value value--xxlarge'). Font family, size, weight and line-height follow the active font bundle and density, so they are always probed, never read from vars. Passstroke(a size token, ortruefor the base ring) to also resolve a text-stroke onto the spec. -
strokeSpec(sizeToken, { el }): the resolved text-stroke ring as{ color, width, radius }. ThesizeTokenis'small'/'medium'/'large'/'xlarge', ornullfor the basetext-stroke.
TypeSpec = {
fontFamily: string | null, // resolved family for the active bundle x density
fontSize: string | null, // e.g. "38px" for .value
fontWeight: string | null,
fontStyle: string | null,
fontVariantNumeric: string | null,
fontVariationSettings: string | null,
webkitFontSmoothing: string | null,
letterSpacing: string | null,
lineHeight: string | null,
color: string | null, // exact computed color; transparent in clipped-tile modes
backgroundColor: string | null, // the text tile under-field
backgroundImage: string | null, // exact computed image; dither ink rides here
backgroundSize: string | null,
backgroundPosition: string | null,
backgroundRepeat:string | null,
clip: string | null, // computed background-clip
textShadow: string | null, // exact 16-ring program when stroke was requested
filter: string | null,
overflow: string | null,
stroke: null | { color, width, radius }, // present only when stroke was requested
}
// The .value role, size/family/weight resolved for the active bundle + density.
var big = TRMNLPaint.type("value", { el: "my-chart" }); // -> TypeSpec
var axis = TRMNLPaint.type("chart-label", { el: "my-chart" });
Painting type
A resolved spec is written back complete, so dither ink and stroke rings survive instead of collapsing to
a solid color. Wrap paints in watch() so type
re-resolves when the bundle, density or theme changes; see
Paint API
Paint API
TRMNLPaint: read the live CSS cascade from JavaScript to resolve framework colors and tile patterns
TRMNLPaint is the framework's public JavaScript paint API. It reads the live CSS cascade (bit depth, dark mode, theme, limited palette, and tiles all resolved) and hands back a canonical Fill, so token mappings are never duplicated in JavaScript. Charts are just one consumer; any plugin can resolve framework colors from JS for any purpose.
.
-
applyType(node, typeSpec): writes aTypeSpec's exact computed font, text paint, clipping and optional stroke longhands onto a node. Dither ink, its under-field and the full 16-ring text-shadow round-trip instead of being reduced to a solid color.
Highcharts labels
The text adapter copies a resolved spec into Highcharts' label options; the fill adapter and the adapter ground rules live on Painting Charts Painting Charts Chart series colors from the framework ramp, with Highcharts adapters The chart resolvers pick evenly spaced series colors from the framework chart ramp, resolved through the live cascade. Adapters convert the resulting Fills into Highcharts color options. .
-
toHighchartsText(typeSpec): turns aTypeSpecinto{ color, textOutline, fontFamily?, fontSize?, ... }. Font keys appear only when resolved, andtextOutlineis'none'unless a real opaque stroke was requested, which kills Highcharts' default white halo on data labels.
// Typography into Highcharts label options.
var label = TRMNLPaint.toHighchartsText(
TRMNLPaint.type("chart-label", { el: "my-chart" }));
// => { color, textOutline: "none", fontFamily, fontSize, fontWeight }
Live example
The two stat tiles below are built from plain spans that carry no framework classes.
TRMNLPaint.type() resolves the
value role (the big-number face used by stat
tiles) and the chart-label role (mapped to
text--small), and
TRMNLPaint.applyType() writes the resolved
font and text-paint longhands onto them. Toggle the font bundle or density in the picker and the tiles
follow, because family and size are probed from the live cascade rather than hardcoded.
<div id="type-specimen" class="grid grid--cols-2 w--full"></div>
<script type="text/javascript">
function whenReady(cb) {
if (window.TRMNLPaint) return cb();
window.addEventListener("load", function () {
if (window.TRMNLPaint) cb();
}, { once: true });
}
whenReady(function () {
var el = "type-specimen";
var TILES = [
{ value: "4,283", caption: "Reams Sold" },
{ value: "12", caption: "Dundie Awards" }
];
// watch() re-resolves the typography whenever bundle/density/theme changes.
TRMNLPaint.watch(el, function () {
var grid = document.getElementById(el);
if (!grid) return;
grid.innerHTML = "";
var big = TRMNLPaint.type("value", { el: el });
var small = TRMNLPaint.type("chart-label", { el: el });
TILES.forEach(function (t) {
var cell = document.createElement("div");
cell.className = "flex flex--col flex--center-x";
var v = document.createElement("span");
v.textContent = t.value;
// applyType writes the complete TypeSpec; the spans themselves carry
// no framework class.
TRMNLPaint.applyType(v, big);
var c = document.createElement("span");
c.textContent = t.caption;
TRMNLPaint.applyType(c, small);
cell.appendChild(v);
cell.appendChild(c);
grid.appendChild(cell);
});
});
});
</script>