Audio Headless
Headless components are the code-only domain objects behind the elements:
engines, runners, and renderers imported from
@webmusic/audio/<capability>/headless. They never touch the DOM.
| Capability | Contents |
|---|---|
| Play | AudioPlayer, clip/queue/mix backends, AudioRecorder and engines. |
| Analyze | Cached analysis sessions, a main-thread realtime sampler and a streaming transient detector; worker clients use their own entry. |
| View | Timeline/view models and pure projection helpers; renderers use the separate /render entry. |
Roles and ownership
Section titled “Roles and ownership”A player may drive clip time, a playlist owns queue selection, a timeline projects another object’s seconds, and a pure helper returns data without running anything. Do not infer a shared session clock, emitter or disposal method from the Headless label. Each owning page states its contract and related public types.
The export tables below are a manual export-ownership map, checked against the public barrel. The Headless documentation gate searches recognized value names on this page and across the capability’s pages; it does not prove that types, signatures, defaults, unique explanation ownership or lifecycle coverage are complete. Those require source review. Browser renderers belong to API / View, and application composition can use UI Kit without changing domain ownership.
@webmusic/audio/play/headless is everything that makes or captures sound
without drawing any of it: the transports, the two engines beneath them, the
recorder and the effect builders.
No DOM, no styles. Import from @webmusic/audio/play/headless; the elements
that wrap these objects are under
Web Components › Play, and the loaders and decoders
that produce a clip in the first place are on
@webmusic/audio/play.
| Export | Kind | Page |
|---|---|---|
AudioPlayer · createAudioPlayer |
class · factory | AudioPlayer |
AudioClipPlayer · createAudioClipPlayer |
class · factory | AudioClipPlayer |
AudioPlaylist · createAudioPlaylist |
class · factory | AudioPlaylist |
AudioMixer · createAudioMixer |
class · factory | AudioMixer |
AudioRecorder · createAudioRecorder |
class · factory | AudioRecorder |
BufferEngine · MediaEngine |
classes | Engines |
gain · filter · delay · compressor · customEffect · chainEffects · insertEffect |
effect builders and graph helpers | Effects |
Type ownership
| Exported types | Explanation owner |
|---|---|
AudioPlayerOptions, AudioPlayerTransport, AudioPlayerEvents |
AudioPlayer |
AudioClipPlayerOptions, AudioClipPlayerEvents, AudioScratchSession, PlayerTimeUpdate, PlayerEngineKind, PlayerLike |
AudioClipPlayer |
AudioPlaylistOptions, AudioPlaylistEvents, AudioPlaylistEntry, AudioPlaylistEntryStatus |
AudioPlaylist |
AudioMixerOptions, AudioMixerEvents, MixerMemberInit, AudioMixerSnapshot, AudioMixerMemberSnapshot |
AudioMixer |
AudioRecorderOptions, AudioRecorderEvents |
AudioRecorder |
PlaybackEngine, BufferEngineOptions, MediaEngineOptions, MediaPlaybackAdapter, MediaPlaybackAdapterFactory |
Engines and metering |
Effect, EffectNodes, GainOptions, FilterOptions, DelayOptions, CompressorOptions |
Effect |
The source barrel is packages/audio/src/play/headless/index.ts. Stateful
transports own commands and lifetimes; lazy effect recipes and PCM helpers do not
acquire an event emitter or dispose method merely by sharing this entry.
One clip, N at once, N in sequence
Section titled “One clip, N at once, N in sequence”The three transports are the three cardinalities, and choosing between them is usually the first decision:
| You have | Reach for |
|---|---|
| one clip | AudioClipPlayer |
| several clips whose start/seek commands should be coordinated | AudioMixer |
| several clips that should play in order | AudioPlaylist |
Contexts can be created or explicitly borrowed. Created mixer/playlist members reuse their owner’s reference context, but independent players retain their own clocks. Borrowed arbitrary PlayerLike objects require compatible time and resource contracts; there is no fixed browser context-count promise.
Analyze
Section titled “Analyze”@webmusic/audio/analyze/headless is the stateful half of audio analysis.
The capability root measures a clip once and returns the numbers; these two
objects keep something between calls — a cache of frames that survives an
edit, a poll loop over a live signal, or state across successive attack observations.
No DOM, no styles, no drawing: analysis produces facts, and
audio/view projects signals. Import from
@webmusic/audio/analyze/headless.
| Export | Kind | Page |
|---|---|---|
createAudioAnalysisSession |
session | createAudioAnalysisSession |
createRealtimeAnalyzer |
analyzer | createRealtimeAnalyzer |
createTransientDetector |
detector | Live transient cues |
Type ownership
| Exported types | Explanation owner |
|---|---|
AudioAnalysisSession, AudioAnalysisSessionOptions |
createAudioAnalysisSession |
RealtimeAnalyzer, RealtimeAnalyzerOptions, RealtimeFrame, RealtimeSource |
createRealtimeAnalyzer |
TransientDetector, TransientInput, TransientObservation |
Live transient cues |
The source barrel is packages/audio/src/analyze/headless/index.ts. Algorithm
option/result types referenced by a session are owned by the Analyze API.
The session owns cached results without a clock or event emitter; the realtime
analyzer owns an interval and has callback delivery plus stop(). The transient
detector retains preceding FFT/RMS evidence and provides reset(), but owns no
timer or graph. None exposes a generic dispose method.
The session analyses a decoded clip you already hold, and re-analyses it
with task-dependent reuse after an edit. The realtime analyzer never sees a clip: it borrows an
AnalyserNode and reports what is passing through it right now. Reach for the
session when you have the recording and the analyzer when you have the signal.
Pair the realtime analyzer’s optional byte spectrum with the detector for
approximate live attack cues, not a beat grid or sample-accurate onset track.
@webmusic/audio/view/headless is the geometry half of drawing audio:
where the viewport is, which columns fall inside it, what a click at x
means. None of it paints. The canvas renderers that do are /render adapters
on @webmusic/audio/view, by the same rule that keeps
every imperative surface out of a /headless entry.
Import from @webmusic/audio/view/headless. The models retain input data
and geometry; a live controller borrows an analyser. A player binding owns
subscriptions and returns unsubscribe(). None draws or creates a playback clock.
| Export | Kind | Page |
|---|---|---|
AudioMeterController · createAudioMeterController · calculateLevelMeter · calculateSpectrumBars |
controller · factory · helpers | Metering |
AudioTimeline · createAudioTimeline |
class · factory | AudioTimeline |
bindPlayerToAudioTimeline |
binding | AudioTimeline |
WaveformViewModel · createWaveformViewModel · fitWaveformColumns |
class · factory · helper | View models |
SpectrogramViewModel · createSpectrogramViewModel |
class · factory | View models |
computeClipPeaks · peaksDuration |
functions | Peaks |
LiveViewController · createLiveViewController · LiveScrollBuffer |
classes · factory | Live projection |
frequencyColumn · timeDomainColumn |
column builders | Live projection |
Type ownership
| Exported types | Explanation owner |
|---|---|
AudioMeterControllerOptions, AudioMeterConfiguration, AudioMeterLevelFrame, LevelMeterFrame, LevelMeterOptions, SpectrumBarsOptions |
Metering |
AudioTimelineOptions, AudioTimelineSnapshot, AudioTimelineHit, AudioTimelineGeometryUpdate, AudioTimelineSubscriber, AudioTimelineBinding, BindAudioTimelineOptions, PlayheadTarget |
AudioTimeline |
WaveformViewModelOptions, WaveformColumn, WaveformChannelPeak, SpectrogramViewModelOptions, SpectrogramFrameView |
View models |
LiveColumn, LiveProjectionType, LiveScrollOptions, LiveViewControllerOptions |
Live projection |
The source barrel is packages/audio/src/view/headless/index.ts. AudioPeaks and
Region input types belong to the Audio core API; SpectrogramData
belongs to the View API. Pure functions such as computeClipPeaks
and fitWaveformColumns have no lifecycle/events. Model query results do not imply
an internal refresh timer.
AudioTimeline and the view models describe a clip you already have;
LiveViewController describes a signal arriving now. The split is the same
one the analyze capability makes, for the same reason: a clip has a length and
a live signal does not.