网易首页 > 网易号 > 正文 申请入驻

前端开发技术之Vue3 相关基础知识点的整理分享

0
分享至

多个根节点编辑器不会报错

Vue3是允许我们有多个根节点的,但是我们如果使用Vetur就会报错,不会影响运行,但是看起来就很烦。所以当我们转向Volar那么就不会出现这个问题了。

编辑器分隔

即便Vue的组件化开发,可以将单文件的代码长度大幅缩短,但还是动辄几百行甚是上千行。那么我们切换template,script和style的时候就要频繁上下翻,虽然有的插件可以直接定位到css,但是你回不去啊!所以这个功能简直是太人性化了。

安装完Volar以后,打开一个.vue文件,看vscode的右上角,有这么一个图标,点一下。

它就会自动给你分隔成三个页面,分别对应template,script和style,这样就太舒服了有没有。

Vue 3 Snippets

推荐的第二个插件叫做Vue 3 Snippets,同样的,它也有自己的Vue2版本。它是干什么的呢,可以看一下下面这张图,我只输入了“v3”,它有很多提示,我们就先选择v3computed,选中回车即可。

然后它就给自动给我们写了如下代码

是不是超级省事,摸鱼的时间又增加了!还有更多有趣的使用方式,小伙伴们自行探索吧。

创建Vue3项目

那么正式开始学习我们的Vue3,先从创建项目开始。

使用 vue-cli 创建

输入下面的命令然后选择配置项进行安装即可,这里注意vue-cli的版本一定要在4.5.0以上

// 安装或者升级
npm install -g @vue/cli
//查看版本 保证 vue cli 版本在 4.5.0 以上
vue --version
// 创建项目
vue create my-project
//然后根据提示一步一步傻瓜式操作就行了
...
复制代码

使用 Vite 创建

// 初始化viete项目
npm init vite-app
// 进入项目文件夹
cd
// 安装依赖
npm install
//启动项目
npm run dev
复制代码
创建完以后我们先来看看入口文件main.ts
// 引入createApp函数,创建对应的应用,产生应用的实例对象
import { createApp } from 'vue';
// 引入app组件(所有组件的父级组件)
import App from '·/App·vue';
// 创建app应用返回对应的实例对象,调用mount方法进行挂载 到#app节点上去
createApp(App).mount('#app');
复制代码
然后看看根组件app.vue
//Vue2组件中的html模板中必须要有一对根标签,Vue3组件的html模板中可以没有根标签

复制代码

Composition API

接下来到了重头戏,Vue3的招牌特性,Composition API

关于Composition API这里有大佬做的动画演示,极力推荐。

那个忙了一夜的Vue3动画很好,就是太短了

Composition API可以更方便的抽取共通逻辑,但是不要过于在意逻辑代码复用,以功能提取代码也是一种思路。

顺便提一句,Vue3兼容大部分Vue2语法,所以在Vue3中书写Vue2语法是没有问题的(废除的除外),但是既然我们已经升级Vue3了,不建议混合使用,除非一些大型特殊项目需要兼容两个版本。

setup

setup是组合Composition API中的入口函数,也是第一个要使用的函数。
setup只在初始化时执行一次,所有的Composition API函数都在此使用。
setup() {
console.log('我执行了') //我执行了
},
复制代码
可以通过console.log看到setup是在beforeCreate生命周期之前执行的(只执行一次)
beforeCreate() {
console.log('beforeCreate执行了');
},
setup() {
console.log('setup执行了');
return {};
},
//setup执行了
//beforeCreate执行了
复制代码

可以通过console.log看到setup是在beforeCreate生命周期之前执行的(只执行一次)

beforeCreate() { console.log('beforeCreate执行了'); }, setup() { console.log('setup执行了'); return {}; }, //setup执行了 //beforeCreate执行了复制代码

由此可以推断出setup执行的时候,组件对象还没有创建,组件实例对象this还不可用,此时this是undefined, 不能通过this来访问data/computed/methods/props。

返回对象中的属性会与data函数返回对象的属性合并成为组件对象的属性,返回对象中的方法会与methods中的方法合并成功组件对象的方法,如果有重名, setup优先。因为在setup中this不可用,methods中可以访问setup提供的属性和方法, 但在setup方法中不能访问data和methods里的内容,所以还是不建议混合使用。

setup函数如果返回对象, 对象中的 属性 或 方法 , 模板 中可以直接使用
//templete

{{number}}


//JS
setup() {
const number = 18;
return {
number,
},
复制代码

注意:setup不能是一个async函数: 因为返回值不再是return的对象, 而是promise, 模板中就不可以使用return中返回对象的数据了。

setup的参数(props,context)`

props: 是一个对象,里面有父级组件向子级组件传递的数据,并且是在子级组件中使用props接收到的所有的属性

context:上下文对象,可以通过es6语法解构 setup(props, {attrs, slots, emit})

  • attrs: 获取当前组件标签上所有没有通过props接收的属性的对象, 相当于 this.$attrs
  • slots: 包含所有传入的插槽内容的对象, 相当于 this.$slots
  • emit: 用来分发自定义事件的函数, 相当于 this.$emit

演示attrs和props
//父组件
//子组件

子组件
msg:{{ msg }}
复制代码
演示emit
//父组件
//子组件
事件分发
复制代码

ref

作用

定义一个响应式的数据(一般用来定义一个基本类型的响应式数据Undefined、Null、Boolean、Number和String)

语法

const xxx = ref(initValue):

复制代码

注意:script中操作数据需要使用xxx.value的形式,而模板中不需要添加.value

用一个例子来演示:实现一个按钮,点击可以增加数字

{{count}}


增加
复制代码

在Vue2中

data() {
return {
conunt: 0,
};
},
methods: {
updateCount() {
this.conunt++;
},
},
复制代码

在Vue3中

setup() {
// ref用于定义一个响应式的数据,返回的是一个Ref对象,对象中有一个value属性
//如果需要对数据进行操作,需要使用该Ref对象的value属性
const count = ref(0);
function updateCount() {
count.value++;
}
return {
count,
updateCount,
};
},
复制代码
在Vue2中我们通过this.$refs来获取dom节点,Vue3中我们通过ref来获取节点
首先需要在标签上添加ref='xxx',然后再setup中定义一个初始值为null的ref类型,名字要和标签的ref属性一致
const xxx = ref(null)
复制代码

注意:一定要在setup的return中返回,不然会报错。

还是用一个例子来演示:让输入框自动获取焦点

App

复制代码

reactive

语法

const proxy = reactive(obj)

复制代码

作用

定义多个数据的响应式,接收一个普通对象然后返回该普通对象的响应式代理器对象(Proxy),响应式转换是“深层的”:会影响对象内部所有嵌套的属性,所有的数据都是响应式的。

代码演示

姓名:{{user.name}}
年龄:{{user.age}}
wife:{{user.wife}}
更新
setup() {
const user = reactive({
name: 'hzw',
age: 18,
wife: {
name: 'xioaohong',
age: 18,
books: ['红宝书', '设计模式', '算法与数据结构'],
},
const updateUser = () => {
user.name = '小红';
user.age += 2;
user.wife.books[0] = '金瓶梅';
return {
user,
updateUser,
},
复制代码

computed函数:

与Vue2中的computed配置功能一致,返回的是一个ref类型的对象

计算属性的函数中如果只传入一个回调函数 表示的是get操作

与Vue2中的computed配置功能一致,返回的是一个ref类型的对象
计算属性的函数中如果只传入一个回调函数 表示的是get操作
import { computed } from 'vue';
const user = reactive({
firstName: '韩',
lastName: '志伟',
});
const fullName1 = computed(() => {
return user.firstName + user.lastName;
});
return {
user,
fullName1,
};
复制代码
计算属性的函数中可以传入一个对象,可以包含set和get函数,进行读取和修改的操作
const fullName2 = computed({
get() {
return user.firstName + '_' + user.lastName;
},
set(val: string) {
const names = val.split('_');
user.firstName = names[0];
user.lastName = names[1];
},
});
return {
user,
fullName2,
};
复制代码

watch函数:

与Vue2中的watch配置功能一致,

  • 参数1:要监听的数据
  • 参数2:回调函数
  • 参数3:配置

作用

监视指定的一个或多个响应式数据, 一旦数据变化, 就自动执行监视回调

默认初始时不执行回调, 但可以通过配置immediate为true, 来指定初始时立即执行第一次

通过配置deep为true, 来指定深度监视

import { watch, ref } from 'vue';
const user = reactive({
firstName: '韩',
lastName: '志伟',
});
const fullName3 = ref('');
watch(
user,
({ firstName, lastName }) => {
fullName3.value = firstName + '_' + lastName;
},
{ immediate: true, deep: true }
);
return {
user,
fullName3,
};
复制代码
watch监听多个数据,使用数组
watch监听非响应式数据的时候需要使用回调函数的形式
watch([()=>user.firstName,()=>user.lastName,fullName3],()=>{console.log('我执行了')})
复制代码

watchEffect函数:

作用

监视数据发生变化时执行回调,不用直接指定要监视的数据, 回调函数中使用的哪些响应式数据就监视哪些响应式数据,默认初始时就会执行第一次, 从而可以收集需要监视的数据。

import { watchEffect, ref } from 'vue';
const user = reactive({
firstName: '韩',
lastName: '志伟',
});
const fullName4 = ref('');
watchEffect(() => {
fullName4.value = user.firstName + '_' + user.lastName;
});
return {
user,
fullName4,
};
watchEffect可以实现计算属性set方法
watchEffect(() => {
const names = fullName3.value.split('_');
user.firstName = names[0];
user.lastName = names[1];
});
复制代码

生命周期对比:

注意:3.0中的生命周期钩子要比2.X中相同生命周期的钩子要快

Composition API还新增了以下调试钩子函数:但是不怎么常用

  • onRenderTracked
  • onRenderTriggered

代码演示

setup() {
onBeforeMount(() => {
console.log('--onBeforeMount')
})
onMounted(() => {
console.log('--onMounted')
})
onBeforeUpdate(() => {
console.log('--onBeforeUpdate')
})
onUpdated(() => {
console.log('--onUpdated')
})
onBeforeUnmount(() => {
console.log('--onBeforeUnmount')
})
onUnmounted(() => {
console.log('--onUnmounted')
})
}
复制代码

toRefs

作用

把一个响应式对象转换成普通对象,该普通对象的每个属性都是一个 ref

应用

我们使用reactive创建的对象,如果想在模板中使用,就必须得使用xxx.xxx的形式,如果大量用到的话还是很麻烦的,但是使用es6解构以后,会失去响应式,那么toRefs的作用就体现在这,,利用toRefs可以将一个响应式 reactive 对象的所有原始属性转换为响应式的ref属性。当然小伙伴们可以自行开发更多应用场景。

代码演示


name:{{name}}


复制代码

provide 与 inject

作用

实现跨层级组件(祖孙)间通信

代码演示

父组件

父组件

当前颜色: {{color}}




复制代码
子组件


子组件


复制代码
孙子组件
孙子组件: {{color}}
复制代码

其他特性

Teleport(瞬移)

作用

Teleport 提供了一种干净的方法, 让组件的html在父组件界面外的特定标签(很可能是body)下插入显示 换句话说就是可以把子组件或者dom节点插入到任何你想插入到的地方去。

语法

使用to属性 引号内使用选择器

复制代码

代码演示

//父组件


App


//子组件


点我打开对话框


class="looklook">
看看我出现在了哪里
Close


复制代码

可以看到在子组件中的looklook元素跑到了body下面,而之前的位置默认出现了两行注释

Suspense(不确定的)

作用

它们允许我们的应用程序在等待异步组件时渲染一些后备内容,可以让我们创建一个平滑的用户体验

语法

LOADING...

复制代码
vue3中引入异步组件的方式
const AsyncComp = defineAsyncComponent(() => import('./AsyncComp.vue'))
复制代码

vue3中引入异步组件的方式

const AsyncComp = defineAsyncComponent(() => import('./AsyncComp.vue'))复制代码

代码演示

父组件

LOADING...

复制代码
子组件
AsyncComp22

{{msg}}


复制代码

通过下图可以看到在异步组件加载出来之前,显示的是fallback中的内容

响应式数据的判断

作用

  • isRef: 检查一个值是否为一个 ref 对象
  • isReactive: 检查一个对象是否是由 reactive 创建的响应式代理
  • isReadonly: 检查一个对象是否是由 readonly 创建的只读代理
  • isProxy: 检查一个对象是否是由 reactive 或者 readonly 方法创建的代理

代码演示

setup() {
const state1 = ref(1);
console.log('isref:', isRef(state1));//isref: true
const state2 = reactive({});
console.log('isReactive:', isReactive(state2));//isReactive: true
const state3 = readonly({});
console.log('isReadonly:', isReadonly(state3));//isReadonly: true
const state4 = reactive({});
console.log('isProxy:', isProxy(state2));//isProxy: true
console.log('isProxy:', isProxy(state4));//isProxy: true
return {};
},
复制代码

其他不常用特性

还有很多很多不常用的新特性,我在日常开发中是没有用到的,很多都是用来做优化的,感兴趣的小伙伴们自行去官网查看,或者大佬们可以介绍一下应用场景。

  • shallowReactive
  • shallowRef
  • readonly
  • shallowReadonly
  • markRaw
  • customRef

语法糖

虽然Composition API用起来已经非常方便了,但是我们还是有很烦的地方,比如

  • 组件引入了还要注册
  • 属性和方法都要在setup函数中返回,有的时候仅一个return就十几行甚至几十行
  • 不想写啊怎么办

好办,Vue3官方提供了script setup语法糖

只需要在script标签中添加setup,组件只需引入不用注册,属性和方法也不用返回,setup函数也不需要,甚至export default都不用写了,不仅是数据,计算属性和方法,甚至是自定义指令也可以在我们的template中自动获得。

但是这么过瘾的语法糖,还是稍微添加了一点点心智负担,因为没有了setup函数,那么props,emit,attrs怎么获取呢,就要介绍一下新的语法了。

setup script语法糖提供了三个新的API来供我们使用:defineProps、defineEmit和useContext

  • defineProps用来接收父组件传来的值props。
  • defineEmit用来声明触发的事件表。
  • useContext用来获取组件上下文context。

代码演示

父组件


我是父组件!
@child-click="handleClick" />


复制代码
子组件
msg: {{ props.msg }}
复制代码

我们点击一下子组件

可以看到context被打印了出来,其中的attrs、emit、slots、expose属性和方法依然可以使用。props也可以输出在页面上,事件也成功派发。

其他知识点

接下来介绍一下我使用Vue3过程中遇到的问题或者小技巧,不全面,想起什么就写什么吧

script setup语法糖请注意

如果在父组件中通过ref='xxx'的方法来获取子组件实例,子组件使用了script setup语法糖,那么子组件的数据需要用expose的方式导出,否则会因为获取不到数据而报错。

代码演示

父组件


我是父组件!


复制代码
子组件先不使用语法糖


我是子组件{{msg}}


复制代码
子组件


我是子组件{{ msg }}


我是按钮1
我是按钮2
复制代码

我们分别点一下按钮1和按钮2,可以看到当我们点了按钮2的时候,控制台会发出警告,但是程序会继续执行,还没想到什么适合的应用场景,但是要知道这个知识点,小伙伴们可以在这搞事情。

跨组件通讯mitt.js

Vue2中怎么实现跨组件通讯呢,很多人第一想法就是event bus。但是Vue3移除了$on,$once,$off导致不能使用这个方法。但是Vue官方给大家推荐了mitt.js,它的原理就是event bus。

代码演示

先安装
npm i mitt -s
复制代码
然后封装一个hook
//mitt.js
import mitt from 'mitt'
const emitter = mitt();
export default emitter;
复制代码
父组件


我是父组件!


复制代码
子组件1


我是子组件1
{{msg}}


复制代码
子组件2


我是子组件2


点击修改msg
复制代码

自定义指令

先看看Vue2自定义指令的钩子

  • bind:当指令绑定在对应元素时触发。只会触发一次。
  • inserted:当对应元素被插入到 DOM 的父元素时触发。
  • update:当元素更新时,这个钩子会被触发(此时元素的后代元素还没有触发更新)。
  • componentUpdated:当整个组件(包括子组件)完成更新后,这个钩子触发。
  • unbind:当指令被从元素上移除时,这个钩子会被触发。也只触发一次。

在 Vue3 中,官方为了更有助于代码的可读性和风格统一,把自定义指令的钩子名称改的更像是组件生命周期,尽管他们是两回事

  • bindbeforeMount
  • insertedmounted
  • beforeUpdate新的钩子,会在元素自身更新前触发
  • update移除
  • componentUpdatedupdated
  • beforeUnmount新的钩子,当元素自身被卸载前触发
  • unbindunmounted

过渡动画

这个没有什么大的改动,只是修改了两个class名字,正是因为没有什么大的改动,导致我曾经在这里栽了大跟头,写完了怎么都不对,后来查官网才知道。

以下是直接引用官网的原文

  • v-enter-from:定义进入过渡的开始状态。在元素被插入之前生效,在元素被插入之后的下一帧移除。
  • v-enter-active:定义进入过渡生效时的状态。在整个进入过渡的阶段中应用,在元素被插入之前生效,在过渡/动画完成之后移除。这个类可以被用来定义进入过渡的过程时间,延迟和曲线函数。
  • v-enter-to:定义进入过渡的结束状态。在元素被插入之后下一帧生效 (与此同时 v-enter-from 被移除),在过渡/动画完成之后移除。
  • v-leave-from:定义离开过渡的开始状态。在离开过渡被触发时立刻生效,下一帧被移除。
  • v-leave-active:定义离开过渡生效时的状态。在整个离开过渡的阶段中应用,在离开过渡被触发时立刻生效,在过渡/动画完成之后移除。这个类可以被用来定义离开过渡的过程时间,延迟和曲线函数。
  • v-leave-to:离开过渡的结束状态。在离开过渡被触发之后下一帧生效 (与此同时 v-leave-from 被删除),在过渡/动画完成之后移除。

特别注意的是v-enter改成了v-enter-form,v-leave改成了v-leave-from。

特别声明:以上内容(如有图片或视频亦包括在内)为自媒体平台“网易号”用户上传并发布,本平台仅提供信息存储服务。

Notice: The content above (including the pictures and videos if any) is uploaded and posted by a user of NetEase Hao, which is a social media platform and only provides information storage services.

相关推荐
热点推荐
我公公,一个小学退休教师,每月退休金7000多,简直是人生赢家!

我公公,一个小学退休教师,每月退休金7000多,简直是人生赢家!

知秋侃史
2024-05-23 03:10:40
30张伪满洲国宣传画,鼓吹王道乐土,意图给民众洗脑,极具蛊惑性

30张伪满洲国宣传画,鼓吹王道乐土,意图给民众洗脑,极具蛊惑性

文史悦读001
2024-06-04 14:46:30
老公每次都草草了事,闺蜜得知后带我去体验刺激的……

老公每次都草草了事,闺蜜得知后带我去体验刺激的……

好笑娱乐君每一天
2024-06-04 23:15:58
正式确定!北京首钢老臣离队,被许利民放弃,告别CBA赛场

正式确定!北京首钢老臣离队,被许利民放弃,告别CBA赛场

体坛瞎白话
2024-06-05 08:56:52
冒天下之大不韪,我也来说说我认为的台州横渡事故原因

冒天下之大不韪,我也来说说我认为的台州横渡事故原因

大宗看萌宠
2024-06-05 02:15:11
河南不少地方只拖欠教师工资和津补贴而从不拖欠行政公职人员的?

河南不少地方只拖欠教师工资和津补贴而从不拖欠行政公职人员的?

郭爱华追问教育
2024-06-05 08:57:59
恭喜火箭队!交易谈判进行中,斯通经理双线作战,猛追明星小前锋

恭喜火箭队!交易谈判进行中,斯通经理双线作战,猛追明星小前锋

熊哥爱篮球
2024-06-05 11:38:11
比恒大还大的雷区出现了,价值高达10万亿,这回许家印可不孤单了

比恒大还大的雷区出现了,价值高达10万亿,这回许家印可不孤单了

简读视觉
2024-04-13 08:40:03
纪实:马未都:丢尽了中国人的脸,他还觉得自己是国民英雄!

纪实:马未都:丢尽了中国人的脸,他还觉得自己是国民英雄!

星辰故事屋
2024-06-03 19:09:34
北京投放共享电单车,扫码即可使用!一边夜查,一边投放,两手抓

北京投放共享电单车,扫码即可使用!一边夜查,一边投放,两手抓

小李子体育
2024-06-05 07:40:39
24岁抗癌网红“桐妈”去世!死前只能躺地上,疑流产后不注意导致

24岁抗癌网红“桐妈”去世!死前只能躺地上,疑流产后不注意导致

裕丰娱间说
2024-06-04 08:29:09
有网友已经拿铁头涂鸦一事,向平台申请解封铁头账号

有网友已经拿铁头涂鸦一事,向平台申请解封铁头账号

映射生活的身影
2024-06-04 17:15:00
女子在深圳买套房,遗忘28年后想起,房子已被人住了20年

女子在深圳买套房,遗忘28年后想起,房子已被人住了20年

一度历史观
2024-05-25 12:54:45
药明康德联合创始人赵宁病逝,曾连续多年登胡润全球富豪榜

药明康德联合创始人赵宁病逝,曾连续多年登胡润全球富豪榜

仰望沧海
2024-06-03 22:01:04
NASA局长承认:重返月球困难重重!55年前能做到,为何现在不行?

NASA局长承认:重返月球困难重重!55年前能做到,为何现在不行?

奇点使者
2024-06-02 17:50:02
铁头已归国,透露对日本干了两件大事,如今第二件事揭晓争议不小

铁头已归国,透露对日本干了两件大事,如今第二件事揭晓争议不小

辣条小剧场
2024-06-04 20:22:24
啤酒销量惨遭“滑铁卢”,人们为啥不爱喝了?3个原因残酷又现实

啤酒销量惨遭“滑铁卢”,人们为啥不爱喝了?3个原因残酷又现实

西山来客
2024-06-05 08:43:45
笑死了!湾湾网友“虎狼之词”要住北京平房?大陆:哪个爹想的?

笑死了!湾湾网友“虎狼之词”要住北京平房?大陆:哪个爹想的?

暖心的小屋
2024-06-03 16:39:10
男子被怀孕女同事蹭车,2个月后拒绝载她,不料第二天警察找上门

男子被怀孕女同事蹭车,2个月后拒绝载她,不料第二天警察找上门

纸鸢奇谭
2024-06-03 22:10:06
中年失业人数哪有那么夸张?网友:刚问了我同事,他们都说有工作

中年失业人数哪有那么夸张?网友:刚问了我同事,他们都说有工作

暖心的小屋
2024-06-04 20:22:31
2024-06-05 11:56:49
IT爱好者小尚
IT爱好者小尚
分享IT教育类信息
630文章数 55关注度
往期回顾 全部

科技要闻

马斯克把特斯拉5亿美元AI芯片提前调拨给X

头条要闻

土耳其外交部长在北京表态:土耳其希望加入金砖国家

头条要闻

土耳其外交部长在北京表态:土耳其希望加入金砖国家

体育要闻

赴美试训的崔永熙,表现究竟怎么样?

娱乐要闻

《青春有你》胡文煊被曝孕期出轨

财经要闻

欧盟推迟对华行动,如何理解?

汽车要闻

又一个水桶车 试驾新“卷王”极狐阿尔法S5

态度原创

房产
艺术
数码
家居
公开课

房产要闻

79.17亿!海开拿下永丰南地块 据说产品90平起

艺术要闻

穿越时空的艺术:《马可·波罗》AI沉浸影片探索人类文明

数码要闻

“女武神”携手“白银”,映泰展出两款英特尔 Z890 主板

家居要闻

温室余闲 平仄之间雅趣浓

公开课

近视只是视力差?小心并发症

无障碍浏览 进入关怀版