瀑布流布局待完善

<template>
  <div class="water-layout">
    <div
      class="img-box default-card-animation"
      v-for="(item, index) in imgsArr_c"
      :key="index"
      :style="{ width: imgWidth + 'px', height: item._height + 'px' }"
      ref="imgBox"
    >
      <img :src="item.src" />
    </div>
  </div>
</template>

<script>
export default {
  data() {
    return {
      imgsArr: [
       {
        src:"https://img0.baidu.com/it/u=3130638399,1281069824&fm=253&fmt=auto&app=120&f=JPEG?w=1280&h=800",

       },
       {
        src:"https://www.ssfiction.com/wp-content/uploads/2020/08/20200820_5f3ec7b395648.jpg",

       },
       {
        src:"https://uploadfile.bizhizu.cn/up/63/2a/a6/632aa6024fe8936ec7fe5c2e80abbe06.jpg.source.jpg",

       },
       {
        src:"https://img0.baidu.com/it/u=3130638399,1281069824&fm=253&fmt=auto&app=120&f=JPEG?w=1280&h=800",

       },

      ], //为图片数组
      imgsArr_c:[],  //处理之后的数组
      loadedCount: 0, // 为已预处理好的图个数
      imgWidth:200, // 为图片的宽度
      beginIndex:0,
      colsHeightArr:[],
      imgBoxEls:null, //所有的dom
      colWidth:"50%",  //列宽
      colNum:2,
    };
  },
  created(){
    this.preLoad()
  },
  methods: {
    // 预加载 目的==》设置并保存图片宽高
    preLoad() {
      // forEach 无法通过 item 直接修改数组元素,需用数组下标修改
      console.log("preload函数开始执行了哦哦")
      this.imgsArr.forEach((item, index) => {
        console.log(item,"函数开始执行了了来了 噜啦噜啦嘞绿绿绿绿绿绿绿")
        if (index < this.loadedCount) return;
        // 无图则把高度设置为0
        if (!item.src) {
            console.log("现在我到底是有图还是没有图")
          // 图片的高度
          this.imgsArr[index]._height = "0";
          ++this.loadedCount;
          // 当前图片都与处理完,则加载图片
          if (this.imgsArr.length === this.loadedCount) {
            this.preloaded();
          }
        } else {
            console.log("有图src请执行我卡卡卡卡卡卡卡卡扩扩扩扩扩扩")
          let img = new Image();
          img.src = item.src;
          console.log(img,"我是img对象香对象对象对象对象对象卡卡卡卡卡卡卡卡扩扩扩")
          img.onload = img.onerror = (e) => {
            // 若加载失败则设置图片高度与宽度一致,加载成功则动态计算图片高度
            console.log(e,"图片onload,事件对象————————————————————————")
            this.imgsArr[index]._height =
              e.type === "load"
                ? Math.round(this.imgWidth * (img.height / img.width))
                : this.imgWidth;
            if (e.type === "error") {
              this.imgsArr[index]._error = true;
            }
            ++this.loadedCount;
            // 当前图片都与处理完,则加载图片
            if (this.imgsArr.length === this.loadedCount) {
              this.preloaded();
            }
          };
        }
      });
    },
    //渲染
    preloaded() {
      // 开始渲染
      this.imgsArr_c = [].concat(this.imgsArr);
      this.$nextTick(() => {
        // 对每个元素进行排列
        this.waterfall();
      });
    },
    

    // waterfall,等到整个视图都渲染完毕再执行   排列布局
    waterfall() {
        console.log("排列函数执行了了了了 啦啦啦啦啦啦")
      // 选择所有图片dom 
      this.imgBoxEls = this.$refs["imgBox"];
      // 若没图片,则返回
      if (!this.imgBoxEls) return;
      let top, left, height;
      // 开始排列的坐标,若为0则重头排列,colsHeightArr 数组保存的是当前每一列的高度
      if (this.beginIndex === 0) this.colsHeightArr = [];
      for (let i = this.beginIndex; i < this.imgBoxEls.length; ++i) {
          console.log("瀑布流量获取到所哟的dom ",this.imgBoxEls[i])
        if (!this.imgBoxEls[i]) return;
        // 当前图片的高度  获取高度关键点


        height = this.imgBoxEls[i].offsetHeight;
        // 第一行,则直接按顺序排列
        if (i < this.colNum) {
          this.colsHeightArr.push(height);
          top = 0;
          // colWidth 为列宽,等于图片宽度加 div 左右的padding,colWidth = imgWdith + 2 * padding
          left = i * this.colWidth;
        } else {
          // 找到当前最低的高度和其索引
          let minHeight = Math.min.apply(null, this.colsHeightArr);
          let minIdx = this.colsHeightArr.indexOf(minHeight);
          // 当前图片的 top,即当前图片应所在的高度
          top = minHeight;
          // 当前图片的 left,即当前图片应该排到目前高度最低那一列下面
          left = minIdx * this.colWidth;

          // 更新第 minIdx 列的高度
          this.colsHeightArr[minIdx] += height;
        }
        // 设置 img-box 位置
        this.imgBoxEls[i].style.top = top + "px";
        this.imgBoxEls[i].style.left = left + "px";
        // 当前图片在窗口内,则加载,这是用于后面的图片懒加载。viewHeight 为窗口高度
        // if (top < this.viewHeight) {
        //   let imgEl = this.imgBoxEls[i].children[0];
        //   imgEl.src = imgEl.getAttribute("data-src");
        //   imgEl.style.opacity = 1;
        //   imgEl.style.transform = "scale(1)";
        // }
      }
      // 排列完之后,之后新增图片从这个索引开始预加载图片和排列,之前排列的图片无需在处理
      this.beginIndex = this.imgBoxEls.length;
    },
  },
};
</script>

<style scoped>
.img-box{
    background-color: #e4e265;
    border:1px solid black;
}
.img-box img{
    height: 100%;
    width: 100%;
}
</style>

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值