Sobald ein ended Hörer abfeuert Sie es entfernen müssen, so wird es nicht wieder
jedoch gefeuert werden, so wie du bist Das Hinzufügen der Ereignis-Listener (auf einmal, im Grunde genommen) bedeutet, dass Sie dem Audio, das mehrmals abgespielt wird, bereits mehrere Listener hinzugefügt haben. Wenn also der wiederholte Audio-Eintrag nicht der letzte im Array ist, werden Sie Ich bekomme einige Probleme, kein Zweifel
Die ideale Lösung ist, den Hörer nur hinzufügen, sobald der Ton startet, und entfernen Sie den Hörer einmal das Ereignis ended
ausgelöst wird.
Diese Antworten enthalten die Anfrag in dem Kommentar für eine optionale „Pause“ zwischen Audio-Element-Wiedergabe - dies durch eine negative Nummer im defaultArrayMelody
function playDefault() {
const defaultArrayMelody = [70, 71, -1000, 69, 70];
const audio = defaultArrayMelody.map(el => el < 0 ? -el : document.querySelector(`audio[data-key="${el}"]`));
var playAudio = function(index) {
if (audio[index]) {
var listener = function() {
this.removeEventListener('ended', listener);
playAudio(index + 1);
};
if (typeof audio[index] == 'number') {
setTimeout(() => playAudio(index + 1), audio[index]);
} else {
audio[index].addEventListener('ended', listener);
audio[index].play();
}
}
};
playAudio(0);
}
document.querySelector(`#playDefault`).addEventListener('click', playDefault);
Ein alternativen Verfahren bezeichnet wird, würde zu verwenden Promise
function playDefault() {
const defaultArrayMelody = [70, 71, -1000, 69, 70];
const audio = defaultArrayMelody.map(el => el < 0 ? -el : document.querySelector(`audio[data-key="${el}"]`));
audio.reduce((prev, item) => prev.then(() => new Promise(resolve => {
var listener = function listener() {
this.removeEventListener('ended', listener);
resolve();
};
if (typeof item== 'number') {
setTimeout(resolve, item); // item is millseconds
} else {
item.addEventListener('ended', listener);
item.play();
}
})), Promise.resolve());
}
document.querySelector(`#playDefault`).addEventListener('click', playDefault);
Hier können Sie mit nicht entfernen Der Ereignis-Listener, da der Event-Listener nur das Versprechen löst - und sobald ein Versprechen gelöst ist, kann es nicht wieder aufgelöst (oder abgelehnt) werden - wodurch sichergestellt wird, dass die Sequenz nur einmal in der Reihenfolge abgespielt wird. Jedoch in dem obigen Code enthalten ich die removeEventListener ... ohne es sieht der Code wie
function playDefault() {
const defaultArrayMelody = [70, 71, -1000, 69, 70];
const audio = defaultArrayMelody.map(el => el < 0 ? -el : document.querySelector(`audio[data-key="${el}"]`));
audio.reduce((prev, item) => prev.then(() => new Promise(resolve => {
if (typeof item== 'number') {
setTimeout(resolve, item); // item is millseconds
} else {
item.addEventListener('ended', resolve);
item.play();
}
})), Promise.resolve());
}
document.querySelector(`#playDefault`).addEventListener('click', playDefault);
Ich nehme an, Sie wirklich wollen Duplikate im Array –
ist [5,3,2,3] arbeiten? –
@ JeremyKahan ja – Garrs