Handle to main window.

O

objectref

Hi to all,

is there a way to get the window handle of the main window of an application
or process ?
For example, if someone opens Microsoft Word, he gets a window so he/she can
write text.
Spy++ gives that this window is called _Wwg.

How we can get a handle to this window assuming that we do not know
beforehand the name of the process,
we just want to find the handle of every application's main window ?
(or the window that currently has the focus/caret).

Is this possible ??

Thanks a lot for any help,

objectref
 
S

Stoitcho Goutsev \(100\) [C# MVP]

Hi objectref,

..NET doesn't provide enumaration of windwos. However you can always use
PInvoke and call one of the windows enumeration APIs.

The only thing that you can do with .NET classes is to call
Process.GetProcesses() method to get array of all processes currently
started on the machine. Then for each process you can read the
MainWindowHandle property.

However, in this way you can read one of the process' toplevel windows.
Process may have more then one main windows. For example look at Windows and
Internet Explorer application. They have only one process and a separate
thread for each GUI. For these application you'll get only one of the main
windows. Another example could be .NET application that runs more then one
application domains, which of which has its own GUI.
 
O

objectref

Hi Stoitcho,

i know all this and that's why i am calling EnumChildWindows based on the
MainWindowHandle of each process.
The problem is that i want to call PostMessage and send some characters in
the window that have the focus at that time, ie, the application's active
window.

Do you know some way of doing that ??

Thanks a lot for your answer,

objectref


Stoitcho Goutsev (100) said:
Hi objectref,

.NET doesn't provide enumaration of windwos. However you can always use
PInvoke and call one of the windows enumeration APIs.

The only thing that you can do with .NET classes is to call
Process.GetProcesses() method to get array of all processes currently
started on the machine. Then for each process you can read the
MainWindowHandle property.

However, in this way you can read one of the process' toplevel windows.
Process may have more then one main windows. For example look at Windows and
Internet Explorer application. They have only one process and a separate
thread for each GUI. For these application you'll get only one of the main
windows. Another example could be .NET application that runs more then one
application domains, which of which has its own GUI.

--

Stoitcho Goutsev (100) [C# MVP]


objectref said:
Hi to all,

is there a way to get the window handle of the main window of an application
or process ?
For example, if someone opens Microsoft Word, he gets a window so he/she can
write text.
Spy++ gives that this window is called _Wwg.

How we can get a handle to this window assuming that we do not know
beforehand the name of the process,
we just want to find the handle of every application's main window ?
(or the window that currently has the focus/caret).

Is this possible ??

Thanks a lot for any help,

objectref
 
A

Adam Clauss

You will have to make calls to the Win32 API using PInvoke to call PostMessage. See:
http://www.pinvoke.net/

--
Adam Clauss
(e-mail address removed)

objectref said:
Hi Stoitcho,

i know all this and that's why i am calling EnumChildWindows based on the
MainWindowHandle of each process.
The problem is that i want to call PostMessage and send some characters in
the window that have the focus at that time, ie, the application's active
window.

Do you know some way of doing that ??

Thanks a lot for your answer,

objectref


Stoitcho Goutsev (100) said:
Hi objectref,

.NET doesn't provide enumaration of windwos. However you can always use
PInvoke and call one of the windows enumeration APIs.

The only thing that you can do with .NET classes is to call
Process.GetProcesses() method to get array of all processes currently
started on the machine. Then for each process you can read the
MainWindowHandle property.

However, in this way you can read one of the process' toplevel windows.
Process may have more then one main windows. For example look at Windows and
Internet Explorer application. They have only one process and a separate
thread for each GUI. For these application you'll get only one of the main
windows. Another example could be .NET application that runs more then one
application domains, which of which has its own GUI.

--

Stoitcho Goutsev (100) [C# MVP]


objectref said:
Hi to all,

is there a way to get the window handle of the main window of an application
or process ?
For example, if someone opens Microsoft Word, he gets a window so he/she can
write text.
Spy++ gives that this window is called _Wwg.

How we can get a handle to this window assuming that we do not know
beforehand the name of the process,
we just want to find the handle of every application's main window ?
(or the window that currently has the focus/caret).

Is this possible ??

Thanks a lot for any help,

objectref
 
O

objectref

Adam,

i am already making the calls using PostMessage... These calls succeds if
the process that
i use PostMessage to, has only one window, for example, a dos box.
I then find the process MainWindowHandle, and then using PostMessage i am
able to send
it some charcters, like the Environment.NewLine key.

But, if the app that is running is, for example, Notepad, then the above
solution does not work.
I have, somehow, to find the Active Window of the process and THEN i use
PostMessage
to send some the characters to.
Notepad is simplel, but MS Word, for example, is more complicated, it starts
with over that 10 windows with it
so i cannot tell for sure which is the active window that user is typing
textand so i will be
able to use PostMessage...
And of course, the processes that are running, are not known to me so i can
hardcode the handles
using Spy++, all that has to be dynamically determined.

Any other ideas ??...


objectref




Adam Clauss said:
You will have to make calls to the Win32 API using PInvoke to call PostMessage. See:
http://www.pinvoke.net/

--
Adam Clauss
(e-mail address removed)

Hi Stoitcho,

i know all this and that's why i am calling EnumChildWindows based on the
MainWindowHandle of each process.
The problem is that i want to call PostMessage and send some characters in
the window that have the focus at that time, ie, the application's active
window.

Do you know some way of doing that ??

Thanks a lot for your answer,

objectref


Stoitcho Goutsev (100) said:
Hi objectref,

.NET doesn't provide enumaration of windwos. However you can always use
PInvoke and call one of the windows enumeration APIs.

The only thing that you can do with .NET classes is to call
Process.GetProcesses() method to get array of all processes currently
started on the machine. Then for each process you can read the
MainWindowHandle property.

However, in this way you can read one of the process' toplevel windows.
Process may have more then one main windows. For example look at
Windows
and
Internet Explorer application. They have only one process and a separate
thread for each GUI. For these application you'll get only one of the main
windows. Another example could be .NET application that runs more then one
application domains, which of which has its own GUI.

--

Stoitcho Goutsev (100) [C# MVP]


Hi to all,

is there a way to get the window handle of the main window of an
application
or process ?
For example, if someone opens Microsoft Word, he gets a window so he/she
can
write text.
Spy++ gives that this window is called _Wwg.

How we can get a handle to this window assuming that we do not know
beforehand the name of the process,
we just want to find the handle of every application's main window ?
(or the window that currently has the focus/caret).

Is this possible ??

Thanks a lot for any help,

objectref
 
A

Adam Clauss

Hmm... I'm not sure about getting the "focused" window.

Is it only certain apps that this will occur in? You mention liked notepad and MSWord, are these part of a set list of applications
you need to interact with, or could it conceivable be ANY application? If it is a set list, you could come up with a routine that
locates the currently in use Window for a given program. Each program in your list would have its own method for doing this. Look
at the title of the main window to determine what program it is, then could use Spy++ to determine what pattern of windows to search
for - ex: Search for a window of class "....", then a child of class "..." and so forth using the FindWindow/FindWindowEx APIs.

Of course, if it is ANY application the above will not work. Would have to do some research to see if there is a
GetWindowWithCurrentFocus type API.

--
Adam Clauss
(e-mail address removed)

objectref said:
Adam,

i am already making the calls using PostMessage... These calls succeds if
the process that
i use PostMessage to, has only one window, for example, a dos box.
I then find the process MainWindowHandle, and then using PostMessage i am
able to send
it some charcters, like the Environment.NewLine key.

But, if the app that is running is, for example, Notepad, then the above
solution does not work.
I have, somehow, to find the Active Window of the process and THEN i use
PostMessage
to send some the characters to.
Notepad is simplel, but MS Word, for example, is more complicated, it starts
with over that 10 windows with it
so i cannot tell for sure which is the active window that user is typing
textand so i will be
able to use PostMessage...
And of course, the processes that are running, are not known to me so i can
hardcode the handles
using Spy++, all that has to be dynamically determined.

Any other ideas ??...


objectref




Adam Clauss said:
You will have to make calls to the Win32 API using PInvoke to call PostMessage. See:
http://www.pinvoke.net/

--
Adam Clauss
(e-mail address removed)

Hi Stoitcho,

i know all this and that's why i am calling EnumChildWindows based on the
MainWindowHandle of each process.
The problem is that i want to call PostMessage and send some characters in
the window that have the focus at that time, ie, the application's active
window.

Do you know some way of doing that ??

Thanks a lot for your answer,

objectref


Hi objectref,

.NET doesn't provide enumaration of windwos. However you can always use
PInvoke and call one of the windows enumeration APIs.

The only thing that you can do with .NET classes is to call
Process.GetProcesses() method to get array of all processes currently
started on the machine. Then for each process you can read the
MainWindowHandle property.

However, in this way you can read one of the process' toplevel windows.
Process may have more then one main windows. For example look at Windows
and
Internet Explorer application. They have only one process and a separate
thread for each GUI. For these application you'll get only one of the main
windows. Another example could be .NET application that runs more then one
application domains, which of which has its own GUI.

--

Stoitcho Goutsev (100) [C# MVP]


Hi to all,

is there a way to get the window handle of the main window of an
application
or process ?
For example, if someone opens Microsoft Word, he gets a window so he/she
can
write text.
Spy++ gives that this window is called _Wwg.

How we can get a handle to this window assuming that we do not know
beforehand the name of the process,
we just want to find the handle of every application's main window ?
(or the window that currently has the focus/caret).

Is this possible ??

Thanks a lot for any help,

objectref
 
A

Adam Clauss

This sounds like it might do it:
GetForegroundWindow()
MSDN:
The GetForegroundWindow function returns a handle to the foreground window (the window with which the user is currently working).

--
Adam Clauss
(e-mail address removed)

objectref said:
Adam,

i am already making the calls using PostMessage... These calls succeds if
the process that
i use PostMessage to, has only one window, for example, a dos box.
I then find the process MainWindowHandle, and then using PostMessage i am
able to send
it some charcters, like the Environment.NewLine key.

But, if the app that is running is, for example, Notepad, then the above
solution does not work.
I have, somehow, to find the Active Window of the process and THEN i use
PostMessage
to send some the characters to.
Notepad is simplel, but MS Word, for example, is more complicated, it starts
with over that 10 windows with it
so i cannot tell for sure which is the active window that user is typing
textand so i will be
able to use PostMessage...
And of course, the processes that are running, are not known to me so i can
hardcode the handles
using Spy++, all that has to be dynamically determined.

Any other ideas ??...


objectref




Adam Clauss said:
You will have to make calls to the Win32 API using PInvoke to call PostMessage. See:
http://www.pinvoke.net/

--
Adam Clauss
(e-mail address removed)

Hi Stoitcho,

i know all this and that's why i am calling EnumChildWindows based on the
MainWindowHandle of each process.
The problem is that i want to call PostMessage and send some characters in
the window that have the focus at that time, ie, the application's active
window.

Do you know some way of doing that ??

Thanks a lot for your answer,

objectref


Hi objectref,

.NET doesn't provide enumaration of windwos. However you can always use
PInvoke and call one of the windows enumeration APIs.

The only thing that you can do with .NET classes is to call
Process.GetProcesses() method to get array of all processes currently
started on the machine. Then for each process you can read the
MainWindowHandle property.

However, in this way you can read one of the process' toplevel windows.
Process may have more then one main windows. For example look at Windows
and
Internet Explorer application. They have only one process and a separate
thread for each GUI. For these application you'll get only one of the main
windows. Another example could be .NET application that runs more then one
application domains, which of which has its own GUI.

--

Stoitcho Goutsev (100) [C# MVP]


Hi to all,

is there a way to get the window handle of the main window of an
application
or process ?
For example, if someone opens Microsoft Word, he gets a window so he/she
can
write text.
Spy++ gives that this window is called _Wwg.

How we can get a handle to this window assuming that we do not know
beforehand the name of the process,
we just want to find the handle of every application's main window ?
(or the window that currently has the focus/caret).

Is this possible ??

Thanks a lot for any help,

objectref
 
S

Stoitcho Goutsev \(100\) [C# MVP]

objectref,

If you want to send keystrokes to the active application use SendKeys class.
This is the easiest.
It might be pretty reasonable as long as there is only one focused window
and it belongs to the foreground (active) window.

Anyways if you want to get the handle to the focused window you need to do a
bit more.


[DllImport("user32.dll")]
private static extern IntPtr GetForegroundWindow();
[DllImport("user32.dll")]
private static extern IntPtr GetWindowThreadProcessId(IntPtr hwnd, IntPtr
lpdwProcessId);
[DllImport("user32.dll")]
private static extern bool AttachThreadInput(IntPtr idAttach , IntPtr
idAttachTo, bool fAttach);
[DllImport("user32.dll")]
private static extern IntPtr GetFocus();

private void button1_Click(object sender, System.EventArgs e)
{
IntPtr thisThreadID = new IntPtr(AppDomain.GetCurrentThreadId());
IntPtr activeHwnd = GetForegroundWindow();
if(activeHwnd != IntPtr.Zero)
{
IntPtr activeThreadID = GetWindowThreadProcessId(activeHwnd,
IntPtr.Zero);
if(AttachThreadInput(activeThreadID, thisThreadID, true))
{
IntPtr focusedHwnd = GetFocus();
if(focusedHwnd != IntPtr.Zero)
{
Console.WriteLine("FocusedHwnd: {0}\n====", focusedHwnd.ToString());
}
AttachThreadInput(activeThreadID, thisThreadID, false);
}
}
}

Bare in mind that the thread executing that code has to be a UI thread. and
that this code cannot detect its own focused window because it cannot attach
a thread to itself. If you want to get your own focused window it is quite
straightforward using Control class.

--
HTH
Stoitcho Goutsev (100) [C# MVP]


objectref said:
Hi Stoitcho,

i know all this and that's why i am calling EnumChildWindows based on the
MainWindowHandle of each process.
The problem is that i want to call PostMessage and send some characters in
the window that have the focus at that time, ie, the application's active
window.

Do you know some way of doing that ??

Thanks a lot for your answer,

objectref


Stoitcho Goutsev (100) said:
Hi objectref,

.NET doesn't provide enumaration of windwos. However you can always use
PInvoke and call one of the windows enumeration APIs.

The only thing that you can do with .NET classes is to call
Process.GetProcesses() method to get array of all processes currently
started on the machine. Then for each process you can read the
MainWindowHandle property.

However, in this way you can read one of the process' toplevel windows.
Process may have more then one main windows. For example look at Windows and
Internet Explorer application. They have only one process and a separate
thread for each GUI. For these application you'll get only one of the main
windows. Another example could be .NET application that runs more then one
application domains, which of which has its own GUI.

--

Stoitcho Goutsev (100) [C# MVP]


objectref said:
Hi to all,

is there a way to get the window handle of the main window of an application
or process ?
For example, if someone opens Microsoft Word, he gets a window so
he/she
can
write text.
Spy++ gives that this window is called _Wwg.

How we can get a handle to this window assuming that we do not know
beforehand the name of the process,
we just want to find the handle of every application's main window ?
(or the window that currently has the focus/caret).

Is this possible ??

Thanks a lot for any help,

objectref
 
O

objectref

Hmmmm....

at first, thanks for your solution, it seems than know i am close enough,
but:

Let's assume that, for simplicity reasons, i want to test your code with a
pre-known
window handle. I take this from enumerating processes, find, let's say an
open Notepad window
and then get it's MainWindowHandle, that is, 3475108.

But, the below code does not work. It reaches the "PostMessage"line but i do
not
get an Enter hit in notepad app.
Can you figure out why ?


private void button1_Click(object sender, System.EventArgs e)
{
IntPtr thisThreadID = new IntPtr(AppDomain.GetCurrentThreadId());
IntPtr activeHwnd = GetForegroundWindow();

if (activeHwnd != IntPtr.Zero)
{
IntPtr activeThreadID = GetWindowThreadProcessId((IntPtr) 3475108,
IntPtr.Zero);
if (AttachThreadInput(activeThreadID, thisThreadID, true))
{
IntPtr focusedHwnd = GetFocus();
if (focusedHwnd != IntPtr.Zero)
{
//Console.WriteLine("FocusedHwnd: {0}\n====",
focusedHwnd.ToString());
listBox1.Items.Add("FocusedHwnd: {0}\n====" +
focusedHwnd.ToString());
PostMessage((IntPtr) focusedHwnd, WM_CHAR, 13, 0);
}
AttachThreadInput(activeThreadID, thisThreadID, false);
}
}
}
 
S

Stoitcho Goutsev \(100\) [C# MVP]

Hi objecref,

The problem I believe is that the Notepad is not the active application. How
I said there is only one focused window at a time and it is or it is a child
to the foreground (active) window. If you try GetFocus for a thread which
hasn't created the foreground window it always return null.

Just a little reminder. Even though you can post key messages to a window it
is not guarantee that the target window will accept them correctly. Each
input (UI) thread has associated keystate buffers and so on that play some
role in the key processing. If you just post key messages it won't go thru
all the internal key processing and won't update those structures. Methods
like GetKeyState, GetAsyncKeyState, GetKeyboardState and so on which
application use won't work. Key messages are only notifications aftere all
the work of precessing the keyboard is done. The only way to simulate real
keyboard activity is to use either SendInput or keybd_event API or SendKeys
class in .NET.
However because they synthesizes keyboard strokes, mouse movements and mouse
button clicks it you cannot specify the target window. Keystorkes go to the
focused window, mouse events go to the window under the mouse cursor
position.
Anyways if you still want to use post messages you may consider using
AttachThreadInput and SetKeyboardState method to handle some of the
situations. However some keys such as CapsLock, NumLock, etc cannot be
simulated unless SendInput or keybd_event are used.
 
O

objectref

Hi Stoitcho,

i finally did that:
I use EnumWindows and EnumChildWindows and i present the user
in a treeview their relation for all open processes in the machine.
Then, the user select the windows that he needs to send keystrokes
and an adjustable timer is responsible to send them at timer intervals.

I did that because, as you said, the GetFocus needs to have the windows
in the foreground. I need these windows to be minimized and the whole
process
need not have any interaction wit the user, no flashing windows, no
SetForeGroundWindow,
nothing of all these.
So, as you understand, SendKeys was not an option for me. Imagine for
example, to have a Notepad app,
a dos-box and another one Winword app, running minimized and all getting the
same characters
at some timer interval, without interrupt the use working on something else
in that machine...

Anyway, the solution as it is right now is working perfectly.

Thanks again, you and Adam for your help!

objectref



Stoitcho Goutsev (100) said:
Hi objecref,

The problem I believe is that the Notepad is not the active application. How
I said there is only one focused window at a time and it is or it is a child
to the foreground (active) window. If you try GetFocus for a thread which
hasn't created the foreground window it always return null.

Just a little reminder. Even though you can post key messages to a window it
is not guarantee that the target window will accept them correctly. Each
input (UI) thread has associated keystate buffers and so on that play some
role in the key processing. If you just post key messages it won't go thru
all the internal key processing and won't update those structures. Methods
like GetKeyState, GetAsyncKeyState, GetKeyboardState and so on which
application use won't work. Key messages are only notifications aftere all
the work of precessing the keyboard is done. The only way to simulate real
keyboard activity is to use either SendInput or keybd_event API or SendKeys
class in .NET.
However because they synthesizes keyboard strokes, mouse movements and mouse
button clicks it you cannot specify the target window. Keystorkes go to the
focused window, mouse events go to the window under the mouse cursor
position.
Anyways if you still want to use post messages you may consider using
AttachThreadInput and SetKeyboardState method to handle some of the
situations. However some keys such as CapsLock, NumLock, etc cannot be
simulated unless SendInput or keybd_event are used.

--
HTH
Stoitcho Goutsev (100) [C# MVP]


objectref said:
Hmmmm....

at first, thanks for your solution, it seems than know i am close enough,
but:

Let's assume that, for simplicity reasons, i want to test your code with a
pre-known
window handle. I take this from enumerating processes, find, let's say an
open Notepad window
and then get it's MainWindowHandle, that is, 3475108.

But, the below code does not work. It reaches the "PostMessage"line but
i
do
not
get an Enter hit in notepad app.
Can you figure out why ?


private void button1_Click(object sender, System.EventArgs e)
{
IntPtr thisThreadID = new IntPtr(AppDomain.GetCurrentThreadId());
IntPtr activeHwnd = GetForegroundWindow();

if (activeHwnd != IntPtr.Zero)
{
IntPtr activeThreadID = GetWindowThreadProcessId((IntPtr) 3475108,
IntPtr.Zero);
if (AttachThreadInput(activeThreadID, thisThreadID, true))
{
IntPtr focusedHwnd = GetFocus();
if (focusedHwnd != IntPtr.Zero)
{
//Console.WriteLine("FocusedHwnd: {0}\n====",
focusedHwnd.ToString());
listBox1.Items.Add("FocusedHwnd: {0}\n====" +
focusedHwnd.ToString());
PostMessage((IntPtr) focusedHwnd, WM_CHAR, 13, 0);
}
AttachThreadInput(activeThreadID, thisThreadID, false);
}
}
}
 
H

hisham serhan

hii
i have read the problem and i have the same problem;
but i cant fix it.
i am working on a MY Task Manager program in c#
i wana do exactly the same one in Windows xp

almost i don but i need your help :
How can i get the list curent Applications Running (windows)
i got the processes list but i need the Application list.

i have thinking that it`s the same problem but you looked for a windows
opens
please help to do that one
thx for all the informations
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Top