WPF Treeview с управлением пейджингом - PullRequest
0 голосов
/ 29 июня 2018

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

Данные древовидной структуры должны быть изменены, если пользователь перемещается по элементу управления пейджингом

Логически я создал один DataPager элемент управления и пытаюсь назначить его как Itemsource Treeview, но не могу завершить.

Пожалуйста, предложите и помогите мне реализовать разбиение на страницы в элементе управления Treeview, так что за один раз должно отображаться только 10 записей, а когда пользователь нажимает на следующую страницу, должны отображаться еще 10 записей, начиная с 11-20

Window1.xaml

<Window x:Class="WPFTreeViewTutorial.Window1"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:local="clr-namespace:WPFTreeViewTutorial"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
Title="Window1" Height="335" Width="441">
<Window.Resources>
    <Style TargetType="{x:Type TreeViewItem}">
        <Setter Property="Foreground" Value="Blue"/>
        <Setter Property="FontSize" Value="12"/>
        <Setter Property="FontWeight" Value="Bold" />
    </Style>
</Window.Resources>
<StackPanel>
    <Grid>

        <TreeView x:Name="trvMenu" Margin="30,50" Height="200">
            <TreeView.Resources>
                <HierarchicalDataTemplate  ItemsSource="{Binding Path=CurrentPage,ElementName=dataPager1}" DataType="{x:Type local:DataPager}">
                    <TextBlock Text="{Binding Name}" />
                </HierarchicalDataTemplate>
            </TreeView.Resources>
        </TreeView>


    </Grid>
    <local:DataPager x:Name="dataPager1" ItemsPerPage="10"/>
</StackPanel>

Window1.xaml.cs

        namespace WPFTreeViewTutorial
        {
            /// <summary>
            /// Interaction logic for Window1.xaml
            /// </summary>
            public partial class Window1 : Window
            {
                public Window1()
                {
                    InitializeComponent();
                    ObservableCollection<Object> People = new ObservableCollection<Object>();
                    for (int i = 0; i < 100; i++)
                        People.Add(new Person());
                    dataPager1.ItemsSource = People;           
                }
            }


            public class Person
            {
                private static int count;
                public int ID { get; set; }
                public string Name { get; set; }
                public int Age { get; set; }
                public Person()
                {
                    ID = count + 1;
                    Name = "Name " + count.ToString();
                    Age = 20 + count % 2;
                    count++;
                }
            }
        }

DataPager.xaml

            <UserControl x:Class="WPFTreeViewTutorial.DataPager"
            xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
            xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml">
          <UserControl.Resources>
            <Style TargetType="{x:Type Button}">
              <Setter Property="Margin" Value="2"/>
            </Style>
          </UserControl.Resources>
          <StackPanel Orientation="Horizontal">
            <Button Content="&lt;&lt;" x:Name="FirstPage" Click="FirstPage_Click"/>
            <Button Content="&lt;" x:Name="PreviousPage" Click="PreviousPage_Click"/>
            <TextBox Width="30" x:Name="page" Margin="2" BorderBrush="Black" Text="{Binding CurrentPageNumber,RelativeSource={RelativeSource FindAncestor, AncestorType={x:Type UserControl}}}"/>
            <Button Content="_Go" x:Name="GoPage" Click="GoPage_Click"/>
            <Button Content="&gt;" x:Name="NextPage" Click="NextPage_Click"/>
            <Button Content="&gt;&gt;" x:Name="LastPage" Click="LastPage_Click"/>
          </StackPanel> 
        </UserControl>

DataPager.xaml.cs

            namespace WPFTreeViewTutorial
            {
                /// <summary>
                /// Interaction logic for DataPager.xaml
                /// </summary>
                public partial class DataPager : UserControl, INotifyPropertyChanged
                {
                    public DataPager()
                    {
                        InitializeComponent();
                        GeneratePages();
                    }

                    private void GeneratePages()
                    {
                        if (ItemsSource != null)
                        {
                            PageCount = (int)Math.Ceiling(ItemsSource.Count / (double)ItemsPerPage);
                            Pages = new ObservableCollection<ObservableCollection<object>>();
                            for (int i = 0; i < PageCount; i++)
                            {
                                ObservableCollection<object> page = new ObservableCollection<object>();
                                for (int j = 0; j < ItemsPerPage; j++)
                                {
                                    if (i * ItemsPerPage + j > ItemsSource.Count - 1) break;
                                    page.Add(ItemsSource[i * ItemsPerPage + j]);
                                }
                                Pages.Add(page);
                            }
                            CurrentPage = Pages[0];
                            CurrentPageNumber = 1;
                        }
                    }

                    private int PageCount;
                    private int _CurrentPageNumber;
                    private ObservableCollection<ObservableCollection<Object>> Pages;
                    private ObservableCollection<Object> _ItemsSource;
                    private ObservableCollection<Object> _CurrentPage;

                    public ObservableCollection<Object> CurrentPage
                    {
                        get { return _CurrentPage; }
                        set
                        {
                            _CurrentPage = value;
                            if (PropertyChanged != null)
                                PropertyChanged(this, new PropertyChangedEventArgs("CurrentPage"));
                        }
                    }
                    public ObservableCollection<Object> ItemsSource
                    {
                        get { return _ItemsSource; }
                        set
                        {
                            _ItemsSource = value;
                            GeneratePages();
                        }
                    }
                    public int CurrentPageNumber
                    {
                        get { return _CurrentPageNumber; }
                        set
                        {
                            _CurrentPageNumber = value;
                            if (PropertyChanged != null)
                                PropertyChanged(this, new PropertyChangedEventArgs("CurrentPageNumber"));
                        }
                    }

                    public int ItemsPerPage
                    {
                        get { return (int)GetValue(ItemsPerPageProperty); }
                        set { SetValue(ItemsPerPageProperty, value); }
                    }
                    public static readonly DependencyProperty ItemsPerPageProperty =
                        DependencyProperty.Register("ItemsPerPage", typeof(int), typeof(DataPager), new UIPropertyMetadata(10));

                    #region INotifyPropertyChanged Members
                    public event PropertyChangedEventHandler PropertyChanged;
                    #endregion

                    private void FirstPage_Click(object sender, RoutedEventArgs e)
                    {
                        if (Pages != null)
                        {
                            CurrentPage = Pages[0];
                            CurrentPageNumber = 1;
                        }
                    }

                    private void PreviousPage_Click(object sender, RoutedEventArgs e)
                    {
                        if (Pages != null)
                        {
                            CurrentPageNumber = (CurrentPageNumber - 1) < 1 ? 1 : CurrentPageNumber - 1;
                            CurrentPage = Pages[CurrentPageNumber - 1];
                        }
                    }

                    private void NextPage_Click(object sender, RoutedEventArgs e)
                    {
                        if (Pages != null)
                        {
                            CurrentPageNumber = (CurrentPageNumber + 1) > PageCount ? PageCount : CurrentPageNumber + 1;
                            CurrentPage = Pages[CurrentPageNumber - 1];
                        }
                    }

                    private void LastPage_Click(object sender, RoutedEventArgs e)
                    {
                        if (Pages != null)
                        {
                            CurrentPage = Pages[PageCount - 1];
                            CurrentPageNumber = PageCount;
                        }
                    }

                    private void GoPage_Click(object sender, RoutedEventArgs e)
                    {
                        if (Pages != null)
                        {
                            CurrentPage = Pages[CurrentPageNumber - 1];
                        }
                    }
                }
            }
...