Media
@knitui/media wraps expo-audio and expo-video in one controller model, with
themed chrome that matches the rest of the kit.
npx expo install @knitui/media expo-audio expo-videoimport { MediaProvider, AudioPlayer } from "@knitui/media";
<MediaProvider>
<AudioPlayer source={{ uri }} />
</MediaProvider>;What is in it
Player, controls, seek bar, time display.
Video surface with the same controller and chrome.
Queue, next/previous, repeat, shuffle.
Recording with level metering.
Real-time level display from the mic.
Spectrum visualisation, drawn with Skia.
One engine, one player at a time
There is exactly one real player element per medium. That is what makes lock-screen controls, background audio and seamless playlist transitions work — and it means two visible players contend: only the active one plays. If you need a list of tracks, drive one player from the list rather than mounting one per row.
State without re-render storms
Playback state changes many times a second. The store is selector-based and
per-field, so a component that reads currentTime re-renders on time updates while
one that reads isPlaying does not:
import { useMediaSelector } from "@knitui/media";
const isPlaying = useMediaSelector((state) => state.isPlaying);Granular events (play, pause, ended, trackChange, …) are derived centrally
from state transitions rather than emitted by each adapter, so web and native fire
the same events at the same moments.
DSP
@knitui/media/dsp is a pure-TypeScript FFT and spectrum analyser — no native
module, no worklet:
import { useAudioSpectrum } from "@knitui/media";
const { bands } = useAudioSpectrum({ bandCount: 32 });One FFT per frame, fed from a ring buffer. Pair it with
@knitui/graphics's AudioVisualizer for the drawing.