• ④ vue 中的动画


    vue 动画

    1 使用 Vue 实现基础的 CSS 过渡与动画效果

    1.1 过渡

    <style>
      .transition {
        transition: 3s background-color ease;
      }
      .blue {
        background: blue;
      }
      .green {
        background: green;
      }
    </style>
    <script>
      const app = Vue.createApp({
        data() {
          return {
            animate: {
              transition: true,
              blue: true,
              green: false
            }
          }
        },
        methods: {
          handleClick() {
            this.animate.blue = !this.animate.blue
            this.animate.green = !this.animate.green
          }
        },
        template: `
          <div>
            <div :class="animate">hello world</div>
            <button @click="handleClick">切换</button>
          </div>
        `
      })
      const vm = app.mount('#root')
    </script>
    
    • 通过数据来控制元素的 DOMstyle
    <style>
      .transition {
        transition: 3s background-color ease;
      }
    </style>
    <script>
      const app = Vue.createApp({
        data() {
          return {
            styleObj: {
              background: 'blue'
            }
          }
        },
        methods: {
          handleClick() {
            if(this.styleObj.background === 'blue') {
              this.styleObj.background = 'green'
            } else if(this.styleObj.background === 'green') {
              this.styleObj.background = 'blue'
            }
          }
        },
        template: `
          <div>
            <div class="transition" :style="styleObj">hello world</div>
            <button @click="handleClick">切换</button>
          </div>
        `
      })
      const vm = app.mount('#root')
    </script>
    

    1.2 动画

    <style>
      @keyframes leftToRight {
        0% {
          transform: translateX(-100px);
        }
        50% {
          transform: translateX(-50px);
        }
        0% {
          transform: translateX(0px);
        }
      }
      .animation {
        animation: leftToRight 3s;
      }
    </style>
    <script>
      const app = Vue.createApp({
        data() {
          return {
            animate: {
              animation: false
            }
          }
        },
        methods: {
          handleClick() {
            this.animate.animation = !this.animate.animation
          }
        },
        template: `
          <div>
            <div :class="animate">hello world</div>
            <button @click="handleClick">切换</button>
          </div>
        `
      })
      const vm = app.mount('#root')
    </script>
    

    2 使用 transition 标签实现单元素组件的过渡和动画效果

    const app = Vue.createApp({
      data() {
        return {
          show: false
        }
      },
      methods: {
        handleClick() {
          this.show = !this.show
        }
      },
      // <transition> --- `v-`
      // <transition name='hello'> --- `hello-`
      // v-if v-show
      template: `
        <div>
          <transition>
            <div v-show="show">hello world</div>
          </transition>
          <button @click="handleClick">切换</button>
        </div>
      `
    })
    const vm = app.mount('#root')
    

    2.1 过渡

      .v-enter-from {
        opacity: 0;
      }
      .v-enter-to {
        opacity: 1;
      }
      .v-leave-to {
        opacity: 0;
      }
      .v-enter-active, 
      .v-leave-active {
        transition: opacity 2s ease-in;
      }
    

    2.2 动画

    @keyframes shake {
      0% {
        transform: translateX(-100px);
      }
      50% {
        transform: translateX(-50px);
      }
      100% {
        transform: translateX(50px);
      }
    }
    .v-enter-active, 
    .v-leave-active {
      animation: shake 2s;
    }
    

    2.3 自定义 class 类名

    <style>
      @keyframes shake {
        0% {
          transform: translateX(-100px);
        }
        50% {
          transform: translateX(-50px);
        }
        100% {
          transform: translateX(50px);
        }
      }
      .hello, 
      .bye {
        animation: shake 2s;
      }
    </style>
    <script>
      const app = Vue.createApp({
        data() {
          return {
            show: false
          }
        },
        methods: {
          handleClick() {
            this.show = !this.show
          }
        },
        template: `
          <div>
            <transition
              enter-active-class="hello"
              leave-active-class="bye"
            >
              <div v-if="show">hello world</div>
            </transition>
            <button @click="handleClick">切换</button>
          </div>
        `
      })
      const vm = app.mount('#root')
    </script>
    
    

    2.4 使用第三动画库 animate

    官网

    <link
      rel="stylesheet"
      href="https://cdnjs.cloudflare.com/ajax/libs/animate.css/4.1.1/animate.min.css"
    />
    <script>
      const app = Vue.createApp({
        data() {
          return {
            show: false
          }
        },
        methods: {
          handleClick() {
            this.show = !this.show
          }
        },
        template: `
          <div>
            <transition
              enter-active-class="animate__animated animate__bounce"
              leave-active-class="animate__animated animate__flash"
            >
              <div v-if="show">hello world</div>
            </transition>
            <button @click="handleClick">切换</button>
          </div>
        `
      })
      const vm = app.mount('#root')
    </script>
    

    2.5 动画 + 过渡

    @keyframes shake {
      0% {
        transform: translateX(-100px);
      }
      50% {
        transform: translateX(-50px);
      }
      100% {
        transform: translateX(50px);
      }
    }
    .v-enter-from {
      color: red;
    }
    .v-enter-active {
      animation: shake 2s;
      transition: color 3s ease-in;
    }
    .v-leave-active {
      color: red;
      animation: shake 2s;
      transition: all 3s ease-in;
    }
    
    • 动画 & 过渡同时存在,<transition> 添加属性 type 实现以动画 animation | 过渡 transition 的时间为准结束该过程
    const app = Vue.createApp({
      template: `
        <div>
          <transition type="transition">
            <div v-if="show">hello world</div>
          </transition>
          <button @click="handleClick">切换</button>
        </div>
      `
    })
    
    • 动画 & 过渡同时存在,<transition> 添加属性 duration 实现以指定时间 (ms为单位) 为准
    const app = Vue.createApp({
      template: `
        <div>
          <transition :duration="{ enter: 1000, leave: 3000 }">
            <div v-if="show">hello world</div>
          </transition>
          <button @click="handleClick">切换</button>
        </div>
      `
    })
    

    2.6 通过数据来控制元素的 DOM 和 style

    const app = Vue.createApp({
      data() {
        return {
          show: false
        }
      },
      methods: {
        handleClick() {
          this.show = !this.show
        },
        handleBeforeEnter(el) {
          el.style.color = "red"
        },
        handleEnter(el, done) {
          const animation = setInterval(() => {
            const color = el.style.color
            if(color === 'red') {
              el.style.color = 'green'
            } else {
              el.style.color = 'red'
            }
          }, 1000);
          setTimeout(() => {
            clearInterval(animation)
            done() // 通知 handleAfterEnter
          }, 5000);
        },
        handleAfterEnter() {
          alert(123)
        }
      },
      template: `
        <div>
          <transition 
            :css="false"
            @before-enter="handleBeforeEnter"
            @enter="handleEnter"
            @after-enter="handleAfterEnter"
            @before-leave="handleBeforeLeave"
            @leave="handleLeave"
            @after-leave="handleAfterLeave"
          >
            <div v-show="show">hello world</div>
          </transition>
          <button @click="handleClick">切换</button>
        </div>
      `
    })
    const vm = app.mount('#root')
    

    3 组件和元素切换动画的实现

    3.1 多个单元素标签之间的切换

    • 动画同时进行
    <style>
      .v-enter-from,
      .v-leave-to {
        opacity: 0;
      }
      .v-enter-active,
      .v-leave-active {
        transition: all 3s ease-in;
      }
      .v-enter-to,
      .v-leave-from {
        opacity: 1;
      }
    </style>
    <script>
      const app = Vue.createApp({
        data() {
          return { show: false }
        },
        methods: {
          handleClick() {
            this.show = !this.show
          }
        },
        template: `
          <div>
            <transition>
              <div v-if="show">hello world</div>
              <div v-else="show">bye world</div>
            </transition>
            <button @click="handleClick">切换</button>
          </div>
        `
      })
      const vm = app.mount('#root')
    </script>
    

    1. <transition> 添加属性 mode 实现多元素的过渡顺序

    1. 先进场再出场:mode="in-out"

    2. 先出场再进场:mode="out-in"

    2. <transition> 添加属性 appear 实现初始动画效果

    3.2 多个单组件之间的切换

    const ComponentA = {
     template: '<div>hello world</div>'
    }
    const ComponentB = {
     template: '<div>bye world</div>'
    }
    const app = Vue.createApp({
     data() {
       return { show: false }
     },
     methods: {
       handleClick() {
         this.show = !this.show
       }
     },
     components: {
       'component-a': ComponentA,
       'component-b': ComponentB,
     },
     template: `
       <div>
         <transition mode="out-in" appear>
           <component-a v-if="show">hello world</component-a>
           <component-b v-else="show">bye world</component-b>
         </transition>
         <button @click="handleClick">切换</button>
       </div>
     `
    })
    const vm = app.mount('#root')
    
    • 动态组件
    const ComponentA = {
      template: '<div>hello world</div>'
    }
    const ComponentB = {
      template: '<div>bye world</div>'
    }
    const app = Vue.createApp({
      data() {
        return { component: 'component-a' }
      },
      methods: {
        handleClick() {
          if(this.component === 'component-a') {
            this.component = 'component-b'
          } else {
            this.component = 'component-a'
          }
        }
      },
      components: {
        'component-a': ComponentA,
        'component-b': ComponentB,
      },
      template: `
        <div>
          <transition mode="out-in" appear>
            <component :is="component" />
          </transition>
          <button @click="handleClick">切换</button>
        </div>
      `
    })
    const vm = app.mount('#root')
    

    4 列表动画

    • <transition-group>
    <style>
      .list-item {
        display: inline-block;
        margin-right: 10px;
      }
    </style>
    <script>
      const app = Vue.createApp({
        data() {
          return { list: [1, 2, 3] }
        },
        methods: {
          handleClick() {
            this.list.unshift(this.list.length + 1)
          }
        },
        template: `
          <div>
            <transition-group>
              <span class="list-item" v-for="item in list" :key="item">{{ item }}</span>
            </transition-group>
            <button @click="handleClick">切换</button>
          </div>
        `
      })
      const vm = app.mount('#root')
    </script>
    

    4.1 新增项的动画效果

    .v-enter-from {
      opacity: 0;
      transform: translateY(30px);
    }
    .v-enter-active {
      transition: all 1s ease-in;
    }
    .v-enter-to {
      opacity: 1;
      transform: translateY(0);
    }
    

    4.2 所有项的动画效果

    .v-enter-from {
      opacity: 0;
      transform: translateY(30px);
    }
    .v-enter-active {
      transition: all 1s ease-in;
    }
    .v-enter-to {
      opacity: 1;
      transform: translateY(0);
    }
    .v-move {
      transition: all 1s ease-in;
    }
    

    5 状态动画

    • 通过 数据 控制动画
    const app = Vue.createApp({
      data() {
        return { 
          number: 1,
          animateNumber: 1
        }
      },
      methods: {
        handleClick() {
          this.number = 10;
          if(this.animateNumber < this.number) {
            const animation = setInterval(() => {
              this.animateNumber += 1;
              if(this.animateNumber === 10) {
                clearInterval(animation)
              }
            }, 100);
          }
        }
      },
    
      template: `
        <div>
          <span>{{ animateNumber }}</span>
          <button @click="handleClick">增加</button>
        </div>
      `
    })
    const vm = app.mount('#root')
    
  • 相关阅读:
    各协议
    2017-2018-2 20155230《网络对抗技术》实验9:Web安全基础
    2017-2018-2 20155230《网络对抗技术》实验8:Web基础
    2017-2018-2 20155230《网络对抗技术》实验7:网络欺诈防范
    2017-2018-2 20155230《网络对抗技术》实验6:信息搜集与漏洞扫描
    2017-2018-2 20155230《网络对抗技术》实验5:MSF基础应用
    2017-2018-2 20155230《网络对抗技术》实验4:恶意代码分析
    2017-2018-2 20155230《网络对抗技术》实验3:免杀原理与实践
    2017-2018-2 20155230《网络对抗技术》实验2:后门原理与实践
    2017-2018-2 20155230《网络对抗技术》实验1:PC平台逆向破解(5)M
  • 原文地址:https://www.cnblogs.com/pleaseAnswer/p/16012105.html
Copyright © 2020-2023  润新知