diff --git a/HandyControl/Controls/Pagination.xaml b/HandyControl/Controls/Pagination.xaml new file mode 100644 index 00000000..a7cc89d4 --- /dev/null +++ b/HandyControl/Controls/Pagination.xaml @@ -0,0 +1,40 @@ + + + + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/HandyControl/Controls/Pagination.xaml.cs b/HandyControl/Controls/Pagination.xaml.cs new file mode 100644 index 00000000..034defbb --- /dev/null +++ b/HandyControl/Controls/Pagination.xaml.cs @@ -0,0 +1,266 @@ +using System; +using System.Windows; +using System.Windows.Controls; +using HandyControl.Data; +using HandyControl.Tools.Extension; + +namespace HandyControl.Controls +{ + /// + /// Pagination.xaml 的交互逻辑 + /// + public partial class Pagination + { + /// + /// 页面更新事件 + /// + public static readonly RoutedEvent PageUpdatedEvent = + EventManager.RegisterRoutedEvent("PageUpdated", RoutingStrategy.Bubble, + typeof(EventHandler>), typeof(Pagination)); + + public Pagination() => InitializeComponent(); + + /// + /// 最大页数 + /// + public static readonly DependencyProperty MaxPageCountProperty = DependencyProperty.Register( + "MaxPageCount", typeof(int), typeof(Pagination), new PropertyMetadata(1, (o, args) => + { + if (o is Pagination pagination && args.NewValue is int value) + { + if (pagination.PageIndex > pagination.MaxPageCount) + { + pagination.PageIndex = pagination.MaxPageCount; + } + pagination.Show(value > 1); + pagination.Update(); + } + }, (o, value) => + { + if (!(o is Pagination)) return 1; + var intValue = (int)value; + if (intValue < 1) + { + return 1; + } + return intValue; + })); + + /// + /// 最大页数 + /// + public int MaxPageCount + { + get => (int)GetValue(MaxPageCountProperty); + set => SetValue(MaxPageCountProperty, value); + } + + /// + /// 每页的数据量 + /// + public static readonly DependencyProperty DataCountPerPageProperty = DependencyProperty.Register( + "DataCountPerPage", typeof(int), typeof(Pagination), new PropertyMetadata(20, (o, args) => + { + if (o is Pagination pagination && args.NewValue is int) + { + pagination.Update(); + } + }, (o, value) => + { + if (!(o is Pagination)) return 1; + var intValue = (int)value; + if (intValue < 1) + { + return 1; + } + return intValue; + })); + + /// + /// 每页的数据量 + /// + public int DataCountPerPage + { + get => (int)GetValue(DataCountPerPageProperty); + set => SetValue(DataCountPerPageProperty, value); + } + + /// + /// 当前页 + /// + public static readonly DependencyProperty PageIndexProperty = DependencyProperty.Register( + "PageIndex", typeof(int), typeof(Pagination), new PropertyMetadata(1, (o, args) => + { + if (o is Pagination pagination && args.NewValue is int value) + { + pagination.Update(); + pagination.RaiseEvent(new FunctionEventArgs(PageUpdatedEvent, pagination) + { + Info = value + }); + } + }, (o, value) => + { + if (!(o is Pagination pagination)) return 1; + var intValue = (int)value; + if (intValue < 0) + { + return 0; + } + if (intValue > pagination.MaxPageCount) return pagination.MaxPageCount; + return intValue; + })); + + /// + /// 当前页 + /// + public int PageIndex + { + get => (int)GetValue(PageIndexProperty); + set => SetValue(PageIndexProperty, value); + } + + /// + /// 表示当前选中的按钮距离左右两个方向按钮的最大间隔(4表示间隔4个按钮,如果超过则用省略号表示) + /// + public static readonly DependencyProperty MaxPageIntervalProperty = DependencyProperty.Register( + "MaxPageInterval", typeof(int), typeof(Pagination), new PropertyMetadata(3, (o, args) => + { + if (o is Pagination pagination) + { + pagination.Update(); + } + }), value => + { + var intValue = (int)value; + return intValue >= 0; + }); + + /// + /// 表示当前选中的按钮距离左右两个方向按钮的最大间隔(4表示间隔4个按钮,如果超过则用省略号表示) + /// + public int MaxPageInterval + { + get => (int)GetValue(MaxPageIntervalProperty); + set => SetValue(MaxPageIntervalProperty, value); + } + + /// + /// 页面更新事件 + /// + public event EventHandler> PageUpdated + { + add => AddHandler(PageUpdatedEvent, value); + remove => RemoveHandler(PageUpdatedEvent, value); + } + + /// + /// 更新 + /// + private void Update() + { + LeftButton.IsEnabled = PageIndex > 1; + RightButton.IsEnabled = PageIndex < MaxPageCount; + if (MaxPageInterval == 0) + { + FirstButton.Visibility = Visibility.Collapsed; + LastButton.Visibility = Visibility.Collapsed; + LeftTextBlock.Visibility = Visibility.Collapsed; + RightTextBlock.Visibility = Visibility.Collapsed; + MainPanel.Children.Clear(); + var selectButton = CreateButton(PageIndex); + MainPanel.Children.Add(selectButton); + selectButton.IsChecked = true; + return; + } + FirstButton.Visibility = Visibility.Visible; + LastButton.Visibility = Visibility.Visible; + LeftTextBlock.Visibility = Visibility.Visible; + RightTextBlock.Visibility = Visibility.Visible; + + //更新最后一页 + if (MaxPageCount == 1) + { + LastButton.Visibility = Visibility.Collapsed; + } + else + { + LastButton.Visibility = Visibility.Visible; + LastButton.Tag = MaxPageCount.ToString(); + } + + //更新省略号 + var right = MaxPageCount - PageIndex; + var left = PageIndex - 1; + RightTextBlock.Visibility = right > MaxPageInterval ? Visibility.Visible : Visibility.Collapsed; + LeftTextBlock.Visibility = left > MaxPageInterval ? Visibility.Visible : Visibility.Collapsed; + + //更新中间部分 + MainPanel.Children.Clear(); + if (PageIndex > 1 && PageIndex < MaxPageCount) + { + var selectButton = CreateButton(PageIndex); + MainPanel.Children.Add(selectButton); + selectButton.IsChecked = true; + } + else if (PageIndex == 1) + { + FirstButton.IsChecked = true; + } + else + { + LastButton.IsChecked = true; + } + + var sub = PageIndex; + for (int i = 0; i < MaxPageInterval - 1; i++) + { + if (--sub > 1) + { + MainPanel.Children.Insert(0, CreateButton(sub)); + } + else + { + break; + } + } + var add = PageIndex; + for (int i = 0; i < MaxPageInterval - 1; i++) + { + if (++add < MaxPageCount) + { + MainPanel.Children.Add(CreateButton(add)); + } + else + { + break; + } + } + } + + private void ButtonPrev_OnClick(object sender, RoutedEventArgs e) + { + PageIndex--; + } + + private void ButtonNext_OnClick(object sender, RoutedEventArgs e) + { + PageIndex++; + } + + private RadioButton CreateButton(int page) + { + return new RadioButton + { + Style = FindResource("PaginationButtonStyle") as Style, + Tag = page.ToString() + }; + } + + private void ToggleButton_OnChecked(object sender, RoutedEventArgs e) + { + if (!(e.OriginalSource is RadioButton button)) return; + PageIndex = int.Parse(button.Tag.ToString()); + } + } +} diff --git a/HandyControl/HandyControl.csproj b/HandyControl/HandyControl.csproj index bec70150..4cde2006 100644 --- a/HandyControl/HandyControl.csproj +++ b/HandyControl/HandyControl.csproj @@ -48,6 +48,9 @@ + + Pagination.xaml + @@ -121,6 +124,10 @@ Designer MSBuild:Compile + + Designer + MSBuild:Compile + Designer MSBuild:Compile @@ -185,6 +192,10 @@ MSBuild:Compile Designer + + Designer + MSBuild:Compile + Designer MSBuild:Compile @@ -205,6 +216,14 @@ Designer MSBuild:Compile + + Designer + MSBuild:Compile + + + Designer + MSBuild:Compile + Designer MSBuild:Compile diff --git a/HandyControl/Themes/Styles/Base/ScrollViewerBaseStyle.xaml b/HandyControl/Themes/Styles/Base/ScrollViewerBaseStyle.xaml new file mode 100644 index 00000000..cdcdf2ee --- /dev/null +++ b/HandyControl/Themes/Styles/Base/ScrollViewerBaseStyle.xaml @@ -0,0 +1,140 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/HandyControl/Themes/Styles/Pagination.xaml b/HandyControl/Themes/Styles/Pagination.xaml new file mode 100644 index 00000000..96243c0a --- /dev/null +++ b/HandyControl/Themes/Styles/Pagination.xaml @@ -0,0 +1,51 @@ + + + + + \ No newline at end of file diff --git a/HandyControl/Themes/Styles/ScrollViewer.xaml b/HandyControl/Themes/Styles/ScrollViewer.xaml new file mode 100644 index 00000000..e1b66ce2 --- /dev/null +++ b/HandyControl/Themes/Styles/ScrollViewer.xaml @@ -0,0 +1,11 @@ + + + + + + + + + + \ No newline at end of file diff --git a/HandyControl/Themes/Styles/Style.xaml b/HandyControl/Themes/Styles/Style.xaml index 46b6e18e..a5596eca 100644 --- a/HandyControl/Themes/Styles/Style.xaml +++ b/HandyControl/Themes/Styles/Style.xaml @@ -3,29 +3,32 @@ + - + + - + + + + - + + + - - - - - --> + + + + + + + + + \ No newline at end of file diff --git a/HandyControlDemo/MainWindow.xaml b/HandyControlDemo/MainWindow.xaml index a15f8e15..290bd2ce 100644 --- a/HandyControlDemo/MainWindow.xaml +++ b/HandyControlDemo/MainWindow.xaml @@ -648,7 +648,7 @@ --> - +