MP3-Tag
view release on metacpan or search on metacpan
examples/mp3info2 view on Meta::CPAN
} elsif ('Regexp' eq ref $t) { # do nothing
return $t
} elsif (ref $t) {
die "panic: reference of type `$t' unexpected"
}
# De-utf-ize if possible...
join '', map chr ord, split //, Encode::decode($e, $t);
}
# if ($opt{e} and exists $opt{p} ? 0 == length $opt{p} : 1) {
my $uE = (($ENV{LANG}||'') =~ /\.utf-8$/i and not (${^UNICODE} & 0x20) and not $ENV{"MP3INFO_DECODE_ARGV_DEFAULT_RESET"});
$opt{e} = 15 if ($opt{U} or $uE) and not defined $opt{e};
if ($opt{e}) {
my $skip;
if ($opt{e} =~ /^(\d+)$/ and $1 <= 15 ) {
require Encode;
my $locale;
if ($opt{U}) {
$locale = 'UTF-8';
} else {
$locale = $ENV{LC_CTYPE} || $ENV{LC_ALL} || $ENV{LANG};
if ($^O eq 'os2' and not eval {Encode::resolve_alias($locale)} ) {
require OS2::Process;
$locale = 'cp' . OS2::Process::out_codepage();
}
}
MP3::Tag->reset_encode_decode_config($locale) if $locale and $opt{e} & 0x08;
# warn "LOCALE=$locale: e=$opt{e}";
$skip = !($opt{e} & 1);
# Reinterpret @ARGV
@ARGV = map my_decode($locale, $_), @ARGV if $opt{e} & 4;
# Reinterpret opts
@opt{keys %opt} = map my_decode_deep($locale, $_), values %opt
if $opt{e} & 2;
$opt{e} = $locale;
} elsif ($opt{e} eq 'binary') {
binmode STDOUT;
$skip = 1;
}
binmode STDOUT, ":encoding($opt{e})" if defined $opt{e} and not $skip;
}
my $e_opt = MP3::Tag->get_config('extra_config_keys');
MP3::Tag->config('extra_config_keys', @$e_opt, qw(empty-F-deletes frames_write_creates_dirs));
MP3::Tag->config('empty-F-deletes', 1)
unless defined MP3::Tag->get_config1('empty-F-deletes');
# keys of %opt to the MP3::Tag keywords:
my %trans = ( 't' => 'title',
'a' => 'artist',
'l' => 'album',
'y' => 'year',
'g' => 'genre',
'c' => 'comment',
'n' => 'track' );
# Interprete Escape sequences:
my %r = ( 'n' => "\n", 't' => "\t", '\\' => "\\" );
my ($e_backsl, $e_interp);
if ($opt{E} =~ s/^\+//) {
($e_backsl, $e_interp) = ((split m(/i:), $opt{E}, 2), '');
$e_backsl .= 'p' unless $e_backsl =~ /p/;
$e_interp =~ s/[Fp]//g;
$e_interp .= 'Fp';
} else {
($e_backsl, $e_interp) = ((split m(/i:), $opt{E}, 2), '');
}
for my $e (split //, $e_backsl) {
$opt{$e} =~ s/\\([nt\\])/$r{$1}/g if defined $opt{$e};
}
$e_interp = {map +($_, 1), split //, $e_interp};
if ($opt{'@'}) {
for my $k (keys %opt) {
if (ref $opt{$k}) {
s/\@/%/g for @{ $opt{$k} };
} else {
$opt{$k} =~ s/\@/%/g;
}
}
}
my %F_human = qw( composer TCOM
text_by TEXT
orchestra TPE2
conductor TPE3
track TRCK
disk_n TPOS); # Only most useful, and not -l etc...
my $FNAME = qr/(?: # 1: Whole specifier
\w{4} # 2: Frame name
(?:
\d\d # 3: Frame number
|
(?: \( [^()]* (?:\([^()]+\)[^()]*)* \) )? # 4: Language part
(?: \[ (?: \\. | [^]\\] )* \] )? # 5: Description part
)?
)
/x;
my $FNAME_human = join '|', keys %F_human;
my @set_f;
my %textish = map +($_, 1), qw( _encoding Text Language Description URL );
for my $F (@{ $opt{F} }) {
my ($lead, @s) = ($F =~ /^(\W)/);
if (defined $lead) {
@s = split /\Q$lead$lead$lead/, substr $F, 1;
} else {
@s = $F;
}
for my $s (@s) {
$s =~ /^($FNAME|$FNAME_human|(?:TAGS|ID3v[12])(?=\s+[\?<>]))(?:=|\s+(\??<|>)\s+)(.*)/so
or die "unrecognized part of -F option: `$s'";
my $FF = $F_human{$1} || $1;
push @set_f, [$FF, $3, ($2 || '')];
}
}
my (@del, @del_tag);
for my $o (@{ $opt{d} }) {
my @D;
push @D, $1 while $o =~ s/^ ( $FNAME | ID3v[12] ) (,|$) //xo;
die "Unrecognized part of -d option: `$o'" if length $o;
push @del_tag, grep /^ID3v[12]$/, @D;
push @del, grep !/^ID3v[12]$/, @D;
}
( run in 1.669 second using v1.01-cache-2.11-cpan-71847e10f99 )