Заполнение CollectionView данными
Пользовательский интерфейс мультиплатформенного приложения .NET (.NET MAUI) CollectionView содержит следующие свойства, определяющие отображаемые данные и его внешний вид:
ItemsSource
IEnumerable
Тип , указывает коллекцию отображаемых элементов и имеет значениеnull
по умолчанию.ItemTemplate
DataTemplateТип , указывает шаблон, применяемый к каждому элементу в коллекции отображаемых элементов.
Эти свойства поддерживаются BindableProperty объектами, что означает, что свойства могут быть целевыми объектами привязки данных.
CollectionView определяет ItemsUpdatingScrollMode
свойство, представляющее поведение CollectionView прокрутки при добавлении в него новых элементов. Дополнительные сведения об этом свойстве см. в разделе "Управление положением прокрутки" при добавлении новых элементов.
CollectionView поддерживает добавочную виртуализацию данных по мере прокрутки пользователем. Дополнительные сведения см. в разделе "Загрузка данных" постепенно.
Заполнение CollectionView данными
A CollectionView заполняется данными, задав свойству ItemsSource
любую коллекцию, которая реализует IEnumerable
. По умолчанию CollectionView отображаются элементы в вертикальном списке.
Внимание
CollectionView Если требуется обновить элементы при добавлении, удалении или изменении в базовой коллекции, базовая коллекция должна быть IEnumerable
коллекцией, которая отправляет уведомления об изменении свойств, напримерObservableCollection
.
CollectionView можно заполнить данными с помощью привязки данных для привязки его ItemsSource
свойства к IEnumerable
коллекции. В XAML это достигается с расширением Binding
разметки:
<CollectionView ItemsSource="{Binding Monkeys}" />
Эквивалентный код на C# выглядит так:
CollectionView collectionView = new CollectionView();
collectionView.SetBinding(ItemsView.ItemsSourceProperty, "Monkeys");
В этом примере ItemsSource
данные свойств привязываются к Monkeys
свойству подключенного представления.
Примечание.
Скомпилированные привязки можно включить для повышения производительности привязки данных в приложениях .NET MAUI. Дополнительные сведения см. в разделе "Скомпилированные привязки".
Сведения об изменении макета см. в разделе "Указание макета CollectionViewCollectionView". Сведения о том, как определить внешний вид каждого элемента в элементе CollectionView, см. в разделе "Определение внешнего вида элемента". Дополнительные сведения о привязке данных см. в разделе "Привязка данных".
Предупреждение
CollectionView вызовет исключение, если оно ItemsSource
обновляется из потока пользовательского интерфейса.
Определение внешнего вида элемента
Внешний вид каждого элемента в CollectionView объекте можно определить, задав CollectionView.ItemTemplate
для свойства значение DataTemplate:
<CollectionView ItemsSource="{Binding Monkeys}">
<CollectionView.ItemTemplate>
<DataTemplate>
<Grid Padding="10">
<Grid.RowDefinitions>
<RowDefinition Height="Auto" />
<RowDefinition Height="Auto" />
</Grid.RowDefinitions>
<Grid.ColumnDefinitions>
<ColumnDefinition Width="Auto" />
<ColumnDefinition Width="Auto" />
</Grid.ColumnDefinitions>
<Image Grid.RowSpan="2"
Source="{Binding ImageUrl}"
Aspect="AspectFill"
HeightRequest="60"
WidthRequest="60" />
<Label Grid.Column="1"
Text="{Binding Name}"
FontAttributes="Bold" />
<Label Grid.Row="1"
Grid.Column="1"
Text="{Binding Location}"
FontAttributes="Italic"
VerticalOptions="End" />
</Grid>
</DataTemplate>
</CollectionView.ItemTemplate>
...
</CollectionView>
Эквивалентный код на C# выглядит так:
CollectionView collectionView = new CollectionView();
collectionView.SetBinding(ItemsView.ItemsSourceProperty, "Monkeys");
collectionView.ItemTemplate = new DataTemplate(() =>
{
Grid grid = new Grid { Padding = 10 };
grid.RowDefinitions.Add(new RowDefinition { Height = GridLength.Auto });
grid.RowDefinitions.Add(new RowDefinition { Height = GridLength.Auto });
grid.ColumnDefinitions.Add(new ColumnDefinition { Width = GridLength.Auto });
grid.ColumnDefinitions.Add(new ColumnDefinition { Width = GridLength.Auto });
Image image = new Image { Aspect = Aspect.AspectFill, HeightRequest = 60, WidthRequest = 60 };
image.SetBinding(Image.SourceProperty, "ImageUrl");
Label nameLabel = new Label { FontAttributes = FontAttributes.Bold };
nameLabel.SetBinding(Label.TextProperty, "Name");
Label locationLabel = new Label { FontAttributes = FontAttributes.Italic, VerticalOptions = LayoutOptions.End };
locationLabel.SetBinding(Label.TextProperty, "Location");
Grid.SetRowSpan(image, 2);
grid.Add(image);
grid.Add(nameLabel, 1, 0);
grid.Add(locationLabel, 1, 1);
return grid;
});
Элементы, указанные в DataTemplate определении внешнего вида каждого элемента в списке. В примере макет в пределах объекта DataTemplate управляется Grid. Image Содержит Grid объект и два Label объекта, которые привязываются ко свойствам Monkey
класса:
public class Monkey
{
public string Name { get; set; }
public string Location { get; set; }
public string Details { get; set; }
public string ImageUrl { get; set; }
}
На следующем снимке экрана показан результат создания шаблонов каждого элемента в списке:
Совет
CollectionView Размещение внутри VerticalStackLayout может остановить прокрутку CollectionView и может ограничить количество отображаемых элементов. В этой ситуации замените VerticalStackLayout элементом Grid.
Дополнительные сведения о шаблонах данных см. в разделе "Шаблоны данных".
Выбор внешнего вида элемента во время выполнения
Внешний вид каждого элемента в объекте CollectionView можно выбрать во время выполнения на основе значения элемента, задав свойству CollectionView.ItemTemplate
DataTemplateSelector объект:
<ContentPage ...
xmlns:controls="clr-namespace:CollectionViewDemos.Controls">
<ContentPage.Resources>
<DataTemplate x:Key="AmericanMonkeyTemplate">
...
</DataTemplate>
<DataTemplate x:Key="OtherMonkeyTemplate">
...
</DataTemplate>
<controls:MonkeyDataTemplateSelector x:Key="MonkeySelector"
AmericanMonkey="{StaticResource AmericanMonkeyTemplate}"
OtherMonkey="{StaticResource OtherMonkeyTemplate}" />
</ContentPage.Resources>
<CollectionView ItemsSource="{Binding Monkeys}"
ItemTemplate="{StaticResource MonkeySelector}" />
</ContentPage>
Эквивалентный код на C# выглядит так:
CollectionView collectionView = new CollectionView
{
ItemTemplate = new MonkeyDataTemplateSelector { ... }
};
collectionView.SetBinding(ItemsView.ItemsSourceProperty, "Monkeys");
Для ItemTemplate
свойства задан MonkeyDataTemplateSelector
объект. В следующем примере показан MonkeyDataTemplateSelector
класс:
public class MonkeyDataTemplateSelector : DataTemplateSelector
{
public DataTemplate AmericanMonkey { get; set; }
public DataTemplate OtherMonkey { get; set; }
protected override DataTemplate OnSelectTemplate(object item, BindableObject container)
{
return ((Monkey)item).Location.Contains("America") ? AmericanMonkey : OtherMonkey;
}
}
Класс MonkeyDataTemplateSelector
определяет AmericanMonkey
и OtherMonkey
DataTemplate свойства, которые задаются различными шаблонами данных. Переопределение OnSelectTemplate
возвращает AmericanMonkey
шаблон, который отображает имя обезьяны и расположение в подростке, когда имя обезьяны содержит "Америка". Если имя обезьяны не содержит "Америка", переопределение возвращает OtherMonkey
шаблон, OnSelectTemplate
который отображает имя обезьяны и расположение в серебре:
Дополнительные сведения о селекторах шаблонов данных см. в разделе "Создание объекта DataTemplateSelector".
Внимание
При использовании CollectionViewникогда не задается корневой элемент объектов DataTemplate ViewCell. Это приведет к возникновению исключения из-за CollectionView отсутствия концепции ячеек.
Контекстные меню
CollectionView поддерживает контекстные меню для элементов данных с помощью SwipeViewконтекстного меню с жестом прокрутки. Это SwipeView элемент управления контейнером, который обтекает элемент содержимого и предоставляет элементы контекстного меню для этого элемента содержимого. Таким образом, контекстные меню реализуются для создания CollectionView SwipeView , который определяет содержимое, которое SwipeView обтекает, и элементы контекстного меню, отображаемые жестом прокрутки. Это достигается путем задания SwipeView в качестве корневого представления в DataTemplate представлении, определяющем внешний вид каждого элемента данных в CollectionView:
<CollectionView x:Name="collectionView"
ItemsSource="{Binding Monkeys}">
<CollectionView.ItemTemplate>
<DataTemplate>
<SwipeView>
<SwipeView.LeftItems>
<SwipeItems>
<SwipeItem Text="Favorite"
IconImageSource="favorite.png"
BackgroundColor="LightGreen"
Command="{Binding Source={x:Reference collectionView}, Path=BindingContext.FavoriteCommand}"
CommandParameter="{Binding}" />
<SwipeItem Text="Delete"
IconImageSource="delete.png"
BackgroundColor="LightPink"
Command="{Binding Source={x:Reference collectionView}, Path=BindingContext.DeleteCommand}"
CommandParameter="{Binding}" />
</SwipeItems>
</SwipeView.LeftItems>
<Grid BackgroundColor="White"
Padding="10">
<!-- Define item appearance -->
</Grid>
</SwipeView>
</DataTemplate>
</CollectionView.ItemTemplate>
</CollectionView>
Эквивалентный код на C# выглядит так:
CollectionView collectionView = new CollectionView();
collectionView.SetBinding(ItemsView.ItemsSourceProperty, "Monkeys");
collectionView.ItemTemplate = new DataTemplate(() =>
{
// Define item appearance
Grid grid = new Grid { Padding = 10, BackgroundColor = Colors.White };
// ...
SwipeView swipeView = new SwipeView();
SwipeItem favoriteSwipeItem = new SwipeItem
{
Text = "Favorite",
IconImageSource = "favorite.png",
BackgroundColor = Colors.LightGreen
};
favoriteSwipeItem.SetBinding(MenuItem.CommandProperty, new Binding("BindingContext.FavoriteCommand", source: collectionView));
favoriteSwipeItem.SetBinding(MenuItem.CommandParameterProperty, ".");
SwipeItem deleteSwipeItem = new SwipeItem
{
Text = "Delete",
IconImageSource = "delete.png",
BackgroundColor = Colors.LightPink
};
deleteSwipeItem.SetBinding(MenuItem.CommandProperty, new Binding("BindingContext.DeleteCommand", source: collectionView));
deleteSwipeItem.SetBinding(MenuItem.CommandParameterProperty, ".");
swipeView.LeftItems = new SwipeItems { favoriteSwipeItem, deleteSwipeItem };
swipeView.Content = grid;
return swipeView;
});
В этом примере содержимое SwipeView определяет Grid внешний вид каждого элемента в элементе CollectionView. Элементы прокрутки используются для выполнения действий с SwipeView содержимым и отображаются при прокрутке элемента управления влево:
SwipeView поддерживает четыре разных направления прокрутки, а направление прокрутки определяется коллекцией направлений SwipeItems
SwipeItems
, к которым добавляются объекты. По умолчанию элемент пальцем выполняется при нажатии пользователя. Кроме того, после выполнения элемента прокрутки элементы пальцем скрыты, а SwipeView содержимое отображается повторно. Однако эти действия можно изменить.
Дополнительные сведения об элементе SwipeView управления см. в разделе "Пальцем".
Потяните, чтобы обновить
CollectionView поддерживает вытягивание для обновления функциональных возможностей с помощью RefreshViewфункции, которая позволяет обновлять данные, отображаемые путем извлечения списка элементов. Это RefreshView элемент управления контейнером, предоставляющий возможность извлечения для обновления функциональных возможностей дочернего элемента, при условии, что дочерний элемент поддерживает прокручиваемое содержимое. Таким образом, вытягивание для обновления реализуется путем CollectionView задания его в качестве дочернего RefreshViewэлемента:
<RefreshView IsRefreshing="{Binding IsRefreshing}"
Command="{Binding RefreshCommand}">
<CollectionView ItemsSource="{Binding Animals}">
...
</CollectionView>
</RefreshView>
Эквивалентный код на C# выглядит так:
RefreshView refreshView = new RefreshView();
ICommand refreshCommand = new Command(() =>
{
// IsRefreshing is true
// Refresh data here
refreshView.IsRefreshing = false;
});
refreshView.Command = refreshCommand;
CollectionView collectionView = new CollectionView();
collectionView.SetBinding(ItemsView.ItemsSourceProperty, "Animals");
refreshView.Content = collectionView;
// ...
Когда пользователь инициирует обновление, выполняется определенное Command
свойством, ICommand которое должно обновить отображаемые элементы. Визуализация обновления отображается во время обновления, которая состоит из анимированного круга выполнения:
Значение RefreshView.IsRefreshing
свойства указывает текущее состояние RefreshViewобъекта. Когда обновление активируется пользователем, это свойство автоматически переходит в true
. После завершения обновления необходимо сбросить свойство false
в значение .
Дополнительные сведения см. в RefreshViewразделе RefreshView.
Добавочная загрузка данных
CollectionView поддерживает добавочную виртуализацию данных по мере прокрутки пользователем. Это позволяет выполнять такие сценарии, как асинхронная загрузка страницы данных из веб-службы при прокрутке пользователя. Кроме того, точка загрузки дополнительных данных настраивается таким образом, чтобы пользователи не видели пустого места или остановлены от прокрутки.
Предупреждение
Не пытайтесь постепенно загружать данные в объекте CollectionView StackLayout. Этот сценарий приведет к тому, что бесконечный цикл будет происходить, когда CollectionView будет продолжаться расширение.
CollectionView определяет следующие свойства для управления добавочной загрузкой данных:
RemainingItemsThreshold
int
Тип , порог элементов, пока не видимых в списке, в которомRemainingItemsThresholdReached
будет запущено событие.RemainingItemsThresholdReachedCommand
ICommandтип , который выполняется приRemainingItemsThreshold
достижении.RemainingItemsThresholdReachedCommandParameter
с типомobject
, который передается как параметр вRemainingItemsThresholdReachedCommand
.
CollectionView также определяет RemainingItemsThresholdReached
событие, которое запускается, когда CollectionView прокручивается достаточно далеко, что RemainingItemsThreshold
элементы не отображались. Это событие можно обрабатывать для загрузки дополнительных элементов. Кроме того, при RemainingItemsThresholdReached
запуске события выполняется выполнение, RemainingItemsThresholdReachedCommand
что позволяет выполнять добавочную загрузку данных в режиме просмотра.
Значение RemainingItemsThreshold
свойства по умолчанию — -1, указывающее, что RemainingItemsThresholdReached
событие никогда не будет запущено. Если значение свойства равно 0, RemainingItemsThresholdReached
событие будет запущено при отображении окончательного элемента в объекте ItemsSource
. Для значений, превышающих 0, событие будет запущено, RemainingItemsThresholdReached
когда ItemsSource
содержится указанное число элементов, до которых еще не прокручено.
Примечание.
CollectionViewRemainingItemsThreshold
проверяет свойство таким образом, чтобы его значение всегда было больше или равно -1.
В следующем примере XAML показано CollectionView , что данные загружаются постепенно.
<CollectionView ItemsSource="{Binding Animals}"
RemainingItemsThreshold="5"
RemainingItemsThresholdReached="OnCollectionViewRemainingItemsThresholdReached">
...
</CollectionView>
Эквивалентный код на C# выглядит так:
CollectionView collectionView = new CollectionView
{
RemainingItemsThreshold = 5
};
collectionView.RemainingItemsThresholdReached += OnCollectionViewRemainingItemsThresholdReached;
collectionView.SetBinding(ItemsView.ItemsSourceProperty, "Animals");
В этом примере кода событие запускается, RemainingItemsThresholdReached
если еще не прокручено 5 элементов, а в ответ выполняется OnCollectionViewRemainingItemsThresholdReached
обработчик событий:
void OnCollectionViewRemainingItemsThresholdReached(object sender, EventArgs e)
{
// Retrieve more data here and add it to the CollectionView's ItemsSource collection.
}
Примечание.
Данные также можно загружать постепенно, привязывая RemainingItemsThresholdReachedCommand
к ICommand реализации в режиме просмотра.