Search code examples
c#wpfelementhost

How to use ContentPresenter with ElementHost


I have

  • three WPF UserControls with their Viewmodels
  • one WPF container for displaying one of the WPF Usercontrols
  • WinForm Usercontrol

I want: display different WPF UserControl, which I set is in WinForms User Control

public partial class WinContainer : UserControl
    {
        public WinContainer()
        {
            InitializeComponent();
            WPFContainer WPFControl = new WPFContainer();
            PartPageViewModel ss = new PartPageViewModel();
            WPFControl.DataContext = ss;
            ElementHost elHost = new ElementHost();
           elHost.Child = WPFControl;
            elHost.Dock = DockStyle.Fill;
            this.Controls.Add(elHost);
        }
    }
<UserControl x:Class="MDMSpecification.Views.WPFContainer"
             xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
             xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
             xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
             xmlns:local="clr-namespace:MDMSpecification.Views"
             xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
             xmlns:services="clr-namespace:MDMSpecification.Services"
             xmlns:viewModels="clr-namespace:MDMSpecification.ViewModels"
             d:DesignHeight="300"
             d:DesignWidth="300"
             mc:Ignorable="d">
    <UserControl.Resources>
        <DataTemplate x:Key="Assembly" DataType="{x:Type viewModels:AssemblyPageViewModel}">
            <local:AssemblyPageView />
        </DataTemplate>
        <DataTemplate x:Key="Part" DataType="{x:Type viewModels:PartPageViewModel}">
            <local:PartPageView />
        </DataTemplate>
        <DataTemplate x:Key="Drawing" DataType="{x:Type viewModels:DrawingPageViewModel}">
            <local:DrawingPageView />
        </DataTemplate>
    </UserControl.Resources>
    <StackPanel>
        <ContentPresenter   Content="{Binding}"  />
    </StackPanel>
</UserControl>

In result I have this: enter image description here

What's wrong with my code?


Solution

  • Remove x:Key="XYZ" from DataTemplate.
    In order to apply a DataTemplate automatically to DataType you should omit the key.
    For example:

    <DataTemplate DataType="{x:Type viewModels:AssemblyPageViewModel}">
         <local:AssemblyPageView />
    </DataTemplate>
    

    This xaml is equivalent to:

    <DataTemplate x:Key={x:Type viewModels:AssemblyPageViewModel} 
                  DataType="{x:Type viewModels:AssemblyPageViewModel}">
        <local:AssemblyPageView />
    </DataTemplate>
    

    DataTemplates with a key should be applied explicitly like this:

    <ContentPresenter Content="{Binding}" ContentTemplate="{StaticResource Assembly}"  />