# How to build a music player in Bubble

- Tool: Bubble
- Difficulty: Beginner
- Time required: 25-30 min
- Compatibility: All Bubble plans
- Last updated: March 2026

## TL;DR

Creating a music player in Bubble involves building a now-playing display with album art and track info, playback controls using an HTML5 audio element, a playlist sidebar with queue management, and shuffle and repeat modes using custom states. This tutorial covers the full standalone music player UI without requiring external services beyond audio file hosting.

## Overview: Creating a Music Player in Bubble

This tutorial shows you how to build a standalone music player interface in Bubble. You will create a now-playing display, control playback via an HTML5 audio element, build a playlist sidebar, and add shuffle and repeat functionality.

## Before you start

- A Bubble app on any plan
- Audio files hosted on a public URL (Bubble file storage, S3, or similar)
- Basic familiarity with HTML elements in Bubble
- Understanding of Bubble custom states

## Step-by-step guide

### 1. Create the Song and Playlist Data Types

In the Data tab, create a Song Data Type with fields: title (text), artist (text), album (text), album_art (image), audio_url (text — URL to the audio file), duration_seconds (number). Create a Playlist Data Type with fields: name (text), songs (list of Songs), creator (User). Upload audio files to Bubble's file manager or host them externally and store the URLs.

**Expected result:** Your database stores song metadata and audio file URLs organized into playlists.

### 2. Build the now-playing display

Create a fixed-position Group at the bottom of your page (like Spotify's player bar). Inside, add: an Image element for album art bound to a custom state 'current_song' (type: Song), Text elements for the song title and artist name, and a progress bar (a narrow Group with a dynamic width representing playback progress). The progress bar width is calculated as: (current_time / duration_seconds) * 100 percent.

**Expected result:** A player bar at the bottom of the page shows the currently playing song's artwork, title, and artist.

### 3. Embed the HTML5 audio element and control playback

Add an HTML element to your page with an <audio> tag. Use JavaScript to control playback. When the current_song custom state changes, update the audio source URL. Add Play/Pause, Previous, and Next icon buttons. Each button triggers a JavaScript action via a Bubble plugin (like Toolbox) or by updating a hidden input that the HTML element watches. Play/Pause toggles the audio playback. Previous and Next change the current_song state to the adjacent song in the playlist.

```
<audio id="player" preload="auto">
  <source src="DYNAMIC_AUDIO_URL" type="audio/mpeg">
</audio>
<script>
  var player = document.getElementById('player');
  // Control via Bubble custom states or hidden inputs
</script>
```

**Expected result:** Audio playback is controlled through buttons that interact with the HTML5 audio element.

### 4. Create the playlist sidebar with queue management

Add a sidebar Group containing a Repeating Group of Songs from the current playlist. Each cell shows the song title, artist, duration, and a play button. Clicking a song sets the current_song custom state and starts playback. Highlight the currently playing song with a Conditional: when Current Cell's Song = page's current_song, change the background color. Add drag-to-reorder functionality (using a drag-and-drop plugin) or Up/Down arrows to let users rearrange the queue.

**Expected result:** A playlist sidebar shows all songs with the current track highlighted and the ability to jump to any song.

### 5. Implement shuffle and repeat modes

Add custom states: 'is_shuffle' (yes/no) and 'repeat_mode' (text — 'none', 'all', 'one'). Add toggle buttons for each. When the current song ends (detected via the audio element's 'ended' event), check the states: if repeat_mode is 'one', replay the same song. If is_shuffle is yes, pick a random song from the playlist. If repeat_mode is 'all' and the current song is the last, go back to the first. Otherwise, play the next song in order. If repeat_mode is 'none' and it is the last song, stop playback.

**Expected result:** Shuffle randomizes the next song and repeat modes control what happens when a song ends.

## Complete code example

File: `Workflow summary`

```text
MUSIC PLAYER ARCHITECTURE
==========================

DATA TYPES:
  Song: title, artist, album, album_art, audio_url, duration_seconds
  Playlist: name, songs (list of Songs), creator

PAGE CUSTOM STATES:
  current_song: Song
  current_playlist: Playlist
  is_playing: yes/no
  is_shuffle: yes/no
  repeat_mode: text (none/all/one)
  current_time: number (seconds)

PLAYER BAR (fixed bottom):
  Album art | Song title | Artist | Progress bar | Controls
  Controls: Previous | Play/Pause | Next | Shuffle | Repeat

PLAYBACK LOGIC:
  Play: Set is_playing = yes, trigger audio play
  Pause: Set is_playing = no, trigger audio pause
  Next: Calculate next song based on shuffle/repeat mode
  Previous: Go to previous song or restart current if > 3 sec in

SONG END LOGIC:
  repeat_mode = 'one': replay current song
  is_shuffle = yes: random song from playlist
  repeat_mode = 'all' + last song: go to first
  repeat_mode = 'none' + last song: stop
  Default: next song in order
```

## Common mistakes

- **Hosting large audio files directly in Bubble's file storage** — Bubble's file storage is not optimized for audio streaming. Large files may buffer slowly and consume storage limits quickly Fix: Host audio files on a CDN or dedicated audio hosting service and store only the URL in Bubble
- **Not providing visual feedback for the current playback state** — Without a progress bar and play/pause state indicator, users cannot tell if music is playing or how far along the track is Fix: Update the progress bar width and play/pause button icon based on the current playback state
- **Losing playback state when navigating between pages** — In a multi-page app, navigating to another page reloads the audio element and stops playback Fix: Use a single-page architecture with custom state navigation, or place the audio player in a reusable element that persists across pages

## Best practices

- Host audio files on a CDN for fast streaming and reduced Bubble storage usage
- Use a fixed-position player bar that stays visible while scrolling
- Show a progress bar and current time for clear playback feedback
- Implement shuffle using random selection to avoid predictable patterns
- Highlight the currently playing song in the playlist view
- Handle the audio ended event to automatically advance to the next track

## Frequently asked questions

### Can I play audio in Bubble without an HTML element?

Bubble has a limited built-in audio element, but for full control over playback (seek, progress tracking, events), an HTML5 audio element gives you much more flexibility.

### Does the music player work on mobile?

Yes, but mobile browsers may require user interaction before audio can play. Add a visible play button that the user must tap to start playback.

### Can I stream audio from Spotify or Apple Music?

Streaming copyrighted music requires licensing agreements. You can display metadata via their APIs but cannot stream their audio content. Use only audio files you have rights to.

### How do I add a volume control?

Add a range input (slider) in an HTML element. Use JavaScript to set the audio element's volume property (0.0 to 1.0) based on the slider value.

### Can RapidDev help build a music player in Bubble?

Yes. RapidDev can build custom audio players with streaming, playlist management, shuffle/repeat modes, and mobile-optimized playback for your Bubble app.

---

Source: https://www.rapidevelopers.com/bubble-tutorial/create-a-music-player-in-bubble
© RapidDev — https://www.rapidevelopers.com/bubble-tutorial/create-a-music-player-in-bubble
