@@ -45,6 +45,7 @@ export default class Format {
4545 target_duration_dec ?: number ;
4646 has_audio : boolean ;
4747 has_video : boolean ;
48+ has_text : boolean ;
4849 language ?: string | null ;
4950 is_dubbed ?: boolean ;
5051 is_descriptive ?: boolean ;
@@ -56,6 +57,14 @@ export default class Format {
5657 matrix_coefficients ?: string ;
5758 } ;
5859
60+ caption_track ?: {
61+ display_name : string ;
62+ vss_id : string ;
63+ language_code : string ;
64+ kind ?: 'asr' | 'frc' ;
65+ id : string ;
66+ } ;
67+
5968 constructor ( data : RawNode , this_response_nsig_cache ?: Map < string , string > ) {
6069 if ( this_response_nsig_cache ) {
6170 this . #this_response_nsig_cache = this_response_nsig_cache ;
@@ -96,32 +105,50 @@ export default class Format {
96105 this . target_duration_dec = data . targetDurationSec ;
97106 this . has_audio = ! ! data . audioBitrate || ! ! data . audioQuality ;
98107 this . has_video = ! ! data . qualityLabel ;
108+ this . has_text = ! ! data . captionTrack ;
99109
100110 this . color_info = data . colorInfo ? {
101111 primaries : data . colorInfo . primaries ?. replace ( 'COLOR_PRIMARIES_' , '' ) ,
102112 transfer_characteristics : data . colorInfo . transferCharacteristics ?. replace ( 'COLOR_TRANSFER_CHARACTERISTICS_' , '' ) ,
103113 matrix_coefficients : data . colorInfo . matrixCoefficients ?. replace ( 'COLOR_MATRIX_COEFFICIENTS_' , '' )
104114 } : undefined ;
105115
106- if ( this . has_audio ) {
116+ if ( Reflect . has ( data , 'audioTrack' ) ) {
117+ this . audio_track = {
118+ audio_is_default : data . audioTrack . audioIsDefault ,
119+ display_name : data . audioTrack . displayName ,
120+ id : data . audioTrack . id
121+ } ;
122+ }
123+
124+ if ( Reflect . has ( data , 'captionTrack' ) ) {
125+ this . caption_track = {
126+ display_name : data . captionTrack . displayName ,
127+ vss_id : data . captionTrack . vssId ,
128+ language_code : data . captionTrack . languageCode ,
129+ kind : data . captionTrack . kind ,
130+ id : data . captionTrack . id
131+ } ;
132+ }
133+
134+ if ( this . has_audio || this . has_text ) {
107135 const args = new URLSearchParams ( this . cipher || this . signature_cipher ) ;
108136 const url_components = new URLSearchParams ( args . get ( 'url' ) || this . url ) ;
109137
110138 const xtags = url_components . get ( 'xtags' ) ?. split ( ':' ) ;
111139
112- const audio_content = xtags ?. find ( ( x ) => x . startsWith ( 'acont=' ) ) ?. split ( '=' ) [ 1 ] ;
113-
114140 this . language = xtags ?. find ( ( x : string ) => x . startsWith ( 'lang=' ) ) ?. split ( '=' ) [ 1 ] || null ;
115- this . is_dubbed = audio_content === 'dubbed' ;
116- this . is_descriptive = audio_content === 'descriptive' ;
117- this . is_original = audio_content === 'original' || ( ! this . is_dubbed && ! this . is_descriptive ) ;
118-
119- if ( Reflect . has ( data , 'audioTrack' ) ) {
120- this . audio_track = {
121- audio_is_default : data . audioTrack . audioIsDefault ,
122- display_name : data . audioTrack . displayName ,
123- id : data . audioTrack . id
124- } ;
141+
142+ if ( this . has_audio ) {
143+ const audio_content = xtags ?. find ( ( x ) => x . startsWith ( 'acont=' ) ) ?. split ( '=' ) [ 1 ] ;
144+ this . is_dubbed = audio_content === 'dubbed' ;
145+ this . is_descriptive = audio_content === 'descriptive' ;
146+ this . is_original = audio_content === 'original' || ( ! this . is_dubbed && ! this . is_descriptive ) ;
147+ }
148+
149+ // Some text tracks don't have xtags while others do
150+ if ( this . has_text && ! this . language && this . caption_track ) {
151+ this . language = this . caption_track . language_code ;
125152 }
126153 }
127154 }
0 commit comments