@moatamed-sce/ui-charts
v0.1.7
Published
SCE Platform data-visualisation components built on ECharts.
Readme
@moatamed-sce/ui-charts
The data-visualisation layer of the SCE Platform: 76 chart components built on Apache ECharts, each one an Angular wrapper that takes typed data in and paints a themed, RTL-aware, accessible chart.
The point of the wrappers is that no feature ever writes an ECharts option object. Series colours, axis ink, tooltip cards, dark mode, Arabic direction, resize handling and instance disposal are solved once here; a page passes [series] and [categories].
Status
Built with @nx/angular:package to dist/libs/ui-charts. Inside the monorepo it resolves through a
TypeScript path alias. For external / local-registry installs, treat it like the other @moatamed-sce/*
libraries — see docs/design-system/RECIPES.md §7–§8.
What's in it
Charts, by family — every one with the selector sce-<name>-chart:
- Comparison — bar, horizontal-bar, diverging-bar, multi-segment-bar, lollipop, dumbbell, pictorial-bar, marimekko, pareto, radial-bar, polar-bar
- Trend — line, area, range-area, bump, burndown, cumulative-flow, control, candlestick, ohlc-volume
- Composition — pie, donut, ring, rose, funnel, pyramid, population-pyramid, sankey, icicle
- Distribution — histogram, boxplot, scatter, scatter-regression, effect-scatter, bubble, quadrant, punch-card, correlation-matrix, parallel-coordinates
- Relationship — chord, arc-diagram, force-graph, network-graph, flow-map
- Time and progress — gantt, calendar-heatmap, heatmap, cohort-retention, gauge, multi-segment-gauge, bullet, scale-indicator
- Geo — region-map
- Supporting —
sce-chart-legend,sce-chart-state,sce-chart-data-table
Plus the theming primitives every chart shares: CHART_PALETTE_LIGHT / CHART_PALETTE_DARK, CHART_SEQUENTIAL, CHART_DIVERGING, CHART_STATUS, CHART_INK, and injectChartMode().
Why injectChartMode() exists
The rest of the design system gets dark mode for free: [data-theme='dark'] on <html> reroutes every CSS custom property. A chart cannot — it is painted onto a <canvas>, which inherits no CSS at all, so its colours are resolved in TypeScript when the option object is built. injectChartMode() returns a signal tracking the theme attribute, and the charts rebuild their options when it flips. Without it a chart keeps light-mode axis ink on a dark surface and its label text all but disappears.
Pass [mode] explicitly only when a chart must ignore the app theme — a chart being rasterised into a PDF, for instance.
Dependencies
Installing @moatamed-sce/ui-charts pulls in echarts and ngx-echarts automatically (they are package dependencies).
You still need these peer packages in the app (same as the rest of the design system — not duplicated by charts):
- Angular 21 (
@angular/core) - RxJS 7.8
@moatamed-sce/core@moatamed-sce/ui-components
Note the direction of that last one: charts may use design-system atoms, and no atom may use a chart. The @nx/enforce-module-boundaries rule makes that machine-enforced, not aspirational.
Quick start
import { SceBarChartComponent, type BarSeriesData } from '@moatamed-sce/ui-charts';
readonly categories = ['Q1', 'Q2', 'Q3', 'Q4'];
readonly series: BarSeriesData[] = [
{ name: 'Contracts', data: [12, 19, 7, 22], color: '#25935f' },
];<sce-bar-chart
[series]="series"
[categories]="categories"
[height]="320"
[loading]="loading()"
[empty]="!series.length"
[ariaLabel]="'DASHBOARD.CHARTS.CONTRACTS_BY_QUARTER' | translate"
/>Per-column colour (sce-bar-chart)
Colour belongs on the category (the column), not on the numeric measure. Pass { label, color? } in categories; keep series.data as plain numbers. Categories without color inherit series.color (or the theme palette). Use series.color when comparing several series across the same labels.
import { SceBarChartComponent, type BarCategoryValue, type BarSeriesData } from '@moatamed-sce/ui-charts';
readonly statusCategories: BarCategoryValue[] = [
{ label: 'Approved', color: '#25935f' },
{ label: 'Pending', color: '#d97706' },
{ label: 'Rejected', color: '#dc2626' },
{ label: 'Draft', color: '#3b82f6' },
];
readonly statusSeries: BarSeriesData[] = [{ name: 'Requests', data: [42, 18, 7, 11] }];
// When pairing with sce-chart-data-table:
// rows = series.map(s => [s.name, ...s.data])<sce-bar-chart
[categories]="statusCategories"
[series]="statusSeries"
[showLegend]="false"
[height]="260"
/>Try it in the design-system lab: Bar chart → Playground → “One colour per column”.
Every chart shares the same state and accessibility inputs, so a page never hand-rolls them:
| Input | Purpose |
| -------------------------- | --------------------------------------------------------- |
| loading / loadingLabel | Skeleton state while data is in flight |
| empty / emptyText | The no-data state, distinct from an error |
| errorText | The failed state, with the message to show |
| ariaLabel | The chart's accessible name — a canvas has none otherwise |
| mode | Force 'light' / 'dark'; omit to follow the app theme |
| isRtl | Force direction; omit to follow the app locale |
| height / width | Explicit size; height defaults to 300 |
Performance
Charts are heavy. Put them behind @defer (on viewport) — the repo's rule for below-the-fold visualisations — so a dashboard's initial bundle does not carry ECharts for a chart the user may never scroll to.
Not in this package
Maps are not here. Leaflet lives in @moatamed-sce/ui-components (sce-osm-leaflet-map) and @moatamed-sce/core. The only geographic component in this library is sce-region-map-chart, which is an ECharts choropleth rather than a tile map.
Docs
License
MIT
