Skip to content

Commit

Permalink
Let icewmbg interpret command-line arguments relative to the current …
Browse files Browse the repository at this point in the history
…working directory for issue #497. Let icewmbg accept additional arguments as images or directories. Add -f,--fork option to icewmbg. Add --postpreferences option to icewmbg.
  • Loading branch information
gijsbers committed Sep 27, 2023
1 parent 210fff6 commit 1186863
Show file tree
Hide file tree
Showing 4 changed files with 128 additions and 37 deletions.
1 change: 1 addition & 0 deletions man/icesh.pod
Original file line number Diff line number Diff line change
Expand Up @@ -784,6 +784,7 @@ Let icewm refresh the desktop background.
=item B<guievents>

Monitor the B<ICEWM_GUI_EVENT> property and report all changes.
Hit C<Ctrl+C> to abort this and continue with the next command.

=item B<delay> [I<time>]

Expand Down
8 changes: 4 additions & 4 deletions man/icewm-menu.pod
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,7 @@ L<xde-menu(1)>, L<xdgmenumaker(1)>.

=head2 FORMAT

The format of the file contains one of the following line syntax:
The file contains lines with the following syntax:

=over

Expand Down Expand Up @@ -58,8 +58,8 @@ them at this point in the menu.

=item B<menuprog> [B<">]I<title>[B<">] I<icon> I<program> I<options>

Specifies a program that will print sub-menu items on standard output
and will be collected and placed in the sub-menu at this point.
Specifies a program that will print sub-menu items on standard output,
which will be collected and placed in the sub-menu at this point.

=item B<menuprogreload> [B<">]I<title>[B<">] I<icon> I<timeout>
I<program> I<options>
Expand Down Expand Up @@ -116,7 +116,7 @@ file that will be run in response to selecting the menu item.
When used with the B<menuprog> keyword, the I<program> must print on
standard output the contents of the menu and is used for dynamic menus.

I<options> is the options and arguments passed to the I<program>
I<options> are the options and arguments passed to the I<program>
verbatim.

=item I<filename>
Expand Down
23 changes: 17 additions & 6 deletions man/icewmbg.pod
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@

=head2 SYNOPSIS

B<icewmbg> [I<OPTIONS>]
B<icewmbg> [I<OPTIONS>] [I<ARGUMENTS>]

=head2 DESCRIPTION

Expand Down Expand Up @@ -36,7 +36,7 @@ conclude that it can safely exit after setting the desktop background,
to free its system memory. If the screen size changes, icewm will then
attempt to restart icewmbg, preferably via icewm-session.

=head2 OPTIONS
=head2 ARGUMENTS

=head2 SPECIFIC OPTIONS

Expand All @@ -52,6 +52,10 @@ or they may start with a tilde or environment variable.

=over

=item B<-f>, B<--fork>

Fork into the background and detach from the terminal.

=item B<-p>, B<--replace>

Replace an existing B<icewmbg>. If there is a running B<icewmbg>,
Expand Down Expand Up @@ -128,6 +132,10 @@ This overrules the C<CycleBackgroundsPeriod> preference.
Redirect all output to I<FILE>.
A leading tilde or environment variable is expanded.

=item B<--postpreferences>

Print a list of all preference values that B<icewmbg> will use.

=back

=head2 GENERAL OPTIONS
Expand Down Expand Up @@ -159,10 +167,13 @@ Use a slow synchronous mode to communicate with the I<X11> server.

Report on some of the activities.

=back

=head2 FILES

Additional arguments, which either are a path or which have an image
extension, are assumed to be background image files or directories.

=back

=head2 PREFERENCES

By default B<icewmbg> loads settings from the L<icewm(1)>
Expand Down Expand Up @@ -215,11 +226,11 @@ What happens for their combination is given by the following table:

# For four unique desktop backgrounds for four workspaces do:

icewmbg -p -i image0,image1,image2,image3 &
icewmbg -f -p -i image0,image1,image2,image3

# Or create a directory with the four images and do:

icewmbg -p -i /path/to/directory &
icewmbg -f -p -i /path/to/directory

# The images should have proper image filename extensions.

Expand Down
133 changes: 106 additions & 27 deletions src/icewmbg.cc
Original file line number Diff line number Diff line change
Expand Up @@ -49,6 +49,7 @@ class Background: public YXApplication, private YTimerListener {
void add(const char* name, const char* value, bool append);
bool become(bool replace = false);
void update(bool force = false);
void printOptions();
void sendQuit() { sendClientMessage(_XA_ICEWMBG_QUIT); }
void sendRestart() { sendClientMessage(_XA_ICEWMBG_RESTART); }
void sendShuffle() { sendClientMessage(_XA_ICEWMBG_SHUFFLE); }
Expand Down Expand Up @@ -896,6 +897,32 @@ bool Background::become(bool replace) {
return pid == mypid;
}

void Background::printOptions() {
for (cfoption* o = icewmbg_prefs; o && o->type; ++o) {
switch (o->type) {
case cfoption::CF_BOOL:
printf("%-26s = %d\n", o->name, *o->v.b.bool_value);
break;
case cfoption::CF_INT:
printf("%-26s = %d\n", o->name, *o->v.i.int_value);
break;
default:
/*ignore*/
break;
}
}
printf("%-26s = ", "DesktopBackgroundImage");
int i = 0;
for (auto s : backgroundImages)
printf("%s%s", i++ ? ", " : "", s.c_str());
printf("\n");
printf("%-26s = ", "DesktopTransparencyImage");
i = 0;
for (auto s : transparencyImages)
printf("%s%s", i++ ? ", " : "", s.c_str());
printf("\n");
}

static const char* get_help_text() {
return _(
"Usage: icewmbg [OPTIONS]\n"
Expand Down Expand Up @@ -984,7 +1011,7 @@ static void bgParse(const char* name, const char* value) {
for (int i = 0; str.splitall(',', &opt, &str); ++i) {
if (i + 1 < ICEBG_MAX_ARGS) {
if ((opt = opt.trim()).nonempty()) {
globalBg->add(name, opt, 0 < i);
globalBg->add(name, opt, true);
}
}
}
Expand Down Expand Up @@ -1042,20 +1069,39 @@ static bool sendMessage(const char* displayArg, const char* text) {
return success;
}

static void appendFile(YArray<const char*>& image, const char* value) {
if (nonempty(value)) {
if (strchr("$/~", *value) == nullptr && access(value, R_OK) == 0) {
char buf[1234] = "";
char* pwd = getcwd(buf, sizeof buf);
if (pwd == buf && strlen(pwd) + strlen(value) + 2 < sizeof buf) {
strlcat(buf, "/", sizeof buf);
strlcat(buf, value, sizeof buf);
image += newstr(buf);
}
} else {
image += value;
}
}
}

int main(int argc, char **argv) {
ApplicationName = my_basename(*argv);

bool daemonize = false;
bool sendRestart = false;
bool sendQuit = false;
bool postpref = false;
bool replace = false;
bool shuffle = false;
bool verbose = false;
const char* overrideTheme = nullptr;
const char* configFile = nullptr;
const char* image = nullptr;
const char* color = nullptr;
const char* trans = nullptr;
const char* semis = nullptr;
typedef YArray<const char*> ArgVector;
ArgVector image;
ArgVector color;
ArgVector trans;
ArgVector semis;
const char* center = nullptr;
const char* scaled = nullptr;
const char* multi = nullptr;
Expand All @@ -1071,6 +1117,9 @@ int main(int argc, char **argv) {
sendRestart = true;
**arg = '\0';
}
else if (is_switch(*arg, "f", "fork")) {
daemonize = true;
}
else if (is_switch(*arg, "q", "quit")) {
sendQuit = true;
}
Expand All @@ -1081,6 +1130,10 @@ int main(int argc, char **argv) {
(arg + 1 == argv + argc || strcspn(arg[1], "01")))
{
shuffle = true;
shuffleArg = "1";
}
else if (is_long_switch(*arg, "postpreferences")) {
postpref = true;
}
else if (is_help_switch(*arg)) {
print_help_xit();
Expand All @@ -1101,16 +1154,16 @@ int main(int argc, char **argv) {
configFile = value;
}
else if (GetArgument(value, "i", "image", arg, argv + argc)) {
image = value;
appendFile(image, value);
}
else if (GetArgument(value, "k", "color", arg, argv + argc)) {
color = value;
color += value;
}
else if (GetArgument(value, "s", "semis", arg, argv + argc)) {
semis = value;
appendFile(semis, value);
}
else if (GetArgument(value, "x", "trans", arg, argv + argc)) {
trans = value;
trans += value;
}
else if (GetArgument(value, "e", "center", arg, argv + argc)) {
center = value;
Expand Down Expand Up @@ -1140,6 +1193,15 @@ int main(int argc, char **argv) {
else if (*arg)
warn(_("Unrecognized option '%s'."), *arg);
}
else if (hasImageExt(*arg)) {
image += *arg;
}
else {
upath path(*arg + (**arg == '!'));
path = path.expand();
if (path.dirExists() && path.isSearchable())
image += *arg;
}
}

if (getpriority(PRIO_PROCESS, 0) < 5) {
Expand All @@ -1164,34 +1226,28 @@ int main(int argc, char **argv) {
}

Background bg(&argc, &argv, verbose);

if (bg.become(replace) == false) {
if (shuffle) {
bg.sendShuffle();
return 0;
}
warn(_("Cannot start, because another icewmbg is still running."));
return 1;
}

globalBg = &bg;
bgLoadConfig(configFile, overrideTheme);
if (image) {
if (image.nonempty()) {
bg.clearBackgroundImages();
bgParse("DesktopBackgroundImage", image);
for (const char* arg : image)
bgParse("DesktopBackgroundImage", arg);
}
if (color) {
if (color.nonempty()) {
bg.clearBackgroundColors();
bgParse("DesktopBackgroundColor", color);
for (const char* arg : color)
bgParse("DesktopBackgroundColor", arg);
}
if (semis) {
if (semis.nonempty()) {
bg.clearTransparencyImages();
bgParse("DesktopTransparencyImage", semis);
for (const char* arg : semis)
bgParse("DesktopTransparencyImage", arg);
bg.enableSemitransparency();
}
if (trans) {
if (trans.nonempty()) {
bg.clearTransparencyColors();
bgParse("DesktopTransparencyColor", trans);
for (const char* arg : trans)
bgParse("DesktopTransparencyColor", arg);
bg.enableSemitransparency();
}
testFlag(&centerBackground, center);
Expand All @@ -1214,7 +1270,30 @@ int main(int argc, char **argv) {
#endif
}

if (postpref) {
bg.printOptions();
}
if (bg.become(replace) == false) {
if (shuffle) {
bg.sendShuffle();
return 0;
}
warn(_("Cannot start, because another icewmbg is still running."));
return 1;
}

globalBg = nullptr;
if (image.nonempty())
image.clear();
if (color.nonempty())
color.clear();
if (semis.nonempty())
semis.clear();
if (trans.nonempty())
trans.clear();

if (daemonize)
daemon(1, 0);

return bg.mainLoop();
}
Expand Down

0 comments on commit 1186863

Please sign in to comment.