[ 前端 ] 简单分析 B 站动态 banner 图

1,928 阅读2分钟

B 站过段时间就会在首页加上一个动态的 banner 图,鼠标放上之后左右移动,banner 图中的各个元素(人物 / 物品)会随之移动,交互性很高且很有吸引力,今天简单分析一下如何实现的。

bilibili_banner.gif

夺冠 动态 banner 图

审查元素之后可以看到,banner 区域的 HTML 结构如下:

<div class='animated-banner'>
  <div class='layer'>
    <img src='0.png' />
  </div>
  <div class='layer'>
    <img src='1.png' />
  </div>
  <div class='layer'>
    <img src='2.png' />
  </div>
  <div class='layer'>
    <img src='3.png' />
  </div>
  ...
</div>    

div.layer 的样式表:

.animated-banner>.layer {
    position: absolute;
    left: 0;
    top: 0;
    height: 100%;
    width: 100%;
    display: -ms-flexbox;
    display: flex;
    -ms-flex-align: center;
    align-items: center;
    -ms-flex-pack: center;
    justify-content: center;
}

从上面的代码可以看出,要实现这样的 banner 图,首先要将一张动态图分割为多个图层,分别保存为 0 - n.png,每一层只有一部分元素,比如:

  • 0.png 只包含背景图
  • 1.png 只包含排球照片,其余部位为透明
  • 2.png 只包含奇数位运动员照片,其余部位为透明
  • 3.png 只包含偶数位运动员照片,其余部位为透明

由于 .layer class 的 position 属性值为 absolute, left 和 top 均为 0,按顺序加载之后,0 - 3 这 4 张 png 图片叠加成一个完整的图片,但是只是一个静态的 banner 图

当然如果只是想实现一个静态的 banner 图,没必要对图片进行拆分,直接加载一张图片就好了。

接下来用鼠标在 banner 图上划过,可以看到每层的图片(除了背景图)都在随着鼠标滑动,但是滑动距离各有不同:

bilibili_banner_debug.gif

可以看到,在 HTML 元素上表现为 每个 layer 层 div 中的 img 元素的样式的 trasform 属性值会随着鼠标的左右滑动而改变,这样原来静态的图片就随着鼠标动了起来。

还可以看到每一层的 img 元素的样式的 transform 属性值变化的速率也不一样,使得每层图片运动距离都不一样,显得动画更真实。

具体在实现方式上应该是给 .layer 的 div 元素绑定了 mousemove 事件,根据鼠标运动的距离和方向对每层图片的 transform 属性值进行动态修改。