ListView、GridView的组件控制器是ScrollController,我们可以通过它来获取视图的滚动信息,并且可以调用里面的方法来更新视图的滚动位置。
ScrollController构造函数如下:
ScrollController常用的属性和方法:
ScrollController间接继承自Listenable,我们可以根据ScrollController来监听滚动事件,如:
示例
我们创建一个ListView,当滚动位置发生变化时,我们先打印出当前滚动位置,然后判断当前位置是否超过1000像素,如果超过则在屏幕右下角显示一个“返回顶部”的按钮,该按钮点击后可以使ListView恢复到初始位置;如果没有超过1000像素,则隐藏“返回顶部”按钮。
ScrollPosition是用来保存可滚动组件的滚动位置的。一个ScrollController对象可以同时被多个可滚动组件使用,ScrollController会为每一个可滚动组件创建一个ScrollPosition对象,这些ScrollPosition保存在ScrollController的positions属性中(List<ScrollPosition>)。ScrollPosition是真正保存滑动位置信息的对象,offset只是一个便捷属性
一个 ScrollController 虽然可以对应多个可滚动组件,但是有一些 *** 作,如读取滚动位置 offset ,则需要一对一!但是我们仍然可以在一对多的情况下,通过其它方法读取滚动位置,举个例子,假设一个 ScrollController 同时被两个可滚动组件使用,那么我们可以通过如下方式分别读取他们的滚动位置:
我们可以通过 controllerpositionslength 来确定 controller 被几个可滚动组件使用。
ScrollPosition 有两个常用方法: animateTo() 和 jumpTo() ,它们是真正来控制跳转滚动位置的方法, ScrollController 的这两个同名方法,内部最终都会调用 ScrollPosition 的。
我们来介绍一下 ScrollController 的另外三个方法:
当 ScrollController 和可滚动组件关联时,可滚动组件首先会调用 ScrollController 的 createScrollPosition() 方法来创建一个 ScrollPosition 来存储滚动位置信息,接着,可滚动组件会调用 attach() 方法,将创建的 ScrollPosition 添加到 ScrollController 的 positions 属性中,这一步称为“注册位置”,只有注册后 animateTo() 和 jumpTo() 才可以被调用。
当可滚动组件销毁时,会调用 ScrollController 的 detach() 方法,将其 ScrollPosition 对象从 ScrollController 的 positions 属性中移除,这一步称为“注销位置”,注销后 animateTo() 和 jumpTo() 将不能再被调用。
需要注意的是, ScrollController 的 animateTo() 和 jumpTo() 内部会调用所有 ScrollPosition 的 animateTo() 和 jumpTo() ,以实现所有和该 ScrollController 关联的可滚动组件都滚动到指定的位置。
Flutter Widget树中子Widget可以通过发送通知(Notification)与父(包括祖先)Widget通信。父级组件可以通过NotificationListener组件来监听自己关注的通知
可滚动组件在滚动时会发送 ScrollNotification 类型的通知, ScrollBar 正是通过监听滚动通知来实现的。通过 NotificationListener 监听滚动事件和通过 ScrollController 有两个主要的不同:
示例
下面,我们监听ListView的滚动通知,然后显示当前滚动进度百分比:
在接收到滚动事件时,参数类型为ScrollNotification,它包括一个metrics属性,它的类型是ScrollMetrics,该属性包含当前ViewPort及滚动位置等信息:
>
初始化问题:这边初始化是在bloc里,直接在构造方法里面赋初值的,state中一旦变量多了,还是这么写,会感觉极其难受,不好管理。需要优化
如果进行一个页面,需要进行复杂的运算或者请求接口后,才能知晓数据,进行赋值,这里肯定需要一个初始化入口,初始化入口需要怎样去定义呢?
首先对state进行优化,新增俩个方法:init()和clone()
init():这里初始化统一用init()方法去管理。
clone():这边克隆方法,是非常重要的,一旦变量达到俩位数以上,就能深刻体会该方法是多么的重要。
定义一个与初始化state相对应的init()初始化方法
这增加了初始化方法,请注意,如果需要进行异步请求,同时需要将相关逻辑提炼一个方法,咱们在这里配套Future和await就能解决在异步场景下同步数据问题
这里使用了克隆方法,可以发现,我们只要关注自己需要改变的变量就行了,其它的变量都在内部赋值好了,我们不需要去关注;这就大大的便捷了页面中有很多变量,只需要变动一俩个变量的场景。
view层增加了个初始化事件。初始化 *** 作直接在创建的时候,在XxxBloc上使用add()方法就行了,就能起到进入页面,初始化一次的效果。
bloc的思想
观察者模式的思想;观察者(回调刷新控件)和被观察者(产生相应事件,添加事件,去通知观察者),bloc层是处于观察者和被观察者中间的一层,我们可以在bloc里面搞业务,搞逻辑,搞网络请求;拿到Event事件传递过来的数据,把处理好的、符合要求的数据返回给view层的观察者就行了。
项目地址: >
以上就是关于Flutter 之 滚动监听及控制(十九)全部的内容,包括:Flutter 之 滚动监听及控制(十九)、Flutter进阶篇(4)-- Flutter的Future异步详解、flutter_bloc使用解析等相关内容解答,如果想了解更多相关内容,可以关注我们,你们的支持是我们更新的动力!
欢迎分享,转载请注明来源:内存溢出
评论列表(0条)