微信小程序实现瀑布流

最近做微信小程序涉及到了瀑布流功能,由于考虑到用户微信版本,所以放弃了官方提供的瀑布流方式(有兴趣可以访问官方文档),经过最终调研,决定使用多个数组来实现。

具体思路:以两列瀑布流为主,需要展示的数据数组为数组A,左边一列展示的为数组B,右边一列展示的为数组C,循环数组A,经过页面的渲染判断当前数据加入数组B还是数组C,比如左侧数据列表高度小于右侧,则数据进入左侧数组B,同时数据渲染,循环这一步骤直到数据渲染完毕。

微信小程序实现瀑布流_第1张图片

 具体实现:

1. 通过flex布局将页面分为两列

  .container {
    width: 100%;
    padding: 0 24rpx; // 设置下左右边距
    box-sizing: border-box;
    display: flex;
    align-items: flex-start; // 沿着交叉轴方向 起点 对齐
    justify-content: space-between; // 两端对齐
  }
  
    
      
        // ....... 瀑布流单个数据块
      
    
    
      
        // ....... 瀑布流单个数据块
      
    
  

2. 获取element的高度

    getElementSize(selector) {
      return new Promise((resolve) => {
        let query = wx.createSelectorQuery()
        query.select(selector).boundingClientRect({
          size: true
        }).exec((res) => {
          resolve(res)
        })
      })
    }

3.循环原数组中的数据,分配到左右两列数组(data中定义 originData、leftData、rightData)

    async splitData(){
      this.setData({ // 左右两侧数组清空
        leftData: [],
        rightData: []
      })
      for (let i in this.data.originData) {
        await this.setItem(this.originData[i],i) // 这里将数据原index保存了下,不需要可忽略
      }
    }

    setItem(item, index) {
      let newItem = deepClone(item) // 这里为了把原数组index保存下,深度拷贝下赋值,不需要可忽略
      newItem.customIndex = index
      let leftData = this.data.leftData
      let rightData = this.data.rightData
      return new Promise((resolve) => {
        Promise.all([
          this.getElementSize('#left'), // 获取左右两列的高度
          this.getElementSize('#right')
        ]).then((res) => {
          let leftElement = res[0][0]
          let rightElement = res[1][0]
          // 通过判断左右两列的高度来决定新的数据置入哪侧
          if (leftElement.height > rightElement.height) {
            leftData.push(newItem)
          } else {
            rightData.push(newItem)
          }
          this.setData({
            leftData,
            rightData
          })
          resolve(true)
        })
      })
    },

 总结:该方法就像买票的两个窗口排队情况,每次来一个人都会去人少的那一列排队,适合那种单个数据块高度不怎么变化、数据不怎么更新的情况。

你可能感兴趣的:(前端,微信小程序)