[Xorg] Composite and Background == None windows
sandmann at daimi.au.dk
Sun Jul 11 04:04:13 PDT 2004
Keith Packard <keithp at keithp.com> writes:
> I'm having trouble getting Background == None windows to work
> right with Composite. The problem is that when these windows
> are mapped, you get garbage contents for the backing pixmap.
> Background == None windows are for two reasons:
> 1) To avoid flashing a background pixel which will
> immediately be replaced by "real" contents.
> 2) To capture an image of the screen inside the window
> I submit that case 1) is a more "legitimate" usage as 2) breaks in the
> presense of different visuals in any case. So, it's important to
> get case 1) right while still letting case 2) do something
Case 2 is legitimate if the visuals are the same. There are also good
reasons an application could do it. For example to move a subwindow
without flicker you can unset the background of both the window and
its parent, set the bitgravity of the window to static, then move the
window with two XMoveResizeWindow(), then use one or more XCopyArea()
to move the pixels, then reset the backgrounds.
I doubt any applications actually do this, but they could. The
protocol spec is unambiguous that depending on this is allowed for
windows with matching visuals.
> For case 1) (used for menus and window manager frames), it seems
> like the right solution is to avoid painting the window at all
> until the application has managed to fill it entirely with the
> correct content. That would require Damage to be modified to let the
> application know when the window was completely painted, probably by
> adding a boolean to the damage event to pass that information along.
> However, when you create a Damage structure for a window, it is
> initialized to the borderClip for that window; if the window is mapped
> (and it often is, even for new windows because applications are pretty
> quick to create/map menus) then the whole window ends up damaged, even
> though it hasn't painted anything yet. I don't see how to fix that --
> the new Damage would have no context to know whether the bits in the
> window were painted by the application or not.
> However, we can easily solve case 2) -- just copy the screen area to the
> backing pixmap when the window is mapped. If the compositing manager is
> doing anything weird with the windows, you may get strange looking results
> though -- any shadows will be painted around the "window", even though
> that "window" was filled with bits from the screen underneath it.
To be compatible with the current protocol the screen area needs to be
copied in the case of reszing a window too. Why not simply copy the
contents and not generate a DamageNotify? Logically the window is not
damaged as the application has not painted anything.
The compositing manager can hold the fancy stuff until it sees a
DamageNotify. If the painting application is double buffering, then
the first painting operation will be a complete paint, but as you say
below, Composite can probably not fix all tearing issues by itself
> I guess the right solution is to implement the trivial fix for 2) and then
> work on ICCCM extensions for applications to communicate with the
> compositing manager about window painting state. Those extensions are
> required to avoid screen artifacts in other cases, so I guess it's not so
> bad that we need them for menus as well.
I agree with this, although synchronous override redirects as
suggested in the 'Why X is Not Our Ideal Window System' paper would
also be helpful in making mapping managed windows flicker less.
More information about the xorg