[vue3学习Day1]创建、setup、ref、toRef、reactive

安装和创建

1.安装node.js

请在官网下载安装:https://nodejs.org/zh-cn/

输入指令node -v

能显示版本号,说明 node 已经装好了

输入指令`npm -v

能显示版本号,说明 npm 可以使用了

2.配置默认安装目录和缓存日志目录

说明:这里的环境配置主要配置的是npm安装的全局模块所在的路径,以及缓存cache的路径,之所以要配置,是因为以后在执行类似:npm install express [-g] (后面的可选参数-g,g代表global全局安装的意思)的安装语句时,会将安装的模块安装到【C:\Users\用户名\AppData\Roaming\npm】路径中,占C盘空间。

2.1 创建默认安装目录和缓存日志目录

比如,我希望将全模块所在路径和缓存路径,放在我node.js安装的文件夹中,则在我安装的文件夹【"D:\Program Files \nodejs】下创建两个文件夹【node_global】及【node_cache】分别作为默认安装目录和缓存日志目录。

2.2 执行命令

将npm的全局模块目录和缓存目录配置到我们刚才创建的那两个目录:

npm config set prefix "D:\Program Files\nodejs\node_global"
npm config set cache "D:\Program Files\nodejs\node_cache"

npm config get prefix

查看npm全局安装包保存路径 npm config get cache查看npm装包缓存路径

还可以输入npm list -global命令来查看全局安装目录

2.node.js环境配置

1、【系统变量】下新建【NODE_PATH】,此处设置第三方依赖包安装目录 如果跟着第2步修改了全局安装目录,则输入【D:\Program Files\nodejs\node_global\node_modules 】

2、【系统变量】下的【Path】添加上node的路径【D:\Program Files\nodejs\】

3、如果设置了全局安装目录,【用户变量】下的【Path】将默认的 C 盘下 APPData/Roaming\npm 修改为【D:\Program Files\nodejs\node_global】,【D:\Program Files\nodejs\node_cache】,这是nodejs默认的模块调用路

4.配置淘宝镜像

 npm install -g cnpm --registry=https://registry.npm.taobao.org`

输入指令cnpm -v,能显示版本号,说明 cnpm 已经装好了

切换镜像命令

npm config set registry http://registry.npm.taobao.org/

查看淘宝镜像

npm get registry

查看vue版本

 npm list vue -g

3.安装vue-cli脚手架

查询vue的cli脚手架

vue -V

参考(41条消息) Vue vscode 创建 vue 项目流程【超详细】一颗不甘坠落的流星的博客-CSDN博客vscode创建vue项目

4.创建vue3项目

1.vue-cli

vue-cli 版本在3.5.0以上
vue create 项目名

2.Vite

npm init vite-app 项目名
cd
npm i
npm run dev

1.setup

vue3.x推荐在vue-cli中使用

添加一个HelloVue3.vue文件,添加以下代码:

<template>
  <section>
    <div>
      <p>
        setup()函数中直接返回的普通变量,模板语法中可以使用,但它是单行绑定的。
      </p>
      <p>{{ text }}</p>
      <input type="text" v-model="text" />
    </div>
  </section>
</template>
​
<script>
export default {
  setup() {
    let text = "Hello Vue3.x";
     function sayHi(){
        alert("text is "+ ${text})
     }
    // setup最后一定要有return返回一个对象,把对象的属性暴露出去
    //返回方式1,返回对象 在模板中可以直接使用
    return { text ,sayHi};
    //返回方式2.返回渲染函数
    //return ()=>h('h1',1)
  },
};
</script>
​
<style>
</style>

Vue3.x推荐使用setup()方法,在方法内部暴露属性给外部,然后在DOM中使用模板语法就可以直接使用暴露出来的属性。

此时直接暴露出来的text变量,模板中虽然可以使用,但是使用v-model无法更改它的值。

因为直接暴露出来的属性,它是非响应式的变量(修改了text的值,标签不会重新渲染新值)。

1.1setup()的执行时机

setup()函数在beforeCreated之前执行一次

所以在setup()中不能使用this来访问当前的vue对象。为undefined

1.2 setup()的参数

props:对象

context:上下文对象
a t t r s , attrs, attrs,slots,$emit:
在这里插入图片描述

1.3 不要混着vue2的配置用

  1. Vue2配置中可以访问倒setup的属性和方法
  2. 但setup中不能访问Vue2的配置
  3. 重名则setup优先

tips:setup不能是async函数,因为返回promise,在模板中用不了

2.ref函数

ref函数用于包装一个基础数据类型,处理成引用对象RefImpl(reference implement引用实现对象),然后获得一个响应式的对象

在这里插入图片描述

ref包装出来的对象,我们在setup中需要使用 . value来修改或者访问它的值。在模板中,直接使用{{暴露出来的对象名}}即可获取到它的值。

ref也可以包装引用数据类型,但是仍然需要使用.value来访问引用数据类型

获取了包装对象之后,最后记得暴露出去。

<template>
  <div>
    <p>姓名:{{name}}</p>
    <p>年龄:{{age}}</p>
    <button @click="sayHi">点击1</button>
     <button @click="sayDay">点击2</button>
  </div>
</template>
​
<script>
import { ref } from "vue";
​
export default {
  setup() {
    let name = ref("MOAN");
    let age = ref(21);
​
    let obj = ref({
      type:"我爱VUE",
      days:"100年"
    })
    function sayHi() {
      console.log(ref(name));
      name.value="lili"
      console.log(ref(name));
    }
     function sayDay() {
      console.log(ref(obj));
      console.log(obj.value);
      obj.value.type="今天学习ref"
    }
      //暴露
    return {
      name,
      age,
      sayHi,
      obj,
      sayDay
    };
  },
};
</script>
​
<style>
</style>
​

在这里插入图片描述

ref处理基础数据类型

底层逻辑和vue2中的数据代理原理基本是相同的,通过Object.defineProerty的get和set方法来实现数据代理和数据劫持

尚硅谷Vue2.0+Vue3.0全套教程丨vuejs从入门到精通哔哩哔哩bilibili

ref 处理引用数据类型如对象,在内部使用reactive将数据转为代理对象Proxy
在这里插入图片描述

vue的响应式简单原理实现

// vue2中的响应式
    //源数据
    let person={
        name:"MAON",
        AGE:21
    }
    let p = {}
    Object.defineProperty(p,"name",{
        configurable:true,//可以修改
        enumerable:true,//可以枚举
        get(){
            return person.name
        },
        set(value){
            console.log("数据改变啦");
            person.name=value
        }
    })

    // vue3中的响应式
    const p = new Proxy(person,{
        get(target,propName){
            console.log(`p身上的${propName} 被读取了`);
            return Reflect.get(target,propName)
          //  return target[propName]
        },
        set(target,propName,value){
            console.log(`p身上的${propName} 被修改了`);
          //  target[propName] = value
            Reflect.set(target,propName,value)
        },
        deleteProperty(target,propName){
            console.log(`p身上的${propName} 被删除了`);
            return Reflect.deleteProperty(target,propName)
            // return delete   target[propName]
        }
    })

可以看这个视频,讲的很清楚 尚硅谷Vue2.0+Vue3.0全套教程丨vuejs从入门到精通_哔哩哔哩_bilibili

3.reactive函数

  • 与ref不同,reactive用于封装一个引用数据类型。
  • 不要使用reactive封装基础数据类型,会报警告并且响应会有延迟BUG。
  • reactive实际上是将原始对象包装成了一个代理对象Proxy,操作代理对象会修改原始对象的值。
  • 不推荐操作原始对象来完成响应式效果,会有响应延迟的BUG。
  • reactive是ref的二次封装,代码中不需要使用.value,直接访问代理对象即可。
  • reactive不要直接复制改变源数组,可以通过push方式改变
<template>
    <div>
      <p>name: <input v-model="people.name"> {{people.name}}</p>
      <p>age:{{people.age}}</p>
  </div>
</template>
​
<script>
​
import {reactive} from "vue"
​
export default {
    setup() {
        // reactive不需要使用.value来获取值
        // 不要使用reactive封装基础数据类型,响应会延缓,会报警告错误
        // reactive是ref的二次封装
        // reactive相当于包装了一个代理对象,用来修改原始对象的值。不要尝试修改原始对象,会造成奇怪错误。
        let obj = {name: "MOAN",age:21}
        let people = reactive(obj); 
​
        setInterval(()=> {
            people.age ++;
            console.log("obj.age = ",obj.age);
        },1000)
​
        return {people}
    }
​
}
</script>
​
<style>
​
</style>

4.toRef函数

  • toRef用于将响应式的对象(通常是用reactive包装的对象)中的某个属性进行包装。
  • 包装的对象保持着保持对源对象的响应式链接。
  • 可以用于将响应式的对象的某几个属性暴露出去,而不是将整个对象暴露出去。
  • 如果对象的某个属性不存在,toRef也可以生成一个响应式对象。
<template>
  <div>
      <h1>toRef</h1>
      <p>name: <input v-model="name"> {{name}}</p>
      <p>学校: <input v-model="school"> {{people.school}}</p>
      <p>name: <input v-model="people.name"> {{people.name}}</p>
      <p>age:{{age}}</p>
  </div>
</template>
​
<script>
​
import {reactive,toRef,ref} from "vue";
export default {
    components: {
        ToRefSub
    },
    setup() {
        let people = reactive({name: "MOAN",age:21});
        // toRef对响应式的对象的某个属性再进行响应式包装
        // 实际上就是对单个属性调用ref()进行包装
        let name = toRef(people,"name");
        let age = toRef(people,"age");
        // people没有学校属性,toRef也会创建一个响应对象,并且来操作对象原本没有的属性
        let school = toRef(people,"school");
        setInterval(() => {
            age.value ++;
            // console.log(age.value);
        }, 1000);
​
        // 如果直接 {name: people.name}这样把响应式对象的属性暴露出去,会有响应延迟的BUG
        return {name,age,people,school}
    }
}
</script>
​
<style>
​
</style>

5.toRefs函数

  • toRefs用于将一个响应式对象转为普通对象。
  • 该普通对象的所有属性,指向源响应式对象的所有响应式属性(即新对象的所有属性实际上也是响应式的)。
  • 通常结构结果使用。
<template>
  <div>
      <h1>toRefs</h1>
      <p>name: <input v-model="name"> {{name}}</p>
      <p>age:{{age}}</p>
  </div>
</template>
<script>
import {reactive,toRefs} from "vue";
export default {
    setup() {
        // 
        let people = reactive({name: "MOAN",age:21});

        // toRefs把一个响应式对象转为一个普通对象,该普通对象的所有属性,都是指向源响应式对象的所有响应式属性。
        // let people2 = toRefs(people);
        // let name = people2.name;
        // let age = people2.age;

        // 通常是解构使用
        let {name,age} = toRefs(people);
        return {name,age}
        
        //return ...toRefs(people)
    }
}
</script>
<style>
</style>

转载:欢迎转载,但未经作者同意,必须保留此段声明;

有问题可以在评论区“踢”我

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值