slimshady
slimshady

Reputation: 87

ItemTemplateSelector not working for ListView without Binding

I have a ListView whose ItemsSource I set programmatically in the code behind. I used to only have one Template but now I want to use multiple templates and select the template according to the item I add to the ListView.

This is the XAML Code I have:

<Page.Resources>
<local:TemplateSelector x:Key="myTemplateSelector" TemplateA="{StaticResource TemplateA}" TemplateB="{StaticResource TemplateB}" />

<!-- TemplateA and TemplateB -->
</Page.Resources>

 <ListView
        x:Name="MasterListView"
        Grid.Row="1"
        ItemContainerTransitions="{x:Null}" 
        ItemTemplateSelector="{StaticResource myTemplateSelector}"
        IsItemClickEnabled="True"
        ItemClick="MasterListView_ItemClick"/>

I then set the ItemSource of the ListView and this is my TemplateSelector:

  public class TemplateSelector : DataTemplateSelector
{
    public DataTemplate TemplateA { get; set; }
    public DataTemplate TemplateB { get; set; }

    public new DataTemplate SelectTemplate(object item, DependencyObject container)
    {

        return TemplateA;
    }
}

However, this does not work. Instead of my desired template I always get the same text for every item: AppName.ViewModels.ViewModel1 (the type of the data I want to show).

In the past when I only had one itemtemplate I used this in the xaml and it worked:

        <ListView
        x:Name="MasterListView"
        Grid.Row="1"
        ItemContainerTransitions="{x:Null}" 
        ItemTemplate="{StaticResource TemplateA}"
        IsItemClickEnabled="True"
        ItemClick="MasterListView_ItemClick"/>

How can I get the ItemTemplateSelector to work? I placed breakpoints there but it does not even get called.

Upvotes: 1

Views: 1693

Answers (2)

user1515791
user1515791

Reputation:

 public override DataTemplate SelectTemplate(object item, DependencyObject container)

instead of

public new DataTemplate SelectTemplate(object item, DependencyObject container)

EDIT, due to access modifier, this is the signature for 4.5.2 (note it's public):

#region Assembly PresentationFramework, Version=4.0.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35
// C:\Program Files (x86)\Reference Assemblies\Microsoft\Framework\.NETFramework\v4.5.2\PresentationFramework.dll
#endregion

namespace System.Windows.Controls
{
//
// Summary:
//     Provides a way to choose a System.Windows.DataTemplate based on the data object
//     and the data-bound element.
public class DataTemplateSelector
{
    //
    // Summary:
    //     Initializes a new instance of the System.Windows.Controls.DataTemplateSelector
    //     class.
    public DataTemplateSelector();

    //
    // Summary:
    //     When overridden in a derived class, returns a System.Windows.DataTemplate based
    //     on custom logic.
    //
    // Parameters:
    //   item:
    //     The data object for which to select the template.
    //
    //   container:
    //     The data-bound object.
    //
    // Returns:
    //     Returns a System.Windows.DataTemplate or null. The default value is null.
    public virtual DataTemplate SelectTemplate(object item, DependencyObject container);
}
}

Upvotes: 1

Jay Zuo
Jay Zuo

Reputation: 15758

As it is described in the Remarks of DataTemplateSelector.SelectTemplate(Object, DependencyObject) method:

App code typically doesn't call SelectTemplate methods; the methods exists so that the infrastructure can call it while choosing the correct templates based on using a DataTemplateSelector instance from a property value such as ItemsControl.ItemsTemplateSelector. To provide a specific template in a derived class, override the SelectTemplateCore(Object, DependencyObject) method.

So we should use

protected override DataTemplate SelectTemplateCore(object item, DependencyObject container)

instead of

public new DataTemplate SelectTemplate(object item, DependencyObject container)

Upvotes: 2

Related Questions