解析和转换TED演讲的JSON字幕

12

这个问题与SuperUser上的另一个问题有关。

我想要下载TED演讲和相应的字幕以供离线观看,例如,就拿Richard St. John的这篇短演讲来说,其高清视频下载URL如下:

http://www.ted.com/talks/download/video/5118/talk/70

相应的JSON编码英文字幕可以在以下位置下载:

http://www.ted.com/talks/subtitles/id/70/lang/eng

这是实际字幕开头的一部分:

{
  "captions": [{
        "content": "This is really a two hour presentation I give to high school students,",
        "startTime": 0,
        "duration": 3000,
        "startOfParagraph": false
      }, {
        "content": "cut down to three minutes.",
        "startTime": 3000,
        "duration": 1000,
        "startOfParagraph": false
      }, {
        "content": "And it all started one day on a plane, on my way to TED,",
        "startTime": 4000,
        "duration": 3000,
        "startOfParagraph": false
      }, {
        "content": "seven years ago."

从字幕的结尾开始:

{
  "content": "Or failing that, do the eight things -- and trust me,",
  "startTime": 177000,
  "duration": 3000,
  "startOfParagraph": false
}, {
  "content": "these are the big eight things that lead to success.",
  "startTime": 180000,
  "duration": 4000,
  "startOfParagraph": false
}, {
  "content": "Thank you TED-sters for all your interviews!",
  "startTime": 184000,
  "duration": 2000,
  "startOfParagraph": false
}]
}

我想编写一个应用程序,自动下载高分辨率视频和所有可用字幕,但是我遇到了很大的困难,因为我必须将字幕转换为(VLC或任何其他好的视频播放器)兼容格式(.srt或.sub是我的首选),而且我不知道JSON文件中的startTimeduration键表示什么

目前我所知道的是:

  • 下载的视频持续时间为3分钟30秒,有29帧每秒=6090帧
  • startTime从0开始duration为3000=3000
  • startTime结束于184000duration为2000=186000

还值得注意的是以下Javascript片段:

introDuration:16500,
adDuration:4000,
postAdDuration:2000,

所以我的问题是,我应该应用什么逻辑来将startTimeduration的值转换为.srt格式兼容的格式:

1
00:01:30,200 --> 00:01:32,201
MEGA DENG COOPER MINE, INDIA

2
00:01:37,764 --> 00:01:39,039
Watch out, watch out!

或者转换为 .sub 兼容格式:

{FRAME_FROM}{FRAME_TO}This is really a two hour presentation I give to high school students,
{FRAME_FROM}{FRAME_TO}cut down to three minutes.

有人能帮我解决这个问题吗?


Ninh Bui完美地解决了它,公式如下:

introDuration - adDuration + startTime ... introDuration - adDuration + startTime + duration

这种方法可以让我直接以.srt格式转换(无需知道长度和FPS),有两种方式:

00:00:12,500 --> 00:00:15,500
This is really a two hour presentation I give to high school students,

00:00:15,500 --> 00:00:16,500
cut down to three minutes.

并且:

00:00:00,16500 --> 00:00:00,19500
And it all started one day on a plane, on my way to TED,

00:00:00,19500 --> 00:00:00,20500
seven years ago.

+1 为详细解释 :) - ukanth
+1 是为了尝试我一直想知道是否能够做到的事情。 - Talvi Watia
5个回答

4
我的猜测是,JSON中的时间以毫秒为单位表示,例如1000 = 1秒。可能有一个主计时器,在那里startTime指示字幕应出现的时间轴上的时间,而duration可能是字幕在视觉上保持的时间量。通过将186000/1000除以= 186秒= 186/60 = 3.1分钟= 3分钟和6秒,该理论得到了进一步证实。剩下的几秒钟可能是掌声;-)有了这些信息,您还可以计算从哪个帧到哪个帧应用您的转换,即您已经知道每秒帧数,所以您只需要将starttime的秒数乘以FPS即可获得开始帧。结束帧可以通过以下方式获得:(startTime + duration)* fps :-)

谢谢,我的转换现在完美同步了。=) - Alix Axel

3

太好了!你还应该提供某种API,以允许自动下载字幕,例如在从播客下载后使用Apple脚本之类的东西。 - Leandro Ardissone

1
我发现另一个网站使用了这种格式。我很快就编写了一个函数来将它们转换为srt,应该很容易理解:
import urllib2
import json

def json2srt(url, fname):
    data = json.load(urllib2.urlopen(url))['captions']

    def conv(t):
        return '%02d:%02d:%02d,%03d' % (
            t / 1000 / 60 / 60,
            t / 1000 / 60 % 60,
            t / 1000 % 60,
            t % 1000)

    with open(fname, 'wb') as fhandle:
        for i, item in enumerate(data):
            fhandle.write('%d\n%s --> %s\n%s\n\n' %
                (i,
                 conv(item['startTime']),
                 conv(item['startTime'] + item['duration'] - 1),
                 item['content'].encode('utf8')))

0

0
我编写了一个Python脚本,可以下载任何TED视频,并创建一个包含所有字幕/元数据的mkv文件 (https://github.com/oxplot/ted2mkv)。
我在TED演讲页面的JavaScript代码中使用变量pad_seconds作为要添加到JSON字幕文件中所有时间戳的偏移量。我认为这是Flash播放器所使用的。

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接