#!/usr/bin/perl
#
-# Copyright © 2008,2010,2012,2019 Nick Bowler
+# Copyright © 2008,2010,2012,2020 Nick Bowler
#
# Silly little script to generate an FVWM menu with various bits of MPD
# status information and controls.
use List::Util qw(any max);
use FindBin;
+use lib "$FindBin::Bin";
+use MPDHacks;
+
use constant {
MPD_MJR_MIN => 0,
MPD_MNR_MIN => 21,
my $sock;
my ($albumid, $trackid);
-my %artistids;
-my $menu;
+my ($topmenu, $menu);
my $mode = "top";
-
-# Quotes the argument so that it is presented as a single argument to MPD
-# at the protocol level. This also works OK for most FVWM arguments.
-sub escape {
- my $s = @_[0] // $_;
-
- # No way to encode literal newlines in the protocol, so we
- # convert any newlines in the arguments into a space, which
- # can help with quoting.
- $s =~ s/\n/ /g;
-
- if (/[ \t\\"]/) {
- $s =~ s/[\\"]/\\$&/g;
- return "\"$s\"";
- }
-
- $s =~ s/^\s*$/"$&"/;
- return $s;
-}
+my %artistids;
# Submit a command to the MPD server; each argument to this function
# is quoted and sent as a single argument to MPD.
sub mpd_exec {
- my $cmd = join(' ', map { escape } @_);
+ my $cmd = join(' ', map { MPD::escape } @_);
print $sock "$cmd\n";
}
}
sub fvwm_cmd {
- fvwm_cmd_unquoted(map { escape } @_);
+ fvwm_cmd_unquoted(map { MPD::escape } @_);
}
# Quotes the argument in such a way that it is passed unadulterated by
sub make_submenu {
my $name = shift;
$name =~ s/-/_/g;
- unshift @_, ("exec", $SELF, "--menu=$name");
+ unshift @_, ("exec", $SELF, "--topmenu=$topmenu", "--menu=$name");
fvwm_cmd("DestroyFunc", "Make$name");
fvwm_cmd("AddToFunc", "Make$name");
fvwm_cmd("DestroyMenu", $name);
fvwm_cmd("AddToMenu", $name, "DynamicPopupAction", "Make$name");
- fvwm_cmd("AddToFunc", "KillMenuMPD", "I", "DestroyMenu", $name);
+ fvwm_cmd("AddToFunc", "Kill$topmenu", "I", "DestroyMenu", $name);
fvwm_cmd("DestroyFunc", "Make$name");
fvwm_cmd("AddToFunc", "Make$name");
fvwm_cmd("+", "I", "DestroyMenu", $name);
fvwm_cmd("+", "I", "-PipeRead",
join(' ', map { fvwm_shell_literal } @_));
- fvwm_cmd("AddToFunc", "KillMenuMPD", "I", "DestroyFunc", "Make$name");
+ fvwm_cmd("AddToFunc", "Kill$topmenu", "I", "DestroyFunc", "Make$name");
return ("Popup", $name);
}
my $cover = mpd_cover_filename($file);
$cover = fvwm_shell_literal($cover // $file);
- fvwm_cmd_unquoted("AddToMenu", escape($menu),
- escape($entry->{thumb}),
+ fvwm_cmd_unquoted("AddToMenu", MPD::escape($menu),
+ MPD::escape($entry->{thumb}),
"Exec", "exec", "geeqie", $cover);
}
}
'V|version' => sub { print_version(); exit },
'H|help' => sub { print_help(); exit },
+
+ 'topmenu=s' => \$topmenu, # top menu name (for submenu generation)
) or do { print_usage; exit 1 };
+unless (defined $menu) {
+ $topmenu //= "MenuMPD";
+ $menu = $topmenu . ($mode ne "top" ? $mode : "");
+}
+$topmenu //= $menu;
+
# Connect to MPD.
$sock = new IO::Socket::INET6(
PeerAddr => $host,
my $entry = $matches->{$mbid};
my $thumb = shift @thumbs;
- my @submenu = make_submenu("$menu-$mbid", "--album-id=$mbid");
+ my @submenu = make_submenu("$topmenu-$mbid",
+ "--album-id=$mbid");
fvwm_cmd("AddToMenu", $menu,
$thumb . fvwm_label_escape($entry->{Album}),
@submenu);