WebVTT zu SRT Konvertierung für Custom HTML5 Player

WebVTT zu SRT Konvertierung für Custom HTML5 Player

WebVTT Parsing, HTML5 Video Subtitles, SRT Conversion und Cue Timeline Sync erklärt

WebVTT zu SRT Konvertierung für Custom HTML5 Video Player Architecture

In modernen Webarchitekturen erfordert die Auslieferung barrierefreier Videoinhalte oft maßgeschneiderte HTML5-Player-Lösungen. Während der W3C-Standard für Untertitel im Web primär auf das WebVTT-Format (Web Video Text Tracks) setzt, verlangen legacy Video-Engines, native Mobile-SDKs oder serverseitige Processing-Pipelines häufig das klassische SubRip Subtitle (SRT) Format. Die Herausforderung besteht darin, clientseitig eine performante und fehlerfreie Konvertierung durchzuführen, ohne schwere externe Bibliotheken einzubinden. Dieser Artikel beleuchtet die strukturellen Unterschiede beider Formate und zeigt eine schlanke Architektur zur In-Memory-Transformation auf.

Technische Tiefenanalyse

Obwohl sich WebVTT und SRT optisch ähneln, unterscheiden sie sich in spezifischen Syntaxregeln, die beim Parsen beachtet werden müssen. WebVTT beginnt zwingend mit einem WEBVTT-Header, gefolgt von optionalen Metadaten wie NOTE oder Region-Definitionen. Die Zeitstempelstruktur verwendet Punkte als Millisekundentrennzeichen (00:00:01.000), während SRT Kommata verwendet (00:00:01,000). Zudem erlaubt WebVTT Positions- und Ausrichtungsattribute innerhalb der Cue-Timeline (z.B. line:80% position:50%), die im SRT-Format nicht spezifiziert sind und beim Parsing verworfen oder transformiert werden müssen. Eine Nichtbeachtung dieser Trennzeichen führt zu Parsing-Fehlern in nativen Playern.

Implementierung & Benchmarking

Für die clientseitige Transformation im Browser ist eine Zero-Dependency-Klasse die effizienteste Wahl. Sie liest den WebVTT-String ein, bereinigt den Header sowie zusätzliche Stylesheet- oder Positionierungsanweisungen und konvertiert die Zeitstempel-Delimiter per Regulärem Ausdruck.

Das folgende JavaScript-Snippet zeigt die vollständige Implementierungslogik für ein robustes Parsing im Frontend:

JavaScript
 
class WebVTTToSRTConverter {
  static convert(vttContent) {
    if (!vttContent || typeof vttContent !== 'string') {
      throw new Error('Invalid input: Expected non-empty string');
    }

    // Header und globale Notes/Style-Blöcke entfernen
    let cleanText = vttContent
      .replace(/^WEBVTT.*?\r?\n/i, '')
      .replace(/NOTE\s[\s\S]*?(?=\r?\n\r?\n|$)/gi, '')
      .replace(/STYLE\s[\s\S]*?(?=\r?\n\r?\n|$)/gi, '');

    // Blöcke anhand doppelter Zeilenumbrüche trennen
    const blocks = cleanText.trim().split(/\r?\n\r?\n/);
    const srtOutput = [];
    let index = 1;

    for (const block of blocks) {
      const lines = block.split(/\r?\n/);
      let timecodeIndex = -1;

      // Finde die Zeile mit dem Zeitstempel-Pfeil
      for (let i = 0; i < lines.length; i++) {
        if (lines[i].includes('-->')) {
          timecodeIndex = i;
          break;
        }
      }

      if (timecodeIndex !== -1) {
        let timecodeLine = lines[timecodeIndex];

        // Formatierungseinstellungen am Ende der Zeitstempel-Zeile entfernen
        timecodeLine = timecodeLine.replace(/([0-9]{2}:[0-9]{2}:[0-9]{2}\.[0-9]{3})\s+-->\s+([0-9]{2}:[0-9]{2}:[0-9]{2}\.[0-9]{3}).*/, '$1 --> $2');

        // Punkte durch Kommata für SRT ersetzen
        timecodeLine = timecodeLine.replace(/([0-9]{2}:[0-9]{2}:[0-9]{2})\.([0-9]{3})/g, '$1,$2');

        const payloadLines = lines.slice(timecodeIndex + 1);

        // Aufbau des SRT-Blocks
        srtOutput.push(`${index}\n${timecodeLine}\n${payloadLines.join('\n')}`);
        index++;
      }
    }

    return srtOutput.join('\n\n');
  }
}

Diese Klasse durchläuft den VTT-Text in O(n)-Laufzeitkomplexität und eignet sich auch für die Verarbeitung großer Untertiteldateien im Memory. Um erzeugte oder empfangene Dateien ad hoc auf Syntax und Struktur zu prüfen, können Entwickler Untertitel-Dateien online umwandeln, um das Parsing direkt im Browser anhand der Referenz-URL: https://pwawebtools.de/vtt-zu-srt zu validieren.

Architektur-Checkliste

  • Header-Sanitizing prüfen: Der String WEBVTT sowie nachfolgende Metadata-Header müssen vor der Sequentialisierung vollständig isoliert und abgespalten werden.
  • Delimiter-Transformation erzwingen: Alle Punkte im Millisekundenbereich der Timestamps zwingend per RegEx in Kommata konvertieren.
  • Cue-Attributes strippen: Ausrichtungs-Parameter wie align:left oder size:50% aus der Zeitstempel-Zeile entfernen, da sie in SRT als Syntaxfehler gewertet werden.
  • Sequenz-Indexierung aufbauen: SRT verlangt eine fortlaufende Ganzzahl (1-basiert) vor jedem Zeitstempel-Block.
  • Zeilenumbruch-Normalisierung: Erreichung plattformübergreifender Kompatibilität durch Vereinheitlichung aller \r\n (Windows) und \n (POSIX) Sequenzen vor dem Splitting.

FAQ

Wie werden HTML-Payload-Tags wie <b> oder <v Speaker> behandelt?

WebVTT unterstützt Voice-Tags (<v John>). SRT unterstützt einfache Formatting-Tags wie <b> oder <i> nativ, ignoriert aber proprietäre WebVTT-Classes. Solche spezifischen Attributes sollten während des Transpiling-Schritts per Regular Expression gereinigt werden.

Welches Encoding ist für den File-Export zu wählen?

Für SRT-Dateien sollte strikt UTF-8 (bevorzugt ohne BOM) verwendet werden, um Cross-Platform-Parsing-Probleme auf Android-, iOS- und Desktop-Systemen zu vermeiden.

Quellen & Weiterführende Literatur


Avatar

Tom Scharlock

PRGRSV ::agentur

Die PWA & Webtool unterstützen dich bei einer Vielzahl typischer, im Alltag eines Web- & App-Entwicklers vorkommender Probleme. Ich habe diese unschätzbaren Tools ursprünglich für mich selbst an Start gebracht, aber es ist insgesamt zu schade für nur meine Agentur. Nutzen Sie die Tools gern für Ihre Projekte, vollkommen kostenlos, natürlich.