Guides
Math channels
Formula channels that behave like columns, an editor preview, and persistence in your backend.
What a channel is
A math channel is a named formula over existing columns. It appears in state.numericColumns and can be plotted by any chart. It is evaluated per dataset, so window functions never cross a dataset boundary.
| Family | Functions |
|---|---|
| Arithmetic | + − × ÷, abs, sqrt, exp, log, trigonometry, min, max, round, mod |
| Conditional | if, nullif, clamp |
| Window | derivative, integral, movavg, lag, lead |
| Filters | Butterworth lowpass and highpass |
FUNCTION_REFERENCE lists every function with its signature and description, ready for an editor’s help panel.
Create and edit
const ch = engine.mathChannels.create({ name: 'speed_kmh', formula: 'speed * 3.6', units: 'km/h' })
engine.mathChannels.update(ch.id, { formula: 'lowpass(speed, 5) * 3.6' })
engine.mathChannels.update(ch.id, { enabled: false })
engine.mathChannels.remove(ch.id)
await engine.mathChannels.importMany(channelsFromYourApi)
const { channels, errors } = await engine.mathChannels.importFile(file) // a JSON export
const blob = engine.mathChannels.exportBlob()Editor preview
import { newMathChannel, parseFormula } from '@kymoscope/sdk'
const parsed = parseFormula(input.value)
if (!parsed.ok) showError(parsed.message)
const draft = newMathChannel({ name: 'draft', formula: input.value })
const result = engine.mathChannels.preview(draft) // null when nothing is plotted
// result.status: 'ok' | 'missing-inputs' | 'parse-error' | 'runtime-error' | 'disabled' | 'references-channel'
// result.values: (number | null)[], result.missingCols, result.messageStoring channels
Without a store, channels live in memory for the session. With a MathChannelStoreAdapter, the engine applies each change locally and calls your store; you push the authoritative list back with sync whenever it changes.
const engine = createEngine({
mathChannels: {
create: (channel) => api.createChannel(channel),
update: (id, patch) => api.updateChannel(id, patch),
remove: (id) => api.deleteChannel(id),
importMany: (channels) => api.importChannels(channels),
},
})
engine.mathChannels.sync(await api.listChannels())
api.onChannelsChanged((list) => engine.mathChannels.sync(list))A rejected create, update or remove is reported as an error event (the engine call itself has already returned). importMany and importFile await the store and reject if it does.