summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authormikeos <mike.osipov@gmail.com>2013-07-15 22:38:02 +0400
committermikeos <mike.osipov@gmail.com>2013-07-15 22:38:02 +0400
commitbe22d8c3a6461fe89661e2e0054d27a3481916a8 (patch)
tree992f61c91cb91103686389728e98d20a6517e2c6
parentfedea15a3a8c94ec392d0a1e303483a2e0ab628d (diff)
add cutter
-rw-r--r--cue.py2
-rwxr-xr-xcutter163
2 files changed, 164 insertions, 1 deletions
diff --git a/cue.py b/cue.py
index 8eae2a2..be33d1d 100644
--- a/cue.py
+++ b/cue.py
@@ -104,7 +104,7 @@ def check(count = None, context = None):
class CueParser:
re_timestamp = re.compile("^[\d]{1,3}:[\d]{1,2}:[\d]{1,2}$")
- rem_commands = ('genre', 'data', 'comment')
+ rem_commands = ('genre', 'date', 'comment')
def __init__(self):
def do_set_attr(name, cue = False, track = False, convert = None):
diff --git a/cutter b/cutter
new file mode 100755
index 0000000..5950afc
--- /dev/null
+++ b/cutter
@@ -0,0 +1,163 @@
+#!/usr/bin/python2
+
+from os.path import basename, dirname
+from cue import read_cue
+
+import audiotools
+import audiotools.text as _
+import sys
+
+progname = basename(sys.argv[0])
+
+if sys.version_info.major == 2:
+ class Encoded:
+ def __init__(self, stream):
+ self.stream = stream
+
+ def write(self, msg):
+ self.stream.write(msg.encode("utf-8"))
+
+ def __getattr__(self, attr):
+ return getattr(self.stream, attr)
+
+ sys.stdout = Encoded(sys.stdout)
+ sys.stderr = Encoded(sys.stderr)
+
+def printf(fmt, *args):
+ sys.stdout.write(fmt % args)
+
+def printerr(fmt, *args):
+ msg = fmt % args
+ if msg[-1] != "\n":
+ msg += "\n"
+ sys.stderr.write("** " + progname + ": " + msg)
+
+def quote(s):
+ return s if " " not in s else "\"%s\"" % s
+
+def msf(ts):
+ m = ts / (60 * 75)
+ s = ts / 75 % 60
+ f = ts % 75
+
+ return "%d:%02d:%02d" % (m, s, f)
+
+def print_cue(cue):
+ for k, v in cue.attrs():
+ printf("%s: %s\n", k.upper(), quote(v))
+
+ for file in cue.files():
+ if file.type != "WAVE":
+ continue
+
+ name = "%s/%s" % (cue.path, file.name)
+ try:
+ fp = audiotools.open(name)
+ except IOError:
+ printerr("unable to open file %s", quote(file.name))
+ continue
+ except audiotools.UnsupportedFile:
+ printerr("%s: unsupported file", quote(file.name))
+ continue
+
+ printf("FILE %s (%d/%d, %d ch)\n", quote(file.name),
+ fp.bits_per_sample(), fp.sample_rate(), fp.channels())
+
+ for track in file.tracks():
+ if track.begin is None:
+ continue
+
+ printf("\tTRACK %02d", track.number)
+ title = track.get("title")
+ if title != "":
+ printf(" %s", quote(title))
+ printf(": %s -", msf(track.begin))
+ if track.end is not None:
+ printf(" %s", msf(track.end))
+ printf("\n")
+
+ for k, v in track.attrs():
+ if k not in ("pregap", "postgap", "title"):
+ printf("\t\t%s: %s\n", k.upper(), quote(v))
+
+def parse_args():
+ parser = audiotools.OptionParser(usage = u"Usage: %prog [options] cuefile")
+ parser.add_option(
+ "--ignore",
+ action="store_true",
+ default=False,
+ dest="ignore",
+ help="ignore cue parsing errors")
+
+ parser.add_option(
+ "--dump",
+ action="store_true",
+ default=False,
+ dest="dump",
+ help="print the content of cue file")
+
+ conversion = audiotools.OptionGroup(parser, _.OPT_CAT_ENCODING)
+
+ conversion.add_option(
+ '-t', '--type',
+ action='store',
+ dest='type',
+ choices=sorted(audiotools.TYPE_MAP.keys()),
+ help=_.OPT_TYPE)
+
+ conversion.add_option(
+ '-q', '--quality',
+ action='store',
+ type='string',
+ dest='quality',
+ help=_.OPT_QUALITY)
+
+ conversion.add_option(
+ '-d', '--dir',
+ action='store',
+ type='string',
+ dest='dir',
+ default='.',
+ help=_.OPT_DIR)
+
+ conversion.add_option(
+ '--format',
+ action='store',
+ type='string',
+ default=audiotools.FILENAME_FORMAT,
+ dest='format',
+ help=_.OPT_FORMAT)
+
+ parser.add_option_group(conversion)
+
+ return parser.parse_args()
+
+def main():
+ options, args = parse_args()
+
+ if len(args) != 1:
+ printf("Usage: %s [options] cuefile\n", progname)
+ return 1
+
+ def on_error(err):
+ printerr("%d: %s\n" % (err.line, err))
+ if not options.ignore:
+ raise StopIteration
+
+ try:
+ cue = read_cue(args[0], on_error=on_error)
+ except StopIteration:
+ return 1
+ except Exception as err:
+ printerr("read_cue failed: %s: %s\n", err.__class__.__name__, err)
+ return 1
+
+ cue.path = dirname(args[0]).decode("utf-8")
+
+ if options.dump:
+ print_cue(cue)
+
+ return 0
+
+if __name__ == '__main__':
+ sys.exit(main())