• Vue3的新特性总结


    一、Vue3 里 script 的三种写法

    首先,Vue3 新增了一个叫做组合式 api 的东西,英文名叫 Composition API。因此 Vue3 的 script 现在支持三种写法。

    1、最基本的 Vue2 写法

    <template>
      <div>{{ count }}</div>
      <button @click="onClick">
        增加 1
      </button>
    </template>
    
    <script>
    export default {
      data() {
        return {
          count: 1,
        };
      },
      methods: {
        onClick() {
          this.count += 1;
        },
      },
    }
    </script>
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21

    2、setup() 属性

    <template>
      <div>{{ count }}</div>
      <button @click="onClick">
        增加 1
      </button>
    </template>
    
    <script>
    import { ref } from 'vue';
    export default {
    
      // 注意这部分
      setup() {
        let count = ref(1);
        const onClick = () => {
          count.value += 1;
        };
        return {
          count,
          onClick,
        };
      },
      
    }
    </script>
    
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26

    标签 script setup

    <template>
      <div>{{ count }}</div>
      <button @click="onClick">
        增加 1
      </button>
    </template>
    
    <script setup>
    import { ref } from 'vue';
    
    const count = ref(1);
    const onClick = () => {
      count.value += 1;
    };
    </script>
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15

    正如你看到的那样,无论是代码行数,还是代码的精简度,

    如果你对 Vue 很熟悉,那么,我推荐你使用

    因为第一种写法的学习负担更小,先学第一种方式,掌握最基本的 Vue 用法,然后再根据我这篇文章,快速掌握 Vue3 里最需要关心的内容。

    第一种写法,跟过去 Vue2 的写法是一样的,所以我们不过多介绍。

    第二种写法,所有的对象和方法都需要 return 才能使用,太啰嗦。除了旧项目,可以用这种方式体验 Vue3 的新特性以外,我个人不建议了解这种方式。

    所以,接下来,我们主要介绍的,也就是 script setup ,这种写法里需要了解的内容。

    注意: setup写在script上的本质上是第二种写法的语法糖,掌握了这种写法,其实第二种写法也基本上就会了。

    二、如何使用 script setup 编写组件

    1、data——唯一需要注意的地方

    整个 data 这一部分的内容,你只需要记住下面这一点。

    以前在 data 中创建的属性,现在全都用 ref() 声明。

    在 template 中直接用,在 script 中记得加 .value 。

    按照官方的推荐要求,建议全部用ref,尽量不要使用reactive。

    写法对比

    // Vue2 的写法
    
    <template>
      <div>{{ count }}</div>
      <button @click="onClick">
        增加 1
      </button>
    </template>
    
    <script>
    export default {
      data() {
        return {
          count: 1,
        };
      },
      methods: {
        onClick() {
          this.count += 1;
        },
      },
    }
    </script>
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
     // Vue3 的写法
    
    <template>
      <div>{{ count }}</div>
      <button @click="onClick">
        增加 1
      </button>
    </template>
    
    <script setup>
    import { ref } from 'vue';
    
     // 用这种方式声明
    const count = ref(1);
    
    const onClick = () => {
       // 使用的时候记得 .value
      count.value += 1;
    };
    </script>
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20

    提示:

    1、什么时候用 ref() 包裹,什么时候不用?

    要不要用ref,就看你的这个变量的值改变了以后,页面要不要跟着变。

    当然,你可以完全不需要关心这一点,跟过去写 data 一样就行。

    只不过这样做,你在使用的时候,需要一直 .value。

    2、不要解构使用
    在使用时,不要像下面这样去写,会丢失响应性。

    也就是会出现更新了值,但是页面没有更新的情况

    // Vue3 的写法
    <template>
      <div>{{ count }}</div>
      <button @click="onClick">
        增加 1
      </button>
    </template>
    
    <script setup>
    import { ref } from 'vue';
    
    const count = ref(1);
    const onClick = () => {
      // 不要这样写!!
      const { value } = count;
      value += 1;
    };
    </script>
    
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19

    2、methods

    声明事件方法,我们只需要在 script 标签里,创建一个方法对象即可。

    剩下的在 Vue2 里是怎么写的,Vue3 是同样的写法。

    // Vue2 的写法
    <template>
      <div @click="onClick">
        这是一个div
      </div>
    </template>
    
    <script>
    export default {
      methods: {
        onClick() {
          console.log('clicked')
        },
      },
    }
    </script>
    
    // Vue3 的写法
    <template>
      <div @click="onClick">
        这是一个div
      </div>
    </template>
    
    <script setup>
    
    // 注意这部分
    const onClick = () => {
      console.log('clicked')
    }
    
    </script>
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32

    3、props

    声明 props 我们可以用 defineProps(),具体写法,我们看代码。

    // Vue2 的写法
    <template>
      <div>{{ foo }}</div>
    </template>
    
    <script>
    export default {
      props: {
        foo: String,
      },
      created() {
        console.log(this.foo);
      },
    }
    </script>
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    // Vue3 的写法
    <template>
      <div>{{ foo }}</div>
    </template>
    
    <script setup>
    
    // 注意这里
    const props = defineProps({
      foo: String
    })
    
    // 在 script 标签里使用
    console.log(props.foo)
    </script>
    
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16

    4、emit事件

    与 props 相同,声明 emits 我们可以用 defineEmits(),具体写法,我们看代码。

    // Vue2 的写法
    <template>
      <div @click="onClick">
        这是一个div
      </div>
    </template>
    
    <script>
    export default {
    
      emits: ['click'], // 注意这里
      methods: {
        onClick() {
          this.$emit('click'); // 注意这里
        },
      },
     
    }
    </script>
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    // Vue3 的写法
    <template>
      <div @click="onClick">
        这是一个div
      </div>
    </template>
    
    <script setup>
    
    // 注意这里
    const emit = defineEmits(['click']);
    
    const onClick = () => {
      emit('click') // 注意这里
    }
    
    </script>
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17

    5、computed

    // Vue2 的写法
    <template>
      <div>
        <span>{{ value }}</span>
        <span>{{ reversedValue }}</span>
      </div>
    </template>
    
    <script>
    export default {
      data() {
        return {
          value: 'this is a value',
        };
      },
      computed: {
        reversedValue() {
          return value
            .split('').reverse().join('');
        },
      },
    }
    </script>
    
    // Vue3 的写法
    <template>
      <div>
        <span>{{ value }}</span>
        <span>{{ reversedValue }}</span>
      </div>
    </template>
    
    <script setup>
    import {ref, computed} from 'vue'
    const value = ref('this is a value')
    
    // 注意这里
    const reversedValue = computed(() => {
      // 使用 ref 需要 .value
      return value.value
        .split('').reverse().join('');
    })
    
    </script>
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35
    • 36
    • 37
    • 38
    • 39
    • 40
    • 41
    • 42
    • 43
    • 44

    6、watch

    这一部分,我们需要注意一下了,Vue3 中,watch 有两种写法。一种是直接使用 watch,还有一种是使用 watchEffect。
    两种写法的区别是:

    watch 需要你明确指定依赖的变量,才能做到监听效果。

    而 watchEffect 会根据你使用的变量,自动的实现监听效果。

    // Vue2 的写法
    <template>
      <div>{{ count }}</div>
      <div>{{ anotherCount }}</div>
      <button @click="onClick">
        增加 1
      </button>
    </template>
    
    <script>
    export default {
      data() {
        return {  
          count: 1,
          anotherCount: 0,
        };
      },
      methods: {
        onClick() {
          this.count += 1;
        },
      },
      watch: {
        count(newValue) {
          this.anotherCount = newValue - 1;
        },
      },
    }
    </script>
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    // Vue3 的写法
    <template>
      <div>{{ count }}</div>
      <div>{{ anotherCount }}</div>
      <button @click="onClick">
        增加 1
      </button>
    </template>
    
    <script setup>
    import { ref, watch } from 'vue';
    
    const count = ref(1);
    const onClick = () => {
      count.value += 1;
    };
    
    const anotherCount = ref(0);
    
    // 注意这里
    // 需要在这里,
    // 明确指定依赖的是 count 这个变量
    watch(count, (newValue) => {
      anotherCount.value = newValue - 1;
    })
    
    </script>
    
    // Vue3 的写法
    <template>
      <div>{{ count }}</div>
      <div>{{ anotherCount }}</div>
      <button @click="onClick">
        增加 1
      </button>
    </template>
    
    <script setup>
    import { ref, watchEffect } from 'vue';
    
    const count = ref(1);
    const onClick = () => {
      count.value += 1;
    };
    
    const anotherCount = ref(0);
    
    // 注意这里
    watchEffect(() => {
      // 会自动根据 count.value 的变化,
      // 触发下面的操作
      anotherCount.value = count.value - 1;
    })
    
    </script>
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35
    • 36
    • 37
    • 38
    • 39
    • 40
    • 41
    • 42
    • 43
    • 44
    • 45
    • 46
    • 47
    • 48
    • 49
    • 50
    • 51
    • 52
    • 53
    • 54
    • 55
  • 相关阅读:
    【pac文件】win10自动配置代理
    c语言的基本类型有哪些
    Nginx入门指南:轻松掌握Web服务器技术
    Codeforces Round #811 (Div. 3)补题(A-G)
    【go】defer的使用
    35 WEB漏洞-逻辑越权之找回机制及接口安全
    微服务开发与实战Day01 - MyBatisPlus
    ISP代理是什么?跨境账号养号为什么要选择它?
    网络安全深入学习第七课——热门框架漏洞(RCE— Fastjson反序列化漏洞)
    Mysql —— “子查询”内容上的打字练习
  • 原文地址:https://blog.csdn.net/huangzhixin1996/article/details/132792114