Flutter ListView播放视频列表①

  • ListView布局
  • 视频播放器加'开始'文字
  • 点击'开始'播放视频
  • 全局控制器修改点击BUG
  • ListView优化.

誓言用来拴骚动的心,终就拴住了虚空。山林不向四季起誓,荣枯随缘;海洋不需对沙岸承诺,遇合尽兴。连语言都应该舍弃,你我之间,只有干干净净的缄默,与存在。

免费参考:

Flutter 轮子:视频广告倒计时页面

Flutter ListView使用

今日完成最终效果:

效果图(1.1):

分析:

  • ListView加载文字和视频
  • ListView上的Item有一层透明的’开始’文字按钮
  • 点击’开始’文字按钮视频开始,'开始’文字按钮消失
  • '开始’文字按钮点击与消失有渐变的效果
  • ListView滑动的时候,显示"加载中…"停下来的时候加载动画

ListView布局

VideoPage类 ListView代码:

 @overrideWidget build(BuildContext context) {return Container(child: buildListView(),);}Widget buildListView() {return ListView.builder(//不缓存cacheExtent: 0,//加载20条数据itemCount: 20,itemBuilder: (BuildContext context, int index) {return buildListViewItems();},);

VideoPage类 ListView Item布局:

 Widget buildListViewItems() {return Container(height: 200,child: Stack(children: [Positioned.fill(child: Text("正在蜕变的CV工程师",textAlign: TextAlign.center,),),Padding(padding: EdgeInsets.all(20),child: VideoItemPageWidget(//只需要传递当前的路径即可url: 'assets/video/kfc.mp4',),),],),);}

这段代码比较简单,就是一个简单的ListView布局,视频播放参考这里

视频播放器加’开始’文字

(正常情况是加的开始播放图片,这里为了醒目我就加文字了)

VideoItemPageWidget类:

class VideoItemPageWidget extends StatefulWidget {String url;///VideoPageEnum.asset 本地视屏/// VideoPageEnum.network 网络视频VideoPageEnum type;VideoItemPageWidget({@required this.url, //路径this.type = VideoPageEnum.asset, //默认为传递本地视频});@override_VideoItemPageWidgetState createState() => _VideoItemPageWidgetState();
}class _VideoItemPageWidgetState extends State<VideoItemPageWidget> {@overrideWidget build(BuildContext context) {return  buildLayout();}/** 视频播放器和控制器布局*/Widget buildLayout() {return Stack(children: [//占满全屏 并 播放视频Positioned.fill(child: AspectRatio(aspectRatio: _controller.value.aspectRatio,child: VideoPlayer(_controller),),),//编辑透明文字buildtext(),],);}bool isCheck = false; //true 播放 false不播放//编辑透明文字Widget buildtext(){Positioned.fill(//透明动画child: AnimatedOpacity(//当 按钮文字问"开始"时,不显示当前文字opacity: isCheck ? 0 : 1,duration: new Duration(seconds: 1),child: Container(color: Colors.grey.withOpacity(0.5),child: Center(child: Text("开始",style: TextStyle(fontSize: 20, color: Colors.white),),),),),),}
}

分析:

  • 通过AnimatedOpacity()来根据isCheck变量来改变当前状态并改变透明度
  • AnimatedOpacity()中opacity参数1不透明 0透明
  • AnimatedOpacity()中duration设置动画时间
  • 视频的代码大家不用很在意,都是复制官方的代码

效果图(1.2):

现在点击开始并没有效果,因为咋们还没有改变isCheck的状态.

点击’开始’播放视频

接下来咋们对开始外层的Container按钮监听,其实就是对视频外层0.5透明度的灰色界面监听.

  bool isCheck = false; //true 播放 false不播放GestureDetector(onTap: () {isCheck = !isCheck;if (isCheck) {//点击开始按钮开始播放_controller.play();} else {//暂停播放_controller.pause();}setState(() {});},child: Container(......),)

分析:

  • 先改变isCheck的状态,若为true则变为false,若为false则为true
  • 然后当为true是则让它播放视频,反之暂停视频
  • 刷新改变isCheck的状态.

效果图(1.3):

存在问题:

  • 当点击开始播放A,在点击开始播放B时,A的状态没有改变成暂停
  • A的状态不但没有改变,还需要重新点击一下,使他的状态由暂停恢复到开始,才可以播放

解决思路:

  • 创建全局控制器,当点击视频播放器时,吧当前状态赋值给全局控制器,
  • 然后通过判断当前状态与传过来的状态是否一致,
  • 一致说明点击的同一个,不一致说明点击的不同,若点击的不同视屏,
  • 则吧上一个视屏关闭掉(pause())

全局控制器修改点击BUG

VideoPage类:

  //创建一个多订阅流final StreamController<VideoPlayerController> _streamController = new StreamController.broadcast();//播放控制器VideoPlayerController _videoPlayerController;@overridevoid initState() {super.initState();_streamController.stream.listen((event) {//当前控制器ID != 传递过来的标识 说明当前传递的是新的标识if (_videoPlayerController != null &&_videoPlayerController.textureId != event.textureId) {//暂停_videoPlayerController.pause();}_videoPlayerController = event;LogUtil.Log(tagging: "streaminitState", title: "接收到消息${_videoPlayerController.textureId}");});}

VideoItemPageWidget类:

  //全局流控制器,用来关闭上一个播放视频StreamController streamController;VideoItemPageWidget({@required this.url, //路径this.streamController,this.type = VideoPageEnum.asset, //默认为传递本地视频});

在点击开始按钮时,吧当前的状态传递给StreamController,让它通过ID去判断是否点击了下一个.

VideoItemPageWidget类:

 GestureDetector(onTap: () {isCheck = !isCheck;if (isCheck) {//点击开始按钮开始播放if (widget.streamController != null) {widget.streamController.add(_controller);}_controller.play();} else {// isCheck = false;//暂停播放_controller.pause();}setState(() {});},child: Container(child: Text("开始").....),),

通过 widget.streamController.add(_controller);将当前视频播放器状态传递给全局播放状态.

然后通过对视频播放控制器的监听,判断当前是否为播放状态

@overridevoid initState() {super.initState();//视频播放初始化_controller = .....();_controller.addListener(() {// isCheck 当前是否是播放状态// _controller.value.isPlaying 如果正在播放视频,则为True。如果暂停,则为False。// 如果当前标识是播放状态,但是播放器已经不播放了 则吧标识改变成不播放状态 跟随播放器改变而改变if (isCheck && !_controller.value.isPlaying) {isCheck = false;LogUtil.Log(tagging: "ischeck", title: '$isCheck');setState(() {});}});}

如果当前的标识是播放状态,但是播放器已经不播放了 则吧标识改变成不播放状态 跟随播放器的状态改变而改变

效果图(1.4):

ListView优化.

对ListView监听,监听当前ListView是否滑动,是否停止

VideoPage类:


bool isScroll = false; //是否滑动onNotification: (notification) {///通知类型switch (notification.runtimeType) {case ScrollStartNotification:print("开始滚动");isScroll = false;break;case ScrollUpdateNotification:print("正在滚动");break;case ScrollEndNotification:print("滚动停止");isScroll = true;setState(() {});break;case OverscrollNotification:print("滚动到边界");break;}return true;},child:ListView.builder(.....)}VideoItemPageWidget(url: 'assets/video/kfc.mp4',isScroll: isScroll,streamController: _streamController,),

VideoItemPageWidget类:

//全局流控制器,用来监听控制视频播放器StreamController streamController;//ListView是否在滑动bool isScroll;VideoItemPageWidget({@required this.url, //路径this.streamController,this.isScroll, //是否播放this.type = VideoPageEnum.asset, //默认为传递本地视频});@overrideWidget build(BuildContext context) {/*widget.isScroll 当前是否是滚动状态*/return widget.isScroll? Center(child: Text("加载中..."),)//视频播放器页面: buildLayout();}

这段代码很简单,通过对ListView滑动的监听,然后通过isScroll变量来标识当前是否滑动,将变量传递给布局来控制,如果正在滑动则显示’加载中’布局,
如果没有在滑动则显示视频播放器页面布局

效果图(1.5):

下一章:Flutter 小知识:ListView播放视频列表(二)

涉及内容:

Flutter 轮子:视频广告倒计时页面

Flutter ListView使用

完整代码

原创不易,您的点赞就是对我最大的支持,留下您的点赞吧~

Flutter 小知识:ListView播放视频列表(一)相关推荐

  1. 微信小程序入门:在小程序中播放视频和发送弹幕

    <移动软件开发>实验3 实验介绍: **本实验来自于周文洁老师的<微信小程序开发实战>第六章.**主要内容是使用小程序媒体API制作一个视频播放小程序,视频素材来自于某高校档案 ...

  2. IOS端微信小程序API播放视频无效,应该这样做

    微信小程序 IOS端通过API播放视频无效 需求 微信小程序项目中需求点击"播放"按钮,直接开始播放视频 问题 直接调用微信API操作视频播放,Adroid端运行一切正常,IOS端 ...

  3. 微信小程序 Video 播放视频,宽高设置

    1. wxml文件 <view class="section"><video class= "videoCss" src='{{url}}' ...

  4. uniapp 小程序里面实现视频列表,播放当前视频,其它视频暂停,视频列表为组件形式引入。

    let video = uni.createVideoContext("video"+index, this) 核心代码     video.play(); 1.inde.vue ...

  5. 微信小程序 涉及播放视频解决办法(证书or腾讯视频插件)

    随着小程序越来越活,很多商家都开始开发自己的小程序啦,最近新的版本需求是在页面添加视频播放,视频是上传到自己的服务器的但是一提交审核之后.无数的问题接踵而至 证书还是在申请中的 但是怎么办 看看其他的 ...

  6. c# winform vlcControl 播放视频列表

    项目中用到vlcControl控件播放多个视频,但是该控件并没有这个特性,参考stackoverflow一位大佬代码. // 首先构建一个视频路径的列表 List<string> play ...

  7. 编程基础小知识之 List(列表)和 tuple(元组),学会就能一定程度上偷懒啦~

    前言 之前我们学习了字符串,整数,浮点数几种基本数据类型, 现在我们接着学习两种新的数据类型,列表(List)和元组(tuple). 一.List(列表) 1.什么是 List (列表) List ( ...

  8. html自动循环播放视频列表

    有多个视频,一个播放完以后另一个播放,知道最后,再从头循环播放. 代码如下: <video id="video1" class="indexBanner" ...

  9. 《公众号、小程序、今日头条、知识星球、视频号、B站视频、星宿UI》协同联动

    这个周末,用了两天的时间,把<口袋故事>.<轻蜂学堂>的公众号.小程序彻底的梳理改造了一遍 感觉很累,但到目前为止,基本实现了多平台的联动 先看下效果,我找个时间详细再写下每种 ...

最新文章

  1. JAVA     面向对象
  2. 独家 | 一个好的事件跟踪字典是什么样的?
  3. 小菜学设计模式——命令模式
  4. linux java 替换jre_Linux系统 无需JRE配置Java
  5. android开发系列之多线程
  6. ACM计算几何题目推荐
  7. C++ 通讯录学习总结
  8. excel合并同类项数据求和
  9. JEECG - 基于代码生成器的J2EE智能开发框架 续二: 代码生成器使用规则
  10. javascript 编辑记录
  11. sqlserver 游标写法
  12. c语言代码出来在哪里运行,C语言代码,怎么运行。
  13. matlab画图时候图例混乱解决方法
  14. 099 《少有人走的路:心智成熟的旅程》简记
  15. rem 用户改变字体大小_用户可以更改字体大小
  16. PMP证书含金量再次提升,纳入北京工作居住证办理范围
  17. VB、VBA、VBS的区别你搞清楚了吗?
  18. 【整理】Python中的re.search和re.findall之间的区别和联系 + re.finall中带命名的组,不带命名的组,非捕获的组,没有分组四种类型之间的区别
  19. 金航数码选择应用 TDengine 时序数据库,改造现有数据库架构
  20. (java)密码加密。某系统的数字密码,比如1983,采用加密方式进行传输,规则如下:先得到每位数,然后每位数都加上5,再对10求余,最后将所有数字反转,得到一串新数。

热门文章

  1. 【送票福利】腾讯2019 TLC 众多技术大咖等你参会,早鸟票5折售卖中
  2. 无法加载文件 D:\xxx\xxx\xxx\activate.ps1,因为在此系统上禁止运行脚本
  3. 考研DS备考|算法复习|编程or上机准备
  4. 总结一下/boot分区被删后的各种悲剧
  5. 4-3.stm32之摄像头 ov7725的使用
  6. Jenkins项目配置流程演示
  7. DFP算法求极值点matlab,DFP算法及Matlab程序
  8. 扒完外卖优惠卷,我好像学到了高效获客的套路!
  9. adxl345取出值怎么算角度_ADXL345测倾斜角(程序)
  10. Spring数据脱敏