0

I have a legacy application which is a mix of WPF and Windows Forms. Essentially a WPF app is loaded onto a Windows Forms Application by adding an ElementHost onto the Windows Form. This WPF application then loads a WPF user control onto it. Embedded within this WPF User control is a legacy Windows Control (a custom browser control) that eventually derives from System.Windows.Forms

Is there a way to grab a handle to this control dynamically from the code? We don't know the name the control would be given when it is rendered. All we know is the basetype of the control which as I mentioned derives from System.WIndows.Forms.

All the examples I have seen so far discuss how a child that is eventually a DependencyObject can be discovered dynamically. I haven't yet come across an example that explains how an old school Windows Form control can be discovered programmatically within a WPF app.

Nikhil
  • 3,304
  • 1
  • 25
  • 42

2 Answers2

0

In order to host Winforms control in WPF control, it has to use WindowsFormsHost. The WindowsFormsHost derives from DependencyObject.

You'd have to locate the WindowsFormsHost element in WPF app, and then you have access to Child property that contains the WebBrowser control.

The pseudocode:

var controlYoureLookingFOr = GiveMeAllChildren(WPFApp)
  .OfType<WindowsFormsHost>
  .First();

var browser = (WebBrowser.Or.Something)controlYoureLookingFOr.Child;
Nikhil
  • 3,304
  • 1
  • 25
  • 42
Erti-Chris Eelmaa
  • 25,338
  • 6
  • 61
  • 78
0

To complete the answer here is the recursion part that I added to ensure the whole window or the parent control and all its descendants are traversed

   public static IEnumerable<T> FindAllChildrenByType<T>(this System.Windows.Forms.Control control)
    {
        IEnumerable<System.Windows.Forms.Control> controls = control.Controls.Cast<System.Windows.Forms.Control>();
        return controls
            .OfType<T>()
            .Concat<T>(controls.SelectMany<System.Windows.Forms.Control, T>(ctrl => FindAllChildrenByType<T>(ctrl)));
    }
    public static IEnumerable<T> FindVisualChildren<T>(this DependencyObject depObj) where T : DependencyObject
    {
        if (depObj != null)
        {
            for (int i = 0; i < VisualTreeHelper.GetChildrenCount(depObj); i++)
            {
                DependencyObject child = VisualTreeHelper.GetChild(depObj, i);
                if (child != null && child is T)
                {
                    yield return (T)child;
                }

                foreach (T childOfChild in FindVisualChildren<T>(child))
                {
                    yield return childOfChild;
                }
            }
        }
    }

You can then use it as

 var windowsFormHost = parentControl.FindVisualChildren<WindowsFormsHost>();
            foreach (var item in windowsFormHost)
            {
                var htmlcontrols = item.Child.FindAllChildrenByType<{sometypehere}
                foreach (var control in htmlcontrols)
                {
                }
             }
Nikhil
  • 3,304
  • 1
  • 25
  • 42