likes
comments
collection
share

各大平台都在使用的瀑布流布局原理解析

作者站长头像
站长
· 阅读数 28

我们在日常刷某短视频时,总是忍不住点进他的商城,而且一刷就停不下来了,这究竟是怎么回事呢?

各大平台都在使用的瀑布流布局原理解析

实际上,这或许和它设计的瀑布流布局有很大的关系,如瀑布流水一般参差不齐的商品页面,半遮半掩,总是能让挽留住你想要点击退出的手。

那么,瀑布流布局应该怎么做呢,下面是不做任何处理,单纯在HTML中放入二十张图片的布局。

HTML代码

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>Document</title>
    <style>
        *{
            margin: 0;
            padding: 0;
        }
        #container{
            position: absolute;
        }
        .box{
            float:left;
            padding: 5px;
        }
        .box-img{
            width: 150px;
            padding: 5px;
            border: 1px solid #2eec48;
        }
        img{
            width: 100%;
        }
    </style>
</head>
<body>
    <div id="container">
    
    
        <div class="box">
            <div class="box-img">
                <img src="./1.webp" alt="">
            </div>
        </div>
        以上代码由./1.webp至./10.webp,结束后再循环一次,构成二十张图片。
        
        
    </div>
        
    

    <script src="./index.js"></script>
</body>
</html>

显示如下:

各大平台都在使用的瀑布流布局原理解析

可以看到二十张图片完全是杂乱无章的排放。

于是我们试着添加JS代码,让图片的堆放形成见缝插针的瀑布流布局:

JS代码

  • imgLocation('container', 'box'):这是调用 imgLocation 函数,- 父元素container和子元素box

  • imgLocation 函数:

    获取父元素和子元素:通过 document.getElementById 获取container,通过 getChildElement 获取container中的box数组。

    计算每行可以容纳的图片数量:根据窗口宽度和每张图片的宽度,计算每行可以容纳的图片数量 num。 - 设置父元素的宽度:将父元素的宽度设置为 num 乘以图片宽度。

    进行图片布局:通过一个循环遍历子元素数组。对于每一个子元素,如果它是第一行的图片,直接记录其高度;否则,找到高度最小的列,并将图片定位在该列的下方,并更新该列的高度。

  • getChildElement(parent, child):它通过遍历HTML代码container中的所有子元素,找到类名为 child(相当于box) 的子元素,并将它们存储在一个数组中返回。

// 获取到用户屏幕的宽度,决定一行能放下几张图
// 操作下一张图,放到上一行最矮的列下面

imgLocation('container','box')

function imgLocation(parent,content){
    // 有多少张图
    var cparent = document.getElementById(parent);
    var ccontent = getChildElement(cparent,content);  //document.querySelectorAll('#container.box');
    //每一个box的宽度
    var imgWidth = ccontent[0].offsetWidth;
    var num = Math.floor(document.documentElement.clientWidth / imgWidth);
    cparent.style.Width = `${imgWidth * num}px`;
    
    // 要操作的是哪一张,每一列的高度
    var BoxHeightArr = [];
    for(var i = 0;i< ccontent.length; i++){
        if(i<num){ // 第一行
          BoxHeightArr[i] = ccontent[i].offsetHeight
        }else{ // 要操作的
          var minHeight = Math.min.apply(null,BoxHeightArr);
          var minIndex = BoxHeightArr.indexOf(minHeight);
          
          // 摆放图片的位置
          ccontent[i].style.position = "absolute";
          ccontent[i].style.top = minHeight + "px";
          ccontent[i].style.left = ccontent[minIndex].offsetLeft + "px";
        
          //更新这一列的高度
          BoxHeightArr[minIndex] = BoxHeightArr[minIndex] + ccontent[i].offsetHeight;
          
        }
    }

}


function getChildElement(parent,child){
    // 获取parent中所有的child
    var childArr = [];
    var allChild = parent.getElementsByTagName('*');
    // 挑出来所有的box
    for(var i =0;i< allChild.length;i++){
        if(allChild[i].className == child){
            childArr.push(allChild[i])
        }
    }
    return childArr;
    
}

通过 <script src="./index.js"></script>,将JS代码引入后,图片自然而然的形成了瀑布流布局,让人赏心悦目。

各大平台都在使用的瀑布流布局原理解析

转载自:https://juejin.cn/post/7370993837303300134
评论
请登录