xpra icon
Bug tracker and wiki

Opened 4 years ago

Closed 4 years ago

#885 closed enhancement (fixed)

honour window position exactly

Reported by: Antoine Martin Owned by: alas
Priority: major Milestone: 0.16
Component: client Version: 0.15.x
Keywords: Cc:

Description

When we map a window at a specific location, either because the application requested it or because it was mapped at a specific location previously (hard to distinguish at present), we should ensure that the window contents end up exactly at the specified location.
At the moment, we ask GTK to place the window frame there and so windows that have a border and title bar end up moved down + right every time they are mapped.

Platform specific:

  • on win32 we can use the get_window_frame_sizes gui API to undo the offset
  • on OSX, no idea
  • on X11: we are supposed to use the _NET_REQUEST_FRAME_EXTENTS request, the problem here is that we don't want to wait for the response (that may never come..) when we create a window..

Attachments (3)

x11-props-with-gtk3.patch (3.7 KB) - added by Antoine Martin 4 years ago.
work in progress patch to allow us to access at least some X11 properties with the gi bindings (GTK3)
ticket885_pre-disconnect_window-across-two-monitors.txt (114.7 KB) - added by alas 4 years ago.
multi-display info with window split between two displays before disconnection
ticket885_post-disconnect_window-across-two-monitors.txt (115.0 KB) - added by alas 4 years ago.
multi-display info with window split between two displays after reconnection

Download all attachments as: .zip

Change History (14)

comment:1 Changed 4 years ago by Antoine Martin

Status: newassigned

Done for win32 in r9595.

comment:2 Changed 4 years ago by Antoine Martin

Mostly done for X11 in r9601, as in: it will work as expected in most cases.

Still TODO:

  • OSX, looks like we want to use contentRectForFrameRect, found some examples:
  • expose the frame geometry to the server so it can respond to the same ​_NET_REQUEST_FRAME_EXTENTS query
  • the code is racy: if we connect to the xpra server faster than the window manager responds to our query, we won't have the values available when the first window is created. Very very unlikely even with a local connection, but still theoretically possible... especially if the X11 server is remote (higher latency than the xpra server). Maybe we should cache the value on disk? (per desktop environment) - meh
  • fix GTK3 support (Gtk.WindowType.POPUP, etc..)
  • maybe this data should be per monitor (need to create on window per monitor..)
  • verify that toggling window decorations on and off works, this may need the same workaround we have used on win32 (moving the window to ensure its contents stay in the same place)
Last edited 4 years ago by Antoine Martin (previous) (diff)

comment:3 Changed 4 years ago by Antoine Martin

We now expose the frame extents (r9605, r9606 only for servers that expose the capability).

The big problem with honouring _NET_REQUEST_FRAME_EXTENTS is that these requests often come in for windows that are realized but not shown yet (ie: that's what our test app does), so that the application can calculate the offsets before showing the window.
But that also means that we don't have a window model for it yet, so we can't receive the message on the window... and for some reason the client message is not being received by the "WM" class either despite it being registered as an event receiver for the root window which is the target of the message.

comment:4 Changed 4 years ago by Antoine Martin

This is almost complete with r9612, see long commit message. (+fixup in r9613)

Still TODO:

  • GTK3
  • OSX: as per this thread's Managment summary, this seems to work:
    import Quartz
    r=Quartz.NSRect()
    Quartz.NSWindow.pyobjc_classMethods.contentRectForFrameRect_styleMask_(r, 1)
    <NSRect origin=<NSPoint x=0.0 y=0.0> size=<NSSize width=0.0 height=-22.0>>
    
  • ideally, we should update the server default frame extents value if we find that the property is changed on our hidden window (and request a new value whenever anything significant is changed: resolution, etc)
  • we should probably not send the "frame" value for each window when we are actually using the default value: saving unnecessary traffic and allowing us to update all the windows in one swoop by setting the new global default value
Last edited 4 years ago by Antoine Martin (previous) (diff)

comment:5 Changed 4 years ago by Antoine Martin

  • GTK3 is going to require some work (some preparatory work in r9614): the HAS_X11_BINDINGS is too coarse and relies on some gtk2 classes
  • OSX seems to be working as of r9616, we should add a platform function to get the window frame directly (since we can do that on OSX: we can just copy the window position and dimensions rather than try to figure out how to access the underlying NSWindow for our gdk.Window)

Changed 4 years ago by Antoine Martin

Attachment: x11-props-with-gtk3.patch added

work in progress patch to allow us to access at least some X11 properties with the gi bindings (GTK3)

comment:6 Changed 4 years ago by Antoine Martin

More improvements (r9627), OSX shortcut (r9629 - includes fix for hello packet failures caused by float values).
r9631 fixes GTK3 and py3k.

Still TODO, moved some refactoring issues to ticket:640#comment:29.

New TODO: we should at least investigate #501

Last edited 4 years ago by Antoine Martin (previous) (diff)

comment:7 Changed 4 years ago by Antoine Martin

Owner: changed from Antoine Martin to alas
Status: assignednew

Ready for testing. (#501 makes no difference here - just confuses me more)

Things to check:

  • easiest thing to check: connecting and re-connecting should place the window in exactly the same place every time - not even 1 pixel off, on all platforms - except with window managers that decide not to honour what we request... and they do exist!
  • the window frame size value used will be shown with:
    xpra info | grep -i "client.window.frame-sizes"
    

It would be interesting to see if this value changes when the DPI changes (esp with OSX and win 8+) - we don't update the defaults which are sent during the initial connection, but the window value should get updated (I hope, assuming the frame size even changes - if not, toggling opengl on and off probably does it as it re-displays the window).

comment:8 Changed 4 years ago by J. Max Mena

Started a Fedora 21 9689 trunk server:

  • Disconnecting and reconnecting from a Fedora 20 client (same branch and revision) has the windows pop up in the same places.
  • Disconnecting and reconnecting from Windows 8.1 works.
  • Disconnecting from Fedora 20 and connecting with Win8.1 works...sort of. It won't put Firefox below the task bar, instead it just moves it up a couple pixels so the bottom of the window rests against the task bar.
  • Will test OSX when I get an OSX machine with a screen big enough to match my other machines..
  • Will test DPI changes later on as I don't want to mess with those settings with my setup. Maybe I'll mess with Testbench when the interns are done...

comment:9 Changed 4 years ago by alas

Status: newassigned

Testing the OSX 0.15.4 r9951 client against a 0.15.4 r9951 fedora 20 server - the windows do indeed display in the same place when re-connecting. Except - when a window is being displayed on the border between two monitors, upon re-connection the window (firefox, xterm, whatever) will display on whichever display they were "more" displaying on before the disconnection. (Confirmed same behavior with windows 0.15.4 r9951 client against same server session.)

Not sure if this behavior is just the result of the xFakeXinerama handling of multiple displays or not, but I'll attach info files for before disconnect and after reconnect with the osx client.


Testing with the OSX client with adjusting resolutions between connection (osx 10.9 doesn't provide any means that I have discovered to adjust in terms of DPI, but it does give four, and only four, resolution scaling options) ... the first thing I discovered is that xpra info | grep -i "client.window.frame-sizes" gives no response. xpra info | grep -i "client.window" only outputs client.windows=True & features.client_window_properties=True.

The client output does give some insight though:

At a resolution (as indicated by system preferences) of 2560 x 1440:

2015-07-16 17:29:47,928 desktop size is 2960x2490 with 1 screen(s):
2015-07-16 17:29:47,929   'schadenfreude.local' (1044x878 mm - DPI: 72x72)
2015-07-16 17:29:47,930     monitor 1 1680x1050 at 1280x1440 (592x370 mm - DPI: 72x72)
2015-07-16 17:29:47,931     monitor 2 2560x1440 (903x508 mm - DPI: 72x72)

At 2048 x 1152

2015-07-16 17:59:36,969 desktop size is 2720x2340 with 1 screen(s):
2015-07-16 17:59:36,969   'schadenfreude.local' (959x825 mm - DPI: 72x72)
2015-07-16 17:59:36,969     monitor 1 1440x900 at 1280x1440 (508x317 mm - DPI: 72x72)
2015-07-16 17:59:36,970     monitor 2 2560x1440 (903x508 mm - DPI: 72x72)

At 1600 x 900

2015-07-16 18:00:49,363 desktop size is 2560x2240 with 1 screen(s):
2015-07-16 18:00:49,364   'schadenfreude.local' (903x790 mm - DPI: 72x72)
2015-07-16 18:00:49,364     monitor 1 1280x800 at 1280x1440 (451x282 mm - DPI: 72x72)
2015-07-16 18:00:49,364     monitor 2 2560x1440 (903x508 mm - DPI: 72x72)

At 1280 x 720

2015-07-16 17:32:32,382 desktop size is 2560x2080 with 1 screen(s):
2015-07-16 17:32:32,382   'schadenfreude.local' (903x733 mm - DPI: 72x72)
2015-07-16 17:32:32,382     monitor 1 1024x640 at 1280x1440 (361x225 mm - DPI: 72x72)
2015-07-16 17:32:32,383     monitor 2 2560x1440 (903x508 mm - DPI: 72x72)

With a windows 8.1 client (resolutions picked at near random... values plucked from server side output, matching client side details)

At 3840 x 2160

2015-07-16 18:14:58,074 client root window size is 5120x2160 with 1 displays:
2015-07-16 18:14:58,074   '1\WinSta-Default' (1354x571 mm - DPI: 96x96) workarea: 5120x2120
2015-07-16 18:14:58,075     DISPLAY1 3840x2160 at 1280x0 (621x341 mm - DPI: 157x160) workarea: 3840x2120
2015-07-16 18:14:58,075     DISPLAY2 1280x720 (597x336 mm - DPI: 54x54) workarea: 1280x680
2015-07-16 18:14:58,109 server virtual display now set to 5120x2560 (best match for 5120x2160)

At 2048 x 1152

2015-07-16 18:19:46,015 client root window size is 3328x1152 with 1 displays:
2015-07-16 18:19:46,016   '1\WinSta-Default' (880x304 mm - DPI: 96x96) workarea: 3328x1112
2015-07-16 18:19:46,016     DISPLAY1 2048x1152 at 1280x0 (621x341 mm - DPI: 83x85) workarea: 2048x1112
2015-07-16 18:19:46,016     DISPLAY2 1280x720 (597x336 mm - DPI: 54x54) workarea: 1280x680
2015-07-16 18:19:46,071 server virtual display now set to 3520x1196 (best match for 3328x1152)

At 1600 x 900

2015-07-16 18:21:52,538 client root window size is 2880x900 with 1 displays:
2015-07-16 18:21:52,538   '1\WinSta-Default' (762x238 mm - DPI: 96x96) workarea: 2880x860
2015-07-16 18:21:52,540     DISPLAY1 1600x900 at 1280x0 (621x341 mm - DPI: 65x67) workarea: 1600x860
2015-07-16 18:21:52,540     DISPLAY2 1280x720 (597x336 mm - DPI: 54x54) workarea: 1280x680
2015-07-16 18:21:52,551 DPI set to 96 x 96
2015-07-16 18:21:52,571 sent updated screen size to 1 clients: 3120x1050 (max 8192x4096)

This last entry, however, resulted from my changing the resolution while still connected.

The plus is that the client and server both outputted updated values, and the display adjusted as expected.

The down-side is that a control-C seems to fail to disconnect the client... the server acknowledges the CTRL_C and disconnects, but the client is hung/Not Responding. I'll file another ticket for that.

Let me know if you need any other info regarding the window frame-sizes as resolutions change, or any more than the info for the multi-display window placement on re-connect.

Changed 4 years ago by alas

multi-display info with window split between two displays before disconnection

Changed 4 years ago by alas

multi-display info with window split between two displays after reconnection

comment:10 Changed 4 years ago by Antoine Martin

the windows do indeed display in the same place when re-connecting. Except - when a window is being displayed on the border between two monitors..


That's fine, the window manager decides that it isn't a good location and overrides us.


xpra info | grep -i "client.window.frame-sizes" gives no response....


Ah, this part is in trunk only...

I think we can close this ticket and follow up in #919

comment:11 Changed 4 years ago by Antoine Martin

Resolution: fixed
Status: assignedclosed
Note: See TracTickets for help on using tickets.