AudioDN Components
HTML custom elements for the Audio Delivery Network: a player, an uploader, and a standalone waveform. Built with Lit and shipped as tree-shakable ES modules.
Installation
NPM
npm install @audiodn/components
Yarn
yarn add @audiodn/components
CDN
Every component has its own ES-module entry you can load directly — request only
the one(s) you need. Each entry pulls in its shared chunks automatically (unpkg
and jsDelivr resolve the relative imports for you), so a single <script> tag is
all that's required.
<script type="module" src="https://unpkg.com/@audiodn/components@latest/dist/player.js"></script>
<audiodn-player
api-key="YOUR_CLIENT_SIDE_PLAYER_KEY"
scope="collection"
id="COLLECTION_ID"
></audiodn-player>
<script type="module" src="https://unpkg.com/@audiodn/components@latest/dist/uploader.js"></script>
<audiodn-uploader
api-key="YOUR_CLIENT_SIDE_UPLOAD_KEY"
collection-id="COLLECTION_ID"
></audiodn-uploader>
<script type="module" src="https://unpkg.com/@audiodn/components@latest/dist/waveform.js"></script>
<audiodn-waveform variant="reflection"></audiodn-waveform>
Prefer jsDelivr? Swap the host, e.g.
https://cdn.jsdelivr.net/npm/@audiodn/components@latest/dist/player.js.
Usage
Import only the component you need via its subpath. Each subpath is a separate
entry point, so a bundler will only pull in the code for what you actually use.
import '@audiodn/components/player' | <audiodn-player> |
import '@audiodn/components/uploader' | <audiodn-uploader> |
import '@audiodn/components/waveform' | <audiodn-waveform> |
import '@audiodn/components' | all three |
Once imported, drop the element into your HTML. All configuration is done through
HTML attributes (documented per component below). Attribute values are strings in
markup; number/boolean attributes are coerced automatically.
<audiodn-player>
An audio player that opens a play session against the AudioDN API and renders
cover art, a tracklist, transport controls, and a waveform progress bar.
import '@audiodn/components/player'
<audiodn-player
api-key="YOUR_CLIENT_SIDE_PLAYER_KEY"
scope="collection"
id="COLLECTION_ID"
variants="hq,lq"
size="large"
></audiodn-player>
You must provide either api-key (the player creates the session) or
play-session-id (you created the session server-side).
Attributes
api-key | string | — | Client-side player API key. The player creates a play session for scope/id. Provide this or play-session-id. |
play-session-id | string | — | Use an existing play session instead of creating one with api-key. |
scope | string | "" | The kind of resource id refers to. Values: track, collection. |
id | string | "" | ID of the track or collection to play (must match scope). |
variants | string | "" | Comma-separated variant indexes to request, in priority order — the first is selected by default. e.g. "hq,lq". |
size | string | large | Layout preset. Values: small, regular, large. |
locale | string | en | UI language. Values: en, fr, es, de. |
volume | number | 0.7 | Initial volume, 0–1. Persisted to sessionStorage after the user changes it. |
session-ttl | number | — | Requested play-session lifetime, in seconds. |
waveform-variant | string | vertical | Waveform style. Values: vertical, reflection, wavy. |
waveform-height | number | 120 | Waveform height, in px. |
waveform-line-width | number | 2 | Waveform bar width, in px. |
waveform-line-color | string | #888888 | Waveform color (any CSS color). Overridden by the track's accent color when available. |
waveform-gap | number | 3 | Gap between waveform bars, in px. |
waveform-scale-strength | number | 0.4 | Waveform contrast/normalization, 0–1. |
Events
All events bubble and are composed (cross shadow DOM).
adn-session-refreshed | { playSessionId } | The session was auto-refreshed (only when api-key is set). |
adn-session-expired | { playSessionId } | The session expired and could not be refreshed (no api-key). |
<audiodn-uploader>
A drag-and-drop uploader that opens an upload session and PUTs audio files
directly to storage with per-file and overall progress.
import '@audiodn/components/uploader'
<audiodn-uploader
api-key="YOUR_CLIENT_SIDE_UPLOAD_KEY"
collection-id="COLLECTION_ID"
accent-color="#ff00ff"
></audiodn-uploader>
You must provide either api-key (the uploader creates the session) or
upload-session-id (you created the session server-side). Only audio/* files
are accepted; multiple files are allowed.
Attributes
api-key | string | — | Client-side upload API key. The uploader creates an upload session. Provide this or upload-session-id. |
upload-session-id | string | — | Use an existing upload session instead of creating one with api-key. |
collection-id | string | — | Collection to upload tracks into (used with api-key). |
accent-color | string | #fe008a | Accent color for the UI. Must be a 6-digit hex color, e.g. #ff00ff. Falls back to the collection's color when not set. |
locale | string | en | UI language. Values: en, fr, es, de. |
disabled | boolean | false | Disables the drop zone and file picker. Presence of the attribute = true. |
Events
All events bubble and are composed.
files-selected | { files } | Audio files are chosen or dropped. |
file-uploaded | { file, trackId } | A file finishes uploading. |
session-error | { error } | The upload session could not be created or fetched. |
adn-session-refreshed | { uploadSessionId } | The session was auto-refreshed (only when api-key is set). |
adn-session-expired | { uploadSessionId } | The session expired and could not be refreshed. |
<audiodn-waveform>
A standalone canvas waveform with hover-scrub, a playhead, and click/tap to
seek. The player embeds this internally, but you can use it on its own by
feeding it amplitude levels.
import '@audiodn/components/waveform'
<audiodn-waveform variant="reflection" height="120"></audiodn-waveform>
<script type="module">
const wf = document.querySelector('audiodn-waveform')
wf.levels = [0.1, 0.4, 0.8, 0.6, ...]
wf.duration = 214
wf.progress = 0.35
</script>
levels is an array, so set it as a JS property (el.levels = [...])
rather than an HTML attribute.
Attributes / properties
levels (property) | number[] | [] | Amplitude samples to draw. Set via JS property. |
variant | string | vertical | Render style. Values: vertical, reflection, wavy. |
height | number | 120 | Canvas height, in px. |
line-color | string | #888888 | Bar color (any CSS color). |
line-width | number | 2 | Bar width, in px. |
gap | number | 3 | Gap between bars, in px. |
scale-strength | number | 0.4 | Contrast/normalization, 0–1. |
progress | number | 0 | Playback position, 0–1. Drives the playhead. |
duration | number | 0 | Track length in seconds. Enables the hover-time tooltip. |
min | number | 0 | Start of the playable/preview region, 0–1. |
max | number | 1 | End of the playable/preview region, 0–1. |
reflection-angle | number | 45 | reflection variant: max lean in degrees (at 0%/100% progress). |
reflection-size | number | 0.25 | reflection variant: reflection height as a fraction of the bar height. |
reflection-opacity | number | 0.55 | reflection variant: reflection opacity at the baseline. |
highlight-from | number | 0 | Left offset (px) of the progress highlight mask. |
highlight-width | number | 1 | Highlight width as a fraction of the container. |
locale | string | en | Language for the ARIA label. Values: en, fr, es, de. |
Events
adni-seek | { percent } | The user clicks or taps to seek. percent is 0–1. |
Theming
Both the player and uploader are themable via --adn-* CSS custom properties
set on the element (or an ancestor). Common ones:
audiodn-player,
audiodn-uploader {
--adn-bg: #0b0b0b;
--adn-color-font: #fff;
--adn-color-font-muted: #bbb;
--adn-color-accent: #c13c5b;
--adn-radius: 8px;
--adn-padding: 0;
--adn-box-shadow: none;
}
The uploader's accent can also be set with the accent-color attribute (above).
Tree-shaking & bundling
- The package publishes one ES entry per component (
player, uploader,
waveform) plus a combined index. Prefer the subpath imports above so
your bundler only includes the components you use — importing
@audiodn/components/uploader will not pull in the player or waveform code.
- Shared code (Lit, internal utilities, sub-components) is emitted once as
shared chunks under
dist/shared/ and referenced by the entries, rather than
being duplicated into each file.
- The player auto-registers the waveform (used for the waveform progress bar);
it resolves the shared waveform chunk rather than inlining a private copy.
lit is bundled into the package (in its own shared chunk), so no additional
install is required for CDN/<script type="module"> usage.
TypeScript Support
This package includes TypeScript definitions. If you're using TypeScript, you'll get full type safety and IntelliSense support.
Full-page example (CDN)
<!DOCTYPE html>
<html>
<head>
<script type="module" src="https://unpkg.com/@audiodn/components@latest/dist/player.js"></script>
</head>
<body>
<audiodn-player
api-key="YOUR_CLIENT_SIDE_PLAYER_KEY"
scope="collection"
id="COLLECTION_ID"
variants="hq,lq"
size="large"
></audiodn-player>
<script type="module">
document.querySelector('audiodn-player')
.addEventListener('adn-session-expired', () => location.reload())
</script>
</body>
</html>
CDN note: the entry files load a few shared chunks from dist/shared/. unpkg
and jsDelivr resolve these relative imports automatically, so a single
<script type="module"> tag is all you need.
Getting started with development
-
Clone this repo
with Git
git clone https://github.com/audiodn/audiodn-components.git
with GitHub CLI
gh repo clone audiodn/audiodn-components
-
Install Dependencies & Tooling
with NPM
npm setup
with Make
make setup
-
Start development server
with NPM
npm run dev
with Make
make dev
Linting & Formatting
-
Run linter
with NPM
npm run lint
with Make
make lint
-
Autofix formatting
with NPM
npm run fmt
with Make
make fmt
Build Preview
Build Release
-
Run build command
with NPM
npm run build
with Make
make build
Check for dependency updates
-
Run update command
with NPM
npm run update
with Make
make update
## Releasing a new version
Releases are published **manually** to npm from a maintainer's machine. There is
no CI publish step (npm's read/write granular tokens expire every 90 days, which
makes automation impractical for an infrequently released package).
You need to be logged in as an npm user who is a member of the `@audiodn` org
with publish rights:
```bash
npm login # one-time, per machine
npm whoami # confirm you're logged in
Then, for each release:
-
Land your code change on main (commit / merge as usual).
-
Bump the version. This updates package.json and creates a git tag:
npm version patch
npm version minor
npm version major
-
Publish. prepublishOnly automatically runs lint + tests + build first,
so a broken build or failing test aborts the publish:
npm publish
access: public is already set in publishConfig, so no extra flag is
needed. To preview exactly what will be shipped without publishing, run
npm publish --dry-run (only dist/, README.md, and LICENSE are
included).
-
Push the commit and tag so GitHub matches npm:
git push --follow-tags
-
(Optional) Cut a GitHub release for release notes:
gh release create v0.1.1 --generate-notes
That's the whole flow: change → npm version → npm publish → git push --follow-tags.
License
MIT License - see LICENSE file for details.