前言
hello world欢迎来到前端的新世界
😜当前文章系列专栏:vue.js
🐱👓博主在前端领域还有很多知识和技术需要掌握,正在不断努力填补技术短板。(如果出现错误,感谢大家指出)🌹
💖感谢大家支持!您的观看就是作者创作的动力
vue2和vue3的区别
Fragments
Vue3支持碎片(Fragments),在一个组件中有多个根节点
例如:
vue3
<template> <div class='form-element'> </div> <h2> {{ title }} </h2> </template>
vue2
<template> <div class='form-element'> <h2> {{ title }} </h2> </div> </template>
Composition API
vue2与Vue3 最大的区别 — Vue2使用选项类型API(Options API)对比Vue3合成型API(Composition API)
旧的选项型API在代码里分割了不同的属性: data,computed属性,methods,等等。新的合成型API能让我们用方法(function)来分割,相比于旧的API使用属性来分组,这样代码会更加简便和整洁。
vue2
export default { props: { title: String }, data () { return { username: '', password: '' } }, methods: { login () { // 登陆方法 } }, components:{ "buttonComponent":btnComponent }, computed:{ fullName(){ return this.firstName+" "+this.lastName; } } }
vue3
export default { props: { title: String }, setup () { const state = reactive({ //数据 username: '', password: '', lowerCaseUsername: computed(() => state.username.toLowerCase()) //计算属性 }) //方法 const login = () => { // 登陆方法 } return { login, state } } }
解决了什么问题
- 逻辑复用困难: 在 Vue 2 中,当多个组件需要共享相似的逻辑时,使用混入(mixins)或者高阶组件(higher-order components)来实现逻辑复用可能会导致代码结构变得混乱和难以维护。Composition API 提供了更灵活的方式来组织和复用逻辑,使得共享逻辑可以更加清晰地封装和抽象。
- 代码组织混乱: 随着组件功能的增长,Options API 中的生命周期钩子和选项可能会变得过于臃肿,导致组件代码难以理解和维护。Composition API 允许按照逻辑相关性将代码组织到一起,使得组件逻辑更加清晰可见。
- 类型推断不足: 在 Vue 2 中,使用 Options API 编写的组件在 TypeScript 中的类型推断和类型校验可能不够完善,因为逻辑是分散在不同的选项和生命周期钩子中的。Composition API 提供了更好的 TypeScript 支持,使得类型推断更准确,从而提高了代码的健壮性和可维护性。
- 代码耦合度高: 在 Options API 中,不同选项之间存在较高的耦合度,这可能导致组件难以被理解、测试和重构。Composition API 允许将相关代码聚集在一起,并且可以更容易地进行切割和重构,从而降低了代码的耦合度。
建立数据 data
Vue2 - 这里把数据放入data属性中
export default { props: { title: String }, data () { return { username: '', password: '' } } }
在Vue3.0,我们就需要使用一个新的setup方法,此方法在组件初始化构造的时候触发。
使用以下三步来建立响应式性数据:
从vue引入reactive
从vue引入ref
使用reactive()方法来声名我们的数据为响应性数据
使用setup()方法来返回我们的响应性数据,从而我们的template可以获取这些响应性数据
import { reactive,ref } from 'vue' export default { props: { title: String }, setup () { const adminName = ref("张三") const state = reactive({ username: '', password: '' }) return { state,adminName } } }
然后通过template使用,可以通过state.username和state.password获得数据的值。
<template> <div> <h2> 管理员名称{{ adminName }} </h2> <h2> 用户名称{{ state.username}} </h2> </div> </template>
生命周期钩子
vue2 | vue3 |
beforeCreate | setup |
created | setup |
beforeMount | onBeforeMount |
mounted | onMounted |
beforeUpdate | onBeforeUpdate |
activeted | onActiveted |
deactiveted | onDeactiveted |
beforeDestory | onBeforeUnmount |
destoryed | onUnmounted |
setup() :开始创建组件之前,在beforeCreate和created之前执行。创建的是data和method
onBeforeMount() : 组件挂载到节点上之前执行的函数。
onMounted() : 组件挂载完成后执行的函数。
onBeforeUpdate(): 组件更新之前执行的函数。
onUpdated(): 组件更新完成之后执行的函数。
onBeforeUnmount(): 组件卸载之前执行的函数。
onUnmounted(): 组件卸载完成后执行的函数
若组件被< keep-alive>包含,则多出下面两个钩子函数。
- onActivated(): 被包含在中的组件,会多出两个生命周期钩子函数。被激活时执行 。
- onDeactivated(): 比如从 A组件,切换到 B 组件,A 组件消失时执行。
vue3 Teleport瞬移组件
Teleport一般被翻译成瞬间移动组件,实际上是不好理解的.我把他理解成"独立组件",
他可以那你写的组件挂载到任何你想挂载的DOM上,所以是很自由很独立的
以一个例子来看:编写一个弹窗组件
<template> <teleport to="#modal"> <div id="center" v-if="isOpen"> <h2><slot>this is a modal</slot></h2> <button @click="buttonClick">Close</button> </div> </teleport> </template> <script lang="ts"> export default { props: { isOpen: Boolean, }, emits: { 'close-modal': null }, setup(props, context) { const buttonClick = () => { context.emit('close-modal') } return { buttonClick } } } </script> <style> #center { width: 200px; height: 200px; border: 2px solid black; background: white; position: fixed; left: 50%; top: 50%; margin-left: -100px; margin-top: -100px; } </style>
在app.vue中使用的时候跟普通组件调用是一样的
<template> <div id="app"> <img alt="Vue logo" src="./assets/logo.png"> <HelloWorld msg="Welcome to Your Vue.js App"/> <HooksDemo></HooksDemo> <button @click="openModal">Open Modal</button><br/> <modal :isOpen="modalIsOpen" @close-modal="onModalClose"> My Modal !!!!</modal> </div> </template> <script> import HelloWorld from './components/HelloWorld.vue' import HooksDemo from './components/HooksDemo.vue' import Modal from './components/Modal.vue' import{ref} from 'vue' export default { name: 'App', components: { HelloWorld, HooksDemo, Modal }, setup() { const modalIsOpen = ref(false) const openModal = () => { modalIsOpen.value = true } const onModalClose = () => { modalIsOpen.value = false } return { modalIsOpen, openModal, onModalClose } } } </script> <style> #app { font-family: Avenir, Helvetica, Arial, sans-serif; -webkit-font-smoothing: antialiased; -moz-osx-font-smoothing: grayscale; text-align: center; color: #2c3e50; margin-top: 60px; } </style>
要是在app.vue文件中使用的时候,modal是在app的 DOM节点之下的,父节点的dom结构和css都会给modal产生影响
于是产生的问题
- modal被包裹在其它组件之中,容易被干扰
- 样式也在其它组件中,容易变得非常混乱
Teleport 可以把modal组件渲染到任意你想渲染的外部Dom上,不必嵌套在#app中,这样就可以互不干扰了,可以把Teleport看成一个传送门,把你的组件传送到任何地方
使用的时候 to属性可以确定想要挂载的DOM节点下面
<template> <teleport to="#modal"> <div id="center"> <h2>柏特better</h2> </div> </teleport> </template>
在public文件夹下的index.html中增加一个节点
<!DOCTYPE html> <html lang="en"> <head> <meta charset="utf-8"> <meta http-equiv="X-UA-Compatible" content="IE=edge"> <meta name="viewport" content="width=device-width,initial-scale=1.0"> <link rel="icon" href="<%= BASE_URL %>favicon.ico"> <title><%= htmlWebpackPlugin.options.title %></title> </head> <body> <noscript> <strong>We're sorry but <%= htmlWebpackPlugin.options.title %> doesn't work properly without JavaScript enabled. Please enable it to continue.</strong> </noscript> <div id="app"></div> <div id="modal"></div> <!-- built files will be auto injected --> </body> </html>
组件通信的不同
Props 和 Emit(Vue 2) vs. Props 和 Setup(Vue 3):
在 Vue 2 中,父子组件之间的通信通常通过 props 和 emit 来实现。父组件通过 props 向子组件传递数据,子组件可以通过触发事件(emit)将数据传递回父组件。
而在 Vue 3 中,引入了 Composition API,可以使用 setup 函数来直接访问 props,并且可以使用响应式的 ref、reactive 等函数创建响应式数据,从而实现更加灵活和直观的父子组件通信。
Provide 和 Inject(Vue 3):
在 Vue 3 中,提供了 provide 和 inject 的方式来实现跨层级组件之间的通信。父组件可以使用 provide 提供数据,子组件可以使用 inject 来接收这些数据。这种方式可以实现更灵活的跨组件通信,而在 Vue 2 中并没有类似的机制。
Teleport(Vue 3):
Vue 3 中新增了 Teleport 组件,可以将子组件渲染到任意的 DOM 节点上,这种方式也可以被看作是一种组件通信的方式,特别适合于处理弹出窗口等场景。
事件总线或全局状态管理:
在 Vue 中,无论是 Vue 2 还是 Vue 3,都可以使用事件总线(EventBus)或者全局状态管理工具(如 Vuex)来实现任意两个组件之间的通信。
后言
创作不易,要是本文章对广大读者有那么一点点帮助 不妨三连支持一下,您的鼓励就是博主创作的动力