fookin perl
#1
Scooby Regular
Thread Starter
Join Date: Nov 2001
Location: Leeds - It was 562.4bhp@28psi on Optimax, How much closer to 600 with race fuel and a bigger turbo?
Posts: 15,239
Likes: 0
Received 1 Like
on
1 Post
fookin perl
Can anyone see if they can get this damn thing to work on windows...
Im fairly sure its down to the abs_path stuff, as it works if I put the script in the folder where the mp3 files are, however if i pass it a folder to work with it doesnt work, nor does it enumerate subfolders..
I also have to do set home=c:\
and set the login details..
Im fairly sure its down to the abs_path stuff, as it works if I put the script in the folder where the mp3 files are, however if i pass it a folder to work with it doesnt work, nor does it enumerate subfolders..
I also have to do set home=c:\
and set the login details..
Code:
#!/usr/bin/perl #use strict; use MP3::Info; use MP3::Tag; use CDDB; use File::Basename; use Cwd qw(abs_path cwd); use Term::ReadLine; use File::Path; my $term = new Term::ReadLine 'mp3cddb'; unless ($term->Features->{preput}) { print q~Error: mp3cddb requires a full featured Term::ReadLine. Either the ::Gnu or ::Perl versions should work ~; exit; } if ($ARGV[0] eq "-h" || $ARGV[0] eq "--help") { print q~ mp3cddb Version 1.0 performs cddb lookups and renaming of mp3s using directories as albums usage: mp3cddb [-h|--help] [-g|--genres] [-n|--nocddb] [-nr|--norename [directory [directory]] --help: print this help message --genres: print out a list of all accepted ID3v1 genres --nocddb: do not try to do any cddb lookup. Useful if the id3 tags are more accurate than the FreeDB data. --norename: do not rename any files, only set ID3 tags directory: a directory containing mp3s that are numerically in track order. if no directory is provided, the current working directory is used. ~; exit; } if ($ARGV[0] eq "-g" || $ARGV[0] eq "--genres") { print "Accepted ID3v1 Genres:\n\n"; print join("\n", sort @{MP3::Tag::ID3v1::genres()}) . "\n"; exit; } my $nocddb = 0; if($ARGV[0] eq "-n" || $ARGV[0] eq "--nocddb") { $nocddb = 1; shift @ARGV; } my $norename = 0; if($ARGV[0] eq "-nr" || $ARGV[0] eq "--norename") { $norename = 1; shift @ARGV; } my %Config; if (open(CONFIG, $ENV{"HOME"} . "/.mp3cddb")) { while (<CONFIG>) { next if (/^(\#.*|\s*)$/); chomp; my ($key, $val) = split(/\s+=\s+/, $_, 2); if (defined $Config{$key}) { print "Error: you have multiple $key declirations in ~/.mp3cddb\n"; exit; } $Config{$key} = $val; } close(CONFIG); if (!$Config{"RENAME"} && !$Config{"DONTRENAME"}) { print "You seem to want me to rename files, yet you don't tell me how to...\n" . "I might be smart, but I can't read your mind..only ~/.mp3cddb\n"; exit; } if($Config{"RENAME"}){ &check_config_rename($Config{"RENAME"}); } if($Config{"RENAMEVA"}){ &check_config_rename($Config{"RENAMEVA"}); } # thanks to irc://irc.openprojects.net/#perl ! # rlandrum: if($var =~ /\{([^\}]+)\}/ && (@x = ($1 =~ m/\%a[aty]/g)) && @x == 1) { # xsdg: perl -e '$txt = "%a - {%b -}%c"; if($txt =~ m#^[^}]* ([^{]* \{ [^}]* \%[^}]+ \})+ [^{}]*$#x){print "moo"}' # xsdg: moo } else { print "you don't seem to have a $ENV{'HOME'}/.mp3cddb config file.\n" . "I am now writing an example one there, be sure to read it and change as needed!\n"; &write_config; exit; } if (! @ARGV) { # ****** DW ******* print "\nSupposed to set path to CWD as you didnt specify anything\n"; push(@ARGV, cwd); } # global hash of what we ended up doing my %result; # global array so that we can re-display errors (in case they get missed) my @errors; my $cddb = new CDDB (Debug=>0, Protocol_Version=>5) or die "unable to connect to CDDB: $!"; # having the complete absolute paths is a GOOD THING my @albums = map { abs_path($_) } @ARGV; ALBUM: foreach my $album (@albums) { next ALBUM unless (-d $album); my @cdtoc; my @cddb_query; my @tracks_in; my %disc_info; print "Working on $album\n"; # wow you really have to quote the hell out of stuff for glob my $quoted = $album; $quoted =~ s/([\[\]])/\\$1/g; foreach my $file (sort { $a=~m!^.*/[^/\d]*(\d+)[^/]+$!; my $c=$1; $b=~m!^.*/[^/\d]*(\d+)[^/]+$!; my $d=$1; $c <=> $d } glob quotemeta($quoted) . "/*.[Mm][Pp]3") { my $info = get_mp3info($file); push (@cdtoc, $info ); push (@tracks_in, basename($file)); } unless ($#tracks_in >= 1) { &do_error("There are 1 or fewer mp3s in '$album'", $album); next ALBUM; } my ($my_disc_id, $my_total_tracks, $my_total_time, @my_frames) = &build_cddb_query(@cdtoc); print "searching for discid: $my_disc_id, total tracks: $my_total_tracks, total time: ". int($my_total_time/60).":".($my_total_time%60)."\n"; my @discs; unless($nocddb) { @discs = $cddb->get_discs($my_disc_id, [@my_frames], $my_total_time); } my $newblank = 0; if (! @discs) { print q~ Disk was not found. Enter a DiscID then Genre (from freedb.org) to use, a url from freedb.org with the DiscID and Genre in it, `blank' to create a blank record, `id3' to aquire data form ID3 tags as a single-artist album, `id3va' to aquire artists from ID3 tags as a various-artist album, or leave empty to skip. ~; my $new_disc_id = $term->readline("DiscID: "); if ($new_disc_id eq "blank") { $newblank = 1; } elsif ($new_disc_id eq "id3") { $newblank = 2; } elsif ($new_disc_id eq "id3va") { $newblank = 3; } elsif (($new_disc_id =~ /^[a-f0-9]{8}$/i) && ((my $new_genre = $term->readline("Genre: ")) ne "")) { @{$discs[0]} = ($new_genre, $new_disc_id, ""); } elsif($new_disc_id =~ /cat=(.+?)\&id=([a-f0-9]{8})/i) { @{$discs[0]} = ($1, $2, ""); } else { &do_error("Skipped directory '$album'", $album); next ALBUM; } } my @ranking; if (!$newblank) { $|=1; # unbuffer output...buffer craps up the status output foreach my $disc (@discs) { print "."; # nice status if there are lots of CD's my ($genre, $cddb_id, $title) = @$disc; $disc_info{"$cddb_id ($genre)"} = $cddb->get_disc_details($genre, $cddb_id); unless($disc_info{"$cddb_id ($genre)"}) { &do_error("Could not find $cddb_id ($genre) for '$album'", $album); next ALBUM; } $disc_info{"$cddb_id ($genre)"}->{'dgenre'} ||= $genre; } print "\n"; # end status stuff $|=0; # can buffer again push (@my_frames, $my_total_time * 75); my @my_lengths = &offsets_to_seconds (@my_frames); my %distance; foreach my $cddb_id (sort keys %disc_info) { my $disc_time = ($disc_info{$cddb_id}->{'disc length'} =~ /(\d+)/)[0]; my $disc_id = $disc_info{$cddb_id}->{'discid'}; my @track_offsets = @{$disc_info{$cddb_id}->{'offsets'}}; push (@track_offsets, $disc_time * 75 + $track_offsets[0]); my @track_lengths = &offsets_to_seconds (@track_offsets); $distance{$cddb_id} = &sqr_distance (\@track_lengths, \@my_lengths); } @ranking = sort { $distance{$a} <=> $distance{$b} } keys %distance; } elsif($newblank == 1) { $disc_info{"new"}->{'dtitle'} = ""; foreach my $i (0..$#tracks_in) { $disc_info{"new"}->{'ttitles'}[$i] = ""; } @ranking = ("new"); } elsif($newblank == 2 || $newblank == 3) { $disc_info{"new"} = get_id3tags($album, ($newblank==3), @tracks_in); @ranking = ("new"); } if (my $choice = &prompt_best ($album, \@ranking, \%disc_info, \@tracks_in)) { &tag_files ($album, $disc_info{$choice}, \@tracks_in); $result{$album} = "tagged"; if ($Config{'DORENAME'} && !$norename) { if (&do_rename ($album, $disc_info{$choice}, \@tracks_in)) { $result{$album} .= " and renamed"; } } } else { print "skipping $album, moving on\n\n\n"; $result{$album} = "skipped"; } } print "Summary of actions:\n"; foreach my $album ( sort keys %result ) { print "$result{$album}\t $album\n"; } if (@errors) { print "\n\nThere seem to have been some errors:\n\n"; print "$_\n\n" foreach @errors; } exit; #################### # # # My subroutines # # # # influenced by # # Thomas Geffert's # # tagit.pl # #################### sub get_id3tags { my ($album, $va, @tracks_in) = @_; my $info; my $mp3 = MP3::Tag->new($album."/".$tracks_in[0]); my @temp = $mp3->autoinfo(); $info->{'dtitle'} = $temp[2]." / ".$temp[3]; $info->{'dyear'} = $temp[5]; $info->{'dgenre'} = $temp[6]; $info->{'comment'} = $temp[4]; $mp3->close(); foreach my $i (0..$#tracks_in) { my $mp3 = MP3::Tag->new($album."/".$tracks_in[$i]); my @temp = $mp3->autoinfo(); if($va) { $info->{'ttitles'}[$i] = $temp[2]." / ".$temp[0]; } else { $info->{'ttitles'}[$i] = $temp[0]; } $mp3->close(); } return $info; } # prints the error and adds it to the global array of errors # if $album is defined, it's a fatal error for that album and $result is updated as such sub do_error { my ($error, $album) = @_; print "$error\n\n\n"; push(@errors, $error); $result{$album} = "error"; } sub check_config_rename { my $rename=shift; unless ($rename =~ m! ^(?: # each start can be anything not special [^{}%]* # test to make sure {}'s match and has only 1 proper %tag (?: \{ [^{}%]* \% (?:a[tagy]|t[abnt]) [^{}%]* \} | # or test just proper %tag not in {}'s \% (?:a[tagy]|t[abnt]) ) )+ # end can be anything not special [^{}%]* $ !oix) # had enough RegEx fun for today? =) { print qq!You seem to have a bad RENAME[VA] line in ~/.mp3cddb. Please check: You have matching {}\'s You have only 1 %tag inside of each {} You are using the apropriate tags (%at, %ta, etc) !; exit; } if ($rename =~ m/\%t[abnt].*\//i) { print q!RENAME[VA] contains track-specific data (ta, tb, tn, tt) inside of a directory name. This will break the renaming, please limit directory names to whole-album data !; exit; } } sub do_rename { my ($album, $info, @tracks) = (shift, shift, @{+shift}); my ($new_dir, @new_files) = &new_names ($album, $info, \@tracks); if (&make_path($new_dir, $album)) { foreach my $num (0 .. $#tracks) { unless( rename "$new_dir/$tracks[$num]", "$new_dir/$new_files[$num]" ) { &do_error("Couldn't move '$album/$tracks[$num]' to\n'$new_dir/$new_files[$num]'\nReason: $!", $album); return undef; } } } else { #make_path errored or something return undef; } return 1; } sub make_path { my ($new_path, $old_path) = @_; return 1 if $new_path eq $old_path; mkpath(dirname($new_path), 0, 755); if ( -d $new_path ) { # $new_path already exists, lets move everything into it and get rid of $old_path my $album_glob = $old_path; $album_glob =~ s/(\s)/\\$1/oig; foreach my $file (glob("$album_glob/*")) { unless( rename $file, "$new_path/" . basename($file) ) { &do_error("Couldn't move '$file' to '$new_path/" . basename($file) . "'\nReason: $!", $old_path); return undef; } } if (glob("$album_glob/*")) { &do_error("There seems to be something left in '$old_path', yet it should be empty"); } else { unless( rmdir($old_path) ) { &do_error("Couldn't remove empty '$old_path'\nReason: $!"); } } } else { # $new_path doesn't exist, so we can just rename old to new and be done unless( rename $old_path, $new_path ) { &do_error("Couldn't move '$old_path' to '$new_path'\nReason: $!", $old_path); return undef; } } return 1; } # For my own reference # %at: Album Title # %aa: Album Artist # %ag: Album Genre # %ay: Album Year # %ac: Album Comment # %tn: Track Number (padded to 2 characters, 01..10..99) # %tt: Track Title # %ta: Track Artist (always set) # %tb: Track Artist (only set if different from Album) # {.*(%..).*}: optional block # %%, %{, %}: replaced by %, {, and } sub new_names { my ($album, $info, @tracks) = (shift, shift, @{+shift}); my @renamed; my %tag_info; # for %%, %{, and %} $tag_info{'%'} = '%'; $tag_info{'{'} = '{'; $tag_info{'}'} = '}'; # get whole-album vars ($tag_info{'aa'}, $tag_info{'at'}) = &split_title($info->{'dtitle'}); $tag_info{'ag'} = $info->{'dgenre'}; $tag_info{'ay'} = $info->{'dyear'}; $tag_info{'ac'} = $info->{'comment'}; my ($new_dir, $new_file); if($info->{'NoVA'} || !$Config{'RENAMEVA'}){ $Config{'RENAME'} =~ /^(.*?)(?:\/)?([^\/]+)$/o; ($new_dir, $new_file) = ($1, $2); } else { $Config{'RENAMEVA'} =~ /^(.*?)(?:\/)?([^\/]+)$/o; ($new_dir, $new_file) = ($1, $2); } if ($new_dir) { foreach my $key (keys %tag_info) { $tag_info{$key} =~ tr!\/\\\:\?\"|\*!-!; $tag_info{$key} =~ tr!<>![]!; $tag_info{$key} =~ tr! !_! if $Config{'UNDERSCORE'}; } # only album stuff (a[tagy]) is allowed in the dir name $new_dir =~ s! (?: \{ ([^%{}]*) \% (a[tagy]|[%{}]) ([^%{}]*) \} | ([^%{}]*) \% (a[tagy]|[%{}]) ([^%{}]*) ) ! ( $5 ? $4.$tag_info{$5}.$6 : ( $tag_info{$2} ? $1.$tag_info{$2}.$3 : '' ) )!xoge; # if it's complete (starts with /) it's fine, otherwise complete it from $album unless($new_dir =~ /^\//o) { $new_dir = dirname($album) . "/" . $new_dir; } } else { # if there's no new directory in the config, just use $album $new_dir = $album; } foreach my $tNumber (0 .. $#tracks) { $tag_info{'tn'} = sprintf("%02u", $tNumber + 1); if($info->{'NoVA'}) { ($tag_info{'tb'}, $tag_info{'tt'}) = (undef, $info->{'ttitles'}[$tNumber]); } else { ($tag_info{'tb'}, $tag_info{'tt'}) = &split_title($info->{'ttitles'}[$tNumber]); } # ta is always set, tb sometimes (VA cds) $tag_info{'ta'} = $tag_info{'tb'} || $tag_info{'aa'}; # we have to do this each time to hit the new track info foreach my $key (keys %tag_info) { $tag_info{$key} =~ tr!\/\\\:\?\"|\*!-!; $tag_info{$key} =~ tr!<>![]!; $tag_info{$key} =~ tr! !_! if $Config{'UNDERSCORE'}; } my $newname = $new_file; unless($newname =~ /\.\S{1,3}$/o) { $newname .= ".mp3"; } $newname =~ s! (?: \{ ([^%{}]*) \% (a[tagy]|t[abnt]|[%{}]) ([^%{}]*) \} | ([^%{}]*) \% (a[tagy]|t[abnt]|[%{}]) ([^%{}]*) ) ! ( $5 ? $4.$tag_info{$5}.$6 : ( $tag_info{$2} ? $1.$tag_info{$2}.$3 : '' ) )!xoge; push(@renamed, $newname); } return $new_dir, @renamed; } sub tag_files { my ($album, $info, @tracks) = (shift, shift, @{+shift}); my ($aArtist, $aTitle) = &split_title($info->{'dtitle'}); foreach my $tNumber (0 .. $#tracks) { my ($tArtist, $tTitle); if($info->{'NoVA'}) { $tTitle = $info->{'ttitles'}[$tNumber]; } else { ($tArtist, $tTitle) = &split_title($info->{'ttitles'}[$tNumber]); } # if there's a track artist, use it...otherwise use album artist $tArtist ||= $aArtist; my $mp3 = MP3::Tag->new($album . "/" . $tracks[$tNumber]); $mp3->get_tags(); if ($Config{"DELID3V1"} && exists $mp3->{ID3v1}) { $mp3->{ID3v1}->remove_tag(); } if ($Config{"DELID3V2"} && exists $mp3->{ID3v2}) { $mp3->{ID3v2}->remove_tag(); } if ($Config{"ID3V1"}) { # remove_tag on ID3v1 doesn't actually remove it, just blanks it.. #so we don't have to worry about recreating it $mp3->new_tag("ID3v1") unless exists $mp3->{ID3v1}; $mp3->{ID3v1}->song($tTitle); $mp3->{ID3v1}->artist($tArtist); $mp3->{ID3v1}->album($aTitle); $mp3->{ID3v1}->comment($info->{'comment'}) if $info->{'comment'}; $mp3->{ID3v1}->year($info->{'dyear'}) if $info->{'dyear'}; $mp3->{ID3v1}->genre($info->{'dgenre'}) if $info->{'dgenre'}; $mp3->{ID3v1}->track($tNumber + 1); $mp3->{ID3v1}->write_tag(); } if ($Config{"ID3V2"}) { # remove_tag on ID3v2 actually destorys the tag, so we have to re-create it when we delete it $mp3->new_tag("ID3v2") unless exists $mp3->{ID3v2} && !$Config{"DELID3V2"}; my $frameID = $mp3->{ID3v2}->get_frame_ids; # remove frame (does nothing if it doesn't exist) and then add new one $mp3->{ID3v2}->remove_frame("TIT2"); $mp3->{ID3v2}->add_frame("TIT2", $tTitle); # artist could be either TPE1 or TPE2, so nuke both $mp3->{ID3v2}->remove_frame("TPE1"); $mp3->{ID3v2}->remove_frame("TPE1"); $mp3->{ID3v2}->add_frame("TPE1", $tArtist); $mp3->{ID3v2}->remove_frame("TALB"); $mp3->{ID3v2}->add_frame("TALB", $aTitle); $mp3->{ID3v2}->remove_frame("COMM"); $mp3->{ID3v2}->add_frame("COMM", "ENG", "Comment", $info->{'comment'}) if $info->{'comment'}; $mp3->{ID3v2}->remove_frame("TYER"); $mp3->{ID3v2}->add_frame("TYER", $info->{'dyear'}) if $info->{'dyear'}; $mp3->{ID3v2}->remove_frame("TCON"); $mp3->{ID3v2}->add_frame("TCON", $info->{'dgenre'}) if $info->{'dgenre'}; $mp3->{ID3v2}->remove_frame("TRCK"); $mp3->{ID3v2}->add_frame("TRCK", ($tNumber + 1) ); $mp3->{ID3v2}->write_tag(); } } } sub prompt_best { my $album = shift; my @ranking = @{+shift}; my %disc_info = %{+shift}; my @tracks_in = @{+shift}; my $current = $ranking[0]; SELECT: while (1) { if ($#ranking) { print "\nMore than one possible matches are available.\n" . "The following is a list of all possible ones, sorted by my best guess:\n"; foreach my $choice_num (0 .. $#ranking) { print join("\t", '', $choice_num + 1, $disc_info{$ranking[$choice_num]}->{'dgenre'}, $disc_info{$ranking[$choice_num]}->{'dtitle'}, $disc_info{$ranking[$choice_num]}->{'discid'}) . "\n"; } print "\nThis is my best guess or your current selection:\n\n"; } else { print "\nHere is the only available match:\n\n"; } my $var_artist = &print_info($disc_info{$current}); if($var_artist) {$disc_info{$current}->{'NoVA'} = 0;} else {$disc_info{$current}->{'NoVA'} = 1;} while (1) { print "\nChoices:\nUse this match (Y)\n"; print "View a different match (1-" . ($#ranking + 1) . ")\n" if $#ranking; print "Edit album info (e)\n"; print "Edit track listing (t)\n"; print "Show example renamed filenames (s)\n" if $Config{'DORENAME'}; print "Disregard this album entirely (n)\n"; print "This appears to be a Various Artist CD, select (a) if the artist (1st) " . "and track name (2nd) to be switched or (v) if this really isn't a VA cd.\n" if $var_artist; my $key = $term->readline("? "); if ($key =~ /^y$/oi || $key eq "") { return $current; } elsif (1 <= $key && $key <= ($#ranking + 1)) { $current = $ranking[$key - 1]; next SELECT; } elsif ($key =~ /^n$/oi) { return undef; } elsif ($key =~ /^e$/oi) { &edit_disc ($disc_info{$current}); next SELECT; } elsif ($key =~ /^t$/oi) { &edit_track ($disc_info{$current}); next SELECT; } elsif ($key =~ /^s$/oi) { my($new_dir, @renamed) = &new_names ($album, $disc_info{$current}, \@tracks_in); foreach my $file (@renamed) { print "$new_dir/$file\n"; } } elsif ($var_artist && $key =~ /^a$/oi) { &swap_titles ($disc_info{$current}); next SELECT; } elsif ($var_artist && $key =~ /^v$/oi) { $disc_info{$current}->{'NoVA'} = 1; next SELECT; } } } } sub edit_disc { my ($info) = @_; my ($artist, $real_title) = &split_title($info->{'dtitle'}); my ($input1, $input2); $input1 = $term->readline("Artist: ",$artist); $input2 = $term->readline("Title: ",$real_title); $info->{'dtitle'} = $input1 . " / " . $input2; print "Make sure this matches the --genres list to be able to write to ID3V1 tags\n"; $info->{'dgenre'} = $term->readline("Genre: ",$info->{'dgenre'}); $info->{'dyear'} = $term->readline("Year: ",$info->{'dyear'}); $info->{'comment'} = $term->readline("Comment ", $info->{'comment'}); } sub edit_track { my ($info) = @_; foreach my $track_number (0 .. $#{$info->{'ttitles'}}) { my ($track_artist, $track_title); if($info->{'NoVA'}) { $track_title = $info->{'ttitles'}[$track_number]; } else { ($track_artist, $track_title) = &split_title($info->{'ttitles'}[$track_number]); } if ($track_artist || $info->{'prompt'}) { $track_artist = $term->readline("Track " . ($track_number + 1) .". Artist ", $track_artist); } $track_title = $term->readline("Track " . ($track_number + 1) .". Title ", $track_title); $info->{'ttitles'}[$track_number] = ($track_artist?"$track_artist / " :'') . $track_title; } } sub print_info { my ($info) = @_; my ($artist, $real_title) = &split_title($info->{'dtitle'}); my $var_artist = 0; print "Artist:\t$artist\nTitle:\t$real_title\n"; print "Year:\t$info->{'dyear'}\n" if $info->{'dyear'}; print "Genre:\t$info->{'dgenre'}\n" if $info->{'dgenre'}; print "Comment:\t$info->{'comment'}\n" if $info->{'comment'}; my @track_titles = @{$info->{'ttitles'}}; foreach my $track_number (0 .. $#track_titles) { my ($artist, $title); if($info->{'NoVA'}) { $title = $track_titles[$track_number]; } else { ($artist, $title) = &split_title($track_titles[$track_number]); } printf "%2d. %-40s%-s\n", ($track_number + 1), ($artist?$artist:$title), ($artist?$title:''); $var_artist = 1 if $artist; } return $var_artist; } sub swap_titles { my ($info) = @_; foreach my $track_number (0 .. $#{$info->{'ttitles'}}) { my ($artist, $title) = &split_title($info->{'ttitles'}[$track_number]); $info->{'ttitles'}[$track_number] = "$title / $artist" if $artist; } } sub split_title { local $_ = shift; my ($artist, $title); if (/(.*?)\s*\/\s*(.*)/) { ($artist, $title) = ($1, $2) } elsif (/(.*?)\s+-+\s+(.*)/) { ($artist, $title) = ($1, $2) } else { ($artist, $title) = (undef, $_) } for ($artist, $title) { s/^\s*//; s/\s*$// } return ($artist, $title); } ####################### # # # CDDB Lookup Stuff # # # # by Meng Weng Wong # ####################### sub sqr_distance { my @vector1 = @{+shift}; my @vector2 = @{+shift}; my $total = 0; foreach my $dimension (0 .. ($#vector1 < $#vector2 ? $#vector1 : $#vector2)) # too much paranoia never hurt anyone { my $difference = abs($vector1[$dimension] - $vector2[$dimension]); my $square = $difference ** 2; $total += $square; } return $total; } sub frames_to_ss { my $frames = shift; my $ss = int($frames / 75); return $ss; } sub ss_to_mmss { my $ss = shift; my $mm = $ss / 60; $ss = $ss % 60; return sprintf ("%02d:%02d", $mm, $ss); } sub offsets_to_seconds { my @offsets = @_; my @track_lengths = (); while (@offsets > 1) { unshift(@track_lengths, pop (@offsets) - $offsets[-1]); } return map { &frames_to_ss ($_) } @track_lengths; } sub build_cddb_query { my @cdtoc = @_; my $count = 1; foreach (@cdtoc) { my ($mm, $ss) = ($_->{MM}, $_->{SS}); } my $discid = cddb_discid(@cdtoc); my @frames = &invent_frame_numbers(@cdtoc); my $total_time = &total_time(@cdtoc); my $total_tracks = @cdtoc; my $login = $ENV{USER}; my $hostname = &hostname; use Sys::Hostname; $hostname = `hostname` if $hostname !~ /\./; my $client_name = "mp3cddb"; my $client_version = "beta"; return ( $discid, $total_tracks, $total_time, @frames ); } sub cddb_sum { my ($n, $ret) = (shift, 0); for (split //, $n) { $ret += $_ } return $ret; } sub total_time { my @cdtoc = @_; my $total_time = 0; foreach my $track (@cdtoc) { my $track_time = $track->{MM} * 60 + $track->{SS}; $total_time += $track_time; } return $total_time; } sub cddb_discid { my @cdtoc = @_; my $n = 0; my $total_time = 0; foreach my $track (@cdtoc) { my $track_time = $track->{MM} * 60 + $track->{SS}; $n += &cddb_sum($total_time); $total_time += $track_time; } return sprintf("%08x", ($n % 0xFF) << 24 | $total_time << 8 | @cdtoc); } sub invent_frame_numbers { my @cdtoc = @_; my $n = 0; my $total_time = 0; foreach my $track (@cdtoc) { $track->{FRAME_OFFSET} = $total_time * 75; my $track_time = $track->{MM} * 60 + $track->{SS}; $total_time += $track_time; } return map { $_->{FRAME_OFFSET} } @cdtoc; } ################################### # # # Write the example config file # # # ################################### sub write_config{ open(WRITE, ">" . $ENV{"HOME"} . "/.mp3cddb") || die "couldn't write example config file!"; print WRITE q~# mp3cddb example configuration file # YOU MUST ENABLE ONE OF THE RENAME LINES OR ELSE THE PROGRAM WILL NOT RUN! # to enable one of the lines remove the # (comment) from before it, or add your own to the bottom # options are 1 for true, 0 for false # ID3V1 / ID3V2: write ID3 V1/2 tags ID3V1 = 1 ID3V2 = 1 # DELID3V1 / DELID3V2: delete any existing ID3 V1/2 # if both this and above are set, then it will remove any existing tag and write a new clean one DELID3V1 = 0 DELID3V2 = 0 # DORENAME: Rename the Files DORENAME = 1 # UNDERSCORE: convert all spaces to underscores in file names UNDERSCORE = 0 # RENAME: defines how to rename the files / directory # Available variables: # %at: Album Title # %aa: Album Artist # %ag: Album Genre # %ay: Album Year # %ac: Album Comment # %tn: Track Number (padded to 2 characters, 01..10..99) # %tt: Track Title # %ta: Track Artist (always set) # %tb: Track Artist (only set if different from Album) # In case you actually want a literal %, {, or } there are the following: # %%, %{, %}: replaced by %, {, and } # You can make a portion optional by enclosing in within {}, for example: # %aa - {%ay - }%at # Will write either "Artist - Title" or "Artist - Year - Title" # NOTE: do NOT put more than one variable within a single {}! # Here are a few examples, showing options and how directories are handled # READ THROUGH ALL OF THEM to get an idea of how exactly you want yours to be # hint: just look for the output that closest resembles your current output! # Each example shows the results on the following 2 files: # /mp3s/New Downloads/into the unknown-Bad_religion-aps/01-its_only_over_when-bad_religion-aps.mp3 # /mp3s/Ska/VA-Ska_Sucks/Ska Sucks- 01- Dance Hall Crashers- He Wants Me Back.mp3 # 1. Ignore directories: if RENAME has no directory info, only the files # inside a directory are renamed # Very simple #RENAME = %tn - %tt # /mp3s/New Downloads/into the unknown-Bad_religion-aps/01 - Its Only Over When.mp3 # /mp3s/Ska/VA-Ska_Sucks/01 - He Wants Me Back.mp3 # Show artist only when different from album #RENAME = %tn - {%tb - }%tt # /mp3s/New Downloads/into the unknown-Bad_religion-aps/01 - Its Only Over When.mp3 # /mp3s/Ska/VA-Ska_Sucks/01 - Dance Hall Crashers - He Wants Me Back.mp3 # Always shows artist #RENAME = %tn - %ta - %tt # /mp3s/New Downloads/into the unknown-Bad_religion-aps/01 - Bad Religion - Its Only Over When.mp3 # /mp3s/Ska/VA-Ska_Sucks/01 - Dance Hall Crashers - He Wants Me Back.mp3 # 2. Rename directory: if RENAME has some directory information, then then the # directory above the files will also be renamed. if RENAME contains more # than one directory, it will create the extra ones # Again, simple example: #RENAME = %aa - %at/%tn - %tt # /mp3s/New Downloads/Bad Religion - Into the Unknown/01 - Its Only Over When.mp3 # /mp3s/Ska/VA - Ska Sucks/01 - He Wants Me Back.mp3 # Show year, if it's defined #RENAME = %aa - {%ay - }%at/%tn - %tt # /mp3s/New Downloads/Bad Religion - 1983 - Into the Unknown/01 - Its Only Over When.mp3 # /mp3s/Ska/VA - Ska Sucks/01 - He Wants Me Back.mp3 # More than one directory: #RENAME = %aa/%at/%tn - %tt # /mp3s/New Downloads/Bad Religion/Into the Unknown/01 - Its Only Over When.mp3 # /mp3s/Ska/VA/Ska Sucks/01 - He Wants Me Back.mp3 # Combination with more than 1 directory, optional year, optional track artist #RENAME = %aa/{%ay - }%at/%tn - {%tb - }%tt # /mp3s/New Downloads/Bad Religion/1983 - Into the Unknown/01 - Its Only Over When.mp3 # /mp3s/Ska/VA/Ska Sucks/01 - Dance Hall Crashers - He Wants Me Back.mp3 # 3. Absolute directory: if RENAME is an absolute directory, then the # directory is moved to the proper location # Again, simple example: #RENAME = /mp3s/%aa - %at/%tn - %tt # /mp3s/Bad Religion - Into the Unknown/01 - Its Only Over When.mp3 # /mp3s/VA - Ska Sucks/01 - He Wants Me Back.mp3 # All of the above exactly, just add a /something to the front of them... # My personal format: #RENAME = /mp3s/%ag/%aa - {%ay - }%at/%tn - {%tb - }%tt # /mp3s/Punk/Bad Religion - 1983 - Into the Unknown/01 - Its Only Over When.mp3 # /mp3s/Ska/VA - Ska Sucks/01 - Dance Hall Crashers - He Wants Me Back.mp3 ~; close(WRITE); }
Last edited by David_Wallis; 17 June 2006 at 07:05 PM.
#2
Scooby Regular
Havent used perl for years but do you have a /.mp3cddb specified?
The script should create one for you as thats where it pucks up the $env bit from, if it isnt doing it might be a problem with permission and not being able to write to the folder.
Have you had any error message and what version of activestate perl are you using?
The script should create one for you as thats where it pucks up the $env bit from, if it isnt doing it might be a problem with permission and not being able to write to the folder.
Have you had any error message and what version of activestate perl are you using?
Thread
Thread Starter
Forum
Replies
Last Post