欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页

WPF自定义分页控件,样式自定义,简单易用

程序员文章站 2022-06-07 10:14:00
...

WPF自定义分页控件

做了许久伸手党,终于有机会贡献一波,搜索一下WPF分页控件,还是多,但是不太通用,主要就是样式问题,这个WPF很好解决,还有一个就是分页控件嘛,只关心几个数字的变动就行了,把页码改变事件暴露出来,数据的加载在这里就做就行,所以这个分页控件很简单...

好像也没啥讲的,直接上代码了

分页控件基本样式

<Style TargetType="{x:Type local:Pager}">
    <Setter Property="Template">
        <Setter.Value>
            <ControlTemplate TargetType="{x:Type local:Pager}">
                <Border Background="{TemplateBinding Background}"
                        BorderBrush="{TemplateBinding BorderBrush}"
                        BorderThickness="{TemplateBinding BorderThickness}">
                    <StackPanel Orientation="Horizontal"
                                VerticalAlignment="Center">
                        <StackPanel.Resources>
                            <Style TargetType="TextBlock">
                                <Setter Property="VerticalAlignment"
                                        Value="Center"></Setter>
                            </Style>
                        </StackPanel.Resources>
                        <TextBlock Text="共"></TextBlock>
                        <TextBlock x:Name="PART_TotalCount">
                        </TextBlock>
                        <TextBlock Text="行,"></TextBlock>
                        <TextBlock Text="每页"></TextBlock>
                        <TextBlock x:Name="PART_PageSize">
                        </TextBlock>
                        <TextBlock Text="行,"></TextBlock>
                        <TextBlock Text="第">
                        </TextBlock>
                        <TextBlock x:Name="PART_PageIndex"></TextBlock>
                        <TextBlock Text="/"></TextBlock>
                        <TextBlock x:Name="PART_TotalPage"></TextBlock>
                        <TextBlock Text="页"></TextBlock>
                        <Button Margin="10,0,0,0"
                                Content="首页"
                                x:Name="PART_FirstPage"></Button>
                        <Button Margin="10,0,0,0"
                                Content="上一页"
                                x:Name="PART_PrePage"></Button>
                        <Button Margin="10,0,0,0"
                                Content="下一页"
                                x:Name="PART_NextPage"></Button>
                        <Button Margin="10,0,10,0"
                                Content="尾页"
                                x:Name="PART_LastPage"></Button>
                        <TextBox Width="50"
                                 x:Name="PART_PageNum"></TextBox>
                        <Button Margin="10,0,0,0"
                                Content="转到"
                                x:Name="PART_PageGo"></Button>
                    </StackPanel>
                </Border>
            </ControlTemplate>
        </Setter.Value>
    </Setter>
</Style>

分页控件代码

[TemplatePart(Name = "PART_TotalCount", Type = typeof(TextBlock))]
[TemplatePart(Name = "PART_PageSize", Type = typeof(TextBlock))]
[TemplatePart(Name = "PART_PageIndex", Type = typeof(TextBlock))]
[TemplatePart(Name = "PART_TotalPage", Type = typeof(TextBlock))]
[TemplatePart(Name = "PART_FirstPage", Type = typeof(Button))]
[TemplatePart(Name = "PART_PrePage", Type = typeof(Button))]
[TemplatePart(Name = "PART_NextPage", Type = typeof(Button))]
[TemplatePart(Name = "PART_LastPage", Type = typeof(Button))]
[TemplatePart(Name = "PART_PageGo", Type = typeof(Button))]
[TemplatePart(Name = "PART_PageNum", Type = typeof(TextBox))]
public class Pager : Control
{
    #region 字段

    private TextBlock _txtTotalCount;
    private TextBlock _txtPageSize;
    private TextBlock _txtPageIndex;
    private TextBlock _txtTotalPage;
    private Button _btnFirstPage;
    private Button _btnPrePage;
    private Button _btnNextPage;
    private Button _btnLastPage;
    private Button _btnPageGo;
    private TextBox _txtBoxPageNum;

    #endregion

    #region 静态构造
    static Pager()
    {
        DefaultStyleKeyProperty.OverrideMetadata(typeof(Pager), new FrameworkPropertyMetadata(typeof(Pager)));
    }
    #endregion

    #region 依赖属性

    #region 总记录数

    public int TotalCount
    {
        get
        {
            return (int)GetValue(TotalCountProperty);
        }
        set
        {
            SetValue(TotalCountProperty, value);
        }
    }

    // Using a DependencyProperty as the backing store for TotalCount.  This enables animation, styling, binding, etc...
    public static readonly DependencyProperty TotalCountProperty =
        DependencyProperty.Register("TotalCount", typeof(int), typeof(Pager), new FrameworkPropertyMetadata(0, FrameworkPropertyMetadataOptions.BindsTwoWayByDefault,
            (obj, e) =>
            {
                var pager = obj as Pager;

                if (pager == null) return;

                pager.SetTotalCount((int)e.NewValue);
            }));

    #endregion

    #region 每页大小

    public int PageSize
    {
        get
        {
            return (int)GetValue(PageSizeProperty);
        }
        set
        {
            SetValue(PageSizeProperty, value);
        }
    }

    // Using a DependencyProperty as the backing store for PageSize.  This enables animation, styling, binding, etc...
    public static readonly DependencyProperty PageSizeProperty =
        DependencyProperty.Register("PageSize", typeof(int), typeof(Pager), new FrameworkPropertyMetadata(0,
            (obj, e) =>
            {
                var pager = obj as Pager;

                if (pager == null) return;

                pager.SetPageSize((int)e.NewValue);
            }));



    #endregion

    #region 当前页

    public int PageIndex
    {
        get
        {
            return (int)GetValue(PageIndexProperty);
        }
        set
        {
            SetValue(PageIndexProperty, value);
        }
    }

    // Using a DependencyProperty as the backing store for PageIndex.  This enables animation, styling, binding, etc...
    public static readonly DependencyProperty PageIndexProperty =
        DependencyProperty.Register("PageIndex", typeof(int), typeof(Pager), new FrameworkPropertyMetadata(0,
            (obj, e) =>
            {
                var pager = obj as Pager;

                if (pager == null) return;

                pager.SetPageIndex((int)e.NewValue);

            }));



    #endregion

    #region 总页数

    public int TotalPage
    {
        get
        {
            return (int)GetValue(TotalPageProperty);
        }
        set
        {
            SetValue(TotalPageProperty, value);
        }
    }

    // Using a DependencyProperty as the backing store for TotalPage.  This enables animation, styling, binding, etc...
    public static readonly DependencyProperty TotalPageProperty =
        DependencyProperty.Register("TotalPage", typeof(int), typeof(Pager), new FrameworkPropertyMetadata(0,
            (obj, e) =>
            {
                var pager = obj as Pager;

                if (pager == null) return;

                pager.SetTotalPage((int)e.NewValue);
            }));

    #endregion

    #endregion

    #region 路由事件

    public static readonly RoutedEvent PageChangedEvent = EventManager.RegisterRoutedEvent("PageChanged",
        RoutingStrategy.Bubble, typeof(EventHandler<PageChangedEventArg>), typeof(Pager));

    public event EventHandler<PageChangedEventArg> PageChanged
    {
        add
        {
            this.AddHandler(PageChangedEvent, value);
        }
        remove
        {
            this.RemoveHandler(PageChangedEvent, value);
        }
    }

    protected virtual void OnPageChanged()
    {
        var pageChangedEventArg = new PageChangedEventArg(PageIndex);
        pageChangedEventArg.RoutedEvent = PageChangedEvent;
        pageChangedEventArg.Source = this;
        this.RaiseEvent(pageChangedEventArg);
    }

    #endregion

    #region 方法

    public void SetTotalPage(int totalPage)
    {
        _txtTotalPage.Text = totalPage.ToString();
    }

    public void SetPageIndex(int pageIndex)
    {
        _txtPageIndex.Text = pageIndex.ToString();
    }

    public void SetPageSize(int pageSize)
    {
        _txtPageSize.Text = pageSize.ToString();
    }

    /// <summary>
    /// 设置总记录数
    /// </summary>
    /// <param name="totalCount"></param>
    public void SetTotalCount(int totalCount)
    {
        _txtTotalCount.Text = totalCount.ToString();
    }

    public override void OnApplyTemplate()
    {
        base.OnApplyTemplate();

        _txtTotalCount = GetTemplateChild("PART_TotalCount") as TextBlock;
        _txtPageSize = GetTemplateChild("PART_PageSize") as TextBlock;
        _txtPageIndex = GetTemplateChild("PART_PageIndex") as TextBlock;
        _txtTotalPage = GetTemplateChild("PART_TotalPage") as TextBlock;

        _btnFirstPage = GetTemplateChild("PART_FirstPage") as Button;
        _btnPrePage = GetTemplateChild("PART_PrePage") as Button;
        _btnNextPage = GetTemplateChild("PART_NextPage") as Button;
        _btnLastPage = GetTemplateChild("PART_LastPage") as Button;
        _btnPageGo = GetTemplateChild("PART_PageGo") as Button;

        _btnFirstPage.Click += _btnFirstPage_Click;
        _btnPrePage.Click += _btnPrePage_Click;
        _btnNextPage.Click += _btnNextPage_Click;
        _btnLastPage.Click += _btnLastPage_Click;
        _btnPageGo.Click += _btnPageGo_Click;

        _txtBoxPageNum = GetTemplateChild("PART_PageNum") as TextBox;
    }

    #endregion

    #region 私有方法
    private void _btnPageGo_Click(object sender, RoutedEventArgs e)
    {
        var pageNum = 1;

        if (int.TryParse(_txtBoxPageNum.Text, out pageNum))
        {
            if (pageNum >= 1 && pageNum <= TotalPage)
            {
                PageIndex = pageNum;

                OnPageChanged();
            }
        }
    }

    private void _btnLastPage_Click(object sender, RoutedEventArgs e)
    {
        PageIndex = TotalPage;

        OnPageChanged();
    }

    private void _btnNextPage_Click(object sender, RoutedEventArgs e)
    {
        if (PageIndex < TotalPage)
        {
            PageIndex++;

            OnPageChanged();
        }
    }

    private void _btnPrePage_Click(object sender, RoutedEventArgs e)
    {
        if (PageIndex > 1)
        {
            PageIndex--;

            OnPageChanged();
        }
    }

    private void _btnFirstPage_Click(object sender, RoutedEventArgs e)
    {
        PageIndex = 1;

        OnPageChanged();
    }

    #endregion
}

事件参数 PageChangedEventArg.cs

public class PageChangedEventArg : RoutedEventArgs
{
    public int PageIndex
    {
        get; set;
    }

    public PageChangedEventArg(int pageIndex) : base()
    {
        PageIndex = pageIndex;
    }
}

Demo和源码都在开源中国上