tags:

views:

102

answers:

2

Hi, I am trying to get the HWND and ThreadID for currently Focussed Window.

Usually GetForegroundWindow() and then then calling GetThreadProcessId() gives me the correct information.

But in Case of IE8 the HWnd the GetForegroundwindow() gives me the HWND of the IE Frame but actually the focussed window (the document object or Internet Explorer_server) is different (running in a different process). So GetForegroundWindow() approach does not work.

So I used GetGuiThreadInfo(DWORD tid) , and passed it the threadId i obtained from GetForegroundWindow.. something like this;

DWORD tid = GetWindowThreadProcessId(GetForegroundWindow(),0);
GetGuiThreadInfo(tid,&guiThreadInfoObject);
HWND focus = guiThreadInfoObject.hwndFocus;

Using the above approach I get the correct HWND for the Internet Explorer_server object which is correct. However I did not understand , even though the GetGuiThreadInfo() is getting the ThreadId of a thread in a different process which is IE Frame , howcome it is able get me the threadinfo about Internet Explorer_server object which is on a different Process and thread?

Thanks

A: 

GetWindowThreadProcessId retrieves the thread ID that created the (in your case foreground) window.
guiThreadInfoObject.hwndFocus is the window that ha input focus.

There's some leeway here - I haven't found any place that specifically states the foreground window is the one with input focus. (maybe it retrieves already the top level parent/owner?).

Also, AttachThreadInput may slightly change the game - by setting a threads input focus to a window of a different process.

Anyway, since it's not spelled out explicitely, I wouldn't bet my life on that behavior - that means testing on many systems and treating the method as a weak spot that should be improved if possible.

peterchen
Thanks.Now as I am getting correct result now.. does it mean that will always be the case. Meaning I want to find out if this is the expected behaviour of the GetGUIThreadInfo() method and it will behave the same for any other application like it does for IE8.
Prakash
As I said, it makes sense, but isn't said explicitely in the documentation.
peterchen
+2  A: 

Getting the window with the focus is pretty easy with GetFocus(). Although I think GetGuiThreadInfo() uses internal data from the window manager. Your approach is liable to fail if IE is minimized or doesn't have the focus.

Use EnumChildWindows() instead, iteratively for each child you find, until you get a window whose GetClassName() call returns "Internet Explorer_Server".

Thanks for bringing this up btw. What IE is doing is expressly forbidden in the docs for SetParent(). I only knew of Acrobat violating this rule, but now you provided evidence of a Microsoft program doing this. That settles it, it is no longer a rule!

Hans Passant
Thanks, but the GetFocus() always return 0 as the window that has the focus is on a different thread.And the application could be anything ..IE8 is just one of them. So I want something generic so I can't use EnumChildWindows() to look for Internet Explorer_server .
Prakash
"Something generic" doesn't make sense. If you want to mess with the windows of another process, you'll need to customize your code to deal with the specific process and its implementation details.
Hans Passant