A股上市公司传智教育(股票代码 003032)旗下技术交流社区北京昌平校区

 找回密码
 加入黑马

QQ登录

只需一步,快速开始

 用vue来实现一个瀑布流效果,加载网络图片,同时有下拉刷新和上拉加载更多功能效果。然后针对这几个效果的实现,捋下思路:
  • 根据加载数据的顺序,依次追加标签展示效果;
  • 选择哪种方式实现瀑布流,这里选择绝对定位方式;
  • 关键问题:由于每张图片的宽高不一样,而瀑布流中要求所有图片的宽度一致,高度随宽度等比缩放。而且由于图片的加载是异步延迟。在不知道图片高度的情况下,每个图片所在的item盒子不好绝对定位。因此在渲染页面前先获取所有图片的高度,是解决问题的关键点!这里选择用JS中的Image类,通过预加载图片的方式提前获取图片宽高,另外通过一个临时变量来计算是否所有图片的高度已经得到。当所有的图片高度获取后,开始渲染页面。
  • 页面渲染后,获取所有图片所在的盒子,循环计算盒子的高度,开始设置每个盒子item的绝对定位。
  • 页面渲染时,会出现闪烁的现象。如何解决这个问题呢?这里用了一个动画样式。不过在第一次加载的时候,还是会有一点闪烁的感觉。
  • 然后就是下拉刷新和上拉加载更多的效果,这里用了有赞的vant组件PullRefresh和List这套组合组件来实现。
先看个效果动图:
静态截图:

二、具体实现步骤2.1、页面结构设计,测试数据准备。
  本地准备一个json文件数据,放在项目public文件夹下。注意,本地测试数据必须放在public文件夹下,网络请求时才能请求到数据,这是vue3.x。新增加一个axios依赖包,用来进行网络请求。部分截图,及关键代码:
//数据请求getDataList(){    this.$axios.get("/json/dataList.json").then((res)=>{         let list = res.data.data ? res.data.data: [];         if (list.length > 0){             //从list中取pageSize条数据出来             var tempList = [];              for (let i = 0; i < this.pageSize; i++){                   if (list.length > 0){                      let tempIndex = parseInt(Math.random() * 1000) % list.length;                      tempList.push(list[tempIndex]);                      list.splice(tempIndex, 1);                  }              }               this.loadImagesHeight(tempList); //模拟预加载图片,获取图片高度          }          else {              this.loadImagesHeight(list);           }      }).catch((res)=>{           console.log("..fail: ", res);           this.$toast.clear();           this.isLoading = false; //下拉刷新请求完成           this.loading = false; //上拉加载更多请求完成     })},

2.2、预加载图片,存储图片高度
  获取数据后,遍历数据数组,预加载图片,计算图片缩放后的高度,存储起来。同时由于图片加载是异步加载,所以用变量计数,当最后一个图片加载完成后,开始渲染页面。
View Code

2.3、渲染页面,设置绝对定位
  所有图片通过预加载获取图片高度后,开始渲染页面。然后遍历所有图片所在盒子标签,获取盒子高度,设置每个盒子的绝对定位。
View Code

2.4、其他说明
  其他页面中如下拉刷新,和上拉加载更多等功能,使用了有赞的组件库中的PullRefreshList这一套组合组件。感觉效果挺棒的,使用步骤也简单。另外就是在页面渲染时,会出现页面闪烁的现象,后面使用了一个css动画处理了这个现象,效果好了很多。但是在第一次加载的时候,还是有轻微的闪烁现象。等后面找到更好的方法,再更新。


0 个回复

您需要登录后才可以回帖 登录 | 加入黑马