Signatur
Beschreibung
Die Schnittstelle BufferedChangeEvent gehört zu den Media Source Extensions (MSE), genauer zum Teil Managed Media Source. Ein BufferedChangeEvent wird im Ereignis bufferedchange auf einem ManagedSourceBuffer ausgelöst, sobald sich dessen gepufferte Zeitbereiche (buffered) ändern.
Das Besondere an ManagedMediaSource: Der Browser darf gepufferte Mediendaten selbst wieder entfernen, etwa wenn der Speicher knapp wird oder das Gerät Energie sparen muss. Über removedRanges erfährt eine Streaming-Anwendung, welche Bereiche verloren gegangen sind und bei Bedarf neu geladen werden müssen. addedRanges zeigt dagegen, welche Bereiche nach einem appendBuffer() neu hinzugekommen sind.
Die Schnittstelle erbt von Event und bietet zusätzlich zwei schreibgeschützte Eigenschaften:
addedRanges(TimeRanges): Zeitbereiche, die seit dem letzten Ereignis neu gepuffert wurden.removedRanges(TimeRanges): Zeitbereiche, die seit dem letzten Ereignis entfernt wurden, egal ob durchremove()oder durch den Browser selbst.
Normalerweise erzeugt man solche Objekte nicht selbst. Man bekommt sie als Argument im Listener. Der Konstruktor new BufferedChangeEvent(type, options) ist trotzdem vorhanden, zum Beispiel für Tests.
Parameter
| Name | Typ | Default | Beschreibung |
|---|---|---|---|
| $type Pflicht | string | Name des Ereignisses, normalerweise "bufferedchange" (Groß- und Kleinschreibung zählt). |
|
| $options | object | {} | Optionales Objekt. Es kann alle Optionen von Event enthalten (bubbles, cancelable, composed) und zusätzlich: |
| $options.addedRanges | TimeRanges | leeres TimeRanges | Zeitbereiche, die als hinzugefügt gemeldet werden. |
| $options.removedRanges | TimeRanges | leeres TimeRanges | Zeitbereiche, die als entfernt gemeldet werden. |
Rückgabewert
BufferedChangeEvent-Objekt, wenn es über den Konstruktor erzeugt wird. Im Normalfall bekommt man es als Argument im bufferedchange-Listener.Beispiele
Hinzugefügte und entfernte Bereiche protokollieren (addEventListener)
const video = document.querySelector('video');
if ('ManagedMediaSource' in window) {
const source = new ManagedMediaSource();
video.disableRemotePlayback = true; // bei ManagedMediaSource auf iOS nötig
video.src = URL.createObjectURL(source);
source.addEventListener('sourceopen', () => {
const sb = source.addSourceBuffer('video/mp4; codecs="avc1.64001f, mp4a.40.2"');
// TimeRanges als lesbaren Text ausgeben
const format = (ranges) =>
Array.from({ length: ranges.length }, (_, i) =>
`${ranges.start(i).toFixed(1)}–${ranges.end(i).toFixed(1)} s`
).join(', ') || '(keine)';
sb.addEventListener('bufferedchange', (event) => {
console.log('Hinzugefügt:', format(event.addedRanges));
console.log('Entfernt:', format(event.removedRanges));
});
});
}
Vom Browser entfernte Segmente neu laden (onbufferedchange)
// Annahme: sb ist ein ManagedSourceBuffer, loadSegment(t) lädt das Segment ab Sekunde t neu
sb.onbufferedchange = (event) => {
const { removedRanges } = event;
const now = video.currentTime;
for (let i = 0; i < removedRanges.length; i++) {
const start = removedRanges.start(i);
const end = removedRanges.end(i);
// Nur Bereiche neu laden, die noch vor der aktuellen Position liegen
if (end > now) {
console.warn(`Browser hat ${start}–${end} s entfernt, lade neu …`);
loadSegment(Math.max(start, now));
}
}
};
// Listener später wieder entfernen
// sb.onbufferedchange = null;
Ereignis im Test selbst erzeugen
// Leeres TimeRanges-Objekt aus einem unbenutzten Medienelement holen
const empty = document.createElement('video').buffered;
const evt = new BufferedChangeEvent('bufferedchange', {
addedRanges: empty,
removedRanges: empty,
});
console.log(evt instanceof Event); // true
console.log(evt.type); // "bufferedchange"
console.log(evt.removedRanges.length); // 0
// Wichtig · Fallstricke
Browser-Kompatibilität: Die API ist experimentell und gehört zu ManagedMediaSource. Stand heute unterstützt sie praktisch nur Safari (ab 17 auf macOS, ab 17.1 auf iOS/iPadOS, dort ist sie die einzige MSE-Variante). Chrome und Firefox bieten sie nicht an. Vorher per 'ManagedMediaSource' in window prüfen und sonst auf das klassische MediaSource zurückfallen. Dieses kennt das Ereignis bufferedchange nicht.
- Nur
ManagedSourceBufferlöst das Ereignis aus. Ein normalerSourceBuffertut das nicht. - Der Browser kann Daten jederzeit entfernen. Deshalb nicht davon ausgehen, dass einmal angehängte Segmente erhalten bleiben. Auf
removedRangesreagieren. addedRangesundremovedRangesbeschreiben nur die Änderung, nicht den vollständigen Puffer. Den aktuellen Stand liefertsourceBuffer.buffered.TimeRangesist kein Array. Einzelne Bereiche liest man mitstart(i)undend(i), die Anzahl mitlength.- Auf iOS muss für
ManagedMediaSourceentwederdisableRemotePlayback = truegesetzt sein oder eine AirPlay-Alternativquelle vorhanden sein. Sonst wird die Quelle nicht geöffnet.