templatesmvvmuwpflipview

TemplateSelector for UWPs FlipView


I've created a Xamarin.Forms UWP app and it felt to me like a bucket full of cement on your feet while trying to cross the mediterranean by swimming. So I switched to native UWP programming.

My application gets created to 95 % dynamically. All pages controls on the pages are dependend on what's saved in the database.

I have one login-page, a carouselPage (FlipView) and a QuitPage.

All other pages are dynamically loaded and added to the FlipView-ItemsSource.

In Xamarin I had a TemplateSelector like the one in this link: https://github.com/alexrainman/CarouselView/blob/master/Demo/Views/MyTemplateSelector.cs

My question is: How can I dynamically create DateTemplates out of my Views/Pages?

BTW: I switched from Xamarin to native because there were heavy performance issues. The Carousel switches everytime to the first item and needed several seconds to show the "actual" page again, after the size was changed (through virtual keyboard).

I hope for a solution without such performance issues when there are more than 30 items in the list.

Maybe someone can explain why there is such a performance issue? I can't believe that every page is gonna be reloaded caused by the size changed by the virtual kb.

Thank you all in advance.

EDIT:

After I found the button for editing, here's what I got so far:

I have a Page named CarouselView. In the Xaml I have the FlipView named "myCarousel".

In the CodeBehind I have the following code:

public partial class WellcomeView : BasePage {
#region Fields + Properties
private int _position;
public int Position { get { return _position; } set { _position = value; } }
#endregion

public CarouselView() {
    InitializeComponent();
    myCarousel.ItemTemplateSelector = new MyTemplateSelector();
    DataContext = new WellcomeViewModel(null, null, null, null, null);
}

public class MyTemplateSelector : Windows.UI.Xaml.Controls.DataTemplateSelector {
    private DataTemplate GreetingTemplate;
            ...

    public MyTemplateSelector() {
        this.GreetingTemplate = (DataTemplate)Windows.UI.Xaml.Markup.XamlReader.Load(new GreetingView().Content.ToString());
        ...
        // Here it throws an error. No matter if MainPage (with content) or other Views (with Content==null). But in every case I get a XamlParseException.
    } // End Ctor

    protected override DataTemplate SelectTemplateCore(object item, DependencyObject container) {
        var TemplateType = item.GetType();
        switch (TemplateType.Name) {
            case "GreetingViewModel":
            return base.SelectTemplateCore(GreetingTemplate );

            default:
            return base.SelectTemplateCore(BegruessungTemplate);
        } // End switch-case
    } // End SelectTemplateCore()
} // End MyTemplateSelector()

} // End class WellcomeView

Here's the Error I get...

And here's the StackTrace:

at Windows.UI.Xaml.Markup.XamlReader.Load(String xaml)
   at MEDePORT_Win_Native.Views.WellcomeView.MyTemplateSelector..ctor()
   at MEDePORT_Win_Native.Views.WellcomeView..ctor()
   at MEDePORT_Win_Native.MEDePORT_Win_Native_XamlTypeInfo.XamlTypeInfoProvider.Activate_11_WellcomeView()
   at MEDePORT_Win_Native.MEDePORT_Win_Native_XamlTypeInfo.XamlUserType.ActivateInstance()
   at Windows.UI.Xaml.Controls.Frame.Navigate(Type sourcePageType, Object parameter)
   at MEDePORT_Win_Native.App.OnLaunched(LaunchActivatedEventArgs e)

EDIT: With "new MyView().Content.ToString()" I only get the name of the type. For example "Windows.Ui.Xaml.Controls.Grid".

So it seems like I need to extract xaml out of a view and convert it to a string.

EDIT EDIT EDIT EDIT EDIT:

What is the UWP equivalent for the following code?

 DataTemplate template = new DataTemplate { DataType = typeof(< Type of the object the template refers>) };

Solution

  • Try to create your templates not as xaml-Files. Just copy the the Template-content to a xaml-DataTemplate in a new Resources.Xaml.

    Then create Your TemplateSelector like this:

    public class MyTemplateSelector : DataTemplateSelector {
                public DataTemplate GreetingTemplate;
                static ResourceDictionary dataTemplates;
    
                public MyTemplateSelector() {
                    if (dataTemplates == null) {
                        dataTemplates = new Templates.DataTemplates();
                    }
    
                    GreetingTemplate = dataTemplates["GreetingTemplate"] as DataTemplate; // Look how to load Your Templates!
                }
    

    And return your templates like this:

    protected override DataTemplate SelectTemplateCore(object item, DependencyObject container) { var TemplateType = item.GetType();

            switch (TemplateType.Name) {
                case "GreetingViewModel":
                    return GreetingTemplate;
    
                default:
                    return base.SelectTemplateCore(GreetingTemplate);
            }
        }
    

    The Class Templates.DataTemplates() from the first code example looks like this:

    public partial class DataTemplates : ResourceDictionary {
            public DataTemplates() {
                InitializeComponent();
            }
        }
    

    and it's xaml contains your DataTemplates.

    Hope, this helps.