Vue3自定义动画指令的封装&注册&使用

说明

该指令用于实现页面元素滚动到窗口可视范围时,执行动画,并且执行一次。动画为从底向上的移入效果,可以指定距离和动画的持续时间,不指定则为默认设置的距离与时间

当书写指令后打开页面没效果先想一下是不是一开始就在可视范围了

当指定的距离是负数时将会从上到下移入

指令源代码

const DISTANCE = 100; // 距离
const ANIMATIONTIME = 500; // 500毫秒
let distance: number | null = null,
  animationtime: number | null = null;
const map = new WeakMap();
const ob = new IntersectionObserver((entries) => {
  for (const entrie of entries) {
    if (entrie.isIntersecting) {
      const animation = map.get(entrie.target);
      if (animation) {
        animation.play();
        ob.unobserve(entrie.target);
      }
    }
  }
});

function isBelowViewport(el: HTMLElement) {
  const rect = el.getBoundingClientRect();
  return rect.top - (distance || DISTANCE) > window.innerHeight;
}

export default {
  mounted(el: HTMLElement, binding: any) {
    if (binding.value) { // 传值?
      console.log(binding.value);// 打印
      distance = binding.value.px;// 接收指定距离
      animationtime = binding.value.time;// 接收指定时间
    }
    if (!isBelowViewport(el)) {
      return;
    }
    const animation = el.animate(
      [
        {
          opacity: 0,
          transform: `translateY(${distance || DISTANCE}px)`,
        },
        {
          opacity: 1,
          transform: `translateY(0px)`,
        },
      ],
      {
        duration: animationtime || ANIMATIONTIME,
        fill: "forwards",
        easing: "ease-in-out",
      }
    );
    animation.pause();
    map.set(el, animation);
    ob.observe(el);
  },

  unmounted(el:HTMLElement) {
    ob.unobserve(el);
  },
};


全局注册 main.ts

import { createApp } from 'vue'
import App from './App.vue'
import top from './util/toTop.ts'

const app = createApp(App)
app.directive('top', top) // 注意要在const app 之后因为你要使用它
app.mount('#app')

不指定距离与时间正常使用

<template>
<h1 v-top>标题内容</h1>
</template>

指定距离与时间定制使用

<template>
<h1 v-top="{ px: 200, time: 2000 }">标题内容</h1>
</template>
  • 8
    点赞
  • 7
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值