3

Background

We are running our application in XenDesktop mode and our window shows some real time information. But if some other application is also launched in that XenDekstop and that application is overlapping our window then we want to stop rendering. And once its moved out of our window then we want to start rendering again. Unfortunately, right now these kind of notifications are not supported by Citrix.

Question

How can we detect when a part or the whole of the application window has been overlapped by other windows, and also detect when that's no longer the case?

I found the WindowFromPoint family of functions when Googling, however, that is not practical for my purpose because I'd need to keep polling all co-ordinates that my window covers.

Bonus points: For a start, it's enough if I can just detect when such overlapping occurs. However, if I can detect exactly which area(s) of my window is/are covered that would be great.

AbdullahC
  • 6,649
  • 3
  • 27
  • 43
  • There is no notification for that beyond WM_ACTIVATE. Implementing the WS_EX_TOPMOST style by hand isn't very practical. Demanding that your window can never be covered isn't very practical. – Hans Passant Sep 23 '15 at 09:03
  • Why do you need this ? What are you trying to achieve ? – Jabberwocky Sep 23 '15 at 09:24
  • @MichaelWalz, We are running our application in XenDesktop mode and our window shows some real time information. But if some other application is also launched in that XenDekstop and that application is overlapping our window then we want to stop rendering. And once its moved out of our window then we want to start rendering again. Unfortunately, right now this kind of notifications are not supported by Citrix. – Ishan Rastogi Sep 23 '15 at 09:49
  • @IshanRastogi you should put this information in your question. – Jabberwocky Sep 23 '15 at 10:13

3 Answers3

3

There is no such API function. And usually the it isn't needed. WM_PAINT cares for itself.

If you get a WM_PAINT message you receive a region and a update rectangle of the area that needs a repaint. But it is a rectangle only, no complex region. Also there is a clipping region too.

But it should be possible to calculate the region by yourself. If we are talking about a top level window.

  • Create a rectangular region that is consists of your window rect
  • Walk all top level windows from back to front
  • Ignore all windows until you find your top level window
  • For each visible top level window create a rectangular region and XOR it with your current one.
  • Should be easy with GetWindow GW_HWNDNEXT

The resulting region is what you are searching for.

Again: There is no such function or message that determine, that is fired or can be executed to find such overlapping. There is no need for such an information. The system cares for itself with the appropriate WM_PAINT message. If an area is covered. There is no need for an action. If an area is uncovered WM_PAINT gets fired.

xMRi
  • 14,982
  • 3
  • 26
  • 59
  • Thanks @xMRi. I'm thinking of going with this approach, using repeated polling every 300 milliseconds or so. I think there will be a moment when the rendering will still be visible on top before I remove it, but hopefully it won't be a big UX issue. The other thing to check would be the performance, but hopefully there won't be a big hit there too because it's mainly mathematical calculations. Do let me know if you have any additional thoughts. Thanks a lot for the help! – AbdullahC Sep 24 '15 at 04:57
2

I think you should be able to get this kind of information when processing the WM_PAINT message, since normally the clipping region would be set accordingly. Calls to the RectVisible() function should tell you, for any part of your window, whether it "should be painted" (and so, whether it was just uncovered).

Medinoc
  • 6,577
  • 20
  • 42
  • Thanks for the tip, but unfortunately, WM_PAINT doesn't seem to be called when another window is brought in front or moved away. I think I'll have to go with the method xMRi describes, though I'll have to poll repeatedly. – AbdullahC Sep 24 '15 at 04:52
  • It's supposed to be when another window is moved away, but Citrix may be messing with that. – Medinoc Sep 24 '15 at 10:25
  • @medinoc If a window that covers 1/4 corner of the window is pulled away, the region gets added to the update region. Does the app not need to be redraw this if it hasn't changed since it was last drawn to, due to DWM, and given that it would still have been being updated and part of the clipping region if the whole client area were selected and previously updated/validated because it's only a 1/4 corner. Do applications generally check this or just always redraw? – Lewis Kelsey Feb 13 '21 at 07:58
  • @LewisKelsey I cannot say, I have not studied the effects of DWM. Sorry. – Medinoc Feb 13 '21 at 16:05
0

Despite this is not a solution to the OP's problem, I want to remark that once an overlapping window reveals part of your window (and also if you drag more area of your window back to screen), you will get a WM_ERASEBKGND message before the WM_PAINT.

SzieberthAdam
  • 3,999
  • 2
  • 23
  • 31