frankborty
frankborty

Reputation: 122

WPF: DataTemplate binding for different usercontrol

I'm new on WPF and I'm tryng to figure out how to implement a binding with different type of user control. After the user clicks a button, a usercontrol (a simple shape like rectangle or ellipse) is added to the window.

I'm tryng to use an MVVM approach so the xaml appears as follow:

    ...
    Title="{Binding Path=Titolo}"
    Height="450" Width="800"
    d:DataContext="{d:DesignInstance vm:MainWindowViewModel}">


<Canvas>
    <Button Content="Add Shape" Command="{Binding TestCommand}"/>
    <ItemsControl ItemsSource="{Binding RectCollection}">
        <ItemsControl.ItemsPanel>
            <ItemsPanelTemplate>
                <Canvas />
            </ItemsPanelTemplate>
        </ItemsControl.ItemsPanel>
        <ItemsControl.ItemTemplate>
            <DataTemplate>
                <uc:MyCustomRectangle/>
            </DataTemplate>
        </ItemsControl.ItemTemplate>

        <ItemsControl.ItemContainerStyle>
            <Style>
                <Setter Property="Canvas.Left" Value="{Binding xLT}" />
                <Setter Property="Canvas.Top" Value="{Binding yLT}" />
            </Style>
        </ItemsControl.ItemContainerStyle>
    </ItemsControl>
</Canvas>

All works fine but I want to add different type of UserControl (not only MyCustomRectangle) using the same button (for example, randomly adding rectangle or ellipse). A possible solution could be duplicate the section of ItemsControl and select a different collection of binding:

<Canvas>
    <Button Content="Add Shape" Command="{Binding TestCommand}"/>
    <ItemsControl ItemsSource="{Binding RectCollection}">
        <ItemsControl.ItemsPanel>
            <ItemsPanelTemplate>
                <Canvas />
            </ItemsPanelTemplate>
        </ItemsControl.ItemsPanel>
        <ItemsControl.ItemTemplate>
            <DataTemplate>
                <uc:MyCustomRectangle/> <!-- bind to my usercontrol -->
            </DataTemplate>
        </ItemsControl.ItemTemplate>

        <ItemsControl.ItemContainerStyle>
            <Style>
                <Setter Property="Canvas.Left" Value="{Binding xLT}" />
                <Setter Property="Canvas.Top" Value="{Binding yLT}" />
            </Style>
        </ItemsControl.ItemContainerStyle>
    </ItemsControl>
 
    <ItemsControl ItemsSource="{Binding EllipseCollection}">
        <ItemsControl.ItemsPanel>
            <ItemsPanelTemplate>
                <Canvas />
            </ItemsPanelTemplate>
        </ItemsControl.ItemsPanel>
        <ItemsControl.ItemTemplate>
            <DataTemplate>
                <uc:MyCustomEllipse/>  <!-- bind to my usercontrol -->
            </DataTemplate>
        </ItemsControl.ItemTemplate>

        <ItemsControl.ItemContainerStyle>
            <Style>
                <Setter Property="Canvas.Left" Value="{Binding xLT}" />
                <Setter Property="Canvas.Top" Value="{Binding yLT}" />
            </Style>
        </ItemsControl.ItemContainerStyle>
    </ItemsControl>
</Canvas>

I don't think this is the correct solution, especially because I would to add many different types of shapes (and also text and images). So, if exist, what is the correct way to bind a data template to different type of usercontrol? Is MVVM the correct approach to solve this problem?

Upvotes: 0

Views: 456

Answers (1)

Klamsi
Klamsi

Reputation: 906

What you can do is to bind to a global list with all Shapes.

And then you can define different DataTemplates for different Types.

Like this:

<ItemsControl.Resources>
    <DataTemplate DataType="{x:Type MyType1}">
        ...
    </DataTemplate>
    <DataTemplate DataType="{x:Type MyType2}">
        ....
    </DataTemplate>
</ItemsControl.Resources>

Upvotes: 1

Related Questions