文字横向滚动的需求在一些首页还是比较常见的,今天手撸一个

核心内容:animation + @keyframes

组件

<template>
  <div class="scrollDiv">
    <div id="demo1" ref="wrap" class="divAnimation">
      <span class="txt alert-msg ">
        {{text}}
      </span>
    </div>
  </div>
</template>

<script>
  export default {
    props:{
      text:{
        type: String,
        default: ''
      },
    },
    watch:{
      text:function(newVal){
        // 使用 forceGet 参数,强制从服务器获取最新的页面
        this.updateAnimation()
      }
    },
    methods:{
      /*动画*/ 
      updateAnimation(){
        let animationTime = 15;
        let dWith,sWidth;
        this.$nextTick(() => { 
          dWith = Math.ceil($(".divAnimation").width());
          sWidth = Math.ceil($(".scrollDiv").width());
          console.log(dWith,sWidth)
          if(dWith > sWidth && dWith>300) 
            animationTime = Math.ceil(dWith/40)
          $(".divAnimation").css({animation:'scroll-animation '+animationTime+'s linear 0s infinite'});
          let keyframes = `@keyframes scroll-animation {
            0% {
              transform: translateX(${sWidth}px);
            }
            100% {
              transform: translateX(-${dWith}px);
            }
          }
          `
          var sheet = document.styleSheets[0]
          if(sheet.cssRules[0] instanceof CSSKeyframesRule) 
            sheet.deleteRule(0);
          sheet.insertRule(keyframes, 0)
        })
      }
    },
    mounted(){ 
    },
  }
</script>
<style lang="scss" scoped>
.scrollDiv {
  position: relative;
  height: 40px;
  line-height: 40px;
  overflow: hidden;
  border: 1px solid #5de1fb;
  border-radius: 5px;
  font-size: 16px;
  background: rgba(123,225,252,.2);
  color: #5de1fb;
  .divAnimation {
    position: absolute;
    width: auto;
    white-space: nowrap;
    display: flex;
    align-items: center;
    .txt{
      width: auto;
    }
    &:hover {
      //鼠标悬停 停止横向滚动
      animation-play-state: paused;
    }
  }
}
</style>

  1. scrollDiV – 外容器,用来包裹要滚动的容器
  2. divAnimation – 实际要滚动展示的容器,包裹需要滚动的文字
  3. txt – 被包裹的文字,如果是数组,这里用v-for循环即可

核心:js部分根据divAnimation实际的滚动宽度,来动态设置keyframes的起点和终点

updateAnimation(){
    let animationTime = 15;
    let dWith,sWidth;
    this.$nextTick(() => { 
      dWith = Math.ceil($(".divAnimation").width());
      sWidth = Math.ceil($(".scrollDiv").width());
      console.log(dWith,sWidth)
      if(dWith > sWidth && dWith>300) 
        animationTime = Math.ceil(dWith/40)
      $(".divAnimation").css({animation:'scroll-animation '+animationTime+'s linear 0s infinite'});
      let keyframes = `@keyframes scroll-animation {
        0% {
          transform: translateX(${sWidth}px);
        }
        100% {
          transform: translateX(-${dWith}px);
        }
      }
      `
      var sheet = document.styleSheets[0]
      if(sheet.cssRules[0] instanceof CSSKeyframesRule) 
        sheet.deleteRule(0);
      sheet.insertRule(keyframes, 0)
    })
    }

注意: 作为组件引入,使用sheet.insertRule(keyframes, 0)增加keyframes时,要判断已经有这个动画的时候要删掉。不然父组件数据变化,这里使用的总是第一次设置的keyframes而不是实时增加的keyframes。

父组件引入

...
  <HorizontalTextSlider :text="whether.info"></HorizontalTextSlider>
 ...
GitHub 加速计划 / vu / vue
207.54 K
33.66 K
下载
vuejs/vue: 是一个用于构建用户界面的 JavaScript 框架,具有简洁的语法和丰富的组件库,可以用于开发单页面应用程序和多页面应用程序。
最近提交(Master分支:2 个月前 )
73486cb5 * chore: fix link broken Signed-off-by: snoppy <michaleli@foxmail.com> * Update packages/template-compiler/README.md [skip ci] --------- Signed-off-by: snoppy <michaleli@foxmail.com> Co-authored-by: Eduardo San Martin Morote <posva@users.noreply.github.com> 4 个月前
e428d891 Updated Browser Compatibility reference. The previous currently returns HTTP 404. 5 个月前
Logo

旨在为数千万中国开发者提供一个无缝且高效的云端环境,以支持学习、使用和贡献开源项目。

更多推荐