Выбор DataTemplate на основе типа ViewModel в Avalonia ItemsControl

Внутри находится UserControl с ItemsControl, и требуется отображать элементы с другим DataTemplate на основе типа элемента коллекции Items.

После TemplateSelector и XAML, созданных на основе этого ответа (Выбор DataTemplate на основе на ресурсе DataContext в Авалонии)

    <ItemsControl Items="{Binding Items}">
        <ItemsControl.DataTemplates>
            <views:ItemsTemplateSelector>
                <DataTemplate x:Key="{x:Type itemViewModels:Item1ViewModel}">
                    <itemsViews:Item1View/>
                </DataTemplate>
                <DataTemplate x:Key="{x:Type itemViewModels:Item2ViewModel}">
                    <itemsViews:Item2View/>
                </DataTemplate>
            </views:ItemsTemplateSelector>
        </ItemsControl.DataTemplates>
    </ItemsControl>
        public ItemsViewModel()
        {
            this.Items = new ObservableCollection<IItemViewModel>();
            this.Items.Add(new Item1ViewModel("Item1"));
            this.Items.Add(new Item2ViewModel("Item2"));
        }

        public ObservableCollection<IitemViewModel> Items { get; }
    public class ItemsTemplateSelector : IDataTemplate
    {
        public bool SupportsRecycling => false;

        [Content]
        public Dictionary<Type, IDataTemplate> Templates { get; } = new Dictionary<Type, IDataTemplate>();

        public IControl Build(object data)
        {
            var type = data.GetType();
            var template = this.Templates[type];
            var control = template.Build(data);

            return control;
        }

        public bool Match(object data)
        {
            return data is IItemViewModel;
        }
    }
    public interface IItemViewModel
    {
        string Name { get; }
    }
    public class Item1ViewModel : IItemViewModel
    {
        public Item1ViewModel (string name)
        {
            this.Name = name;
        }

        public string Name { get; }
    }
<UserControl
  xmlns="https://github.com/avaloniaui"
  xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
  xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
  xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
  x:Class="Desktop.Views.Items.Item1View">

  <TextBlock Text="{Binding Name}"/>

</UserControl>

Во время выполнения появляется исключение:

Avalonia.Markup.Xaml.XamlLoadException: «Предварительно скомпилированный XAML не найден для Desktop.Views.Items.Item1View, обязательно укажите x:Class и включите файл XAML как AvaloniaResource»

Если в ItemsControl вместо <itemsViews:Item1View/> указать <TextBlock Text="{Binding Name}"/>, то все работает хорошо. Но я хотел бы разделить разметку для каждого элемента в отдельный файл XAML с отдельной ViewModel. Предметы могут быть совершенно разными.

Можно ли решить эту проблему, чтобы ItemsControl выбирал DataTemplate на основе типа ViewModel?


person Aliaksei Luferau    schedule 07.04.2021    source источник
comment
Похоже, это не связано с DataGrid, а связано с вашим UserControl. Попробуйте поместить экземпляр вашего UserControl прямо в окно и сначала посмотрите, сработает ли это.   -  person Grokys    schedule 07.04.2021


Ответы (1)


Чтобы решить эту проблему, я вручную отредактировал файл проекта *.csproj, добавив элемент AvaloniaResource.

<AvaloniaResource Include="..\Desktop\Views\Items*.xaml">
    <SubType>Designer</SubType>
</AvaloniaResource>
person Aliaksei Luferau    schedule 19.05.2021