Documentation

Timeseries charts

@infoplaza/platform/timeseries-charts

A portable point-forecast chart — Recharts composed LINE series with DIRECTION arrows, VALUE labels, and PRECIPITATION_TYPE icons on the axis — without the map stack or app chrome. The models catalog is the same as timeseries tables (GET /api/platform/timeseries-models, or marine-timeseries-models when domain="marine"). Series load from GET /api/platform/timeseries-point-forecast (or marine-timeseries-point-forecast) unless the host passes charts / getCharts. See the timeseries charts demo. See API request counts and token credits in the charts platform example.

Packaged vs composed

Sibling product to the timeseries table and ensemble. Import only from @infoplaza/platform/timeseries-charts. Do not extend table TimeseriesCellView with LINE.

<TimeseriesChartsForecast
  lat={52.3676}
  lon={4.9041}
  model="gfs"
  showToolbar={false}
/>
<TimeseriesModelsProvider lat={52.3676} lon={4.9041}>
  <TimeseriesChartsProvider>
    <TimeseriesChartsToolbar />
    <TimeseriesChartsBuilder>
      <TimeseriesChartsChart />
    </TimeseriesChartsBuilder>
  </TimeseriesChartsProvider>
</TimeseriesModelsProvider>

Default groups follow domain: land uses DEFAULT_LAND_TIMESERIES_CHART_GROUPS (Temperature, Precipitation, Wind); marine uses DEFAULT_MARINE_TIMESERIES_CHART_GROUPS (Wind and Wave). Each group is one composed chart. Group-visibility footer pills are off for now. Below Tailwind sm (640px) the charts show one day at a time, with a sticky day pager shared across the stack (tap a day or swipe the plot). At sm and up they keep the full forecast domain.

Pass elementGroups to replace those defaults (it does not merge). Reuse a default group or define new ones. Optional thresholds only apply to LINE series on each chart. Optional line on a LINE item sets color, thickness, dash, opacity, and curve. Optional yAxis.domain on a group sets the shared Y scale (graph.config.domain stays the X-axis time range):

const GROUPS = [
  DEFAULT_LAND_TIMESERIES_CHART_GROUPS.find((g) => g.key === 'temperature')!,
  {
    key: 'clouds',
    title: 'Cloud cover',
    items: [
      { slug: 'clouds_total', title: 'Total cloud cover', element: 'cloudcovertotal', unit: '%', view: 'LINE' },
      { slug: 'clouds_low', title: 'Low clouds', element: 'cloudcoverlow', unit: '%', view: 'LINE' },
      { slug: 'clouds_mid', title: 'Mid clouds', element: 'cloudcovermiddle', unit: '%', view: 'LINE' },
      { slug: 'clouds_high', title: 'High clouds', element: 'cloudcoverhigh', unit: '%', view: 'LINE' },
      { slug: 'clouds_rh', title: 'Relative humidity', element: 'relativehumidity', level: '2m', unit: '%', view: 'LINE' },
      { slug: 'clouds_vis', title: 'Visibility', element: 'visibility', unit: 'km', view: 'VALUE', stripLabel: 'Vis' },
    ],
  },
  {
    key: 'pressure',
    title: 'Pressure',
    yAxis: { domain: ['dataMin', 'dataMax'] },
    items: [
      { slug: 'pressure_msl', title: 'Mean sea level pressure', element: 'pressure_meansealevel', unit: 'hPa', view: 'LINE' },
      { slug: 'pressure_surface', title: 'Surface pressure', element: 'pressure', level: 'surface', unit: 'hPa', view: 'LINE' },
    ],
  },
]

const THRESHOLDS = {
  ignored_hours: [],
  conditions: {
    yellow: [
      { rows: [{ elementId: 'cloudcovertotal', operator: 'greater-than', from: 50, to: null }] },
      { rows: [{ elementId: 'relativehumidity', operator: 'greater-than', from: 80, to: null }] },
      { rows: [{ elementId: 'pressure_meansealevel', operator: 'less-than', from: 1010, to: null }] },
    ],
    orange: [
      { rows: [{ elementId: 'cloudcovertotal', operator: 'greater-than', from: 75, to: null }] },
      { rows: [{ elementId: 'relativehumidity', operator: 'greater-than', from: 90, to: null }] },
      { rows: [{ elementId: 'pressure_meansealevel', operator: 'less-than', from: 1000, to: null }] },
    ],
    red: [
      { rows: [{ elementId: 'cloudcovertotal', operator: 'greater-than', from: 90, to: null }] },
      { rows: [{ elementId: 'relativehumidity', operator: 'greater-than', from: 95, to: null }] },
      { rows: [{ elementId: 'pressure_meansealevel', operator: 'less-than', from: 990, to: null }] },
    ],
  },
}

<TimeseriesChartsForecast
  lat={52.3676}
  lon={4.9041}
  model="gfs"
  elementGroups={GROUPS}
  thresholds={THRESHOLDS}
/>
{
  key: 'temperature',
  title: 'Temperature',
  items: [
    {
      slug: 'temperature_temperature',
      title: 'Temperature',
      element: 'temperature',
      level: '2m',
      unit: '°C',
      view: 'LINE',
      line: { color: '#E63A48', strokeWidth: 2, type: 'monotone' },
    },
    {
      slug: 'temperature_dewpoint',
      title: 'Dewpoint',
      element: 'dewpoint',
      level: '2m',
      unit: '°C',
      view: 'LINE',
      line: { color: '#3b82f6', strokeDasharray: '4 4' },
    },
    {
      slug: 'temperature_temperatureapparent',
      title: 'Feels like',
      element: 'temperatureapparent',
      level: '2m',
      unit: '°C',
      view: 'LINE',
      line: { color: '#b45309', strokeWidth: 1, opacity: 0.55 },
    },
  ],
}

API

@infoplaza/platform/timeseries-charts

Compound API. TimeseriesModelsProvider is the only writer of the catalog. TimeseriesChartsProvider loads charts by default and stacks every configured group.
import {
  TimeseriesChartsForecast,
  TimeseriesModelsProvider,
  TimeseriesChartsProvider,
} from '@infoplaza/platform/timeseries-charts'

Also exported: DEFAULT_LAND_TIMESERIES_CHART_GROUPS, DEFAULT_MARINE_TIMESERIES_CHART_GROUPS, DEFAULT_TIMESERIES_CHART_PLOT_HEIGHT, hooks useTimeseriesCharts / useTimeseriesChartsContext / useTimeseriesChartBlock, and types such as TimeseriesChartBlock, TimeseriesChartGraphConfig, TimeseriesChartLineStyle, TimeseriesChartYAxis, TimeseriesChartView.

TimeseriesChartsForecast

Packaged composed charts with toolbar and charts.

Wraps TimeseriesModelsProvider and TimeseriesChartsProvider, then optional Toolbar, Builder + Chart. lat and lon are required. Charts load from GET /api/platform/timeseries-point-forecast (or marine-timeseries-point-forecast when domain is marine) unless you pass charts or getCharts. One config group becomes one composed chart (LINE + DIRECTION + VALUE + PRECIPITATION_TYPE). Applies ip-platform for you.

import { TimeseriesChartsForecast } from '@infoplaza/platform/timeseries-charts'
  • Do not pass a models array. The catalog is loaded from GET /api/platform/timeseries-models (or marine-timeseries-models when domain is marine).
  • domain defaults to land. Set domain="marine" on Forecast or TimeseriesModelsProvider.
  • Builder stacks every group in elementGroups.
  • showToolbar defaults to true. showFooter is off for now (group-visibility pills are disabled).

Required props

PropTypeDefaultDescription
latnumber—Latitude of the forecast point.
lonnumber—Longitude of the forecast point.

Optional props

PropTypeDefaultDescription
basePathstring'/api/platform'Auth handler mount path.
domain'land' | 'marine''land'Which PlatformAuth proxy to use. land hits timeseries-models and timeseries-point-forecast; marine hits the marine-timeseries-* routes.
model / defaultModel / onModelChangestring—Preferred catalog slug. model without onModelChange (or defaultModel) is the initial selection; model + onModelChange is controlled. If the slug is not in the fetched catalog, the first model is used.
showToolbarbooleantrueRender the model / run pill toolbar.
showFooterbooleanfalseGroup-visibility pills. Off for now; leave false.
elementGroupsTimeseriesChartElementGroup[]DEFAULT_LAND_TIMESERIES_CHART_GROUPS when domain is land, DEFAULT_MARINE_TIMESERIES_CHART_GROUPS when marineChart config. Each group is one composed chart. Item view is LINE, DIRECTION, VALUE, or PRECIPITATION_TYPE. LINE items may set optional line (color, strokeWidth, strokeDasharray, opacity, type). Groups may set optional yAxis.domain ([number | auto | dataMin | dataMax, ...]); omit to keep Y pinned at 0. Graph config.domain remains the X-axis time range. A defined array replaces domain defaults (it does not merge). Omit to use land or marine defaults from domain.
visibleGroups / defaultVisibleGroups / onVisibleGroupsChangestring[]—Which group keys are shown. Defaults to every group.
chartsTimeseriesChartBlock[]—Host-owned chart blocks. When defined, skips the point-forecast fetch.
getCharts(options) => TimeseriesChartBlock[]—Sync override when charts is omitted. Receives model, run, models, elementGroups, visibleGroups, locale, timezone.
localestring'en'Date axis labels: 'en' | 'nl' | 'de' | 'it' | 'es' | 'fr'.
plotHeightnumber320Plot-area height in pixels. Also sizes the Builder loading skeleton. Chart/Graph can override. fixedHeight still overrides the total Recharts container.
hourInterval1 | 3 | 66Vertical unlabeled hour grid lines in the plot. Day-boundary ticks stay on the X axis. For 3h and 6h, strip overlays (direction, value, precipitation type) show the latest point in each bucket, centered; 1h keeps hourly strip points. LINE series are unchanged. Chart/Graph can override.
thresholdsTimeseriesChartThresholds | null—Optional project-style object; only conditions and ignored_hours are used. Each chart keeps AND-groups whose elementIds are all LINE series on that chart, then draws dashed Y-lines and a status strip above the date labels. Chart/Graph can override.
classNamestring—Extra class on the root wrapper.

Example

<TimeseriesChartsForecast
  lat={52.3676}
  lon={4.9041}
  model="gfs"
  locale="en"
/>

TimeseriesModelsProvider

Location-filtered timeseries catalog (re-exported).

Same provider as @infoplaza/platform/timeseries. Required lat and lon. Fetches GET {basePath}/timeseries-models?lat=&lon= (or marine-timeseries-models when domain is marine). Re-exported so composed charts can import from one package.

import { TimeseriesModelsProvider, useTimeseriesModels } from '@infoplaza/platform/timeseries-charts'

Required props

PropTypeDefaultDescription
latnumber—Latitude of the forecast point.
lonnumber—Longitude of the forecast point.

Optional props

PropTypeDefaultDescription
basePathstring'/api/platform'Auth handler mount path.
domain'land' | 'marine''land'land uses timeseries-models; marine uses marine-timeseries-models.

TimeseriesChartsProvider

Selection, chart blocks, and group visibility.

Must sit under TimeseriesModelsProvider. Holds model / run / visibleGroups, loads chart blocks, and exposes them to Toolbar, Builder, and Footer. No models prop. Fetches point forecast unless charts / getCharts is passed.

import { TimeseriesChartsProvider, useTimeseriesCharts } from '@infoplaza/platform/timeseries-charts'
  • useTimeseriesCharts() throws outside the provider. useTimeseriesChartsContext() is nullable.

Required props

None.

Optional props

PropTypeDefaultDescription
model / defaultModel / onModelChangestring—Preferred catalog slug. model without onModelChange (or defaultModel) is the initial selection; model + onModelChange is controlled. If the slug is not in the fetched catalog, the first model is used.
run / defaultRun / onRunChangenumber | 'all'—Runtime selection. all fetches one payload per catalog runtime.
elementGroupsTimeseriesChartElementGroup[]—Replaces domain defaults when defined (does not merge). Land uses DEFAULT_LAND_TIMESERIES_CHART_GROUPS, marine uses DEFAULT_MARINE_TIMESERIES_CHART_GROUPS. LINE items may set optional line; groups may set optional yAxis.domain.
visibleGroups / defaultVisibleGroups / onVisibleGroupsChangestring[]—Group keys currently shown.
chartsTimeseriesChartBlock[]—Host-owned blocks. Skips the fetch.
getCharts(options) => TimeseriesChartBlock[]—Sync override when charts is omitted.
localestring'en'Date axis locale.
plotHeightnumber320Plot-area height in pixels. Flows to Chart/Graph and the Builder loading skeleton.
hourInterval1 | 3 | 66Vertical unlabeled hour grid lines. For 3h and 6h, strip overlays summarize to the latest point in each bucket, centered. Flows to Chart/Graph.
thresholdsTimeseriesChartThresholds | null—Optional. conditions + ignored_hours. Per-chart Y-lines and status strip for LINE elements on that chart. Flows to Chart/Graph.

TimeseriesChartsToolbar

Model and run pills.

Resolves props ?? context and returns null if neither exists — it does not throw. Reuses timeseries pills internally, not map controls.

import { TimeseriesChartsToolbar } from '@infoplaza/platform/timeseries-charts'

Required props

None.

Optional props

PropTypeDefaultDescription
modelstring—Falls back to context.
onModelChange(slug: string) => void—Falls back to context.
runnumber | 'all'—Falls back to context.
onRunChange(run: number | 'all') => void—Falls back to context.

TimeseriesChartsBuilder

Maps chart blocks onto Chart. Does not fetch.

Requires TimeseriesChartsProvider. Loading skeleton, then one chart-block context per TimeseriesChartBlock (runtime × group). Clone children once per block. Below Tailwind sm (640px) it shows a sticky day pager so every stacked chart stays on the same calendar day.

import { TimeseriesChartsBuilder, TimeseriesChartsChart } from '@infoplaza/platform/timeseries-charts'

Required props

None.

Optional props

PropTypeDefaultDescription
childrenReactNode—Typically <TimeseriesChartsChart />.

Example

<TimeseriesChartsBuilder>
  <TimeseriesChartsChart />
</TimeseriesChartsBuilder>

TimeseriesChartsChart

Bridge from block context to TimeseriesGraph.

Reads the current chart block (or explicit graph props) and renders TimeseriesGraph.

import { TimeseriesChartsChart } from '@infoplaza/platform/timeseries-charts'

Required props

None.

Optional props

PropTypeDefaultDescription
configTimeseriesChartGraphConfig—Explicit graph config. Otherwise reads the current builder block.
plotHeightnumbercontext, else 320Plot-area height in pixels. Falls back to TimeseriesChartsProvider.
hourInterval1 | 3 | 6context, else 6Vertical unlabeled hour grid lines. For 3h and 6h, strip overlays summarize to the latest point in each bucket, centered. Falls back to TimeseriesChartsProvider.
thresholdsTimeseriesChartThresholds | null—Falls back to TimeseriesChartsProvider.

TimeseriesGraph

Low-level Recharts ComposedChart.

LINE series in the plot; DIRECTION arrows, VALUE labels, and PRECIPITATION_TYPE icons in a Customized strip band under the plot (height grows with overlay rows). Precipitation-type icons use the point-forecast palette (the same visualization as the map legend); hail is off-white so it stays readable on the strip. Day banding, hour lines, and the hover cursor continue through the band. Hover values float in the title row (centered overlay, no layout shift) and list every group item at the hovered hour: LINE values, DIRECTION (arrow + degrees + compass), VALUE, and PRECIPITATION_TYPE. Below Tailwind sm (640px) the graph windows the X domain to one calendar day, labels hours on the axis, wraps hover values under the title, and shows a day pager (or uses the Builder pager when stacked). Swipe the plot to change day. At sm and up it keeps the full domain. Optional thresholds add dashed Y-lines for in-scale LINE elements, a status color strip above the date labels, a Thresholds legend, and Watch / Caution / Critical on hover. LINE series read color, strokeWidth, dash, opacity, and curve from the series; Y-axis domain comes from config.yAxis or defaults to [0, auto]. config.domain is the X-axis time range.

import { TimeseriesGraph } from '@infoplaza/platform/timeseries-charts'

Required props

PropTypeDefaultDescription
configTimeseriesChartGraphConfig—Aligned LINE rows plus DIRECTION / VALUE / PRECIPITATION_TYPE overlays.

Optional props

PropTypeDefaultDescription
idstring—Key prefix for series.
titlestring—Chart title (group name).
titleExtrastring—Secondary title, e.g. latest.
subtitlestring—Shown under the title (e.g. formatted runtime).
localestring—Date formatting locale.
timezonestring | null—Date axis timezone.
plotHeightnumber320Plot-area height in pixels. The strip band (direction/value/precipitation-type rows) and axis chrome are added on top.
hourInterval1 | 3 | 66Vertical unlabeled hour grid lines. Day-boundary ticks stay on the X axis. For 3h and 6h, strip overlays show the latest point in each bucket, centered; 1h keeps hourly strip points. LINE series are unchanged.
thresholdsTimeseriesChartThresholds | null—Optional. Only conditions and ignored_hours are read. Per-chart Y-lines and status strip for LINE elements plotted on this graph.
fixedWidthnumber—Optional fixed pixel width.
fixedHeightnumber—Optional fixed pixel height. Overrides plotHeight plus chrome.