UWP的一种下拉刷新实现
简介
我们最近实现了一个在UWP中使用的下拉刷新功能,以满足用户的需求,因为这是下拉刷新是一种常见的操作方式,而UWP本身并不提供这一机制。
通过下拉刷新这一机制,可以让移动端的界面设计变得更加简单,更符合广大用户的使用习惯。
NEW github链接:https://github.com/MS-UAP/PullToRefresh.UWP
该组件的nuget链接:https://www.nuget.org/packages/PullToRefresh.UWP
并且,我们实现的这一下拉刷新功能,具有以下优点:
- 支持自定义下拉头部,包括及时显示下拉进度,分辨率较高。
- 用于ListView时,支持UI虚拟化和增量加载,不影响诸如ListView.Header等属性。
基本使用
使用效果如图:

只需要简单的:
<pr:PullToRefreshBox x:Name="pr" RefreshInvoked="PullToRefreshBox_RefreshInvoked">
<ListView x:Name="lv" ItemTemplate="{StaticResource ColorfulRectangle}" />
</pr:PullToRefreshBox>
这是默认的效果。用户只需要订阅 RefreshInvoked 事件即可。
该事件类型为:TypedEventHandler<DependencyObject, object>,第一个参数sender为PullToRefreshBox的Content,第二个参数总是null。
更多设置
我们的下拉刷新控件提供更多设置可供开发者自定义其表现。
- double RefreshThreshold {get;set;} :设置触发刷新的阈值,即有效下拉距离。
- DataTemplate TopIndicatorTemplate {get;set;} :自定义下拉头部模板。这是一个DataTemplate,其DataContext只是一个double值,表示相对于下拉阈值的百分比(可以超过100%)。而该模板本身会决定可用的下拉大小。
同时,我们还提供了一个PullRefreshProgressControl控件,方便开发者进行简单的头部定制。
该控件提供两个VisualState:Normal和ReleaseToRefresh,表示下拉过程中的两种状态(未到达刷新阈值,和已到达阈值)。
通过定义PullRefreshProgressControl.Template可以使用它(同样也要设定一下PullToRefreshBox.TopIndicatorTemplate,并且对PullRefreshProgressControl.Progress属性进行绑定)。
接下来为大家展示一下简单的定制效果:

相关代码如下:
<Grid>
<pr:PullToRefreshBox RefreshInvoked="pr_RefreshInvoked">
<pr:PullToRefreshBox.TopIndicatorTemplate>
<DataTemplate>
<Grid Background="LightBlue"
Height="130"
Width="200">
<pr:PullRefreshProgressControl Progress="{Binding}"
HorizontalAlignment="Center"
VerticalAlignment="Bottom">
<pr:PullRefreshProgressControl.Template>
<ControlTemplate>
<Grid>
<VisualStateManager.VisualStateGroups>
<VisualStateGroup x:Name="VisualStateGroup">
<VisualState x:Name="Normal" />
<VisualState x:Name="ReleaseToRefresh">
<Storyboard>
<ObjectAnimationUsingKeyFrames Storyboard.TargetName="txt" Storyboard.TargetProperty="Text">
<DiscreteObjectKeyFrame KeyTime="0" Value="释放刷新" />
</ObjectAnimationUsingKeyFrames>
</Storyboard>
</VisualState>
</VisualStateGroup>
</VisualStateManager.VisualStateGroups> <Grid.RowDefinitions>
<RowDefinition Height="auto" />
<RowDefinition Height="auto" />
</Grid.RowDefinitions> <TextBlock x:Name="txt"
Text="下拉刷新"
Grid.Row="1"
FontSize="20"
HorizontalAlignment="Center" />
<TextBlock Text="{Binding}"
FontSize="24"
Foreground="Gray"
HorizontalAlignment="Center" /> </Grid>
</ControlTemplate>
</pr:PullRefreshProgressControl.Template>
</pr:PullRefreshProgressControl> </Grid> </DataTemplate>
</pr:PullToRefreshBox.TopIndicatorTemplate> <ListView x:Name="ic">
<ListView.ItemContainerStyle>
<Style TargetType="ListViewItem">
<Setter Property="HorizontalAlignment" Value="Center" />
</Style>
</ListView.ItemContainerStyle>
<ListView.ItemTemplate>
<DataTemplate>
<Rectangle Width="100" Height="200">
<Rectangle.Fill>
<SolidColorBrush Color="{Binding}" />
</Rectangle.Fill>
</Rectangle>
</DataTemplate>
</ListView.ItemTemplate> </ListView>
</pr:PullToRefreshBox>
</Grid>
如果想要更加复杂的效果,则需要完全自定义PullToRefreshBox.TopIndicatorTemplate。
实现原理
采用外部嵌套ScrollViewer的方式实现。同时监控ScrollViewer的大小变化,以调整Content(即PullToRefreshBox.Content)的大小。
同时在下拉发生后,通过DirectManipulationCompleted事件,确定松开手指的时刻,并将下拉头部滚出ScrollViewer的可视区域。
在ScrollViewer.ViewChanged事件中计算下拉距离,以实现分辨率较高的进度绑定。
已知问题
- 用于StackPanel,Canvas这类有无限大空间的控件 且不指定PullToRefreshBox的具体大小时,其大小会恒定不变,而不会随Content大小变化而变化。
该组件的nuget链接:https://www.nuget.org/packages/PullToRefresh.UWP
如果大家在使用中遇到了什么问题,希望能向我们反馈,以使得我们的实现变得更好。
感谢 h82258652 提出的意见!
UWP的一种下拉刷新实现的更多相关文章
- Android-PullToRefresh下拉刷新库基本用法
How:(使用) 转自:http://blog.csdn.net/hantangsongming/article/details/42490277 PullToRefresh是一套实现非常好的下拉刷新 ...
- 微信小程序-自定义下拉刷新
最近给别个公司做技术支持,要实现微信小程序上拉刷新与下拉加载更多 微信给出的接口不怎么友好,最终想实现效果类似QQ手机版 ,一共3种下拉刷新状态变化,文字+图片+背景颜色 最终实现后的效果(这里提示有 ...
- mui 动态加载数据出现的问题处理 (silder轮播组件 indexedList索引列表 下拉刷新不能继续加载数据)
mui-slider 问题:动态给mui的图片轮播添加图片,轮播不滚动. 解决:最后把滚动轮播图片的mui(".mui-slider").slider({interval: 300 ...
- MaterialRefreshLayout+ListView 下拉刷新 上拉加载
效果图是这样的,有入侵式的,非入侵式的,带波浪效果的......就那几个属性,都给出来了,自己去试就行. 下拉刷新 上拉加载 关于下拉刷新-上拉加载的效果,有许许多多的实现方式,百度了一下竟然有几十种 ...
- (UWP开发)更为合理的一种ListView下拉刷新(PullToRefresh)实现方法
最近在做的一个项目需要用到下拉刷新,但是参考了现在网络上比较普遍的方法,觉得都不太好,因为要在外部套上一个SrollViewer,容易出现滚动错误.于是刚开始的时候就把思路定到了ListView内部的 ...
- ListView下拉刷新及上拉更多两种状态
一.前言: 很多应用都会用到ListView,当然如果是iOS就会用UITableViewController,这两个控件在不同的OS上,功能是一样的,只是有些细微的不同(iOS的UITableVie ...
- UWP开发入门(七)——下拉刷新
本篇意在给这几天Win10 Mobile负面新闻不断的某软洗地,想要证明实现一个简单的下拉刷新并不困难.UWP开发更大的困难在于懒惰,缺乏学习的意愿.而不是“某软连下拉刷新控件都没有”这样的想法. 之 ...
- UWP 下拉刷新控件(PullToRefreshControl)
最近项目里面有下拉刷新的需求,自己做了一个,效果还不错. <Style TargetType="local:PullToRefreshControl"> <Set ...
- Android几种强大的下拉刷新库
BeautifulRefreshLayout 众多优秀的下拉刷新(除了我写的之外T_T) 说起下拉刷新,好像经历一段历史的洗礼... (1)在我刚学android的时候,用的是XListView,在g ...
随机推荐
- MySQL安装之后没有MySQL数据库的原因
mysql安装完之后,登陆后发现只有两个数据库:mysql> show databases;+--------------------+| Database |+------ ...
- 海量数据相似度计算之simhash和海明距离
通过 采集系统 我们采集了大量文本数据,但是文本中有很多重复数据影响我们对于结果的分析.分析前我们需要对这些数据去除重复,如何选择和设计文本的去重算法?常见的有余弦夹角算法.欧式距离.Jaccard相 ...
- 不容错过!2016年度优秀UI/UX设计文章
本文整理了一些2016年度最受欢迎的文章,例如有关UI / UX设计的理论知识,书籍和工具,如何做出更好的设计的方法和建议,以及新的设计趋势. 1. 2017年用户体验设计趋势 我们期待着2017年用 ...
- PoEdu - C++阶段班【Po学校】- 第3天
引用 C中指针的功能强大,使用起来繁杂,因为指针要控制的东西太多:有指针的类型,指针的解引用,指针空间内的值,它本身是有空间的,有自己的地址等.指针也是强大的,比如:我们要在函数之内,修改方法之外的值 ...
- Clone
Clone: 构建一个对象的时候,是不是一定要调用构造函数! package com.edu.test; public class Zhenzhen implements Cloneable{ pub ...
- ZOJ3795_Grouping
告诉你某些人的年龄大小关系,问你把所有的人分成若干个组,最少需要多少组,使得组内任意两个人的年龄不可比. 首先考虑特殊情况,如果所有年龄关系构成了一个环,那么这个环中所有人的年龄都是相等,也就是可比的 ...
- linux mysql 操作命令
1.linux下启动mysql的命令:mysqladmin start/ect/init.d/mysql start (前面为mysql的安装路径) 2.linux下重启mysql的命令:mysqla ...
- netload 加载程序集抛异常----无法加载程序集解决办法
netload 加载程序集抛异常----无法加载程序集 错误信息如下: 无法加载程序集.错误详细信息: System.BadImageFormatException: 未能加载文件或程序集“file: ...
- 替换CENTOS自带的yum源为网易163镜像源
首先确保你的系统是centos5或者centos6 先备份你系统自带的repo mv /etc/yum.repos.d/CentOS-Base.repo /etc/yum.repos.d/Cent ...
- JavaScript (jquery) 数组去重的算法探讨
方法很巧妙 但是要事先知道对应的name或其他属性名称 主键值只适用于已知数据对象进行调用: var arr1 = [{ name: ' ...