Blog Stats
  • Posts - 99
  • Articles - 5
  • Comments - 236
  • Trackbacks - 105

 

Hosting another process in your GUI

 

Someone asked about this today on MS newsgroups so I figured I would blog the answer as others may find this to be useful functionality .. I know I have!

I need to display two VB6 applications side by side within a single
'windows manager'

My thought is that I could use a split screen form, using the 2.0
framework and visual studio 2005, that display the UI of each of the
VB6 apps within some control or container on the windows form.

The obvious solution is to rebuild the VB6 apps as com objects and
place the com objects on the form. Is there a solution that doesn't
require me to rebuild the VB6 apps?

The code that solves this problem ...

    public class Native {
        [DllImport("user32.dll", SetLastError = true)]
        private static extern uint SetParent(IntPtr hWndChild, IntPtr hWndNewParent);
        public static void LoadProcessInControl(string _Process, Control _Control)
        {
            System.Diagnostics.Process p = System.Diagnostics.Process.Start(_Process);
            p.WaitForInputIdle();
            Native.SetParent(p.MainWindowHandle, _Control.Handle);
        }
    }

Now lets create a quick app to show the functionality (2.0)

Put a splitter on the form (default names or change in code).

    public partial class Form1 : Form {
        public Form1()
        {
            InitializeComponent();
        }
        private void Form1_Load(object sender, EventArgs e)
        {
            LoadProcessInControl("notepad.exe", this.splitContainer1.Panel1);
            LoadProcessInControl("notepad.exe", this.splitContainer1.Panel2);
        }
    }

When run this it will produce the following output ...

 

You can also maximize the processes and they will fill the container area... add the following code to the native class

        [DllImport("user32.dll")]
        private static extern
        bool ShowWindowAsync(IntPtr hWnd, int nCmdShow);

        private const int SW_HIDE = 0;
        private const int SW_SHOWNORMAL = 1;
        private const int SW_SHOWMINIMIZED = 2;
        private const int SW_SHOWMAXIMIZED = 3;
        private const int SW_SHOWNOACTIVATE = 4;
        private const int SW_RESTORE = 9;
        private const int SW_SHOWDEFAULT = 10;
        private static bool ShowWindow(Process _Process, int nCmdShow)
        {
            return ShowWindowAsync(_Process.MainWindowHandle, nCmdShow);
        }

now add the following line to the end of LoadProcessInControl

ShowWindow(p, SW_SHOWMAXIMIZED);

Now when we run our app we see the following.

 

You can also do this with MDI apps ...

Remove the splitter control and make the form a MDI container ...

Now change form load to ..

        private void Form1_Load(object sender, EventArgs e)
        {
            Native.LoadProcessInControl("notepad.exe", this);
            Native.LoadProcessInControl("notepad.exe", this);
        }

The output when run will look like this ...

Note that the notepad windows have become MDI children of the application.

 

 

 

  • Share This Post:
  • Share on Twitter
  • Share on Facebook
  • Share on Technorati

Feedback

# re: Hosting another process in your GUI

Gravatar This works great with Notepad and Iexplore etc but doesn't work with vb6 applications. the MainWindowHandle doesn't seem to return the correct handle and therefore doesn't pull in the form. 11/8/2006 5:22 AM | Shane

# re: Hosting another process in your GUI

Gravatar I tried this with a tabControl1 and when the main form is re-sized the Notepad does not re-size. How can Notepad be re-sized when the main form is re-sized 7/11/2008 2:40 PM | Marty Skitch

# re: Hosting another process in your GUI

Gravatar I just see your example .i have some question .Is it possible to use in a same winform 4 panel with notepad that open in each one and inside the panel .can we use notepad with all the function open file etc...can we do the same with paint and every application exe .I use sharpdevelop and have no idea how to insert the code as your example .The result of your example is interesting .Thanks 10/22/2008 10:53 AM | NC

# re: Hosting another process in your GUI

Gravatar Like an interface running with different application 10/22/2008 10:57 AM | NC

# re: Hosting another process in your GUI

Gravatar hi bro,
The code you posted on your blog doesn't exactly solve the problem . But the output of that program is very interesting.

thnx a lots 4 sharing...

Nifty Tips || Sure Shot Tips

9/17/2010 12:57 AM | Nifty Tips

# Mr

Gravatar Interesting articles you place here.
It would be useful to read anything more concerning this topic.
Thnx for tell that information.
With best regards Angela!

Sureshot Commodity Tips 10/20/2010 2:35 AM | commodity tips mcx

# re: Hosting another process in your GUI

Gravatar Hi,

here some more tips concerning this topic (re-parenting).:

get Handles:
If you are starting an app you should get the handle in most cases from the process by MainWindowHandle. BUT, some apps dont create their window handles directly at start or are running in 'iconified' state e.g. the office communicator. In this case you have to use the 'FindWindow' function.

Sometimes you will have the problem that your re-parented window wil not accept text input, then you should try to use SetFocus() before the SetParent().

Appearence of the re-parented apps:
If you want to manipulate the window styles, e.g. remove the titlebar, you can use SetWindowLong in kombination with SetWindowPos and its flags ( for example: SWP_FRAMECHANGED | SWP_NOMOVE) (this will activate the style settings!!!).

Sometimes it will be tricky to get it working properly, then you will have to try out a different order of the commands. In my (little) experience the probably best order is:
1) set styles including the child flag
2) set focus to the app you want to reparent
3) call SetParent()
4) call SetWindowPos() ; call refresh() on the form or panel

best regards
Ralf 1/11/2011 6:17 AM | Ralf Z

# re: Hosting another process in your GUI

Gravatar Can I have you code please ? 2/9/2011 8:13 AM | Gunawan

# re: Hosting another process in your GUI

Gravatar You should call AttachThreadInput() in order to prevent losing focus of main window (Form1) 5/22/2011 1:00 PM | Torvin

# re: Hosting another process in your GUI

Gravatar So would this be how explorer.exe works? 11/6/2011 9:23 PM | Cole

Post A Comment
Title:
Name:
Email:
Website:
Comment:
Verification:
 
 

 

 

Copyright © Greg Young