#!/usr/bin/perl
use strict;

# The Only Cue-Splitter In Existence (Dead Serious)
#   <ed@irc.rizon.net>, MIT-licensed
#   https://ocv.me/dev/?tocsieds.pl
#   ver. 2019-01-14, 21:38

# usage:
#   ./tocsieds.pl < some.cue | bash

# example cuesheet to provide on stdin:
# FILE "Otaku Hardcore Revolution 2019 Day 1 2019-01-12.m4a" WAVE
#   TRACK 01 AUDIO
#     TITLE "SET 00"
#     PERFORMER "Pre-event chiptunes"
#     INDEX 01 00:00:00
#   TRACK 02 AUDIO
#     TITLE "SET 01"
#     PERFORMER "MYXOMOPBL & 4NZU"
#     INDEX 01 17:16:66
#   TRACK 03 AUDIO


##
## CONFIG START

my $ext = 'm4a';  # output file extension

## CONFIG END
##


# [ntr]ack, [tit]le, [prf]ormer, [sec]onds
my %prev;  # previous track in cuesheet
my %curr;  # most recent track in cuesheet

my $infile = undef;  # the file to extract from


# make a string shell-safe
sub esc {
	return $_[0] =~ s/'/'\\''/gr;
}


# output an ffmpeg command based on %prev and %curr
sub gencmd() {
	die 'could not find input filename in cuesheet' unless defined($infile);
	
	if (defined $prev{'sec'}) {
		my $dur = '';
		if (defined $curr{'sec'}) {
			$dur = $curr{'sec'} - $prev{'sec'};
			$dur = sprintf("-t %.2f", $dur);
		}
		
		my $seek = sprintf("%.2f", $prev{'sec'});
		my $tags = "-metadata track='$prev{'ntr'}'";
		my $outfile = "split/$prev{'ntr'}";
		
		if (defined $prev{'prf'}) {
			$tags .= " -metadata artist='$prev{'prf'}'";
			$outfile .= ". $prev{'prf'}";
		}
		
		if (defined $prev{'tit'}) {
			$tags .= " -metadata title='$prev{'tit'}'";
			$outfile .= " - $prev{'tit'}";
		}
		
		print "ffmpeg -nostdin -hide_banner -y -ss $seek -i '$infile' -map 0 -codec copy $dur -map_metadata 0 $tags '$outfile.$ext'\n";
	}
	
	%prev = %curr;
	%curr = ();
}


print "mkdir split\n";

while (<>) {
	if (/^FILE "(.*)" WAVE/) {
		$infile = esc($1);
	}
	if (/^  TRACK ([0-9]+) AUDIO/) {
		gencmd();
		$curr{'ntr'} = $1;
	}
	if (/^    TITLE "(.*)"/) {
		$curr{'tit'} = esc($1);
	}
	if (/^    PERFORMER "(.*)"/) {
		$curr{'prf'} = esc($1);
	}
	if (/^    INDEX 01 ([0-9]+):([0-9]+):([0-9]+)/) {
		$curr{'sec'} = $1 * 60 + $2 + $3 / 75;
	}
}
