从mkv文件中提取字幕


39

问题在于Ubuntu中的视频播放器在集成中欧字幕时存在问题,解决方案是提取字幕。有谁知道终端中是否有命令或程序从mkv文件中提取字幕?

Answers:


58

安装mkvtoolnix使用sudo apt-get install mkvtoolnix

从终端运行: mkvextract tracks <your_mkv_video> <track_numer>:<subtitle_file.srt>

使用mkvinfo以获取有关轨道的信息。

使用此实用程序,您可以提取任何轨道,甚至音频或视频。


9
不要使用mkvinfo“ Track number:2(mkvmerge&mkvextract:1的轨道ID)”之类的令人困惑的东西。使用mkvmerge -i <filename>
gcb

还要注意的是,如在指定的文档mkvextract 由轨道类型,而不是给定扩展确定文件输出格式(因此检查类型为所报告mkvmerge -i <filename>)。
制图师

字幕的数据(字节)是否放置在所有文件容器中?因为视频文件越大,它的工作速度就越慢...(500mb 1 gb 4gb .mkv文件)我认为它将工作得更快,并且我认为字幕的字节放置在视频容器文件的特定部分,但似乎ffmpeg或mkvextract读取仅在读取所有文件后才提取所有文件并提取字幕(这非常慢)
16:25的user25

2
@gcb,如果用mkvmerge&mkvextract的英文曲目ID表示它会引起混淆吗?很简单,只需将跟踪ID用于mkvextract或mkvmerge。数组的长度和元素在编程中的索引对您来说也令人困惑吗?
user25

8

您可以使用mkvtoolnix。

sudo apt-get install mkvtoolnix

现在的另一个技巧是,由于mkv文件可能包含许多字幕,因此该技巧是您可以搜索所需语言的脚本,例如,如果要使用英语,它将仅下载英语。

剧本:

#!/bin/bash
# Extract subtitles from each MKV file in the given directory

# If no directory is given, work in local dir
if [ "$1" = "" ]; then
  DIR="."
else
  DIR="$1"
fi

# Get all the MKV files in this dir and its subdirs
find "$DIR" -type f -name '*.mkv' | while read filename
do
  # Find out which tracks contain the subtitles
  mkvmerge -i "$filename" | grep 'subtitles' | while read subline
  do
    # Grep the number of the subtitle track
    tracknumber=`echo $subline | egrep -o "[0-9]{1,2}" | head -1`

    # Get base name for subtitle
    subtitlename=${filename%.*}

    # Extract the track to a .tmp file
    `mkvextract tracks "$filename" $tracknumber:"$subtitlename.srt.tmp" > /dev/null 2>&1`
    `chmod g+rw "$subtitlename.srt.tmp"`


    # Do a super-primitive language guess: ENGLISH
    langtest=`egrep -ic ' you | to | the ' "$subtitlename".srt.tmp`
    trimregex=""



    # Check if subtitle passes our language filter (10 or more matches)
    if [ $langtest -ge 10 ]; then
      # Regex to remove credits at the end of subtitles (read my reason why!)
      `sed 's/\r//g' < "$subtitlename.srt.tmp" \
        | sed 's/%/%%/g' \
        | awk '{if (a){printf("\t")};printf $0; a=1; } /^$/{print ""; a=0;}' \
        | grep -iv "$trimregex" \
        | sed 's/\t/\r\n/g' > "$subtitlename.srt"`
      `rm "$subtitlename.srt.tmp"`
      `chmod g+rw "$subtitlename.srt"`
    else
      # Not our desired language: add a number to the filename and keep anyway, just in case
      `mv "$subtitlename.srt.tmp" "$subtitlename.$tracknumber.srt" > /dev/null 2>&1`
    fi
  done
done

保存此脚本名称youwant.sh并使其可执行

现在在终端中将目录更改为脚本文件夹并写入 ./nameyouwant.sh /pathtosave


奇怪的是,它不适用于一个视频,但是通过执行接受的答案中给出的命令,它可以工作。
匈苏2014年

感谢漂亮的脚本。您能否添加解释为什么要删除字幕结尾处的字幕?脚本的那部分对我不起作用,并导致一个空的srt文件。
m000

1
这个答案似乎来自computernerdfromhell.com。删除字幕的原因是:“荷兰字幕制作者习惯在字幕的最后几行中插入字幕或喊叫。这没什么错,除非它发生在字幕的最后一行之后。这部电影可能还会再播放5分钟,我不希望DaNoodleBrain向BoogerGuzzler大喊大叫,从而放弃了宣誓的结尾,所以我用另一个简单的正则表达式删除了它们”
Dror S.
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.