как остановить создание шаблона в определенном состоянии - PullRequest
1 голос
/ 11 января 2012

У меня есть список категорий. Для каждой категории создается шаблон с расширителем и сеткой данных, которые будут отображать список элементов, связанных с категорией. Моя проблема в том, что если для категории нет элементов, я не хочу, чтобы шаблон создавался для этой категории. В настоящее время я могу скрыть шаблон, но он оставляет пробел в том месте, где он был создан.

<StackPanel Name="CatagoryPanel" Grid.Row="2" Grid.ColumnSpan="6">
            <ItemsControl ItemsSource="{Binding Path=CategoryList}">
                <ItemsControl.ItemTemplate>
                    <DataTemplate>
                        <DataTemplate.Triggers>
                            <DataTrigger Binding="{Binding Path=Items.Count, UpdateSourceTrigger=PropertyChanged}" Value="0">
                                <Setter Property="Visibility" Value="Hidden"/>
                                <Setter Property="IsEnabled" Value="False"/>
                            </DataTrigger>
                        </DataTemplate.Triggers>
                        <Expander />
                        <DataGrid />
                    </DataTemplate>
                </ItemsControl.ItemTemplate>
            </ItemsControl>
        </StackPanel>

1 Ответ

1 голос
/ 11 января 2012

Недавно я обнаружил свойство ItemTemplateSelector ItemsControl, которое позволяет вам предоставлять разные шаблоны данных для каждого элемента в ItemsControl, зависит от некоторой логики, выполняемой во время выполнения.

Похоже на Setter, но более элегантно.

Сначала определите класс, производный от DataTemplateSelector.Правильно сделать это в коде файла * .cs (так как он является частью View).

public class CategoryTemplateSelector : DataTemplateSelector
{
    public override DataTemplate SelectTemplate(object item, DependencyObject container)
    {
        Category category = item as MusicViewModel.Category;
        FrameworkElement element = container as FrameworkElement;

        string key = (category.Count) > 0 ? "Category" : "EmptyCategory";
        DataTemplate dt = element.FindResource(key) as DataTemplate;

        return dt;
    }
}

Затем на панели стека определите два шаблона данных как ресурсы, а такжекак селектор:

<StackPanel Name="CatagoryPanel" Grid.Row="2" Grid.ColumnSpan="6">
    <StackPanel.Resources>
        <DataTemplate x:Key="EmptyCategory">
            <StackPanel><Expander /><DataGrid /></StackPanel>
        </DataTemplate>
        <DataTemplate x:Key="Category">
            <Expander />
        </DataTemplate>                
        <gms:CategoryTemplateSelector x:Key="selector" />
    </StackPanel.Resources>

    <!-- now, define the actual ItemsControl: -->
    <ItemsControl ItemsSource="{Binding }" ItemTemplateSelector="{StaticResource selector}" />

</StackPanel>

Лично я нахожу этот подход чище, чем триггеры, хотя логически они очень похожи.

Надеюсь, это помогло.

...