我有一个ItemsRepeater。我知道我可以使用
ItemsRepeater.ItemsSourceView
获取所有元素,但是我如何找出哪些元素是实现的(而不是虚拟化的)(例如,用于聚焦最右边实现的项目)?
ItemsRepeater.TryGetElement
迭代列表并查看返回非空值的唯一方法吗?
您尝试过 ItemsRepeater 的 Lifecycle Events 吗?
ElementPrepared。对于新创建的元素以及已经存在且正在从回收队列中重新使用的元素都会发生这种情况。
ElementClearing 每次将元素发送到回收队列时都会立即发生,例如当它超出已实现项目的范围时。
检查此示例代码:
public class Person
{
public string Id { get; set; }
}
public sealed partial class MainPage : Page
{
public MainPage()
{
this.InitializeComponent();
for (int i = 0; i < 10_000; i++)
{
People.Add(new Person { Id = $"{i + 1}" });
}
}
public ObservableCollection<Person> People { get; } = new();
public ObservableCollection<Person> LoadedItems { get; } = new();
private void ItemsRepeaterControl_ElementPrepared(ItemsRepeater sender, ItemsRepeaterElementPreparedEventArgs args)
{
if (sender.ItemsSourceView.GetAt(args.Index) is not Person item ||
args.Element is not FrameworkElement frameworkElement)
{
return;
}
frameworkElement.DataContext = item;
LoadedItems.Add(item);
}
private void ItemsRepeaterControl_ElementClearing(ItemsRepeater sender, ItemsRepeaterElementClearingEventArgs args)
{
if (args.Element is not FrameworkElement frameworkElement ||
frameworkElement.DataContext is not Person item)
{
return;
}
LoadedItems.Remove(item);
}
}
<Grid ColumnDefinitions="*,*">
<Grid.Resources>
<DataTemplate
x:Key="PersonItemTemplate"
x:DataType="local:Person">
<Grid>
<TextBlock Text="{x:Bind Id, Mode=OneWay}" />
</Grid>
</DataTemplate>
</Grid.Resources>
<Grid
Grid.Column="0"
RowDefinitions="Auto,*">
<TextBlock Grid.Row="0">
<Run Text="Items Count: " />
<Run Text="{x:Bind People.Count, Mode=OneWay}" />
</TextBlock>
<ScrollView Grid.Row="1">
<ItemsRepeater
ElementClearing="ItemsRepeaterControl_ElementClearing"
ElementPrepared="ItemsRepeaterControl_ElementPrepared"
ItemsSource="{x:Bind People, Mode=OneWay}">
<ItemsRepeater.ItemTemplate>
<DataTemplate x:DataType="local:Person">
<Grid>
<TextBlock Text="{x:Bind Id, Mode=OneWay}" />
</Grid>
</DataTemplate>
</ItemsRepeater.ItemTemplate>
</ItemsRepeater>
</ScrollView>
</Grid>
<Grid
Grid.Column="1"
RowDefinitions="Auto,*">
<TextBlock Grid.Row="0">
<Run Text="Loaded Count: " />
<Run Text="{x:Bind LoadedItems.Count, Mode=OneWay}" />
</TextBlock>
<ScrollView Grid.Row="1">
<ListView ItemsSource="{x:Bind LoadedItems, Mode=OneWay}">
<ListView.ItemTemplate>
<DataTemplate x:DataType="local:Person">
<Grid>
<TextBlock Text="{x:Bind Id, Mode=OneWay}" />
</Grid>
</DataTemplate>
</ListView.ItemTemplate>
</ListView>
</ScrollView>
</Grid>
</Grid>