Compose Media Player audio module is a lightweight audio-only player for Compose Multiplatform. It supports Android, iOS, JVM Desktop (macOS/Windows/Linux), and Web (Wasm).
For the video module, see README_VIDEO.MD.
- Features
- Installation
- Usage
- State and Controls
- Error Handling
- Platform Notes
- Audio Format Support
- Sample
- Multiplatform Support: Works on Android, iOS, JVM Desktop, and Web (Wasm).
- Local and Remote Playback: Play files from disk or stream from HTTP(S) URLs.
- Simple Controls: Play, pause, stop, seek, and volume.
- Live State Helper:
rememberAudioPlayerLiveState()exposes state, position, duration, and volume. - Error Callbacks: Hook into playback errors via
setOnErrorListener.
Add the audio module dependency in your build.gradle.kts:
dependencies {
implementation("io.github.kdroidfilter:composemediaplayer-audio:<version>")
}@Composable
fun AudioSample() {
val audioState = rememberAudioPlayerLiveState()
val url = "https://example.com/stream.mp3"
Row {
Button(onClick = { audioState.player.play(url) }) { Text("Play") }
Button(onClick = { audioState.player.pause() }) { Text("Pause") }
Button(onClick = { audioState.player.stop() }) { Text("Stop") }
}
}For local files, pass a file path or file URI:
val player = AudioPlayer()
player.play("/path/to/file.mp3")
// or: player.play("file:///path/to/file.mp3")If you are using FileKit, you can pass PlatformFile.getUri():
val file = FileKit.openFilePicker(type = FileKitType.File("mp3", "wav"))
file?.let { audioState.player.play(it.getUri()) }currentPosition()andcurrentDuration()return milliseconds. Duration may be null for live streams.currentPlayerState()returnsAudioPlayerState.PLAYING,PAUSED,BUFFERING, orIDLE.seekTo(timeMs)works only when the source is seekable.setVolume(volume)expects a value between 0.0 and 1.0.setRate(rate)is supported on Android/iOS/Web; on JVM it is currently a no-op.
audioState.player.setOnErrorListener(object : ErrorListener {
override fun onError(message: String?) {
println("Audio error: ${message ?: "Unknown error"}")
}
})- Android uses Media3, iOS uses AVFoundation, Web uses HTML5 Audio, JVM uses Rodio.
- Seeking and duration availability depend on the source (stream vs file).
Audio format support depends on OS/browser decoders. The tables below show typical baseline support per backend. Legend: Yes supported, No not supported, Partial device/browser-dependent.
| Format | Local | HTTP | HLS | Seeking |
|---|---|---|---|---|
| MP3 | Yes | Yes | Yes | Yes |
| AAC | Yes | Yes | Yes | Yes |
| FLAC | Yes | Yes | No | Yes |
| OGG | Yes | Yes | No | Yes |
| WAV | Yes | Yes | No | Yes |
| Format | Local | HTTP | HLS | Seeking |
|---|---|---|---|---|
| MP3 | Yes | Yes | Yes | Yes |
| AAC | Yes | Yes | Yes | Yes |
| FLAC | Yes | Yes | No | Yes |
| OGG | Yes | Yes | No | Yes |
| WAV | Yes | Yes | No | Yes |
| Format | Local | HTTP | HLS | Seeking |
|---|---|---|---|---|
| MP3 | Yes | Yes | Partial | Yes |
| AAC | Yes | Yes | Yes | Yes |
| FLAC | Partial | Partial | No | Partial |
| OGG | No | No | No | No |
| WAV | Yes | Yes | No | Yes |
| Format | Local | HTTP | HLS | Seeking |
|---|---|---|---|---|
| MP3 | Yes | Yes | Partial | Yes |
| AAC | Yes | Yes | Partial | Yes |
| FLAC | Partial | Partial | No | Partial |
| OGG | Partial | Partial | No | Partial |
| WAV | Yes | Yes | No | Yes |
Notes:
- Web "Local" assumes a
blob:orfile:URL from a file picker; browser security rules apply. - Web HLS is supported only in Safari unless you provide a custom HLS loader.
- iOS FLAC support varies by OS version and device.
See sample/composeApp/src/commonMain/kotlin/sample/app/AudioPlayerScreen.kt for a complete example.