kyillische mp3-Tags nach utf konvertieren
Matthias Taube
no_html.max50kb at nurfuerspam.de
Fre Dez 15 21:14:30 GMT 2006
mailing_lists at gmx.net schrieb:
> Allerdings muss man so jedes tag einzeln konvertieren.
> Daher werde ich mir id3v2 näher anschauen. Wenn möglich würde ich
> nämlich gerne batch-konvertieren.
Ich habe schon vor längerer Zeit dafür ein Perl-Script geschrieben.
Es verwendet Encode::from_to( $tags{$wert}, $opt_ie, "utf8" );
Wobei opt_ie die Input-Encoding ist.
Die entsprechenden Codeausschnitte, für eigene Scripts:
sub lese_tag {
my $file = shift;
unless ( -r $file ) { error("cant read $file\n"); return; }
my ( $basename, $path, $art ) = &basename($file);
unless ( defined $art ) { error("only ogg|flac|mp3 files\n"); return; }
my (
$title, $track, $artist, $album, $comment, $year,
$genre, $part, $sourcemedia, $discid, $encoding
);
my %tags = ();
if ( $art eq "flac" ) {
my $flac = Audio::FLAC->new($file) or return;
my $flacTags = $flac->tags();
foreach ( keys %$flacTags ) {
my $tag = uc($_);
$tags{$tag} = $flacTags->{$_};
}
}
if ( $art eq "ogg" ) {
my $ogg = Ogg::Vorbis::Header->new($file) or return;
my @werte = $ogg->comment_tags;
foreach my $wert (@werte) {
my @inhalte = $ogg->comment($wert);
my $inhalt = shift(@inhalte);
$wert = uc($wert);
$tags{$wert} = $inhalt;
}
}
if ( $art eq "mp3" ) {
my $mp3 = MP3::Tag->new($file) or return;
$mp3->get_tags;
if ( exists $mp3->{ID3v2} ) {
my $id3v2 = $mp3->{ID3v2};
$title = $id3v2->get_frame("TIT2");
$track = $id3v2->get_frame("TRCK");
$artist = $id3v2->get_frame("TPE1");
$album = $id3v2->get_frame("TALB");
my $comment_hash = $id3v2->get_frame("COMM");
if ( defined $comment_hash ) {
my %comments = %{$comment_hash};
$comment = $comments{'Text'};
}
$year = $id3v2->get_frame("TYER");
$genre = $id3v2->get_frame("TCON");
$part = $id3v2->get_frame("TPOS");
$sourcemedia = "mp3"; # $id3v2->get_frame("TMED");
$discid = $id3v2->get_frame( "MCDI", 'raw' );
$encoding = $id3v2->get_frame("TENC");
}
if ( exists $mp3->{ID3v1} ) {
my $id3v1 = $mp3->{ID3v1};
$title = $id3v1->title unless ( defined $title );
$track = $id3v1->track unless ( defined $track );
$artist = $id3v1->artist unless ( defined $artist );
$album = $id3v1->album unless ( defined $album );
$comment = $id3v1->comment unless ( defined $comment );
$year = $id3v1->year unless ( defined $year );
$genre = $id3v1->genre unless ( defined $genre );
}
$mp3->close();
%tags = (
"ALBUM" => $album,
"ARTIST" => $artist,
"COMMENT" => $comment,
"DATE" => $year,
"DISCID" => $discid,
"ENCODING" => $encoding,
"GENRE" => $genre,
"PART" => $part,
"SOURCEMEDIA" => $sourcemedia,
"TITLE" => $title,
"TRACKNUMBER" => $track
);
}
foreach my $wert ( keys %tags ) {
if ( ( not defined $tags{$wert} ) or ( $tags{$wert} eq "" ) ) {
delete $tags{$wert};
}
else {
if ( defined $opt_ie ) {
if ( $opt_ie eq "" ) { $opt_ie = "latin1"; }
Encode::from_to( $tags{$wert}, $opt_ie, "utf8" );
}
}
}
%tags = &check_genre(%tags);
return (%tags);
}
sub schreibe_tag {
my ( $file, %tags ) = @_;
foreach my $wert ( keys %tags ) {
if ( ( not defined $tags{$wert} ) or ( $tags{$wert} eq "" ) ) {
delete $tags{$wert};
}
else {
if ( defined $opt_oe ) {
if ( $opt_oe eq "" ) { $opt_oe = "latin1"; }
Encode::from_to( $tags{$wert}, "utf8", $opt_oe );
}
}
}
%tags = &check_genre(%tags);
unless ( -w $file ) { error("cant write $file\n"); return; }
my ( $basename, $path, $art ) = &basename($file);
unless ( defined $art ) { error("only ogg|flac|mp3 files\n"); return; }
if ( $art eq "ogg" ) {
my $ogg = Ogg::Vorbis::Header->new($file) or return;
foreach my $tag_bezeichnung ( sort keys %tags ) {
my $tag_inhalt = $tags{$tag_bezeichnung};
my @werte = $ogg->comment_tags;
foreach my $wert (@werte) {
if ( $wert =~ m/^$tag_bezeichnung/i ) {
while ( defined $ogg->delete_comment("$wert") ) {
# print "del_comment: $wert\n";
}
}
}
$ogg->add_comments( $tag_bezeichnung, $tag_inhalt );
# print "add_comment $tag_bezeichnung, $tag_inhalt\n";
}
$ogg->write_vorbis;
}
if ( $art eq "flac" ) {
my @zeilen = `metaflac --export-tags-to=- \"$file\"`;
my @zeilen_neu = ();
foreach my $zeile (@zeilen) {
chomp($zeile);
my $zeile_neu = $zeile;
my ( $tag, $inh ) = split( /=/, $zeile, 2 );
if ( ( defined $tag ) and ( defined $inh ) ) {
$tag = uc($tag);
foreach my $tag_bezeichnung ( keys %tags ) {
if ( $tag_bezeichnung eq $tag ) {
$zeile_neu = "";
}
}
if ( $zeile_neu ne "" ) { push @zeilen_neu, $zeile_neu; }
}
}
foreach my $tag_bezeichnung ( sort keys %tags ) {
my $tag_inhalt = $tags{$tag_bezeichnung};
push @zeilen_neu, "$tag_bezeichnung=$tag_inhalt";
}
my $file_name = "$basename.tag";
my $sek = "";
my $tmp_file = "/tmp/" . $sek . $file_name;
while ( -e $tmp_file ) {
$sek = time;
$tmp_file = "/tmp/" . $sek . $file_name;
}
open( TAGFILE, ">$tmp_file" ) or die("$!");
foreach (@zeilen_neu) {
print TAGFILE "$_\n";
}
close(TAGFILE) or die("$!");
`metaflac --remove-all-tags --import-tags-from="$tmp_file" "$file"`;
unlink($tmp_file);
}
if ( $art eq "mp3" ) {
my $album = $tags{ALBUM};
my $artist = $tags{ARTIST};
my $comment = $tags{COMMENT};
my $year = $tags{DATE};
my $discid = $tags{DISCID};
my $encoding = $tags{ENCODING};
my $genre = $tags{GENRE};
my $genre_nr = $tags{GENRE_NR};
my $part = $tags{PART};
my $sourcemedia = $tags{SOURCEMEDIA};
my $title = $tags{TITLE};
my $track = $tags{TRACKNUMBER};
my $mp3 = MP3::Tag->new("$file");
$mp3->get_tags;
$mp3->new_tag("ID3v1") unless ( exists $mp3->{ID3v1} );
my $id3v1 = $mp3->{ID3v1};
$id3v1->album($album) if ( defined $album );
$id3v1->artist($artist) if ( defined $artist );
$id3v1->comment($comment) if ( defined $comment );
$id3v1->year($year) if ( defined $year );
# discid
# encoding
$id3v1->genre($genre) if ( defined $genre );
# genre_nr
# part
# sourcemedia
$id3v1->title($title) if ( defined $title );
$id3v1->track($track) if ( defined $track );
$id3v1->write_tag;
$mp3->new_tag("ID3v2") unless ( exists $mp3->{ID3v2} );
my $id3v2 = $mp3->{ID3v2};
if ( defined $album ) {
$id3v2->remove_frame("TALB");
$id3v2->add_frame( "TALB", $album );
}
if ( defined $artist ) {
$id3v2->remove_frame("TPE1");
$id3v2->add_frame( "TPE1", $artist );
}
if ( defined $comment ) {
$id3v2->remove_frame("COMM");
$id3v2->add_frame( "COMM", "DE", "COMM", $comment );
}
if ( defined $year ) {
$id3v2->remove_frame("TYER");
$id3v2->add_frame( "TYER", $year );
}
if ( defined $discid ) {
$id3v2->remove_frame("MCDI");
$id3v2->add_frame( "MCDI", $discid );
}
if ( defined $title ) {
$id3v2->remove_frame("TIT2");
$id3v2->add_frame( "TIT2", $title );
}
if ( defined $track ) {
$id3v2->remove_frame("TRCK");
$id3v2->add_frame( "TRCK", $track );
}
if ( defined $genre ) {
$id3v2->remove_frame("TCON");
if ( defined $genre_nr ) {
$id3v2->add_frame( "TCON", $genre_nr );
}
else {
$id3v2->add_frame( "TCON", $genre );
}
}
if ( defined $part ) {
$id3v2->remove_frame("TPOS");
$id3v2->add_frame( "TPOS", $part );
}
if ( defined $sourcemedia ) {
$id3v2->remove_frame("TMED");
$id3v2->add_frame( "TMED", $sourcemedia );
}
if ( defined $encoding ) {
$id3v2->remove_frame("TENC");
$id3v2->add_frame( "TENC", $encoding );
}
$id3v2->write_tag();
$mp3->close();
}
}