@@ -89,6 +89,34 @@ export const findActiveSubtitle = (cues: SubtitleCue[], currentTime: number): Su
8989 return cues . find ( cue => currentTime >= cue . start && currentTime <= cue . end ) || null ;
9090} ;
9191
92+ /**
93+ * Parse M3U8 playlist content to extract VTT file URL
94+ */
95+ const parseM3U8ForVTTUrl = ( content : string , baseUrl : string ) : string | null => {
96+ const lines = content . split ( '\n' ) ;
97+
98+ for ( const line of lines ) {
99+ const trimmedLine = line . trim ( ) ;
100+ // Look for lines that end with .vtt and don't start with #
101+ if ( ! trimmedLine . startsWith ( '#' ) && trimmedLine . includes ( '.vtt' ) ) {
102+ let vttUrl = trimmedLine ;
103+
104+ // Resolve relative URL if needed
105+ if ( vttUrl . startsWith ( '/' ) ) {
106+ const urlObj = new URL ( baseUrl ) ;
107+ vttUrl = `${ urlObj . protocol } //${ urlObj . host } ${ vttUrl } ` ;
108+ } else if ( ! vttUrl . startsWith ( 'http' ) ) {
109+ const basePath = baseUrl . substring ( 0 , baseUrl . lastIndexOf ( '/' ) + 1 ) ;
110+ vttUrl = basePath + vttUrl ;
111+ }
112+
113+ return vttUrl ;
114+ }
115+ }
116+
117+ return null ;
118+ } ;
119+
92120/**
93121 * Fetch and parse subtitle file from URL
94122 */
@@ -104,29 +132,9 @@ export const fetchSubtitleFile = async (url: string): Promise<SubtitleCue[]> =>
104132
105133 // Check if this is an M3U8 playlist instead of a VTT file
106134 if ( content . trim ( ) . startsWith ( '#EXTM3U' ) ) {
107- // Parse the M3U8 to find the actual VTT file URL
108- const lines = content . split ( '\n' ) ;
109- let vttUrl = null ;
110-
111- for ( const line of lines ) {
112- const trimmedLine = line . trim ( ) ;
113- // Look for lines that end with .vtt and don't start with #
114- if ( ! trimmedLine . startsWith ( '#' ) && trimmedLine . includes ( '.vtt' ) ) {
115- vttUrl = trimmedLine ;
116- break ;
117- }
118- }
135+ const vttUrl = parseM3U8ForVTTUrl ( content , url ) ;
119136
120137 if ( vttUrl ) {
121- // Resolve relative URL if needed
122- if ( vttUrl . startsWith ( '/' ) ) {
123- const urlObj = new URL ( url ) ;
124- vttUrl = `${ urlObj . protocol } //${ urlObj . host } ${ vttUrl } ` ;
125- } else if ( ! vttUrl . startsWith ( 'http' ) ) {
126- const baseUrl = url . substring ( 0 , url . lastIndexOf ( '/' ) + 1 ) ;
127- vttUrl = baseUrl + vttUrl ;
128- }
129-
130138 // Recursively fetch the actual VTT file
131139 return await fetchSubtitleFile ( vttUrl ) ;
132140 } else {
0 commit comments