The HTML loop attribute
The HTML loop attribute restarts audio or video from the beginning each time it ends. It is a boolean attribute of <audio> and <video>, and while it is set the ended event does not fire.
Overview
The loop attribute sends a media element back to the beginning whenever playback reaches the end. It is a boolean attribute of <video> and <audio>, and the loop property in JavaScript reflects it, so video.loop = true has the same effect as writing the attribute.
Looping changes which events you get. A looping element seeks back to the start instead of ending, so the ended event does not fire and the ended property stays false. Each wrap-around is a seek, which means seeking and seeked events fire on every repeat.
Counting seeked events is one way to track how many times a looping clip has played. The attribute has no count of its own, so a clip that should play three times needs a script that sets loop to false during the third pass.
The attribute does not start playback by itself. Pair it with autoplay and muted for a background video, or let the viewer start it through controls. Turning the property off mid-play lets the current pass finish, and the next time the media reaches its end the ended event fires as usual.
Syntax
<video src="waves.mp4" autoplay muted loop playsinline></video>
Values
| Value |
|---|
| A boolean attribute: present or absent. |
Example
<video id="bg" src="https://codeshack.io/web/example.mp4" width="300" autoplay muted loop playsinline controls></video>
<p>Repeats: <output id="loops">0</output>, ended events: <output id="ends">0</output></p>
<script>
const bg = document.getElementById('bg');
let loops = 0;
let ends = 0;
bg.addEventListener('seeked', () => {
if (bg.currentTime < 1) document.getElementById('loops').textContent = ++loops;
});
bg.addEventListener('ended', () => {
document.getElementById('ends').textContent = ++ends;
});
</script>
Best practices
- Keep looping background videos short and silent, and add muted and playsinline so they can autoplay.
- Always offer a way to pause looping media, such as the native controls or your own pause button.
- Listen for
seekedortimeupdateinstead ofendedwhen you need to react to each repeat. - Set the
loopproperty to false from script when a clip should finish its current pass and stop.
Accessibility
Looping media that starts by itself can fail two WCAG 2.2 criteria. Audio that plays automatically for more than 3 seconds needs a pause, stop or volume control under 1.4.2.
Moving video that starts on its own, lasts more than five seconds and sits beside other content needs a way to pause, stop or hide it under 2.2.2. A clip that keeps looping eventually passes both time limits, however short the file is.