Flutter无限循环滑动的PageView

2024-03-04 01:18

本文主要是介绍Flutter无限循环滑动的PageView,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

Flutter循环滑动的PageView

    • 序言
    • 准备新的数据源
    • 定时切换
    • 滑动冲突

序言

Android原生里一般会使用ViewPager来实现Banner区域,当然Flutter中的PageView也可以实现类似的效果,今天就来撸一把循环滑动的PageView。

在Android中想要实现循环滑动的ViewPager,最常用的方法是,在原数据源的基础上,通过前后补位来操作:即准备新的数据集合list , 第一个位置插入原数据中的最后一个元素、最后一个位置插入原数据中的第一个元素,Flutter中PageView实现循环滑动的方法如出一辙,如下图所示:

在这里插入图片描述
在用户滑动过程中,当(2)被选中后,无动画切换到2的位置;当(0)被选中后,此时无动画切换到0的位置。即可实现循环滑动的PageView。

准备新的数据源

这里需要解释下,如果只有一个数据的话,不考虑循环滑动

  /// 初始化Page/// 准备一个新的数据源list/// 在原数据data的基础上,前后各添加一个view  data[data.length-1]、data[0]void _initWidget() {currentIndex = widget.controller.initialPage;if (widget.children == null || widget.children.isEmpty) return;if (widget.children.length == 1) {_children.addAll(widget.children);} else {_children.add(widget.children[widget.children.length - 1]);_children.addAll(widget.children);_children.add(widget.children[0]);}}

当用户在滑动到新位置的Page后,会触发PageView的回调监听onPageChanged(int index),参数即为新选中的Page索引,此时我们需要及时将页面切换到正确的位置

/// Page切换后的回调,及时修复索引void _onPageChanged(int index) async {if (index == 0) {//当前选中的是第一个位置,自动选中倒数第二个位置currentIndex = _children.length - 2;await Future.delayed(widget.duration);widget.controller?.get()?.jumpToPage(currentIndex);realPosition = currentIndex - 1;} else if (index == _children.length - 1) {//当前选中的是倒数第一个位置,自动选中第二个索引currentIndex = 1;await Future.delayed(widget.duration);widget.controller?.get()?.jumpToPage(currentIndex);realPosition = 0;} else {currentIndex = index;realPosition = index - 1;if (realPosition < 0) realPosition = 0;}setState(() {});}

定时切换

目前已经实现了PageView的循环滑动,那么现在我们加一个定时器,每隔2s自动切换下一个页面。

/// 创建定时器void createTimer() {if (widget.isTimer) {cancelTimer();_timer = Timer.periodic(widget.delay, (timer) => _scrollPage());}}/// 定时切换PageView的页面void _scrollPage() {++currentIndex;var next = currentIndex % _children?.length;widget.controller?.get()?.animateToPage(next,duration: widget.duration,curve: Curves.ease,);}/// 开始定时滑动void _start() {if (!widget.isTimer) return;if (!isActive) return;if (_children.length <= 1) return;createTimer();}/// 停止定时滑动void _stop() {if (!widget.isTimer) return;cancelTimer();}/// 取消定时器void cancelTimer() {_timer?.cancel();}

滑动冲突

到这里就实现了可以定时自动循环滑动的PageView,但是看下实际效果你会发现,当用户在滑动过程中,定时器还在进行,此时就需要取消定时器,当用户手指离开后再开启定时器自动轮播。

所以这里你可以给PageView包裹一层NotificationListener来监听用户滑动

@overrideWidget build(BuildContext context) => NotificationListener(onNotification: (notification) => _onNotification(notification),child: PageView(scrollDirection: widget.scrollDirection,reverse: widget.reverse,controller: widget.controller?.get(),physics: widget.physics,pageSnapping: widget.pageSnapping,onPageChanged: _onPageChanged,children: _children,dragStartBehavior: widget.dragStartBehavior,allowImplicitScrolling: widget.allowImplicitScrolling,restorationId: widget.restorationId,clipBehavior: widget.clipBehavior,),);
/// Page滑动监听_onNotification(notification) {if (notification is ScrollStartNotification) {isEnd = false;} else if (notification is UserScrollNotification) {//用户滑动时回调顺序:start - user , end - userif (isEnd) {isUserGesture = false;_start();return;}isUserGesture = true;_stop();} else if (notification is ScrollEndNotification) {isEnd = true;if (isUserGesture) {_start();}}}

值得注意的是,自动滑动和用户滑动都会触发start、end事件,但是用户滑动时会触发user事件,滑动时回调顺序:start - user 、 end - user,所以只需要在user事件回调中判断是否手指离开了,即可区分用户滑动和页面滑动,实现用户滑动状态下暂停定时器,用户手指离开后启动定时器。

看下最终的实现效果,代码里时加了页面圆点指示器的,可以参考代码自定义配置。

插件地址:

Github
pub.dev

这篇关于Flutter无限循环滑动的PageView的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!


原文地址:
本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.chinasem.cn/article/771553

相关文章

Nginx部署React项目时重定向循环问题的解决方案

《Nginx部署React项目时重定向循环问题的解决方案》Nginx在处理React项目请求时出现重定向循环,通常是由于`try_files`配置错误或`root`路径配置不当导致的,本文给大家详细介... 目录问题原因1. try_files 配置错误2. root 路径错误解决方法1. 检查 try_f

Spring三级缓存解决循环依赖的解析过程

《Spring三级缓存解决循环依赖的解析过程》:本文主要介绍Spring三级缓存解决循环依赖的解析过程,具有很好的参考价值,希望对大家有所帮助,如有错误或未考虑完全的地方,望不吝赐教... 目录一、循环依赖场景二、三级缓存定义三、解决流程(以ServiceA和ServiceB为例)四、关键机制详解五、设计约

Flutter实现文字镂空效果的详细步骤

《Flutter实现文字镂空效果的详细步骤》:本文主要介绍如何使用Flutter实现文字镂空效果,包括创建基础应用结构、实现自定义绘制器、构建UI界面以及实现颜色选择按钮等步骤,并详细解析了混合模... 目录引言实现原理开始实现步骤1:创建基础应用结构步骤2:创建主屏幕步骤3:实现自定义绘制器步骤4:构建U

Spring 中的循环引用问题解决方法

《Spring中的循环引用问题解决方法》:本文主要介绍Spring中的循环引用问题解决方法,本文给大家介绍的非常详细,对大家的学习或工作具有一定的参考借鉴价值,需要的朋友参考下吧... 目录什么是循环引用?循环依赖三级缓存解决循环依赖二级缓存三级缓存本章来聊聊Spring 中的循环引用问题该如何解决。这里聊

C# foreach 循环中获取索引的实现方式

《C#foreach循环中获取索引的实现方式》:本文主要介绍C#foreach循环中获取索引的实现方式,本文给大家介绍的非常详细,对大家的学习或工作具有一定的参考借鉴价值,需要的朋友参考下吧... 目录一、手动维护索引变量二、LINQ Select + 元组解构三、扩展方法封装索引四、使用 for 循环替代

Spring Boot循环依赖原理、解决方案与最佳实践(全解析)

《SpringBoot循环依赖原理、解决方案与最佳实践(全解析)》循环依赖指两个或多个Bean相互直接或间接引用,形成闭环依赖关系,:本文主要介绍SpringBoot循环依赖原理、解决方案与最... 目录一、循环依赖的本质与危害1.1 什么是循环依赖?1.2 核心危害二、Spring的三级缓存机制2.1 三

springboot循环依赖问题案例代码及解决办法

《springboot循环依赖问题案例代码及解决办法》在SpringBoot中,如果两个或多个Bean之间存在循环依赖(即BeanA依赖BeanB,而BeanB又依赖BeanA),会导致Spring的... 目录1. 什么是循环依赖?2. 循环依赖的场景案例3. 解决循环依赖的常见方法方法 1:使用 @La

Flutter打包APK的几种方式小结

《Flutter打包APK的几种方式小结》Flutter打包不同于RN,Flutter可以在AndroidStudio里编写Flutter代码并最终打包为APK,本篇主要阐述涉及到的几种打包方式,通... 目录前言1. android原生打包APK方式2. Flutter通过原生工程打包方式3. Futte

Python循环缓冲区的应用详解

《Python循环缓冲区的应用详解》循环缓冲区是一个线性缓冲区,逻辑上被视为一个循环的结构,本文主要为大家介绍了Python中循环缓冲区的相关应用,有兴趣的小伙伴可以了解一下... 目录什么是循环缓冲区循环缓冲区的结构python中的循环缓冲区实现运行循环缓冲区循环缓冲区的优势应用案例Python中的实现库

Jackson库进行JSON 序列化时遇到了无限递归(Infinite Recursion)的问题及解决方案

《Jackson库进行JSON序列化时遇到了无限递归(InfiniteRecursion)的问题及解决方案》使用Jackson库进行JSON序列化时遇到了无限递归(InfiniteRecursi... 目录解决方案‌1. 使用 @jsonIgnore 忽略一个方向的引用2. 使用 @JsonManagedR