使用VirtualizingStackPanel的ItemsControl中的精确滚动条控件 [英] Accurate scrollbar control in an ItemsControl with a VirtualizingStackPanel

查看:310
本文介绍了使用VirtualizingStackPanel的ItemsControl中的精确滚动条控件的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我有一个ItemsControl,该控件使用VirtualizingStackPanel来显示庞大(并且正在增长)的项目列表:

I have an Itemscontrol using a VirtualizingStackPanel to display a huge (and growing) list of items:

<ItemsControl Grid.Row="1" Name="ConversationItemsControl" VirtualizingStackPanel.VirtualizationMode="Recycling">
    <ItemsControl.ItemsPanel>
        <ItemsPanelTemplate>
            <VirtualizingStackPanel Orientation="Vertical" />
        </ItemsPanelTemplate>
    </ItemsControl.ItemsPanel>
    <ItemsControl.Template>
        <ControlTemplate TargetType="ItemsControl">
            <ScrollViewer>
                <ItemsPresenter />
            </ScrollViewer>
        </ControlTemplate>
    </ItemsControl.Template>
    <ItemsControl.ItemTemplate>
        <DataTemplate>
            <local:Message />
        </DataTemplate>
    </ItemsControl.ItemTemplate>
</ItemsControl>

虚拟化的工作原理很吸引人,但是我无法正确管理滚动条.如果我尝试以编程方式(例如在加载时)滚动到底部,就像我在非虚拟化StackPanels中所做的那样:

The virtualization is working like a charm, but i cannot get the management of the scrollbar right. If I try to programmatically (e.g. on load) scroll to the bottom like i do in non-virtualized StackPanels:

var scrollViewer = VisualTreeHelper.GetChild(ConversationItemsControl, 0) as ScrollViewer;
scrollViewer.ChangeView(null, double.MaxValue, 1f, true);

scrollviewer尝试滚动到底部,但没有完全这样做-它总是在真实"底部之前停下来一点.这在某种意义上是有道理的,因为VirtualizingStackPanels使用滚动值来确定要渲染的项目,但是这完全使我费力,最终用户无法接受.

the scrollviewer tries to scroll to the bottom, but does not do so completely - it always stops a bit before the "real" bottom. This makes sense in a way since VirtualizingStackPanels are using the scroll value to determine which items to render, but it is totally grinding my gears and unacceptable for end users.

如何滚动到真实"底部?如果我想精确地向下滚动 到一定程度,以至于某个项目的顶部位于视口的顶部(除非真实"底部自然太近了),我该怎么办?

How can I scroll to the "real" bottom? What do I have to do if i want to scroll exactly so far down that the top of a certain item is at the top of the viewport (unless the "real" bottom is too close, naturally)?

推荐答案

这是因为内置的ItemsControl类不支持虚拟化.您可以尝试使用默认情况下使用UI虚拟化的ListBox.

This is because the built-in ItemsControl class doesn't support virtualization. You can try a ListBox instead, which uses UI virtualization by default.

如果您不希望选择行为,只需设置:

If you don't want to have selection behaviour, just set:

<ListBox x:Name="lbCustom">
        <ListBox.ItemContainerStyle>
            <Style TargetType="ListBoxItem">
                <Setter Property="Template">
                    <Setter.Value>
                        <ControlTemplate TargetType="ListBoxItem">
                            <ContentPresenter/>
                        </ControlTemplate>
                    </Setter.Value>
                </Setter>
            </Style>
        </ListBox.ItemContainerStyle>
    </ListBox>

然后类似:

 lbCustom.ScrollIntoView(lbCustom.Items[lbCustom.Items.Count - 1]

这篇关于使用VirtualizingStackPanel的ItemsControl中的精确滚动条控件的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆