VueJS教程

介绍

软件版本

软件名称 版本
NodeJS v18.16.0
NPM 9.5.1
Vue 3.3.2
Vue Router 4.2.0
Vuex 4.1.0

npm初始化项目

npm常用命令

当然,请看下面的表格,这里是用 Markdown 表格格式整理的信息:

命令 描述
npm config set registry xxx 将 npm 仓库设置为本地仓库,地址为 xxx
npm root -g 查看全局安装目录
npm config set prefix "d:\npm" 将全局安装目录设置为 d:\npm
npm list -g 查看全局安装的包列表
npm install <module_name> --save/-S 安装一个模块作为生产环境依赖
npm view <module_name> version 查看远程模块的最新版本
npm view <module_name> versions 查看远程模块的所有版本
npm uninstall <module_name> 卸载局部模块
npm uninstall <module_name> -g 卸载全局模块

这些命令可以帮助管理 npm 包,从设置仓库到安装、查看和卸载模块(无论是在本地还是全局),同时区分开发和生产依赖。

npm初始化VueJS项目

创建一个项目目录比如:vuejs

npm install -g @vue/cli

查看npm安装全局路径

npm -g root

添加环境变量

#vi ~/.zshrc
export VUE_HOME=/Users/allen/workspace/node_modules/lib/node_modules/@vue/cli
PATH=$PATH:$VUE_HOME/bin
#source ~/.zshrc

创建项目

vue.js create blog-vue

执行命令之后在src目录下会生成一个vuejs的项目目录

├── README.md
├── babel.config.js
├── jsconfig.json
├── package-lock.json
├── package.json
├── public
│   ├── favicon.ico
│   └── index.html
├── src
│   ├── App.vue
│   ├── assets
│   │   └── logo.png
│   ├── components
│   │   └── HelloWorld.vue
│   ├── main.js
│   ├── router
│   │   └── index.js
│   ├── store
│   │   └── index.js
│   └── views
│   ├── AboutView.vue
│   └── HomeView.vue
└── vue.config.js

在src/main.js中创建应用APP,并且挂载

import { createApp } from 'vue'
import App from './App.vue'
import router from './router'

const app = createApp(App)

app.use(router)

app.mount('#app')

在App.vue中设置变量msg

<script setup>
const msg = "www.acaiblog.top"
</script>
<template>
<div>
msg: {{ msg }}
</div>
</template>

计算属性compute

在Vue.js 3中,计算属性(Computed Properties)是用于根据已有的响应式数据计算并返回一个新的衍生值的函数。计算属性可以在模板中像普通属性一样使用,但实际上是基于依赖进行缓存和计算的。

计算属性的特点

响应式更新:当计算属性依赖的响应式数据发生变化时,计算属性会自动重新计算,并且会在需要时触发依赖该计算属性的相关更新。
缓存机制:计算属性会根据其依赖的响应式数据进行缓存。只有当依赖的数据发生变化时,计算属性才会重新计算。在后续的访问中,如果依赖的数据没有变化,计算属性会直接返回缓存的值,而不会重新计算。

计算属性使用案例

<script setup>
import { ref, computed } from "vue";
const value = ref(5)
const computeValue = computed(() => {
return value.value * 2
})
</script>
<template>
<div>
原始值:{{ value }}
计算属性值:{{ computeValue }}
</div>
</template>

监听器watch

监听器(Watcher)是一种机制,用于监视数据的变化并执行相应的操作。它可以在数据发生改变时,自动触发一些逻辑,例如更新视图、调用函数等。

Vue.js 3中的监听器有两种类型

响应式监听器(Reactive Watcher):它是最常用的监听器类型,用于监视响应式数据的变化。当响应式数据发生改变时,Vue会自动检测到这些变化并执行绑定的监听器函数。
手动监听器(Manual Watcher):它是一种更底层的监听器类型,可以手动创建和管理。手动监听器不依赖于响应式数据,而是通过显式地指定要监听的数据源,并提供一个回调函数来处理数据变化。

监听器案例:点击按钮count值+1

<script>
import { ref, watch } from "vue";
export default {
setup() {
const count = ref(0)
watch(count, (newValue, oldValue) => {
console.log("Count changed:", newValue, oldValue)
})
const increment = () => {
count.value++
}
return {
count,
increment
}
}
}

</script>
<template>
<div>
count: {{ count }}
<button @click="increment">increment</button>
</div>
</template>

指令

内置指令

指令 描述 使用场景
v-if 根据条件条件性地渲染元素 条件性渲染,根据条件决定是否显示元素
v-show 根据条件切换元素的显示和隐藏 根据条件切换元素的可见性
v-for 循环渲染元素 渲染列表、根据数组或对象创建重复的元素
v-bind 动态地绑定属性或组件的属性 动态绑定属性、根据数据动态设置元素属性
v-on 监听事件并触发对应的方法 响应用户交互事件、绑定事件处理函数
v-model 在表单元素和应用状态之间双向绑定数据 实现表单元素的双向数据绑定
v-text 将元素的文本内容设置为表达式的值 设置元素的文本内容
v-html 将元素的 HTML 内容设置为表达式的值 设置元素的 HTML 内容
v-cloak 在渲染完成前隐藏绑定的元素 隐藏元素,直到 Vue 实例完成编译
v-pre 跳过元素和子元素的编译过程 阻止元素和子元素的编译过程
v-once 一次性地渲染元素,不再响应数据的变化 只渲染元素一次,不再跟踪数据的变化

v-bind属性绑定

class绑定

语法

v-bind:class='表达式'或:class='表达式'
class的表达式可以用以下三种方式:

类型 示例
字符串 :class="activeClass"
对象 :class="{active: isActive,error:hasError}"
数组 :class="['active','error']"

示例代码

解析:
:class="activeClass":将 activeClass 的值作为类名绑定到元素的 class 属性上。
:class="{ active: isActive, error: hasError }":根据 isActive 和 hasError 的值来动态绑定类名。如果 isActive 为 true,则添加 active 类名;如果 hasError 为 true,则添加 error 类名。
:class="['active', 'error']":通过数组的方式来绑定类名。元素将同时应用 active 和 error 类名。

<template>
<div>
<p :class="activeClass">这是一个使用 v-bind 的示例</p>
<p :class="{ active: isActive, error: hasError }">这是另一个使用 v-bind 的示例</p>
<p :class="['active', 'error']">这是第三个使用 v-bind 的示例</p>
</div>
</template>

<script>
import { ref } from 'vue';

export default {
setup() {
const activeClass = ref('active');
const isActive = ref(true);
const hasError = ref(false);

return {
activeClass,
isActive,
hasError
};
}
};
</script>
<style scoped>
.active{
color: green;
}
.error{
color: red;
}
.delete{
background-color: orange;
}
</style>

style绑定

语法

v-bind:style='表达式'或:style='表达式'
style的表达式一般为对象::style="{color:activeColor,fontSize:fontSize+'px'}"

使用案例

<template>
<div id="app">
<p :style="{ color: fontColor, fontSize: fontSize + 'px' }">v-bind动态绑定样式style</p>
</div>
</template>

<script>
import { ref } from 'vue';

export default {
setup() {
const fontColor = ref('red');
const fontSize = ref(100);

return {
fontColor,
fontSize
};
}
};
</script>

v-if条件渲染

v-ifv-show的区别

v-ifv-show 是 Vue.js 中用于条件性渲染元素的指令,但它们在实现方式和使用场景上有一些区别:

v-if:根据条件条件性地渲染元素。当条件为真时,元素会被渲染到 DOM 中;当条件为假时,元素会被完全从 DOM 中移除。每当条件发生变化时,Vue.js 会对元素进行创建或销毁操作。因为 v-if 控制元素的存在与否,所以它适用于在不同条件下切换大块的内容。

<div v-if="condition">这个元素会根据条件 condition 的值进行条件性渲染</div>

v-show:根据条件切换元素的显示和隐藏。当条件为真时,元素会显示在 DOM 中,并使用 CSS 的 display: none 隐藏;当条件为假时,元素仍然存在于 DOM 中,但是不可见。v-show 在切换显示和隐藏时只是修改了元素的样式,而不会进行频繁的创建和销毁操作。因此,适用于需要频繁切换显示和隐藏的元素。

<div v-show="condition">这个元素会根据条件 condition 的值进行显示或隐藏</div>

总结:v-if 适用于需要在不同条件下动态切换大块内容的场景,而 v-show 适用于需要频繁切换显示和隐藏的元素。选择使用哪个指令取决于您的具体需求。
请注意,由于 v-if 控制的元素会被完全移除和重新创建,它在初始渲染时可能会有更高的切换开销。而 v-show 则在初始渲染时会有更高的初始渲染开销,但切换开销较小。

使用案例

点击复选框隐藏红色方块

<template>
<div id="app">
<input type="checkbox" v-model="see">点击隐藏红色方块
<div v-if="see" :style="styles"></div>
<div v-else>红色方块隐藏了</div>
</div>
</template>

<script>
import { ref, reactive } from 'vue';

export default {
setup() {
const see = ref(true);
const styles = reactive({
backgroundColor: 'red',
height: '100px',
width: '100px'
});

return {
see,
styles
};
}
};
</script>

v-for循环渲染

使用v-for可以渲染列表、字典、字符串等数据

v-for使用案例

循环列表

<template>
<div id="app">
<li v-for="e in emps" :key="e.name">
姓名:{{ e.name }} 年龄:{{ e.age }} 地址:{{ e.addr }}
</li>
</div>
</template>

<script>
import { reactive } from 'vue';

export default {
setup() {
const emps = reactive([
{ name: 'allen', age: 28, addr: 'BeiJing' },
{ name: 'tony', age: 34, addr: 'XiAn' }
]);

return {
emps
};
}
};
</script>

循环字典

<template>
<div id="app">
<li v-for="(value, key, index) in objs" :key="key">
编号:{{ index }} {{ key }} = {{ value }}
</li>
</div>
</template>

<script>
import { reactive } from 'vue';

export default {
setup() {
const objs = reactive({
name: 'allen',
age: 28
});

return {
objs
};
}
};
</script>

v-on事件监听

v-on 指令用于监听 DOM 事件并触发相应的方法或表达式。它可以用于绑定事件处理程序、自定义事件以及键盘事件等。

v-on语法

完整语法:v-on:事件名="函数名"v-on:事件名="函数名(参数1……)"
缩写语法:@事件名="函数名"@事件名="函数名(参数1……)"
event:函数中的默认形参,代表原生dom事件; 当调用的函数有多个参数时需要使用dom事件,则通过$event作为实参传入;作用用于监听dom事件

使用案例

点击按钮输出信息

<template>
<div id="app">
<button @click="aaa">点击事件</button>
<button @click="bbb('hello', $event)">传入原生dom点击事件</button>
</div>
</template>

<script>
import { reactive } from 'vue';

export default {
setup() {
const msg = reactive({
value: 'hello, allen'
});

const aaa = () => {
alert(msg.value);
};

const bbb = (name, event) => {
alert(`${name}, ${event.target.tagName}`);
};

return {
aaa,
bbb
};
}
};
</script>

事件修饰符

修饰符 用法 描述
.stop @click.stop 阻止事件冒泡
.prevent @submit.prevent 阻止默认的表单提交行为
.capture @focus.capture 使用事件捕获模式
.self @click.self 仅当事件在元素自身上触发时调用事件处理程序
.once @click.once 仅触发一次事件处理程序
.passive @touchstart.passive 使用被动事件监听器,提升滚动性能(适用于滚动相关事件,如 touchstarttouchmovemousewheel 等)
.capture.once @click.capture.once 使用事件捕获模式,并且仅触发一次事件处理程序
.prevent.default @click.prevent.default 阻止默认行为和冒泡
使用案例:
<!-- 阻止事件冒泡 -->
<button @click.stop="handleClick">点击我</button>

<!-- 阻止默认行为 -->
<a href="#" @click.prevent="handleClick">点击我</a>

<!-- 使用事件捕获模式 -->
<div @click.capture="handleClick">点击我</div>

<!-- 仅当事件在该元素自身上触发时才调用处理程序 -->
<div @click.self="handleClick">点击我</div>

<!-- 仅触发一次处理程序 -->
<button @click.once="handleClick">点击我</button>

按键修饰符

修饰符 描述
.enter 监听回车键(Enter)
.tab 监听制表键(Tab)
.delete 监听删除键(Delete)或退格键(Backspace)
.esc 监听 Escape 键
.space 监听空格键
.up 监听上箭头键
.down 监听下箭头键
.left 监听左箭头键
.right 监听右箭头键
.ctrl 监听 Ctrl 键
.alt 监听 Alt 键
.shift 监听 Shift 键
.meta 监听 Meta 键(如 Windows 键或 Command 键)
.exact 完全匹配修饰符,需要与其他键一起使用,如 .exact.ctrl

使用案例:

<!-- 当用户按下回车键时,触发事件:-->
<div @keydown.enter="handleEnter">按下回车键</div>

<!--当用户按下 Tab 键时,触发事件:-->
<div @keydown.tab="handleTab">按下Tab键</div>

<!--当用户按下 Delete 键或退格键时,触发事件:-->
<div @keydown.delete="handleDelete">按下Delete键或退格键</div>

<!--当用户按下 Escape 键时,触发事件:-->
<div @keydown.esc="handleEscape">按下Escape键</div>

<!--当用户按下空格键时,触发事件:-->
<div @keydown.space="handleSpace">按下空格键</div>

<!--当用户按下上箭头键时,触发事件:-->
<div @keydown.up="handleUpArrow">按下上箭头键</div>

<!--当用户按下下箭头键时,触发事件:-->
<div @keydown.down="handleDownArrow">按下下箭头键</div>

<!--当用户按下左箭头键时,触发事件:-->
<div @keydown.left="handleLeftArrow">按下左箭头键</div>

<!--当用户按下右箭头键时,触发事件:-->
<div @keydown.right="handleRightArrow">按下右箭头键</div>

<!--当用户按下 Ctrl 键时,触发事件:-->
<div @keydown.ctrl="handleCtrl">按下Ctrl键</div>

<!--当用户按下 Alt 键时,触发事件:-->
<div @keydown.alt="handleAlt">按下Alt键</div>

<!--当用户按下 Shift 键时,触发事件:-->
<div @keydown.shift="handleShift">按下Shift键</div>

<!--当用户按下 Meta 键(如 Windows 键或 Command 键)时,触发事件:-->
<div @keydown.meta="handleMeta">按下Meta键</div>

<!--当用户按下指定的修饰符组合时,触发事件(例如同时按下 Ctrl 键和 Shift 键):-->
<div @keydown.ctrl.shift="handleCtrlShift">按下Ctrl + Shift键</div>

v-mode数据双向绑定

双向绑定v-mode和单向绑定v-bind的区别

类型 双向绑定 单向绑定
定义方式 使用 v-model 指令 使用插值语法 {{ }}v-bind 指令
适用对象 适用于表单元素(<input><textarea><select> 等) 适用于任何元素
数据流向 数据在视图和数据模型之间双向同步 数据只从数据模型流向视图
更新方式 数据的变化会实时更新视图,视图的变化也会更新数据 数据的变化会更新视图,但视图的变化不会更新数据
实现方式 使用 v-model 绑定到 Vue 实例的数据属性 使用插值语法 {{ }}v-bind 绑定到 Vue 实例的数据属性
示例 <input v-model="message"> <span>{{ message }}</span>

v-model双向绑定数据支持以下几种类型

表单元素类型 示例
输入框 <input type="text">
多行文本框 <textarea></textarea>
单选框 <input type="radio">
复选框 <input type="checkbox">
下拉列表 <select><option></option></select>
开关 <input type="checkbox"> 或自定义组件
数字输入 <input type="number">
日期选择器 <input type="date"> 或自定义组件
时间选择器 <input type="time"> 或自定义组件
文件上传 <input type="file"> 或自定义组件
<!--输入框-->
<input type="text" v-model="inputText">

<!--多行文本框-->
<textarea v-model="textareaText"></textarea>

<!--单选框-->
<input type="radio" id="option1" value="option1" v-model="selectedOption">
<label for="option1">Option 1</label>

<input type="radio" id="option2" value="option2" v-model="selectedOption">
<label for="option2">Option 2</label>

<!--复选框-->
<input type="checkbox" id="checkbox1" value="value1" v-model="selectedOptions">
<label for="checkbox1">Option 1</label>

<input type="checkbox" id="checkbox2" value="value2" v-model="selectedOptions">
<label for="checkbox2">Option 2</label>

<!--下拉列表-->
<select v-model="selectedOption">
<option value="option1">Option 1</option>
<option value="option2">Option 2</option>
</select>

<!--开关-->
<input type="checkbox" id="toggleSwitch" v-model="toggleSwitchValue">
<label for="toggleSwitch">Toggle Switch</label>

<!--数字输入-->
<input type="number" v-model="numericValue">
<!--日期选择器-->
<input type="date" v-model="selectedDate">

<!--时间选择器-->
<input type="time" v-model="selectedTime">

<!--文件上传-->
<input type="file" v-model="selectedFile">

自定义指令

在 Vue.js 3 中,可以通过使用 directive 函数来自定义指令。如下示例:当选中复选框打印log
解析:
1.watchEffect 函数来监视 isChecked 的变化。当 isChecked 的值发生变化时,watchEffect 内部的回调函数会被触发。在回调函数中,我们判断 isChecked 是否为 true,如果是,则打印 log 信息。
2.在 Vue.js 3 中,使用 watchEffect 来监听数据的变化,而不是像 Vue.js 2 中的 watch 函数。
3.在 directives 对象中,我们定义了一个名为 log 的自定义指令。 在 log 指令的 mounted 钩子函数中,我们可以对元素进行一些操作。mounted 钩子函数会在指令所绑定的元素被插入到 DOM 中时触发。
4.el 是指令所绑定的元素,可以通过该参数访问和操作元素的属性、样式等。
5.binding 是一个包含了指令信息的对象,其中包含了一些属性和方法。在这里,我们主要使用了 binding.value 属性。
6.在 mounted 钩子函数中,我们使用 addEventListener 方法给元素添加了一个点击事件监听器。 当元素被点击时,点击事件的回调函数会被触发,并在回调函数中将 binding.value 的值设置为 true。

<template>
<div>
<label>
<input type="checkbox" v-model="isChecked"> 打印 Log
</label>
<p v-log="isChecked">这是一个自定义指令示例</p>
</div>
</template>

<script>
import { watchEffect, ref } from 'vue';

export default {
setup() {
const isChecked = ref(false);

watchEffect(() => {
if (isChecked.value) {
console.log('Log 被打印了');
}
});

return {
isChecked
};
},
directives: {
log: {
mounted(el, binding) {
el.addEventListener('click', () => {
binding.value = true;
});
}
}
}
};
</script>

过渡动画

过渡效果和过渡动画的区别

过渡效果(Transition Effect):过渡效果指的是元素在状态变化过程中产生的视觉变化效果。当元素从一种状态过渡到另一种状态时,通过添加或删除CSS属性、改变元素的样式或位置等方式,使元素呈现出平滑、渐变或其他形式的过渡效果。过渡效果可以通过CSS过渡、动画或其他技术来实现。
过渡动画(Transition Animation):过渡动画是指在元素状态发生变化时,通过连续的帧动画来实现平滑的过渡效果。它使用动画技术将元素的样式逐渐改变,从而产生视觉上的过渡效果。过渡动画可以通过CSS动画、JavaScript动画库或前端框架(如Vue.js)提供的过渡功能来实现。
总结:过渡效果更侧重于描述状态变化过程中的视觉变化,而过渡动画则是一种实现过渡效果的具体手段。

过渡效果

在CSS中操作trasition过滤或anmation动画达到不同的效果,为目标元素添加一个父元素 ,让父元素通过自动应用class类名来达到效果; 过渡与动画时,会为对应元素动态添加的相关class类名:

过渡类名 效果描述
xxx-enter 元素显示前的初始状态
xxx-enter-active 元素显示过程中的过渡效果
xxx-enter-to 元素显示后的最终状态
xxx-leave 元素隐藏前的初始状态
xxx-leave-active 元素隐藏过程中的过渡效果
xxx-leave-to 元素隐藏后的最终状态

这些类名通常与Vue的过渡组件()一起使用,用于定义元素在进入或离开过程中的不同状态和过渡效果。
案例:使用过渡效果实现渐变效果

<template>
<div>
<button @click="show = !show">渐变效果</button>
<transition name="mxg">
<p v-if="show">渐变过渡效果</p>
</transition>
<transition name="meng">
<p v-if="show">渐变平滑效果</p>
</transition>
</div>
</template>

<script>
import { ref } from 'vue';

export default {
name: 'App',
setup() {
const show = ref(true);

return {
show
};
}
};
</script>

<style>
.mxg-enter-active, .mxg-leave-active {
transition: opacity 5s;
}

.mxg-enter, .mxg-leave-to {
opacity: 0;
}

.meng-enter-active {
transition: all 1s;
}

.meng-leave-active {
transition: all 5s;
}

.meng-enter, .meng-leave-to {
opacity: 0;
transform: translateX(20px);
}
</style>

过渡动画

案例:缩小动画效果

<template>
<div>
<button @click="show = !show">显示方法隐藏缩小动画效果</button>
<transition name="bounce">
<p v-if="show">阿才的博客</p>
</transition>
</div>
</template>

<script>
import { ref } from 'vue';

export default {
name: 'App',
setup() {
const show = ref(true);

return {
show
};
}
};
</script>

<style>
.bounce-enter-active {
animation: bounce-in 3s;
}

.bounce-leave-active {
animation: bounce-in 3s reverse;
}

@keyframes bounce-in {
0% {
transform: scale(0);
}
50% {
transform: scale(1.5);
}
100% {
transform: scale(1);
}
}
</style>

组件化开发

vue组件

什么是vue组件

Vue中的组件化开发就是把网页的重复代码抽取出来封装成一个个可复用的视图组件,然后将这些组件凭借到一起构成一个完成的系统。这种方式非常灵活可以提供开发和维护效率。

vue组件的特点

特点 描述
复用性 组件可以在应用程序的不同部分多次使用,提高了代码的复用性和维护性。
封装性 组件将相关的功能、数据和样式封装在一起,使得组件的内部实现对外部不可见,提高了代码的模块化程度。
可组合性 组件可以通过嵌套和组合来构建更复杂的界面,将界面拆分为更小的可管理单元,方便开发和维护。
单一责任 每个组件负责特定的功能和视图逻辑,使得代码更易于理解、测试和维护。
通信机制 组件之间可以通过 props、events、provide/inject 等机制进行数据传递和通信,实现了组件之间的解耦和灵活的交互。

vue组件的使用

为了能够在模板中使用,这些组件必须先注册以便Vue能够识别,注册组件分为两种类型:全局注册和局部注册

全局注册组件

import { createApp } from 'vue';
import App from './App.vue';
import MyComponent from './components/MyComponent.vue';

const app = createApp(App);

app.component('my-component', MyComponent);

app.mount('#app');

局部注册组件

import { defineComponent } from 'vue';
import MyComponent from './MyComponent.vue';

export default defineComponent({
components: {
'my-component': MyComponent
},
// ...
});

多组件使用案例

<template>
<div id="app">
<header-component></header-component>
<main-component></main-component>
<foot-component></foot-component>
</div>
</template>

<script>
import HeaderComponent from './components/Header.vue';
import MainComponent from './components/Main.vue';
import FootComponent from './components/Foot.vue';

export default {
components: {
HeaderComponent,
MainComponent,
FootComponent,
},
}
</script>

vue组件通讯

vue组件通讯分为以下几种方式

通信方式 描述
Props和Events 父组件通过props将数据传递给子组件,子组件通过events向父组件发送消息。
Provide和Inject 父组件通过provide向所有子孙组件提供数据,子孙组件通过inject获取父组件提供的数据。
$emit和$on 组件间可以使用事件总线机制,通过$emit触发事件并传递数据,其他组件通过$on监听事件并接收数据。
Vuex Vuex是Vue.js官方提供的状态管理库,用于管理共享状态。组件可以通过Vuex共享状态并进行数据更新和获取。
$refs 通过ref属性给组件或元素添加引用,可以直接通过this.$refs来访问组件或元素,并进行相应的操作。

父子组件通讯

Props和Events

父组件

<template>
<div>
<child-component :message="parentMessage"></child-component>
</div>
</template>

<script>
import ChildComponent from './ChildComponent.vue';

export default {
components: {
ChildComponent,
},
data() {
return {
parentMessage: 'Hello from parent component',
};
},
};
</script>

子组件

<template>
<div>
<p>{{ message }}</p>
</div>
</template>

<script>
export default {
props: ['message'],
};
</script>

Provide和Inject

父组件

在父组件中使用 provide 来提供数据,可以是一个对象或一个返回对象的函数。

const ParentComponent = {
provide() {
return {
message: 'Hello from parent',
count: 42
};
},
// ...
};

子组件

在子组件中使用 inject 来注入父组件提供的数据。你可以在 inject 中指定要注入的属性名称,也可以使用对象的解构语法将多个属性注入。

const ChildComponent = {
inject: ['message', 'count'],
mounted() {
console.log(this.message); // 输出:Hello from parent
console.log(this.count); // 输出:42
},
// ...
};

同级组件通讯

$emit和$on

父组件

在触发事件的组件中使用 $emit 来触发自定义事件,并传递需要传递的数据。

const ComponentA = {
methods: {
handleClick() {
this.$emit('custom-event', 'Hello from Component A');
}
},
// ...
};

子组件

在监听事件的组件中使用 $on 来注册事件监听器,并定义处理事件的回调函数。

const ComponentB = {
mounted() {
this.$on('custom-event', (data) => {
console.log(data); // 输出:Hello from Component A
});
},
// ...
};

生命周期钩子函数

在 Vue.js 3 中,”生命周期钩子”已经被废弃,取而代之的是 “生命周期钩子函数”。Vue.js 3 中的生命周期钩子函数提供了在组件不同阶段执行自定义逻辑的能力。通过这些钩子函数,你可以在组件的生命周期中进行初始化、数据加载、DOM 操作、销毁等操作。
生命周期钩子函数,如下:

生命周期钩子函数 说明
beforeCreate 在实例被创建之前调用,此时组件的数据观测和事件还未初始化。
created 在实例被创建之后调用,此时组件的数据观测和事件已经初始化完成。
beforeMount 在组件挂载到 DOM 之前调用。
mounted 在组件挂载到 DOM 之后调用。
beforeUpdate 在组件更新之前调用,即数据发生变化但尚未更新到 DOM。
updated 在组件更新之后调用,即数据变化已经更新到 DOM。
beforeUnmount 在组件卸载之前调用。
unmounted 在组件卸载之后调用。

使用案例

const app = Vue.createApp({
data() {
return {
message: 'Hello, Vue.js 3!',
};
},
beforeCreate() {
console.log('beforeCreate');
// 在此阶段无法访问到实例上的数据
},
created() {
console.log('created');
// 可以访问实例上的数据
console.log(this.message);
},
beforeMount() {
console.log('beforeMount');
// 可以进行一些 DOM 操作
document.querySelector('#app').style.backgroundColor = 'red';
},
mounted() {
console.log('mounted');
// 可以访问实例上的 DOM 元素
console.log(this.$el);
},
beforeUpdate() {
console.log('beforeUpdate');
// 可以访问更新前的数据和 DOM 元素
console.log(this.message);
console.log(this.$el);
},
updated() {
console.log('updated');
// 可以访问更新后的数据和 DOM 元素
console.log(this.message);
console.log(this.$el);
},
beforeUnmount() {
console.log('beforeUnmount');
// 可以进行一些清理操作
},
unmounted() {
console.log('unmounted');
// 实例已被销毁
},
});

app.mount('#app');

数据持久化

在VueJS中常见的数据持久化有:localStorage、Cookie

localStorage

案例

// 存储数据
localStorage.setItem('myData', JSON.stringify(data));

// 获取数据
const savedData = JSON.parse(localStorage.getItem('myData'));

案例

import Cookies from 'js-cookie';

// 存储数据
Cookies.set('myData', data);

// 获取数据
const savedData = Cookies.get('myData');

Axios

在 Vue.js 3 中,axios 是一个流行的用于发送 HTTP 请求的第三方库。它可以用于与服务器进行数据交互,例如获取数据、提交表单、处理文件上传等。

axios的使用

安装axios

npm install axios

案例:
使用 onMounted 函数来替代 Vue 2.x 中的 mounted 钩子函数,它会在组件挂载完成后执行相应的逻辑。

import { ref, onMounted } from 'vue';
import axios from 'axios';

export default {
setup() {
const users = ref([]);

onMounted(() => {
axios.get('https://api.example.com/users')
.then(response => {
users.value = response.data;
})
.catch(error => {
console.error(error);
});
});

return {
users
};
}
};

axios封装api接口

在api.js中定义api接口

import axios from 'axios';

// 创建 axios 实例
const api = axios.create({
baseURL: 'https://api.example.com', // API 接口的基础 URL
timeout: 5000 // 请求超时时间
});

// 封装 API 接口
export const getUser = (userId) => {
return api.get(`/users/${userId}`);
};

export const createUser = (userData) => {
return api.post('/users', userData);
};

// 其他 API 接口的封装...

在vue组件中调用

import { getUser, createUser } from './api.js';

export default {
methods: {
async fetchUser(userId) {
try {
const response = await getUser(userId);
const user = response.data;
// 处理返回的用户数据
console.log(user);
} catch (error) {
// 处理请求失败的错误
console.error(error);
}
},
async addUser(userData) {
try {
const response = await createUser(userData);
const newUser = response.data;
// 处理返回的新用户数据
console.log(newUser);
} catch (error) {
// 处理请求失败的错误
console.error(error);
}
}
}
};

axios异常处理

在axios响应拦截器中处理异常编辑src/utils/request.js

//响应拦截器 和异常中关闭加载效果
axios_request.interceptors.response.use(response =>{
loading.close()
//当 请求接口code代码不是200说明后台服务异常可在此统一处理
if(response.data.code !== 200){
Message({
message:response.data.data.msg
})
}
return response
},error =>{
loading.close()
//当接口异常时,进行弹出错误提示
Message({
message:error.message,
type:'error',
duration: 5*1000
})
return Promise.reject(error)
})

加载效果

当页面请求数据时进行加载效果,请求数据完成关闭加载效果。编辑src/utils/request.js

// eslint-disable-next-line no-unused-vars
import axios from 'axios';
import {Loading,Message} from "element-ui";

//定义加载效果
const loading = {
loadingInstance: null,
open:function (){
if(this.loadingInstance == null){
this.loadingInstance = Loading.service({
target:'.main'
})
}
},
close:function (){
if(this.loadingInstance !== null){
this.loadingInstance.close()
}
}
}

// eslint-disable-next-line no-unused-vars
const axios_request = axios.create({
baseURI: 'http://127.0.0.1:8000/api',
timeout: 5000
})
//请求拦截器打开加载效果
axios_request.interceptors.request.use(config =>{
loading.open() //打开加载效果
return config
},error =>{
loading.close() //关闭加载效果
return Promise.reject(error)
})

//响应拦截器 和异常中关闭加载效果
axios_request.interceptors.response.use(response =>{
loading.close()
return response
},error =>{
loading.close()
return Promise.reject(error)
})
export default axios_request //导出自定义创建axios对象

路由

什么是VueJs路由

Vue Router是Vue.js官方的路由管理器,它和Vue.js的核心深度集成,让构建单页面变得非常简单。 通过根据不同的请求路径,切换显示不同组件进行渲染页面。

使用路由

安装Vue Router

npm install vue-router

创建router.js文件,并配置路由

import { createRouter, createWebHistory } from 'vue-router';

// 导入组件
import Home from './components/Home.vue';
import About from './components/About.vue';
import Contact from './components/Contact.vue';

// 创建路由实例
const router = createRouter({
history: createWebHistory(),
routes: [
{ path: '/', component: Home },
{ path: '/about', component: About },
{ path: '/contact', component: Contact }
]
});

export default router;

根组件使用路由

<template>
<div>
<nav>
<router-link to="/">Home</router-link>
<router-link to="/about">About</router-link>
<router-link to="/contact">Contact</router-link>
</nav>
<router-view></router-view>
</div>
</template>

<script>
export default {
name: 'App'
};
</script>

main.js入口使用路由

import { createApp } from 'vue';
import App from './App.vue';
import router from './router.js';

createApp(App).use(router).mount('#app');

<router-link> 是 Vue Router 提供的组件,用于生成路由导航链接。它可以通过配置的路由规则生成对应的 URL,并自动添加激活状态的类名,以及处理点击事件来实现路由切换。

使用router link

<router-link to="/path">Link Text</router-link>

router link的属性

属性 描述
to 指定要跳转的路径,可以是字符串或对象形式,详细说明见下方
exact 是否精确匹配路由路径,默认为 false
tag 指定渲染的标签类型,默认为 "a"
active-class 自定义激活状态的类名,默认为 "router-link-active"
exact-active-class 自定义精确匹配激活状态的类名,默认为 "router-link-exact-active"
aria-current 自定义激活状态时的 ARIA 属性值,默认为 "page"。当 exact 属性为 true 时,ARIA 属性值为 "true"
event 触发导航的事件名称或事件数组,默认为 "click"
replace 点击链接后是否使用 replace 而不是 push 进行路由切换,默认为 false

示例用法:

<router-link to="/home" exact>Home</router-link>

<router-link :to="{ path: '/about' }" tag="button">About</router-link>

<router-link to="/contact" active-class="custom-active">Contact</router-link>

<router-link to="/products" exact-active-class="custom-exact-active">Products</router-link>

<router-link to="/dashboard" aria-current="page">Dashboard</router-link>

<router-link to="/logout" event="mouseover">Logout</router-link>

<router-link to="/login" replace>Login</router-link>

插件

以下是VueJS3.0支持的第三方插件

插件名称 描述
Vuex Vue.js 的官方状态管理库,用于管理应用程序的状态。
Vue Router Vue.js 的官方路由库,用于实现单页面应用程序的路由功能。
Vue CLI Vue.js 的官方脚手架工具,用于快速创建和管理 Vue.js 项目。
Axios 一个基于 Promise 的 HTTP 库,用于进行网络请求。
VeeValidate 用于表单验证的插件,提供了强大的验证规则和错误提示功能。
VueI18n 用于国际化的插件,支持应用程序的多语言切换和翻译。
VueXfire 用于将 Vue.js 和 Firebase 集成的插件,简化了与 Firebase 实时数据库的交互。
Vue-Moment 提供了在 Vue.js 中格式化和处理日期时间的功能。
Vue-Router-Next-Transition 用于在 Vue Router 中实现过渡动画效果的插件。
Vue-Awesome-Swiper 集成了 Swiper 轮播库的 Vue.js 组件。
文章作者: 慕容峻才
文章链接: https://www.acaiblog.top/VueJS教程/
版权声明: 本博客所有文章除特别声明外,均采用 CC BY-NC-SA 4.0 许可协议。转载请注明来自 阿才的博客
微信打赏
支付宝打赏