How to fullscreen application across both monitors of dual head display?

I have two Ubuntu 10.4 machines (and Ubuntu continues to hide more and more xorg.conf config such that I no longer know where to find it). One is a laptop running dual headed - DP1 is the internal screen, and VGA1 is an external monitor; both are running at 1600x900. The other machine is a desktop running both VGA1 and HDMI1 (which is actually a display port with a DVI adapter) at 1600x900. So in both instances my desktop is 3200x900. I run a VNC server on the laptop and connect to it (via SSH tunnel) from the desktop - when I press the full screen hot key, I get a 1600x900 view of the remote machine on one monitor, and half of my local desktop on the other monitor - the "full screen" only expands to fill one local monitor.

Normally this is exactly what you want when you full screen a web browser, email client, or other application. I'm sure there's some X magic to make it clear what a full screen actually entails, and the vnc client application is just dutifully accepting what it's told. While I would like to keep the normal full screen behavior for regular applications, but when I'm VNCing to another 3200x900 machine, I'd really like full screen to stretch across both local displays. Resizing the window to be "close" isn't quite good enough since I still have local panels at the top and bottom of one display (though I can set them to autohide), plus the VNC client application window border (since it doesn't appear to respect -notitle).

Is there any good way to have X lie to a single application about the "full screen" size? Can I get it to lie to all applications? xrandr --noprimary appears to have no effect.


Solution 1:

I did some digging. The modern version of the X11 magic I hypothesized is actually window manager magic, _NET_WM_STATE_FULLSCREEN. My VNC client is in fact using that request, and getting expanded to a single monitor. It appears that it should first be setting _NET_WM_FULLSCREEN_MONITORS to describe which monitors to use as the top/bottom/left/right edges, but it is not. However, I pulled the source from dpkg and dug in to hack it up. Even with _NET_WM_FULLSCREEN_MONITORS I could not elicit the correct behavior. The VNC client does know that it wants to get to 3200x900, and it attempts several times (30) to resize to that (setting both the base and max widths and heights in XA_WM_NORMAL_HINTS and then using XResizeWindow()) on the top window, but it is always ignored. Perhaps compiz is misbehaving?

But the VNC client also has code for dealing with X directly instead of going through a window manager. When I cut out the WM detection code, it modifies the root window more directly (XtNoverrideRedirect, XReparentWindow to the top, XMapRaised, etc) and that works like a charm (as long as I also disable the detection code in the un-fullscreen function). It arguably works even better - alt-tab and other window managing keys now go through to the remote machine until I un-fullscreen the VNC client window.

So it may be hacky and otherwise have some gotchas*, but at least for now I have gotten it to behave acceptably in my mind.

*: un-fullscreening does not properly redraw the root window or other windows that had been covered up. But switching to a different viewport and then switching back forces a redraw, which is an acceptable workaround.