Xfce Forum

Sub domains
 

You are not logged in.

#1 2022-01-07 19:20:48

espas
Member
Registered: 2021-09-29
Posts: 12

[SOLVED] Problems with dual monitors

I began using dual monitors and this quickly became a problem with Xfce because the shared workspaces Xfce uses is the worst possible setup for multiple monitors. If each monitor had their own workspaces or the second monitor had a single workspace it would be fine, but shared workspaces is not usable. Is there a way to make windows in the second monitor automatically become visible in all workspaces and stop this if they are moved to the primary monitor? Idk if there is already a script for this out there.

My second problem is not unique to Xfce because I think other DEs also have this problem. Some applications do not open in the right display. Most Xfce apps do, but some apps like MPV or qimgv don't. Is there a way to fix this and make all apps open where they were launched?

Last edited by espas (2022-01-08 15:51:06)

Offline

#2 2022-01-07 21:09:27

ToZ
Moderator
From: Canada
Registered: 2011-06-02
Posts: 8,506

Re: [SOLVED] Problems with dual monitors

espas wrote:

Is there a way to make windows in the second monitor automatically become visible in all workspaces and stop this if they are moved to the primary monitor? Idk if there is already a script for this out there.

Challenge accepted!

Here is a script I've quickly thrown together. Give it a go and see if it works. You need to change the first 4 variables (EXTx, EXTy, EXTw, EXTh) to suit your system. This will be the xrandr dimensions of what you consider an external monitor. So for example, if your primary monitor dimensions are 0,0,1366,768 and the external monitor is to the right and also sized 1366x768, then as per xrandr the dimensions would be 1367,0,2732,768. It is currently coded only to deal with side by side monitors.

#!/bin/bash
# requires wmctrl

# x,y,width,height of "external" monitor - based on xrandr
EXTx=0 
EXTy=0
EXTw=1920
EXTh=1080

# make sure that only one instance of this script is running per user
lockfile=/tmp/.emsa.$USER.lockfile
if ( set -o noclobber; echo "locked" > "$lockfile") 2> /dev/null; then
   trap 'rm -f "$lockfile"; exit $?' INT TERM EXIT
   echo "emsaDEBUG: Locking succeeded" >&2

   while true
   do
      # get a list of visible windows and put it in an array
      readarray -t windows < <(wmctrl -lG | grep -v "\-1")
		
      # walk the list of windows to see if the top corner of any window is in the monitor range
      for x in "${windows[@]}"
      do
         if [ $(echo $x | awk '{print $3}') -ge $EXTx -a $(echo $x | awk '{print $3}') -le $EXTw ]
         then

            # save the windowID
            WIN=$(echo $x | awk '{print $1}')
			
            # sticky the window
            wmctrl -i -r $(echo $x|awk '{print $1}') -b add,sticky
				
            # wait until window no longer exists or is no longer in the monitor range
            while : 
            do
               
               # get stickied windows new info
               tWIN=$(wmctrl -lG | grep $WIN)

               # if window no longer exists, break
               if [ $? -eq 1 ]; then break; fi

               # get windows current x value
               tWINx=$(echo $tWIN | awk '{print $3}')

               # if no longer in the range....
               if ! [ $tWINx -ge $EXTx -a $tWINx -le $EXTw ]
               then
                  # remove stick bit and break out
                  wmctrl -i -r $(echo $x|awk '{print $1}') -b remove,sticky 
                  break
               fi
						
               sleep 1
            done

         fi
      done 

      # pause for next cycle
      sleep 1

   done

# can't create lockfile - notify user and quit
else
   echo "emsaDEBUG: Lock failed, check for existing process and/or lock file and delete - exiting." >&2
   exit 1
fi			

exit 0

My second problem is not unique to Xfce because I think other DEs also have this problem. Some applications do not open in the right display. Most Xfce apps do, but some apps like MPV or qimgv don't. Is there a way to fix this and make all apps open where they were launched?

Because this is controlled by the app, there is nothing that Xfce can do, but you can use a tool like devilspie to force placement of application windows.

Edit: fixed code formatting

Last edited by ToZ (2022-01-07 21:24:35)

Offline

#3 2022-01-07 22:04:15

espas
Member
Registered: 2021-09-29
Posts: 12

Re: [SOLVED] Problems with dual monitors

Thanks. I tried this script and it makes one window visible in all workspace but not all windows in the monitor. Maybe I'm not using it correctly, but it made a single window visible on all workspace and it wasn't in the monitor I wanted (probably because I didn't use the variables correctly) but it seems like even if I did it would only work for 1 window.

Offline

#4 2022-01-08 00:54:39

ToZ
Moderator
From: Canada
Registered: 2011-06-02
Posts: 8,506

Re: [SOLVED] Problems with dual monitors

Yes, it was coded for just one window. I misread. Here is a version of the script that will sticky all windows whose top left corner sits in the boundary of the external monitor:

#!/bin/bash
# requires wmctrl

# x1, y1, x2, y2 of "external" monitor - based on xrandr
EXTx=0 
EXTy=0
EXTw=1920
EXTh=1080

# make sure that only one instance of this script is running per user
lockfile=/tmp/.emsa.$USER.lockfile
if ( set -o noclobber; echo "locked" > "$lockfile") 2> /dev/null; then
   trap 'rm -f "$lockfile"; exit $?' INT TERM EXIT
   echo "emsaDEBUG: Locking succeeded" >&2

   # variable to hold stickied windows
   STICKS=""

   while true
   do
      # get a list of visible windows and put it in an array
      readarray -t windows < <(wmctrl -lG | grep -v "\-1")
		
      # walk the list of visible windows to see if the top corner of any window is in the monitor range and sticky it
      for x in "${windows[@]}"
      do
         if [ $(echo $x | awk '{print $3}') -ge $EXTx -a $(echo $x | awk '{print $3}') -le $EXTw ]
         then
            # sticky the window
            WINID=$(echo $x | awk '{print $1}')
            wmctrl -i -r $WINID -b add,sticky

            # save the window ID
            STICKS=$(echo "$STICKS $WINID" | awk '{for (i=1;i<=NF;i++) if (!a[$i]++) printf("%s%s",$i,FS)}{printf("\n")}')
         fi
      done 

      # convert list of stickied window IDs to an array
      IFS=' ' read -a stickies <<< "$STICKS"
      
      # walk the list of stickied windows to make sure they still need to be sticky
      for y in "${stickies[@]}"
      do
         yx=$(wmctrl -lG | grep $y)
         if ! [ $(echo $yx | awk '{print $3}') -ge $EXTx -a $(echo $yx | awk '{print $3}') -le $EXTw ]
         then                  
            # remove the sticky bit
            wmctrl -i -r $y -b remove,sticky
            STICKS=$(echo $STICKS | sed "s/ $y//g")
         fi
      done
         
      unset windows stickies
      
      # pause for next cycle
      sleep 1

   done

# can't create lockfile - notify user and quit
else
   echo "emsaDEBUG: Lock failed, check for existing process and/or lock file and delete - exiting." >&2
   exit 1
fi			

exit 0

Post back the results of "xrandr" and I'll tell you what settings you need to use for the first 4 variables.

Offline

#5 2022-01-08 04:02:54

espas
Member
Registered: 2021-09-29
Posts: 12

Re: [SOLVED] Problems with dual monitors

This one is working, but I can't make it work on the right monitor.

This is the xrandr output:

Screen 0: minimum 8 x 8, current 3840 x 1080, maximum 32767 x 32767
DVI-D-0 disconnected (normal left inverted right x axis y axis)
HDMI-0 disconnected (normal left inverted right x axis y axis)
DP-0 connected 1920x1080+1920+0 (normal left inverted right x axis y axis) 527mm x 296mm
   1920x1080     60.00 + 144.00*  119.98   119.88    99.93    74.97    59.94    50.00  
   1280x1024     75.02    60.02  
   1280x720      59.94    50.00  
   1024x768     119.99    99.97    75.03    70.07    60.00  
   800x600      119.97    99.66    75.00    72.19    60.32    56.25  
   720x576       50.00  
   720x480       59.94  
   640x480      119.52    99.77    75.00    72.81    59.94    59.93  
DP-1 disconnected (normal left inverted right x axis y axis)
DP-2 disconnected (normal left inverted right x axis y axis)
DP-3 disconnected (normal left inverted right x axis y axis)
DP-4 connected primary 1920x1080+0+0 (normal left inverted right x axis y axis) 527mm x 296mm
   1920x1080     60.00 + 144.00*  119.98   119.88    99.93    59.94    50.00  
   1680x1050     59.88  
   1440x900      59.90  
   1280x1024     75.02    60.02  
   1280x720      60.00    59.94    50.00  
   1024x768     119.99    99.97    75.03    70.07    60.00  
   800x600      119.97    99.66    75.00    72.19    60.32    56.25  
   720x576       50.00  
   720x480       59.94  
   640x480      119.52    99.77    75.00    72.81    59.94    59.93  
DP-5 disconnected (normal left inverted right x axis y axis) 

Offline

#6 2022-01-08 11:48:50

ToZ
Moderator
From: Canada
Registered: 2011-06-02
Posts: 8,506

Re: [SOLVED] Problems with dual monitors

Try these settings:

EXTx=1921
EXTy=0
EXTw=1919
EXTh=1080

Offline

#7 2022-01-08 12:12:26

espas
Member
Registered: 2021-09-29
Posts: 12

Re: [SOLVED] Problems with dual monitors

ToZ wrote:

Try these settings:

EXTx=1921
EXTy=0
EXTw=1919
EXTh=1080

Doesn't work. Nothing happens.

Offline

#8 2022-01-08 12:17:07

ToZ
Moderator
From: Canada
Registered: 2011-06-02
Posts: 8,506

Re: [SOLVED] Problems with dual monitors

Am I correct in assuming that DP-4 is your primary monitor and that DP-0 is to the right of it?
I see what I did wrong. Try the following:

EXTx=1921
EXTy=0
EXTw=3840
EXTh=1080

Last edited by ToZ (2022-01-08 12:18:56)

Offline

#9 2022-01-08 15:50:18

espas
Member
Registered: 2021-09-29
Posts: 12

Re: [SOLVED] Problems with dual monitors

ToZ wrote:

Am I correct in assuming that DP-4 is your primary monitor and that DP-0 is to the right of it?
I see what I did wrong. Try the following:

EXTx=1921
EXTy=0
EXTw=3840
EXTh=1080

It's working perfectly now. Thank you very much!

Offline

#10 2022-01-08 20:29:49

ToZ
Moderator
From: Canada
Registered: 2011-06-02
Posts: 8,506

Re: [SOLVED] Problems with dual monitors

Updated version:
- Found a bug around the logic of managing windows IDs that resulted in unnecessary unstickying and eventually an error if no windows in target area
- Optimized so that sticky action is only applied when needed (not every time as before)
- tweaked so it works for both side-by-side and above-and-below monitor layouts

#!/bin/bash
# requires wmctrl

# x1,y1,x2,y2 bounding box of "external" monitor - based on xrandr

# --- horizontal example ---
EXTx=1921 
EXTy=0
EXTw=3840
EXTh=1080
ORIENTATION=horizontal
# --- vertical example ---
#EXTx=0 
#EXTy=0
#EXTw=1920
#EXTh=1080
#ORIENTATION=vertical

### don't change anything below #####################################################################################3
# make sure that only one instance of this script is running per user
lockfile=/tmp/.emsa.$USER.lockfile
if ( set -o noclobber; echo "locked" > "$lockfile") 2> /dev/null; then
   trap 'rm -f "$lockfile"; exit $?' INT TERM EXIT
   echo "emsaDEBUG: Locking succeeded" >&2

   # variable to hold stickied windows
   STICKS=""

   while true
   do
      # get a list of visible windows and put it in an array
      readarray -t windows < <(wmctrl -lG | grep -v "\-1")
		
      # walk the list of visible windows to see if the top corner of any window is in the monitor range and sticky it
      for x in "${windows[@]}"
      do
         case $ORIENTATION in
            horizontal) 
               if [ $(echo $x | awk '{print $3}') -ge $EXTx -a $(echo $x | awk '{print $3}') -le $EXTw ] 
               then
                  WINID=$(echo $x | awk '{print $1}')
                  if ! [ $(echo $STICKS | grep $WINID) ]
                  then 
                     # sticky the window
                     wmctrl -i -r $WINID -b add,sticky
                  fi
               fi
            ;;
            vertical)
               if [ $(echo $x | awk '{print $4}') -ge $EXTy -a $(echo $x | awk '{print $4}') -le $EXTh ] 
               then
                  WINID=$(echo $x | awk '{print $1}')
                  if ! [ $(echo $STICKS | grep $WINID) ]
                  then 
                     # sticky the window
                     wmctrl -i -r $WINID -b add,sticky
                  fi
               fi
            ;;
            *) echo "Error: ORIENTATION not defined"
               exit 1
            ;;
         esac

            # save the window ID ensuring no duplicates
            STICKS=$(echo "$STICKS $WINID" | awk '{for (i=1;i<=NF;i++) if (!a[$i]++) printf("%s%s",$i,FS)}{printf("\n")}')
      done 

      # convert list of stickied window IDs to an array
      IFS=' ' read -a stickies <<< "$STICKS"
      
      # walk the list of stickied windows to make sure they still need to be sticky
      for y in "${stickies[@]}"
      do
         yx=$(wmctrl -lG | grep $y)
         case $ORIENTATION in
            horizontal)
               if ! [ $(echo $yx | awk '{print $3}') -ge $EXTx -a $(echo $yx | awk '{print $3}') -le $EXTw ] 
               then                  
                  # remove the sticky bit
                  wmctrl -i -r $y -b remove,sticky
                  STICKS=$(echo $STICKS | sed "s/ $y//g")
               fi
            ;;
            vertical)
               if ! [ $(echo $yx | awk '{print $4}') -ge $EXTy -a $(echo $yx | awk '{print $4}') -le $EXTh ] 
               then                  
                  # remove the sticky bit
                  wmctrl -i -r $y -b remove,sticky
                  STICKS=$(echo $STICKS | sed "s/$y//g")
               fi
            ;;
            *) echo "Error: ORIENTATION not defined properly"
               exit 1
            ;;
         esac
      done
         
      unset windows stickies WINID y
      
      # pause before next cycle
      sleep 1

   done

# can't create lockfile - notify user and quit
else
   echo "emsaDEBUG: Lock failed, check for existing process and/or lock file and delete - exiting." >&2
   exit 1
fi			

exit 0

Offline

Board footer

Powered by FluxBB