1

I want to create automated screenshots of my WinForm-application. So e.g. I have a Form containing a TabControl and some Buttons. Then in the code I want to iterate through the Forms children, get their position by their Location-property and highlight them in the screenshot. In the example I'd have the TabControl, get its active page, screenshot the complete application and draw a rectangle around the page.

This could totally be done by adding a custom "Screenshot"-UserControl, but I'd like to separate this from the rest of the application, like having a programm that spawns the actual Form and then iterates through its children.

My current approaches so far:

  • Using the managed win-api as a wrapper for PInvoke to iterate through the Form's handles
    • Failed, because I couldn't determine, what type of Control I got (I used the ClassName-property)
  • Using a custom AppDomain to spawn the application

I think the AppDomain-thing is the way to go, but I can't seem to find a way of grabbing an instanciated object from the custom domain. The AppDomain.CreateInstanceAndUnwrap(string name, string type) creates new instances, so this won't help me I guess.

AppDomain d = AppDomain.CreateDomain("CaptureDomain");
domain.ExecuteAssembly(path);

object[] o = domain.GetObjects(); // <-- like this

foreach (object k in o) 
{
    Console.WriteLine(o.GetType().Name);
     if (o is System.Windows.Forms.Form)
     {
         //iterate through children
     }
}

Question

How can I make automated screenshots of my application?

daniele3004
  • 13,072
  • 12
  • 67
  • 75
michaeln
  • 1,032
  • 17
  • 33
  • 2
    I can't get the link between the question title, and the question body... – Steve B Sep 18 '14 at 15:55
  • Sorry, whilst typing the body my question changed a bit, so the title didn't suit anymore. I edited it. – michaeln Sep 18 '14 at 16:08
  • I don't really get, why this question got a downvote. Just in case you're wondering, I'm not trying to exploit anything, I just want to automatically generate screenshots of my application for documentation purpose. – michaeln Sep 18 '14 at 18:05
  • I still don't understand why you want to play with AppDomain to take screenshot. Maybe you are facing the [XY problem](http://meta.stackexchange.com/questions/66377/what-is-the-xy-problem)? That said, [this question](http://stackoverflow.com/questions/1163761/capture-screenshot-of-active-window) has an answer that show how to take a screenshot of the current application. – Steve B Sep 19 '14 at 06:53
  • I think you're right, I edited it and it should be clearer now. – michaeln Sep 19 '14 at 09:15
  • I get your point, but I read his question and it's partly right, still not exactly what I wanted. I want to iterate through the Form's children controls. Like I said, I tried the WinApi to do so. But this API only allows me to get the actual object by its handle, not what type it is (so I could determine if I want a screenshot of it or not). – michaeln Oct 04 '14 at 13:20
  • I don't think you can get the control type *eg label, picturebox, panel etc...* from a handle. There are basic types like *static, button, edit* but thats it. – γηράσκω δ' αεί πολλά διδασκόμε Oct 04 '14 at 16:44
  • I read in another stack question, that WinForms has it's own way of creating the Instances. You actually _can_ create a Control from a handle, if it's in the same Runtime, but not from a handle _outside_ of the current application, so I thought the AppDomain or anything like this would be the way to go. – michaeln Oct 05 '14 at 12:20

1 Answers1

1

Consider taking a look at the UIA and MSAA (UIA's predecessor) APIs, both part of the Windows Automation API. This framework is typically used by UI Test Automation tools as well as accesibility tools (screen readers etc.) and is the recommended way of accessing Winforms / WPF user controls from external processes.

Windows Automation API

MSAA vs. UIA

andreask
  • 4,248
  • 1
  • 20
  • 25
  • The automation API looks a bit like what I want, but it still is it's own Framework. I'll mark this answer as solution if nobody else comes up with a solution closer to WinForms, as it will somehow work the way I need it. – michaeln Oct 05 '14 at 12:28