vue3 + Typescript学习笔记 二

一、用 reactive()函数优化程序

  1. 上节课的代码可以说没什么章法可言,所有的变量和方法都混淆在一起,我最不能忍受的是在setup中要改变和读取一个值的时候,还要加上value。这种代码一定是可以优化的,需要引入一个新的 APIreactive。它也是一个函数(方法),只不过里边接受的参数是一个 Object(对象)。
    然后无论是变量和方法,都可以作为 Object 中的一个属性,而且在改变selectGirl值的时候也不用再加讨厌的value属性了。再return返回的时候也不用一个个返回了,只需要返回一个data,就可以了。

    <script lang="ts">
    import { ref, reactive } from "vue";
    export default {
      name: "App",
      setup() {
        const data = reactive({
          girls: ["大脚", "刘英", "晓红"],
          selectGirl: "",
          selectGirlFun: (index: number) => {
            data.selectGirl = data.girls[index];
          },
        });
    
        return {
          data,
        };
      },
    };
    </script>
    
  2. 修改完成<script>部分的代码后,还需要修改template部分的代码,因为我们这时候返回的只有data,所以模板部分的字面量前要加入data。

    <template>
      <img alt="Vue logo" src="./assets/logo.png" />
      <div>
        <h2>欢迎光临红浪漫洗浴中心</h2>
        <div>请选择一位美女为你服务</div>
      </div>
      <div>
        <button
          v-for="(item, index) in data.girls"
          v-bind:key="index"
          @click="data.selectGirlFun(index)"
        >
          {{ index }} : {{ item }}
        </button>
      </div>
      <div>你选择了【{{ data.selectGirl }}】为你服务</div>
    </template>
    
  3. 这个修改完成后,可以在Terminal终端里打开yarn serve,查看一下效果了,如果没有错误,应该和原来的效果一样。效果虽然一样,但是这时候代码,要比上节课优雅了很多。着一些的功劳要归属于reactive函数。

    给 data 增加类型注解

  4. 这时的代码虽然可以完美的运行,但是细心的小伙伴可以发现data这个变量,我们并没有作类型注解,而是采用了TypeScript的类型推断。
    这样的代码,在我们公司是不允许出现的,必须要增加类型注解。所以我们先定义一个接口,用接口(interface)来作类型注解。

    interface DataProps {
      girls: string[];
      selectGirl: string;
      selectGirlFun: (index: number) => void;
    }
    

    编写完成后,你在显示的为 data 变量作一个类型注解.

    cosnt data: DataProps = ...
    

用 toRefs()继续优化

  1. 现在template中,每次输出变量前面都要加一个data,这是可以优化的。有的小伙伴说了,我用…扩展运算符就可以解决这个问题了。
    在这里我就可以告诉你不行,因为结构后就变成了普通变量,不再具有响应式的能力。所以要解决这个问题,需要使用 Vue3 的一个新函数toRefs()。使用前需要先进行引入。

    import { reactive, toRefs } from "vue";
    

    引入后就可以对data进行包装,把 data 变成refData,这样就可以使用扩展运算符的方式了。具体代码如下:

     export default {
      name: "App",
      setup() {
        // const girls = ref(["大脚", "刘英", "晓红"]);
        // const selectGirl = ref("");
        // const selectGirlFun = (index: number) => {
        //   selectGirl.value = girls.value[index];
        // };
        const data: DataProps = reactive({
          girls: ["大脚", "刘英", "晓红"],
          selectGirl: "",
          selectGirlFun: (index: number) => {
            data.selectGirl = data.girls[index];
          },
        });
        const refData = toRefs(data);
    
        return {
          ...refData,
        };
      },
    };
    

    这样写之后,你的template就应该去掉 data,而是直接使用变量名和方法,就可以了。

    <template>
      <img alt="Vue logo" src="./assets/logo.png" />
      <div>
        <h2>欢迎光临红浪漫洗浴中心</h2>
        <div>请选择一位美女为你服务</div>
      </div>
      <div>
        <button
          v-for="(item, index) in girls"
          v-bind:key="index"
          @click="selectGirlFun(index)"
        >
          {{ index }} : {{ item }}
        </button>
      </div>
      <div>你选择了【{{ selectGirl }}】为你服务</div>
    </template>
    

如何选择 Ref()和 reactive()

  1. 网络上对这两个方法的争论还是不少的,但到目前为止,还没有什么实质性的理论到底是用Ref()好,还是reactive()好,也就是两种方法都可以。他们的作用都是生成响应式对象,目前来看只是编写上有所不同。
    我个人更倾向于使用reactive(),因为它让程序看起来更规范。如果你学到这里还犹豫不定,也没关系,随着你进一步的深入学习,一定会有你自己的最佳选择。

二、Vue3.x 的生命周期和钩子函数

  1. Vue3 版本的生命周期和 Vue2 比有了些变化,所以我先站在一个初学者的角度(没有学过 Vue2 版本的新手),从新讲一下 Vue3.x 的生命周期,等你完全理解之后,我们再来和 Vue2.x 的生命周期作一个对比。

  2. 什么是生命周期

  3. Vue 是组件化编程,从一个组件诞生到消亡,会经历很多过程,这些过程就叫做生命周期。

  4. 来个比喻,生命周期和人从出生到入土是一样的。有少年时期、有青年时期、有中年时期、有老年时期。每个时期都应该有不同的任务,可以作不同的事。
    当你理解了什么是生命周期,你还了解一个概念“钩子函数”。

  5. 钩子函数: 伴随着生命周期,给用户使用的函数,操控生命周期,主要是操控钩子函数。
    Vue3 的生命周期比较多,我们需要一个个给大家讲。

    setup() :开始创建组件之前,在beforeCreate和created之前执行。创建的是data和method
    onBeforeMount() : 组件挂载到节点上之前执行的函数。
    onMounted() : 组件挂载完成后执行的函数。
    onBeforeUpdate(): 组件更新之前执行的函数。
    onUpdated(): 组件更新完成之后执行的函数。
    onBeforeUnmount(): 组件卸载之前执行的函数。
    onUnmounted(): 组件卸载完成后执行的函数
    onActivated(): 被包含在<keep-alive>中的组件,会多出两个生命周期钩子函数。被激活时执行。
    onDeactivated(): 比如从 A 组件,切换到 B 组件,A 组件消失时执行。
    onErrorCaptured(): 当捕获一个来自子孙组件的异常时激活钩子函数(以后用到再讲,不好展现)。
    
  6. 注:使用组件会将数据保留在内存中,比如我们不想每次看到一个页面都重新加载数据,就可以使用组件解决。

三、钩子函数的使用

  1. Vue3.x 生命周期在调用前需要先进行引入,我们先暂时演示前五个生命周期。

    import {
      reactive,
      toRefs,
      onMounted,
      onBeforeMount,
      onBeforeUpdate,
      onUpdated,
    } from "vue";
    
  2. 先来说setup(),setup 这个函数是在beforeCreate和created之前运行的,所以你可以用它来代替这两个钩子函数。
    为了看出钩子函数执行的时机,我在setup()函数里,编写了下面的代码:

    <script lang="ts">
    
    //....
    const app = {
      name: "App",
      setup() {
        console.log("1-开始创建组件-----setup()");
        const data: DataProps = reactive({
          girls: ["大脚", "刘英", "晓红"],
          selectGirl: "",
          selectGirlFun: (index: number) => {
            data.selectGirl = data.girls[index];
          },
        });
        onBeforeMount(() => {
          console.log("2-组件挂载到页面之前执行-----onBeforeMount()");
        });
    
        onMounted(() => {
          console.log("3-组件挂载到页面之后执行-----onMounted()");
        });
        onBeforeUpdate(() => {
          console.log("4-组件更新之前-----onBeforeUpdate()");
        });
    
        onUpdated(() => {
          console.log("5-组件更新之后-----onUpdated()");
        });
    
        const refData = toRefs(data);
    
        return {
          ...refData,
        };
      },
    };
    export default app;
    </script>
    
  3. 写完后可以到浏览器看一下效果,效果和你想象的应该是一样的。

    1 - 开始创建组件---- - setup();
    2 - 组件挂载到页面之前执行---- - onBeforeMount();
    3 - 组件挂载到页面之后执行---- - onMounted();
    4 - 组件更新之前---- - onBeforeUpdate();
    5 - 组件更新之后---- - onUpdated();
    
  4. 你这时候一定会有个疑问,那Vue2.X版本的生命周期函数还可以使用吗?答案是肯定的。
    你可以在setup()函数之后编写Vue2的生命周期函数,代码如下:

    beforeCreate() {
      console.log("1-组件创建之前-----beforeCreate()");
    },
    beforeMount() {
      console.log("2-组件挂载到页面之前执行-----BeforeMount()");
    },
    mounted() {
      console.log("3-组件挂载到页面之后执行-----Mounted()");
    },
    beforeUpdate() {
      console.log("4-组件更新之前-----BeforeUpdate()");
    },
    updated() {
      console.log("5-组件更新之后-----Updated()");
    },
    

    这时候可以看到,原来的生命周期也是完全可以使用。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值