hsetroot icon indicating copy to clipboard operation
hsetroot copied to clipboard

Default X screen / screen selection

Open mkoskar opened this issue 5 years ago • 4 comments

Now there is an option -screens that translates into variable screen_mask and is used like this:

  unsigned long screen_mask = ~0;
  for (/* global */ screen = 0; screen < ScreenCount(display); screen++) {
    if ((screen_mask & (1 << screen)) == 0)
      continue;

So if I would like to operate on a single screen say 0, I would have to pass -screens 1, for 1 it would be -screens 2, for 2 it would be -screens 4 etc.

Moreover (and this is my use case), it's impossible to operate on default (preferred in XCB lingo) screen, i.e., if DISPLAY=:1.1 I would like hsetroot just to manipulate root window of X screen 1.

I have hardcoded following quick & dirty solution to do so:

diff --git a/hsetroot.c b/hsetroot.c
index 79e5c7b..4c23393 100644
--- a/hsetroot.c
+++ b/hsetroot.c
@@ -284,9 +284,15 @@ main(int argc, char **argv)
     outputs = XineramaQueryScreens(display, &noutputs);
   }
 
+  int screen_def = DefaultScreen(display);
+  printf("screen_def = %d\n", screen_def);
+
   for (/* global */ screen = 0; screen < ScreenCount(display); screen++) {
-    if ((screen_mask & (1 << screen)) == 0)
-      continue;
+    //if ((screen_mask & (1 << screen)) == 0)
+    //  continue;
+
+    if (screen != screen_def)
+        continue;
 
     Imlib_Context *context = imlib_context_new();
     imlib_context_push(context);

Because I feel like operating on multiple X screens might be useful for somebody I would suggest leaving -screens be and creating new option e.g., -screen <int>, which would take a preference before -screens and specify single X screen to work on, or -1 for the DefaultScreen(display).

mkoskar avatar Oct 20 '19 06:10 mkoskar

Aah, finally, I knew there must be somebody still using X screens :).

Your propsal sounds reasonable, just one question:

Right now, not using -screens (or -screen) gives you screen 0. What if we used DefaultScreen(display) by default?

If I understand correctly, this would still just give 0 for most people, but DISPLAY=whatever.123 would be respected. (And you could still force a different screen manually using -screens or -screen.)

(I'm not aware of -1 being a convention for default screen anywhere, so I don't want to introduce that if not needed.)

himdel avatar Oct 20 '19 11:10 himdel

Aah, finally, I knew there must be somebody still using X screens :).

Haha, yeah, I'm kinda playing with zaphod mode (multiple separate X screens).

Right now, not using -screens (or -screen) gives you screen 0.

I don't think that's true. screen_mask defaults to ~0 which makes above loop to go over all X screens. In my case I have :1.0 and :1.1 so one hsetroot invocation manipulates root windows of both screens.

But changing it so it defaults only to DefaultScreen(display) would work, and then depending on -screens or -screen work on single X screen or more.

TBH now thinking about it, probably best would be to drop -screens completely and have -screen <int> only where <int> would directly match index of a screen, so for :1.0 it will be -screen 0 for :1.1 it will be -screen 1 ... and then since there won't be any -screens option anymore, it can default to DefaultScreen(display) like we said above.

BTW this is how it's done in xdotool mousemove, well at least it's meant to work that way but the default is always 0 which is a bug (I'll probably open issue there but there's not much activity with it anyway so meh).

Removing -screens makes it simpler and then, when you're running multiple X screens you anyway are starting X clients separately for them, so there is no problem in running hsetroot multiple times for each screen and have it to address correct default/preferred screen.

mkoskar avatar Oct 20 '19 13:10 mkoskar

Thanks! And you're right, maybe just a -screen <int> would be the best. (Though, I still feel like maybe DISPLAY=:1.0 should just touch screen 0, whereas DISPLAY=:1 should touch all of them.)

I'll try to look into this over the weekend :)

himdel avatar Oct 22 '19 12:10 himdel

No problem ;)

Though, I still feel like maybe DISPLAY=:1.0 should just touch screen 0, whereas DISPLAY=:1 should touch all of them.

When screen number is omitted (e.g., :1) screen 0 should be assumed, as per X(7):

screennumber
        Some displays share their input devices among two or more monitors.  These may be configured as a single logical screen, which allows windows to move across screens, or as
        individual  screens,  each with their own set of windows.  If configured such that each monitor has its own set of windows, each screen is assigned a screen number (begin‐
        ning at 0) when the X server for that display is started.  If the screen number is not given, screen 0 will be used.

Well in the end DefaultScreen(dpy) behaves as such, same its XCB equivalent. Handling :1 and :1.0 differently would be rather interesting take on it, certainly possible. Would mean doing DISPLAY parsing "manually" though (haven't looked at Xlib API to that extent).

Either way thanks for considering this ;)

mkoskar avatar Oct 22 '19 19:10 mkoskar