mirror of
https://github.com/yt-dlp/yt-dlp.git
synced 2024-11-27 06:10:12 +01:00
[pp/FFmpegEmbedSubtitle] Embed JSON subtitles as Matroska attachments
Since we can't embed them as regular subtitles (due to them not having any consistent structure), we embed them as file attachments, if exporting as Matroska. This allows us to have single-file downloads with everything embedded for e.g. archival purposes.
This commit is contained in:
parent
339828d777
commit
ba3a7232f0
|
@ -619,13 +619,19 @@ def run(self, info):
|
|||
webm_vtt_warn = False
|
||||
mp4_ass_warn = False
|
||||
|
||||
json_names, json_filenames = [], []
|
||||
|
||||
for lang, sub_info in subtitles.items():
|
||||
if not os.path.exists(sub_info.get('filepath', '')):
|
||||
self.report_warning(f'Skipping embedding {lang} subtitle because the file is missing')
|
||||
continue
|
||||
sub_ext = sub_info['ext']
|
||||
if sub_ext == 'json':
|
||||
self.report_warning('JSON subtitles cannot be embedded')
|
||||
if info['ext'] in ('mkv', 'mka'):
|
||||
json_names.append(lang)
|
||||
json_filenames.append(sub_info['filepath'])
|
||||
else:
|
||||
self.report_warning('JSON subtitles can only be embedded in mkv/mka files.')
|
||||
elif ext != 'webm' or ext == 'webm' and sub_ext == 'vtt':
|
||||
sub_langs.append(lang)
|
||||
sub_names.append(sub_info.get('name'))
|
||||
|
@ -644,11 +650,15 @@ def run(self, info):
|
|||
input_files = [filename, *sub_filenames]
|
||||
|
||||
opts = [
|
||||
# Attached JSON subtitles don't have a codec id and we have to
|
||||
# instruct FFMPEG to not discard them because of that.
|
||||
'-copy_unknown',
|
||||
*self.stream_copy_opts(ext=info['ext']),
|
||||
# Don't copy the existing subtitles, we may be running the
|
||||
# postprocessor a second time
|
||||
'-map', '-0:s',
|
||||
]
|
||||
|
||||
for i, (lang, name) in enumerate(zip(sub_langs, sub_names)):
|
||||
opts.extend(['-map', f'{i + 1}:0'])
|
||||
lang_code = ISO639Utils.short2long(lang) or lang
|
||||
|
@ -657,12 +667,21 @@ def run(self, info):
|
|||
opts.extend([f'-metadata:s:s:{i}', f'handler_name={name}',
|
||||
f'-metadata:s:s:{i}', f'title={name}'])
|
||||
|
||||
for (json_filename, json_name) in zip(json_filenames, json_names):
|
||||
escaped_json_filename = self._ffmpeg_filename_argument(json_filename)
|
||||
opts.extend([
|
||||
'-map', f'-0:m:filename:{json_name}.json?',
|
||||
'-attach', escaped_json_filename,
|
||||
f'-metadata:s:m:filename:{escaped_json_filename}', 'mimetype=application/json',
|
||||
f'-metadata:s:m:filename:{escaped_json_filename}', f'filename={json_name}.json',
|
||||
])
|
||||
|
||||
temp_filename = prepend_extension(filename, 'temp')
|
||||
self.to_screen(f'Embedding subtitles in "{filename}"')
|
||||
self.run_ffmpeg_multiple_files(input_files, temp_filename, opts)
|
||||
os.replace(temp_filename, filename)
|
||||
|
||||
files_to_delete = [] if self._already_have_subtitle else sub_filenames
|
||||
files_to_delete = [] if self._already_have_subtitle else sub_filenames + json_filenames
|
||||
return files_to_delete, info
|
||||
|
||||
|
||||
|
|
Loading…
Reference in New Issue
Block a user