先推荐两个vscode插件
Volar
首先推荐Volar
,使用vscode
开发Vue
项目的小伙伴肯定都认识Vetur
这个神级插件,有了它可以让我们得开发如鱼得水。那么Volar
可以理解为Vue3
版本的Vetur
,代码高亮,语法提示,基本上Vetur
有的它都有。
特色功能
当然作为新的插件出山,肯定有它独有的功能。
多个根节点编辑器不会报错
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
以上
使用 Vite 创建
都说Vue3.0
和Vite2
更配,各种优化,各种快,但都不属于本文的内容,本文的目的我们只需要知道它特别好用,怎么用就行了。我这里是多选择了TS
,每行都有注释,一目了然。
创建完以后我们先来看看入口文件main.ts
然后看看根组件app.vue
Composition API
接下来到了重头戏,Vue3
的招牌特性,Composition API
关于Composition API
这里有大佬做的动画演示,极力推荐。
Composition API
可以更方便的抽取共通逻辑,但是不要过于在意逻辑代码复用,以功能提取代码也是一种思路。
顺便提一句,Vue3
兼容大部分Vue2
语法,所以在Vue3
中书写Vue2
语法是没有问题的(废除的除外),但是既然我们已经升级Vue3
了,不建议混合使用,除非一些大型特殊项目需要兼容两个版本。
setup
setup
是组合Composition API
中的入口函数,也是第一个要使用的函数。
setup
只在初始化时执行一次,所有的Composition API
函数都在此使用。
可以通过console.log
看到setup
是在beforeCreate
生命周期之前执行的(只执行一次)
此可以推断出setup
执行的时候,组件对象还没有创建,组件实例对象this
还不可用,此时this
是undefined
, 不能通过this
来访问data/computed/methods/props
。
返回对象中的属性会与data
函数返回对象的属性合并成为组件对象的属性,返回对象中的方法会与methods
中的方法合并成功组件对象的方法,如果有重名, setup
优先。因为在setup
中this
不可用,methods
中可以访问setup
提供的属性和方法, 但在setup
方法中不能访问data
和methods
里的内容,所以还是不建议混合使用。
setup
函数如果返回对象, 对象中的 属性 或 方法 , 模板 中可以直接使用
注意: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
//父组件
<template>
<child :msg="msg" msg2='哈哈哈' />
</template>
<script lang='ts'>
import { defineComponent, ref } from 'vue';
// 引入子组件
import Child from './components/Child.vue';
export default defineComponent({
name: 'App',
components: {
Child,
},
setup() {
const msg = ref('hello,vue3');
return {
msg,
};
},
});
</script>
//子组件
<template>
<h2>子组件</h2>
<h3>msg:{{ msg }}</h3>
</template>
<script lang='ts'>
import { defineComponent } from 'vue';
export default defineComponent({
name: 'Child',
props: ['msg'],
setup(props, {attrs, slots, emit}) {
console.log('props:', props);//msg: "hello,vue3"
console.log('attrs:', attrs);//msg2: "哈哈哈"
return {};
},
});
</script>
演示emit
//父组件
<template>
<child @show="show" />
</template>
<script lang='ts'>
setup() {
const show = () => {
console.log('name:', 'hzw');
};
return {
show,
};
},
</script>
//子组件
<template>
<button @click='emitFn'>事件分发</button>
</template>
<script lang='ts'>
import { defineComponent } from 'vue';
export default defineComponent({
name: 'Child',
setup(props, { emit }) {
const emitFn = () => {
emit('show');
};
return {
emitFn,
};
},
});
</script>
复制代码
ref
作用
定义一个响应式的数据(一般用来定义一个基本类型的响应式数据Undefined
、Null
、Boolean
、Number
和String
)
注意:script
中操作数据需要使用xxx.value
的形式,而模板中不需要添加.value
用一个例子来演示:实现一个按钮,点击可以增加数字
在Vue2中
在Vue3中
在Vue2
中我们通过this.$refs
来获取dom
节点,Vue3
中我们通过ref
来获取节点
首先需要在标签上添加ref='xxx'
,然后再setup
中定义一个初始值为null
的ref
类型,名字要和标签的ref
属性一致
注意:一定要在setup
的return
中返回,不然会报错。
还是用一个例子来演示:让输入框自动获取焦点
reactive
语法
作用
定义多个数据的响应式,接收一个普通对象然后返回该普通对象的响应式代理器对象(Proxy)
,响应式转换是“深层的”:会影响对象内部所有嵌套的属性,所有的数据都是响应式的。
代码演示
computed函数:
与Vue2
中的computed
配置功能一致,返回的是一个ref
类型的对象
计算属性的函数中如果只传入一个回调函数 表示的是get
操作