Corrupted XImage retrieved from a Window area
Aaron Plattner
aplattner at nvidia.com
Tue Aug 2 17:35:32 UTC 2016
I think I found the problem and sent a patch:
https://lists.x.org/archives/xorg-devel/2016-August/050544.html
https://patchwork.freedesktop.org/patch/102574/
On 08/01/2016 07:44 AM, Fabien Lelaquais wrote:
> Thansk again to you, Thomas, and Carsten.
> I suspect I still was not clear enough. My problem is not the hidden
> pixels. I know they will be undefined (or I can use an XCopyArea and
> process the GraphicsExpose events).
> My problem is that visible pixels (well defined, and in this case,
> white) are retrieved as black pixels.
> To make things more clear, if you cannot reproduce my problem.
> I have two top windows A and B.
> B is smaller than A, and located on top of it.
> A is entirely on my screen (and B obviously is as well).
> Here what it looks like: (sorry guys, you'll need a monospaced font to
> see this properly)
> +------------+
> | A |
> | +-----+ |
> | | B | |
> | +-----+ |
> +------------+
> If I XGetImage() from A a rectangle that contains the area covered by
> B (but still inside A), what I expect is:
> +------------+
> | |
> | ####### |
> | ####### |
> | ####### |
> +------------+
> Where the # signs indicate an undefined value: all the pixels covered
> by B. Makes sense.
> But what I really get is:
> +------------+
> | |
> | ######### |
> | ######### |
> | ######### |
> +------------+
> That is, more pixels are reported as undefined, to the right of the
> expected 'undefined' region (the one covered by B).
> My experiments show that the more I translate the capture rectangle to
> the right (limited to the surface of A), the more undefined pixels I
> will get.
> If the capture rectangle has its left edge at 0 (on the A left-hand
> border), the image is perfect. This makes no sense at all.
> Unfortunately, I cannot rely on the BackingStore or other properties:
> I may not be the one that created the Window (I'm working on a library
> that sits on top of X).
> And yes, I suspect a bug in the server but honestly I don't believe it.
> I tried this today: I can work the problem around by creating a
> temporary Pixmap (the size of my capture area), XCopyArea the window A
> into it, then XGetImage on that Pixmap.
> Then my image is fine, at the cost of an additional Pixmap
> (potentially large) and a GC (where I dropped the generation of
> GraphicsExpose events that I don't care about).
> All my pixels are correct, except the covered ones, which is fair.
> Thanks!
> Fabien
> -----Original Message-----
> From: Carsten Haitzler [mailto:raster at rasterman.com]
> Sent: lundi 1 août 2016 00:50
> To: Fabien Lelaquais <Fabien.Lelaquais at roguewave.com>
> Cc: xorg at freedesktop.org
> Subject: Re: Corrupted XImage retrieved from a Window area
> On Sun, 31 Jul 2016 07:51:08 +0000 Fabien Lelaquais
> <Fabien.Lelaquais at roguewave.com
> <mailto:Fabien.Lelaquais at roguewave.com>> said:
> > Thanks a lot for your answer.
> > Unfortunately I may not be able to rely of the Composite extension
> > (app would be deployed in environments I don't control).
> >
> > Regarding the XGetImage documentation, that I've read ten times:
> > My drawable (mainWindow) is indeed a viewable window.
> > It has no inferior, and an overlapping window on its center. The
> > specified rectangle that I provide, which is the center part of the
> > source window, is both fully visible on the screen and wholly
> > contained in mainWindow. I have no X error. And that's why I'm calling for help.
> you won't get an x error unless the region ends up being out of screen
> bounds.
> if pixels of a window are clipped by the screen, a parent window, a
> shape rectangle list, or are covered by another window... they "do not
> exist" by default in x11. that is how it works. that is why thomas
> suggested pixmap redirection to ensure that pixels DO exist and force
> them to live in a pixmap irrespective of windows overlapping or the
> window being offscreen. without this you are in regular old x11 mode
> and if your source is a window... if at the time you grab, you cannot
> SEE the pixels on a screen... they do not exist.
> irrespective of if someone drew to them just before. you can never get
> them.
> you can "deal with it" and get pixels by setting includeinferiors in
> your gc subwindowmode before you grab. this will ignore clipping of
> overlapping windows and just grab whatever is there in the framebuffer
> as long as your resulting rectangle at the time x performs the grab is
> still within screen limits. this will get you the content including
> overlapping window content. this is effectively how you do screenshots
> in x11.
> if the region is within screen limits of course... if it is not -
> problems. if you are managed by a window manager there is always then
> a race condition where the wm may have moved you off screen but you
> have not seen the event yet. you can xgrabserver first, then get
> geometry of your window and translate relative to root to ensure you
> have the correct clipping coordinates, getimage, then xungrab server
> to work around the race (and please at least xflush or xsync after the
> xungrabserver.
> note. i'm totally ignoring multiple visuals and depths here. :) if
> your screen consists of lots of windows with differing visuals and
> depths life gets complex. xv also creates problems if it is using
> overlays and colorkeys. :)
> > Thanks again,
> >
> > Cheers,
> > Fabien
> >
> > -----Original Message-----
> > From: Thomas Lübking [mailto:thomas.luebking at gmx.de]
> > Sent: samedi 30 juillet 2016 16:03
> > To: Fabien Lelaquais <Fabien.Lelaquais at roguewave.com <mailto:Fabien.Lelaquais at roguewave.com>>
> > Cc:xorg at freedesktop.org <mailto:xorg at freedesktop.org>
> > Subject: Re: Corrupted XImage retrieved from a Window area
> >
> > On Sat, Jul 30, 2016 at 08:34:20AM +0000, Fabien Lelaquais wrote:
> > >Hi all,
> > >I'm trying to create an XImage that represents a rectangular portion
> > >of a Window (because I need to be able to access the actual pixel
> > >values). My experimentations show that if the source window has an
> > >hidden region (overlapping window) and if the origin of the rectangle
> > >I query is not (0, 0), then the data is corrupted, resulting in
> > >pixels set to 0 in the image data (and a black area in the XImage).
> > >
> > >I use a raw XGetImage.
> >
> > You want to use XCompositeRedirectWindow. This redirects the window
> > into a pixmap. (What compositors like xcompmgr do)
> >
> >
> > From man XGetImage:
> > -------------------
> > If the drawable is a window, the window must be viewable, and it must
> > be the case that if there were no inferiors or overlapping windows,
> > the specified rectangle of the window would be fully visible on the
> > screen and wholly contained within the outside edges of the window, or a BadMatch error results.
> >
> > Cheers,
> > Thomas
> > _______________________________________________
> >xorg at lists.x.org <mailto:xorg at lists.x.org>: X.Org support
> > Archives:http://lists.freedesktop.org/archives/xorg
> > Info:https://lists.x.org/mailman/listinfo/xorg
> > Your subscription address: %(user_address)s
> --
> ------------- Codito, ergo sum - "I code, therefore I am" --------------
> The Rasterman (Carsten Haitzler) raster at rasterman.com
> <mailto:raster at rasterman.com>
>
>
> _______________________________________________
> xorg at lists.x.org: X.Org support
> Archives: http://lists.freedesktop.org/archives/xorg
> Info: https://lists.x.org/mailman/listinfo/xorg
> Your subscription address: %(user_address)s
nvpublic
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <https://lists.x.org/archives/xorg/attachments/20160802/aa39f458/attachment.html>
More information about the xorg
mailing list