赞
踩
Composition API:这是一个新的编写组件的方式,可以让我们更好地复用和组织代码,避免了mixins和scoped slots的一些缺陷。
**SFC Composition API Syntax Sugar (script setup) **:这是一个简化了Composition API的语法糖,可以让我们在单文件组件中更方便地使用Composition API。
Teleport:这是一个新的内置组件,可以让我们将子组件渲染到任意位置,而不受父组件的影响,可以让我们更容易地处理一些弹窗、模态框、通知等场景。
Fragments:这是一个新的特性,可以让我们在组件中返回多个根节点,而不需要包裹在一个额外的元素中,可以让我们的模板更加灵活和自由。
Filters:这是一个被移除的特性,因为它与JavaScript本身的管道运算符有冲突,而且它也不是响应式的,我们可以用其他方式来实现过滤器的功能,比如计算属性或者方法。
Experimental Suspense feature:这是一个实验性的特性,可以让我们更好地处理异步组件的加载状态。
Experimental state-driven CSS variables (v-bind in ):这是一个实验性的特性,可以让我们在单文件组件中使用v-bind来绑定CSS变量,从而实现动态样式。
Single file component changes:这是一个改变了单文件组件中 (style scoped) 行为的特性,可以让我们在 (style scoped) 中包含全局规则或者只针对插槽内容的规则。
Multiple v-models:这是一个新的特性,可以让我们在同一个组件上使用多个v-model来绑定多个属性。
Lifecycle naming changes:这是一个改变了部分生命周期钩子名称的特性,以便于与Composition API保持一致。
<template> <div> <h1>{{ state.title }}</h1> <p>{{ state.count }}</p> <button @click="increment">+</button> <button @click="decrement">-</button> </div> </template> <script> import { reactive, computed } from "vue"; export default { setup() { // 创建一个响应式对象 const state = reactive({ title: "Hello Vue 3", count: 0, }); // 创建一个计算属性 const doubleCount = computed(() => state.count * 2); // 创建一个方法 const increment = () => { state.count++; }; const decrement = () => { state.count--; }; // 返回需要在模板中使用的数据和方法 return { state, doubleCount, increment, decrement, }; }, }; </script>
这个示例代码展示了如何使用Composition API来编写一个简单的计数器组件。我们可以看到,我们在setup函数中使用reactive函数来创建一个响应式对象state,它包含了我们需要的数据title和count。然后我们使用computed函数来创建一个计算属性doubleCount,它根据state.count的变化而变化。接着我们定义了两个方法increment和decrement,它们分别用于增加和减少state.count的值。最后我们将需要在模板中使用的数据和方法返回,这样我们就可以在模板中绑定它们。这样我们就实现了一个简单的计数器组件,而且我们可以看到,我们的代码是按照逻辑关注点来组织的,而不是按照组件选项来组织的,这样可以让我们更好地复用和组织代码。
<template> <div> <h1>{{ title }}</h1> <p>{{ count }}</p> <button @click="increment">+</button> <button @click="decrement">-</button> </div> </template> <script setup> import { ref } from "vue"; // 创建一个响应式引用 const title = ref("Hello Vue 3"); // 创建一个响应式引用 const count = ref(0); // 创建一个方法 const increment = () => { count.value++; }; // 创建一个方法 const decrement = () => { count.value--; }; </script>
这个示例代码展示了如何使用SFC Composition API Syntax Sugar来编写一个简单的计数器组件。我们可以看到,我们在
<template> <div class="container"> <h1>Teleport Demo</h1> <button @click="showModal = true">Show Modal</button> <!-- 使用teleport组件将modal渲染到body元素下 --> <teleport to="body"> <!-- 使用v-if控制modal的显示 --> <div v-if="showModal" class="modal"> <div class="modal-content"> <h2>Modal Title</h2> <p>Modal Content</p> <button @click="showModal = false">Close Modal</button> </div> </div> </teleport> </div> </template> <script setup> import { ref } from "vue"; // 创建一个响应式引用 const showModal = ref(false); </script> <style scoped> .container { margin: 20px; } .modal { position: fixed; top: 0; left: 0; width: 100%; height: 100%; background-color: rgba(0, 0, 0, 0.5); } .modal-content { position: absolute; top: 50%; left: 50%; transform: translate(-50%, -50%); width: 300px; height: 200px; background-color: white; border-radius: 10px; } </style>
这个示例代码展示了如何使用teleport组件来实现一个简单的模态框组件。我们可以看到,我们在模板中使用teleport组件将modal渲染到body元素下,这样就可以避免modal被父组件的样式或者其他元素影响。然后我们使用v-if指令来控制modal的显示,根据showModal的值来决定是否渲染modal。最后我们在modal-content中定义了模态框的标题、内容和关闭按钮,并且给关闭按钮绑定了一个点击事件,用于将showModal设置为false。这样我们就实现了一个简单的模态框组件,而且我们可以看到,teleport组件让我们更容易地处理一些弹窗、模态框、通知等场景
<template>
<!-- 返回多个根节点 -->
<h1>Hello Vue 3</h1>
<p>This is a fragment component.</p>
</template>
<script setup></script>
<style scoped></style>
这个示例代码展示了如何使用fragments特性来返回多个根节点。我们可以看到,在模板中,我们直接返回了两个元素:h1和p,并没有将它们包裹在一个额外的元素中。这样就可以让我们在组件中返回多个根节点,而不需要添加多余的标签或者数组。这样可以让我们的模板更加灵活和自由。
<template> <!-- 在Vue2中使用过滤器 --> <h1>{{ title | capitalize }}</h1> <!-- 在Vue3中使用计算属性或者方法 --> <h1>{{ capitalizedTitle }}</h1> <!-- 或者 --> <h1>{{ capitalize(title) }}</h1> </template> <script setup> import { ref, computed } from "vue"; // 创建一个响应式引用 const title = ref("hello vue"); // 创建一个计算属性 const capitalizedTitle = computed(() => { return title.value.charAt(0).toUpperCase() + title.value.slice(1); }); // 创建一个方法 const capitalize = (str) => { return str.charAt(0).toUpperCase() + str.slice(1); }; </script> <style scoped></style>
这个示例代码展示了如何在Vue3中替代过滤器的功能。我们可以看到,在Vue2中,我们可以使用过滤器来对数据进行一些格式化或者转换,比如将title转换为首字母大写。但是在Vue3中,过滤器被移除了,因为它与JavaScript本身的管道运算符有冲突,而且它也不是响应式的。所以在Vue3中,我们可以使用计算属性或者方法来实现过滤器的功能,比如创建一个capitalizedTitle计算属性或者capitalize方法来将title转换为首字母大写。这样就可以让我们用其他方式来实现过滤器的功能,比如计算属性或者方法。
<template> <!-- 使用suspense组件包裹异步组件 --> <suspense :timeout="3000"> <!-- 定义异步加载成功时显示的内容 --> <template #default> <hello-world /> </template> <!-- 定义异步加载失败时显示的内容 --> <template #fallback> <p>Loading...</p> </template> <!-- 定义异步加载超时时显示的内容 --> <template #timeout> <p>Timeout!</p> </template> </suspense> </template> <script setup> import { defineAsyncComponent } from "vue"; // 定义一个异步组件 const HelloWorld = defineAsyncComponent(() => { return new Promise((resolve) => { setTimeout(() => { resolve(import("./HelloWorld.vue")); }, 2000); }); }); </script> <style scoped></style>
这个示例代码展示了如何使用suspense组件来处理异步组件的加载状态。我们可以看到,我们在模板中使用suspense组件来包裹一个异步组件HelloWorld,它是通过defineAsyncComponent函数来定义的,它返回一个Promise,用于延迟加载HelloWorld.vue文件。然后我们在suspense组件中定义了三个插槽:default、fallback和timeout,分别用于定义异步加载成功、失败和超时时显示的内容。我们还给suspense组件绑定了一个timeout属性,用于设置异步加载的超时时间。这样就可以让我们更好地处理异步组件的加载状态,而且我们可以自定义不同状态下显示的内容。
<template> <div class="container"> <h1>Hello Vue 3</h1> <button @click="toggleTheme">Toggle Theme</button> </div> </template> <script setup> import { ref } from "vue"; // 创建一个响应式引用 const theme = ref("light"); // 创建一个方法 const toggleTheme = () => { theme.value = theme.value === "light" ? "dark" : "light"; }; </script> <style scoped> .container { /* 使用v-bind绑定CSS变量 */ v-bind: { "--bg-color": theme === "light" ? "white" : "black", "--text-color": theme === "light" ? "black" : "white", } } h1 { /* 使用CSS变量设置样式 */ color: var(--text-color); } button { /* 使用CSS变量设置样式 */ background-color: var(--bg-color); color: var(--text-color); } </style>
这个示例代码展示了如何使用v-bind在
<template> <div class="container"> <h1>Hello Vue 3</h1> <slot></slot> </div> </template> <script setup></script> <style scoped> .container { border: 1px solid black; } /* 使用::v-deep选择器来定义全局规则 */ ::v-deep p { color: red; } /* 使用::v-slotted选择器来定义只针对插槽内容的规则 */ ::v-slotted span { font-weight: bold; } </style>
这个示例代码展示了如何在
<template> <div class="container"> <h1>Hello Vue 3</h1> <custom-input v-model:title="title" v-model:content="content" /> <p>Title: {{ title }}</p> <p>Content: {{ content }}</p> </div> </template> <script setup> import { ref } from "vue"; import CustomInput from "./CustomInput.vue"; // 创建两个响应式引用 const title = ref(""); const content = ref(""); </script> <style scoped></style>
<template> <div class="custom-input"> <label for="title">Title:</label> <input id="title" type="text" v-model="title" /> <label for="content">Content:</label> <textarea id="content" v-model="content"></textarea> </div> </template> <script setup> import { computed } from "vue"; // 获取父组件传入的props const props = defineProps({ title: String, content: String, }); // 获取父组件传入的emit函数 const emit = defineEmits(["update:title", "update:content"]); // 创建两个计算属性 const title = computed({ get: () => props.title, set: (value) => emit("update:title", value), }); const content = computed({ get: () => props.content, set: (value) => emit("update:content", value), }); </script> <style scoped></style>
这个示例代码展示了如何在同一个组件上使用多个v-model来绑定多个属性。我们可以看到,在父组件中,我们引入了一个自定义组件CustomInput,并且给它绑定了两个v-model:title和content,分别对应两个响应式引用title和content。然后我们在模板中显示这两个数据。在子组件中,我们定义了两个props:title和content,并且定义了两个emit函数:update:title和update:content,分别用于更新父组件中的数据。然后我们创建了两个计算属性title和content,并且将它们与props和emit函数关联起来。最后我们在模板中使用v-model指令将这两个计算属性绑定到input和textarea元素上。这样就可以让我们在同一个组件上使用多个v-model来绑定多个属性。
<template> <h1>Hello Vue 3</h1> </template> <script setup> import { onBeforeMount, onMounted, onBeforeUpdate, onUpdated, onBeforeUnmount, onUnmounted } from "vue"; // 在Vue2中使用beforeCreate和created钩子,在Vue3中使用setup函数替代 // 在Vue2中使用beforeMount钩子,在Vue3中使用onBeforeMount函数替代 onBeforeMount(() => { console.log("before mount"); }); // 在Vue2中使用mounted钩子,在Vue3中使用onMounted函数替代 onMounted(() => { console.log("mounted"); }); // 在Vue2中使用beforeUpdate钩子,在Vue3中使用onBeforeUpdate函数替代 onBeforeUpdate(() => { console.log("before update"); }); // 在Vue2中使用updated钩子,在Vue3中使用onUpdated函数替代 onUpdated(() => { console.log("updated"); }); // 在Vue2中使用beforeDestroy钩子,在Vue3中使用onBeforeUnmount函数替代 onBeforeUnmount(() => { console.log("before unmount"); }); // 在Vue2中使用destroyed钩子,在Vue3中使用onUnmounted函数替代 onUnmounted(() => { console.log("unmounted"); }); </script> <style scoped></style>
这个示例代码展示了如何在Vue3中使用新的生命周期函数。我们可以看到,我们从vue模块中导入了一些以on开头的函数,它们分别对应了Vue2中的一些生命周期钩子,只是名称有所变化,以便于与Composition API保持一致。然后我们在setup函数中调用这些函数,并传入一个回调函数,用于执行一些逻辑。这样就可以让我们更清楚地区分不同类型的生命周期函数。
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。