Answers:
Shnsplit可以直接读取提示文件,这也意味着它可以访问提示文件中的其他数据(不仅是断点),而且可以生成比'split-*。flac'更好的文件名:
shnsplit -f file.cue -t %n-%t -o flac file.flac
当然,如果原始flac文件位于同一目录中,这将使使用cuetag.sh更加困难。
sudo apt-get install cuetools shntool
cuetag file.cue [0-9]*.flac
sudo apt-get install flac
我只知道CLI方式。您将需要cuetools和shntool。
cuebreakpoints file.cue | shnsplit -o flac file.flac
cuetag.sh file.cue "split-*".flac
cuebreakpoints file.cue | shnsplit -o flac file.flac
了很长时间了。第二位将有很大帮助!
cuetag
似乎破坏了包含空格的文件名,但是删除它们后它起作用了。
Flacon是一个直观的开源GUI,它确实做到了:用CUE拆分FLAC。
Flacon从一个包含整个音乐专辑的大音频文件中提取单个曲目,并将它们另存为单独的音频文件。为此,它使用适当CUE文件中的信息。
它支持以下方面:
支持的输入格式:WAV,FLAC,APE,WavPack,True Audio(TTA)。
支持的格式:FLAC,WAV,WavPack,AAC,OGG或MP3。
CUE文件的自动字符集检测。
要使用它,您只需要*.cue
使用Flacon 打开文件。然后,它将自动检测大*.flac
文件(如果没有,则可以手动指定),然后选择Flac输出格式(并选择配置编码器),然后开始转换过程。
如果正在使用高质量的文件,则shnsplit会很高兴地将错误信息与
shnsplit: error: m:ss.ff format can only be used with CD-quality files
幸运的是,flac二进制文件支持--skip = mm:ss.ss和--until = mm:ss.ss,因此脚本可以使用如下提示点:
[..]
time[0]="00:00.00"
c=1
for ts in $(cuebreakpoints "${cue_file}"); do
time[${c}]=${ts}
c=$((c+1))
done
time[${c}]='-0'
for ((i=0;i<$((${#time[@]}-1));i++)); do
trackno=$(($i+1))
TRACKNUMBER="$(printf %02d ${trackno})"
title="$(cueprint --track-number ${trackno} -t '%t' "${cue_file}")"
flac --silent --exhaustive-model-search --skip=${time[$i]} --until=${time[$(($i+1))]} --tag=ARTIST="${ARTIST}" --tag=ALBUM="${ALBUM}" --tag=DATE="${DATE}" --tag=TITLE="${title}" --tag=TRACKNUMBER="${TRACKNUMBER}" "${aud_file}" --output-name="${TRACKNUMBER}-${title}.flac"
done
有一个项目可用于多个输入文件:split2flac
从项目描述:
split2flac使用CUE工作表将一个大的APE / FLAC / TTA / WV / WAV音频图像(或递归此类文件的集合)分割为FLAC / M4A / MP3 / OGG_VORBIS / WAV轨道,并对工作表进行标记,重命名,字符集转换,专辑封面图片。它还使用配置文件,因此无需每次都传递很多参数,只需输入一个文件即可。应该可以在任何符合POSIX的外壳中使用。
我发现mac
(shntool
用于解码APE文件的命令)的容忍度比ffmpeg
源文件中包含小错误的容忍度小。
通常,在处理过程中很可能引发错误的ffmpeg
同时,仍将完全转换文件mac
。
因此,我最终编写了一个脚本,用于通过解析CUE文件并将APE文件转换为使用ffmpeg用标题分隔的FLAC文件来分割APE文件:
#!/usr/bin/env python2.7
import subprocess as subp
import sys
import os
from os.path import splitext, basename
import random
import glob
records = []
filename = ""
album=''
alb_artist=''
codec = 'flac'
ffmpeg_exec = 'ffmpeg'
encodingList = ('utf-8','euc-kr', 'shift-jis', 'cp936', 'big5')
filecontent = open(sys.argv[1]).read()
for enc in encodingList:
try:
lines = filecontent.decode(enc).split('\n')
encoding = enc
break
except UnicodeDecodeError as e:
if enc == encodingList[-1]:
raise e
else:
pass
for l in lines:
a = l.split()
if not a:
continue
if a[0] == "FILE":
filename = ' '.join(a[1:-1]).strip('\'"')
elif a[0]=='TRACK':
records.append({})
records[-1]['index'] = a[1]
elif a[0]=='TITLE':
if len(records)>0:
records[-1]['title'] = ' '.join(a[1:]).strip('\'"')
else:
album = ' '.join(a[1:]).strip('\'"')
elif a[0]=='INDEX' and a[1]=='01':
timea = a[2].split(':')
if len(timea) == 3 and int(timea[0]) >= 60:
timea.insert(0, str(int(timea[0])/60))
timea[1] = str(int(timea[1])%60)
times = '{0}.{1}'.format(':'.join(timea[:-1]), timea[-1])
records[-1]['start'] = times
elif a[0]=='PERFORMER':
if len(records)>1:
records[-1]['artist'] = ' '.join(a[1:]).strip('\'"')
else:
alb_artist = ' '.join(a[1:]).strip('\'"')
for i, j in enumerate(records):
try:
j['stop'] = records[i+1]['start']
except IndexError:
pass
if not os.path.isfile(filename):
tmpname = splitext(basename(sys.argv[1]))[0]+splitext(filename)[1]
if os.path.exists(tmpname):
filename = tmpname
del tmpname
else:
for ext in ('.ape', '.flac', '.wav', '.mp3'):
tmpname = splitext(filename)[0] + ext
if os.path.exists(tmpname):
filename = tmpname
break
if not os.path.isfile(filename):
raise IOError("Can't not find file: {0}".format(filename))
fstat = os.stat(filename)
atime = fstat.st_atime
mtime = fstat.st_mtime
records[-1]['stop'] = '99:59:59'
if filename.lower().endswith('.flac'):
tmpfile = filename
else:
tmpfile = splitext(filename)[0] + str(random.randint(10000,90000)) + '.flac'
try:
if filename != tmpfile:
ret = subp.call([ffmpeg_exec, '-hide_banner', '-y', '-i', filename,
'-c:a', codec,'-compression_level','12','-f','flac',tmpfile])
if ret != 0:
raise SystemExit('Converting failed.')
for i in records:
output = i['index'] +' - '+ i['title']+'.flac'
commandline = [ffmpeg_exec, '-hide_banner',
'-y', '-i', tmpfile,
'-c', 'copy',
'-ss', i['start'], '-to', i['stop'],
'-metadata', u'title={0}'.format(i['title']),
'-metadata', u'artist={0}'.format(i.get('artist', '')),
'-metadata', u'performer={0}'.format(i.get('artist', '')),
'-metadata', u'album={0}'.format(album),
'-metadata', 'track={0}/{1}'.format(i['index'], len(records)),
'-metadata', u'album_artist={0}'.format(alb_artist),
'-metadata', u'composer={0}'.format(alb_artist),
'-metadata', 'encoder=Meow',
'-write_id3v1', '1',
output]
ret = subp.call(commandline)
if ret == 0:
os.utime(output, (atime, mtime))
finally:
if os.path.isfile(tmpfile):
os.remove(tmpfile)
if os.path.isfile(tmpfile)
以if tmpfile != filename and os.path.isfile(tmpfile)
避免错误删除原始文件。
len(records)>0
。
shntool
在Ubuntu 14.04上
snhtool
缺少mac
(Monkey的音频控制台)可执行文件依赖项,而我能找到的唯一软件包在flacon
PPA中:
sudo add-apt-repository -y ppa:flacon
sudo apt-get update
sudo apt-get install -y flacon shntool
shntool split -f *.cue -o flac -t '%n - %p - %t' *.ape
flacon
是的GUI shntool
,但它随附了所需的所有编解码器...否则出现错误:
shnsplit: warning: failed to read data from input file using format: [ape]
shnsplit: + you may not have permission to read file: [example.ape]
shnsplit: + arguments may be incorrect for decoder: [mac]
shnsplit: + verify that the decoder is installed and in your PATH
shnsplit: + this file may be unsupported, truncated or corrupt
shnsplit: error: cannot continue due to error(s) shown above