Start · Sprachen · JavaScript · Referenz · AudioBufferSourceNode.buffer

AudioBufferSourceNode.buffer

Eigenschaft

Liest oder setzt den <code>AudioBuffer</code>, dessen Audiodaten ein <code>AudioBufferSourceNode</code> abspielt, oder <code>null</code>, wenn noch kein Puffer zugewiesen ist.

seit JavaScript Web Audio API – Baseline: alle modernen Browser Kategorie: webapi

Signatur

AudioBufferSourceNode.buffer

Beschreibung

Die Eigenschaft buffer legt fest, welche Audiodaten ein AudioBufferSourceNode abspielt. Der zugewiesene AudioBuffer liegt vollständig im Arbeitsspeicher. Deshalb eignet sich der Knoten gut für kurze Klänge mit geringer Verzögerung, etwa Soundeffekte in Spielen, Klicks in der Oberfläche, Samples oder selbst erzeugte Signale wie Rauschen.

Einen Puffer bekommst du meist, indem du eine Audiodatei mit fetch() lädst und mit BaseAudioContext.decodeAudioData() dekodierst. Alternativ legst du mit AudioContext.createBuffer() oder new AudioBuffer() einen leeren Puffer an und füllst ihn selbst mit Samples. Den Puffer kannst du vor oder nach start() zuweisen. Ist beim Start noch kein Puffer gesetzt, gibt der Knoten Stille aus, bis einer zugewiesen wird.

Wichtig: Einen AudioBufferSourceNode kannst du nur einmal starten. Einen Puffer (nicht null) kannst du ihm nur einmal zuweisen. Willst du einen Klang mehrfach abspielen, erzeugst du für jede Wiedergabe einen neuen, günstigen Quellknoten und verwendest denselben AudioBuffer wieder. Das Dekodieren ist der teure Teil.

Parameter

Name Typ Default Beschreibung
$value AudioBuffer | null null Der Puffer, der abgespielt werden soll (beim Setzen). Er enthält einen oder mehrere Kanäle mit Float32-Samples.

Rückgabewert

Typ
AudioBuffer | null
Beschreibung
Der aktuell zugewiesene AudioBuffer oder null, wenn noch keiner gesetzt wurde.

Beispiele

Audiodatei laden, dekodieren und abspielen

const ctx = new AudioContext();

const loadSound = async (url) => {
  const response = await fetch(url);
  const arrayBuffer = await response.arrayBuffer();
  return ctx.decodeAudioData(arrayBuffer);
};

document.querySelector('#play').addEventListener('click', async () => {
  await ctx.resume(); // Autoplay-Sperre aufheben
  const audioBuffer = await loadSound('/sounds/klick.mp3');

  const source = ctx.createBufferSource();
  source.buffer = audioBuffer;
  source.connect(ctx.destination);
  source.start();

  console.log(`Dauer: ${source.buffer.duration.toFixed(2)} s`);
});
Dauer: 0.35 s

Einen dekodierten Puffer mehrfach abspielen

const ctx = new AudioContext();
const response = await fetch('/sounds/schuss.wav');
const shotBuffer = await ctx.decodeAudioData(await response.arrayBuffer());

// Für jede Wiedergabe einen neuen Quellknoten, denselben Puffer
const playShot = () => {
  const source = new AudioBufferSourceNode(ctx, { buffer: shotBuffer });
  source.connect(ctx.destination);
  source.start();
};

playShot();
setTimeout(playShot, 200); // überlappend möglich

Weißes Rauschen erzeugen und in Schleife abspielen

const ctx = new AudioContext();
const seconds = 2;
const noise = ctx.createBuffer(1, ctx.sampleRate * seconds, ctx.sampleRate);

const data = noise.getChannelData(0);
for (let i = 0; i < data.length; i++) {
  data[i] = Math.random() * 2 - 1; // Werte zwischen -1 und 1
}

const source = ctx.createBufferSource();
console.log(source.buffer); // noch kein Puffer
source.buffer = noise;
source.loop = true;
source.connect(ctx.destination);
source.start();
source.stop(ctx.currentTime + 5);
null

Zweites Zuweisen löst einen Fehler aus

const ctx = new AudioContext();
const a = ctx.createBuffer(1, 44100, 44100);
const b = ctx.createBuffer(1, 44100, 44100);

const source = ctx.createBufferSource();
source.buffer = a;
try {
  source.buffer = b;
} catch (err) {
  console.log(err.name);
}
InvalidStateError

// Wichtig · Fallstricke

  • Nur einmal zuweisen: Hat der Knoten schon einen Puffer erhalten (nicht null), wirft jede weitere Zuweisung eines Puffers eine InvalidStateError-DOMException. Das gilt auch, wenn du zwischendurch null setzt.
  • Einmal starten: start() kannst du pro Knoten nur einmal aufrufen. Für wiederholte Wiedergabe erzeugst du neue Knoten. Das ist so vorgesehen und kostet wenig.
  • Speicherverbrauch: Ein AudioBuffer hält dekodierte PCM-Daten (32-Bit-Float) im Arbeitsspeicher. Eine Minute Stereo bei 48 kHz belegt etwa 23 MB. Für lange Musikstücke eignen sich <audio> mit MediaElementAudioSourceNode besser.
  • Abtastrate: Weicht die Abtastrate des Puffers von der des Kontexts ab, rechnet der Browser sie automatisch um (Resampling).
  • Autoplay: Browser starten einen AudioContext oft im Zustand suspended. Rufe ctx.resume() nach einer Nutzeraktion auf.
  • CORS: Audiodateien von fremden Servern lassen sich mit fetch() nur laden, wenn der Server passende CORS-Header sendet.
  • Die Eigenschaft wird in allen aktuellen Browsern unterstützt (Chrome, Firefox, Safari, Edge). Sehr alte Safari-Versionen benötigten webkitAudioContext.