J'ai acheté une boîte de DVD de "Mayday!: La vérité et la vérité des accidents d'avion" (titre anglais Air Crash Investigation). C'est une version anglaise, mais je pensais qu'il y aurait des sous-titres, mais je n'avais même pas de sous-titres anglais ...
Heureusement, le contrôle d'accès par CSS (Content Scramble System) n'était pas appliqué, j'ai donc essayé de créer des sous-titres d'une manière ou d'une autre.
Pour macOS, vous pouvez l'installer à l'aide de homebrew. Il est également nécessaire que vous puissiez utiliser Python 3 et pip.
brew install ffmpeg mkvtoolnix
pip3 install boto3
Avec ffmpeg, vous pouvez facilement copier dans un fichier contenant uniquement des données audio.
ffmpeg -i original.m4v -acodec copy -vn output.m4a
Pour utiliser Amazon Transcribe, vous devez télécharger des données audio sur S3. Cette fois, pour plus de simplicité, j'ai écrit un script simple en Python qui se télécharge simplement sur S3 et soumet une tâche à Amazon Transcribe.
Le code qui sort après ceci est un code que j'ai écrit en un peu plus de 10 minutes, donc c'est assez approximatif dans l'ensemble ...
01-transcribe.py
from boto3 import client, resource
import os
import sys
AWS_ACCESS_KEY = "hogehoge"
AWS_SECRET_ACCESS_KEY = "fugafuga"
BUCKET = "somebucket"
def upload(filepath):
basename = os.path.basename(filepath)
s3_client = resource(
"s3",
region_name="ap-northeast-1",
aws_access_key_id=AWS_ACCESS_KEY,
aws_secret_access_key=AWS_SECRET_ACCESS_KEY,
)
s3_client.Bucket(BUCKET).upload_file(filepath, basename)
def transcribe(filename):
url = "s3://{}/{}".format(BUCKET, filename)
transcribe_client = client(
"transcribe",
region_name="ap-northeast-1",
aws_access_key_id=AWS_ACCESS_KEY,
aws_secret_access_key=AWS_SECRET_ACCESS_KEY,
)
response = transcribe_client.start_transcription_job(
TranscriptionJobName=filename,
LanguageCode="en-US",
MediaFormat="mp4",
Media={
"MediaFileUri": url
},
OutputBucketName=BUCKET,
)
def main():
filepath = sys.argv[1]
upload(filepath)
transcribe(os.path.basename(filepath))
if __name__ == "__main__":
main()
Passez le fichier précédent comme argument et exécutez.
python 01-transcribe.py output.m4a
Téléchargez le fichier JSON résultant à partir de la console Web. (Omission)
Le JSON résultant contient un tableau de mots reconnus et leurs heures de début et de fin. Si vous affichez chaque mot comme un sous-titre tel quel, il sera trop difficile à lire.
Par conséquent, j'ai décidé de générer des données de sous-titres (srt) en décidant de la plage d'affichage selon certaines règles.
Cette règle est décidée de manière appropriée, alors jouez avec elle comme vous le souhaitez.
02-makesrt.py
import json
import sys
def sec2time(sec):
h = int(sec/3600)
m = int((sec%3600) / 60)
s = int(sec % 60)
mils = int((sec%1)*1000)
return "{:02d}:{:02d}:{:02d},{:03d}".format(h, m, s, mils)
def convert2srt(filepath):
with open(filepath, "r") as f:
data = json.load(f)
start_time = 0
end_time = 0
s = ""
index = 0
for item in data["results"]["items"]:
is_output = False
if "start_time" in item:
item["start_time"] = float(item["start_time"])
item["end_time"] = float(item["end_time"])
if item["start_time"] - end_time > 3:
#As-tu eu le temps
is_output = True
elif len(s) >= 110:
#Si ça s'allonge
is_output = True
if s != "":
if len(s)>1 and s[-2].isupper():
pass
else:
last = s[-1]
if last in (".", "?", "!"):
is_output = True
if last == "," and len(s) > 80:
is_output = True
if is_output:
end_time = min(item["start_time"], end_time+2.0)
if s != "":
print(index)
index += 1
print("{0} --> {1}".format(sec2time(start_time), sec2time(end_time)))
print(s)
print("")
start_time = 0
end_time = 0
s = ""
if "start_time" in item:
if start_time == 0:
start_time = item["start_time"]
end_time = item["end_time"]
if s and (len(item["alternatives"][0]["content"])>1 or s[-1] != "."):
s += " " + item["alternatives"][0]["content"]
else:
s += item["alternatives"][0]["content"]
else:
s += item["alternatives"][0]["content"]
if s != "":
print(index)
index += 1
print("{0} --> {1}".format(sec2time(start_time), sec2time(end_time+2.0)))
print(s)
print("")
def main():
filepath = sys.argv[1]
convert2srt(filepath)
if __name__ == "__main__":
main()
Spécifiez un fichier JSON comme argument et enregistrez le résultat dans un fichier texte par redirection.
python 02-makesrt.py result.json > result.srt
La sortie devrait ressembler à ceci
output
64
00:06:00,139 --> 00:06:16,839
Then the next Nano second, it was pure, unadulterated pandemonium Way number three going down.
65
00:06:16,839 --> 00:06:18,720
It looks like we lost number three engine.
66
00:06:18,720 --> 00:06:23,149
We're descending rapidly coming back.
Vous pouvez facilement intégrer des données de sous-titres dans un fichier mkv à l'aide de mkvmerge.
mkvmerge -o output.mkv original.m4v --language 0:eng --track-name 0:English result.srt
Les sous-titres intégrés peuvent être affichés lors de la lecture sur VLC.
Eh bien, je pense qu'il est affiché presque sans aucune gêne.
Le vrai plaisir de la programmation est que vous pouvez créer rapidement des outils à de tels moments.
Recommended Posts