适合人群 :有 HTML/CSS/JavaScript 基础,想快速上手 Vue 3 的前端初学者
学习目标 :掌握 Vue 3 核心概念,能独立开发简单交互应用
技术栈:Vue 3 + Composition API + Vite(2026 年最新实践)
一、为什么选择 Vue 3?
在 React、Angular、Svelte 等框架中,Vue 凭借以下优势成为新手友好之选:
| 特性 | 说明 |
|---|---|
| 渐进式框架 | 可从 CDN 引入,也可构建大型 SPA |
| 中文文档完善 | 官方提供高质量中文文档 |
| Composition API | 逻辑复用更灵活(类似 React Hooks) |
| 开发体验优秀 | Vite 极速启动,HMR 热更新毫秒级 |
💡 2026 年现状:Vue 3 已成主流,Vue 2 于 2023 年停止维护。
二、环境准备:30 秒启动项目
方式 1:CDN 快速体验(推荐新手)
xml
<!DOCTYPE html>
<html>
<head>
<title>My First Vue App</title>
<!-- 从 CDN 加载 Vue 3 -->
<script src="https://unpkg.com/vue@3/dist/vue.global.js"></script>
</head>
<body>
<div id="app">
<h1>{{ message }}</h1>
<button @click="reverseMessage">反转消息</button>
</div>
<script>
const { createApp, ref } = Vue
createApp({
setup() {
const message = ref('Hello Vue!')
const reverseMessage = () => {
message.value = message.value.split('').reverse().join('')
}
return {
message,
reverseMessage
}
}
}).mount('#app')
</script>
</body>
</html>
✅ 打开浏览器 → 点击按钮 → 文字反转!你已成功运行 Vue!
方式 2:Vite 脚手架(生产级开发)
yaml
# 创建项目
npm create vue@latest my-vue-app
# 按提示选择(建议全选默认)
✔ Project name: ... my-vue-app
✔ Add TypeScript? ... No
✔ Add JSX Support? ... No
✔ Add Vue Router? ... No
✔ Add Pinia? ... No
✔ Add Vitest? ... No
✔ Add Cypress? ... No
✔ Add ESLint? ... Yes
✔ Add Prettier? ... Yes
# 进入目录并安装依赖
cd my-vue-app
npm install
# 启动开发服务器
npm run dev
访问 http://localhost:5173,看到 Vue 官方欢迎页即成功!
三、核心概念精讲(附代码示例)
1. 响应式数据:ref 与 reactive
ref:用于基本类型(字符串、数字、布尔值)
xml
<script setup>
import { ref } from 'vue'
// 创建响应式引用
const count = ref(0)
// 修改值必须通过 .value
const increment = () => {
count.value++
}
</script>
<template>
<p>计数: {{ count }}</p>
<button @click="increment">+1</button>
</template>
🔍 关键点 :模板中自动解包
.value,但 JS 逻辑中需显式使用。
reactive:用于对象/数组
xml
<script setup>
import { reactive } from 'vue'
const user = reactive({
name: 'Alice',
age: 25
})
const updateAge = () => {
user.age++ // 直接修改属性
}
</script>
<template>
<p>{{ user.name }} - {{ user.age }}岁</p>
<button @click="updateAge">长大一岁</button>
</template>
💡 何时用哪个?
- 单个值 →
ref- 复杂对象 →
reactive- 不确定?统一用
ref(更安全)
2. 事件处理:@click 与方法
xml
<template>
<!-- 方法调用 -->
<button @click="greet">打招呼</button>
<!-- 内联处理器 -->
<button @click="count++">直接修改</button>
<!-- 传递参数 -->
<button @click="deleteItem(item.id)">删除</button>
<!-- 修饰符:阻止默认行为 -->
<form @submit.prevent="handleSubmit">
<input type="text" v-model="input">
<button type="submit">提交</button>
</form>
</template>
<script setup>
const greet = () => {
alert('Hello!')
}
const deleteItem = (id) => {
console.log('删除ID:', id)
}
const handleSubmit = () => {
console.log('表单提交')
}
</script>
📌 常用修饰符:
.prevent:阻止默认行为(如表单提交刷新).stop:阻止事件冒泡.once:只触发一次
3. 条件渲染:v-if vs v-show
xml
<template>
<!-- v-if:条件为假时完全移除 DOM -->
<div v-if="isLoggedIn">欢迎回来!</div>
<!-- v-else / v-else-if -->
<div v-else-if="isLoading">加载中...</div>
<div v-else>请先登录</div>
<!-- v-show:始终渲染 DOM,仅切换 display -->
<div v-show="showModal" class="modal">弹窗内容</div>
</template>
⚠️ 性能区别:
- 频繁切换 →
v-show(避免重复创建/销毁)- 条件很少改变 →
v-if(节省内存)
4. 列表渲染:v-for
xml
<template>
<!-- 渲染数组 -->
<ul>
<li v-for="item in items" :key="item.id">
{{ item.name }}
</li>
</ul>
<!-- 渲染对象 -->
<div v-for="(value, key) in userInfo" :key="key">
{{ key }}: {{ value }}
</div>
<!-- 带索引 -->
<div v-for="(item, index) in list" :key="item.id">
{{ index + 1 }}. {{ item.title }}
</div>
</template>
<script setup>
const items = [
{ id: 1, name: '苹果' },
{ id: 2, name: '香蕉' }
]
const userInfo = {
name: 'Bob',
email: 'bob@example.com'
}
</script>
🔑 必须加
:key!帮助 Vue 高效更新列表(避免复用错误)
5. 表单绑定:v-model
xml
<template>
<!-- 文本输入 -->
<input v-model="message" placeholder="输入消息">
<p>实时预览: {{ message }}</p>
<!-- 多行文本 -->
<textarea v-model="description"></textarea>
<!-- 复选框 -->
<input type="checkbox" v-model="isChecked">
<span>{{ isChecked ? '已选中' : '未选中' }}</span>
<!-- 单选按钮 -->
<input type="radio" v-model="picked" value="A"> A
<input type="radio" v-model="picked" value="B"> B
<!-- 下拉选择 -->
<select v-model="selected">
<option disabled value="">请选择</option>
<option>A</option>
<option>B</option>
</select>
</template>
<script setup>
import { ref } from 'vue'
const message = ref('')
const description = ref('')
const isChecked = ref(false)
const picked = ref('A')
const selected = ref('')
</script>
💡 修饰符:
.trim:自动去除首尾空格 →v-model.trim="text".number:转为数字 →v-model.number="age".lazy:失去焦点时更新(非 input 时)→v-model.lazy="comment"
四、组件化开发:构建可复用 UI
1. 创建组件(Button.vue)
xml
<!-- src/components/MyButton.vue -->
<template>
<button
class="my-button"
:class="{ 'primary': primary }"
@click="handleClick"
>
<slot></slot> <!-- 插槽:接收父组件内容 -->
</button>
</template>
<script setup>
defineProps({
primary: Boolean // 接收父组件传入的属性
})
const emit = defineEmits(['click']) // 声明触发的事件
const handleClick = () => {
emit('click') // 触发 click 事件
}
</script>
<style scoped>
.my-button {
padding: 8px 16px;
border: 1px solid #ccc;
border-radius: 4px;
cursor: pointer;
}
.primary {
background: #409eff;
color: white;
}
</style>
2. 使用组件(App.vue)
xml
<script setup>
import MyButton from './components/MyButton.vue'
import { ref } from 'vue'
const count = ref(0)
const increment = () => count.value++
</script>
<template>
<div>
<p>计数: {{ count }}</p>
<!-- 使用组件,传递 props 和监听事件 -->
<MyButton
:primary="true"
@click="increment"
>
点我加1!
</MyButton>
</div>
</template>
🧩 组件三要素:
- Props:父 → 子 传递数据
- Events:子 → 父 通信
- Slots:父组件向子组件插入内容
五、实战:待办事项(Todo List)
将所学知识整合为一个完整小应用!
1. 项目结构
css
src/
├── components/
│ └── TodoItem.vue
└── App.vue
2. App.vue(主组件)
xml
<script setup>
import { ref } from 'vue'
import TodoItem from './components/TodoItem.vue'
const newTodo = ref('')
const todos = ref([
{ id: 1, text: '学习 Vue', done: false }
])
const addTodo = () => {
if (newTodo.value.trim()) {
todos.value.push({
id: Date.now(),
text: newTodo.value,
done: false
})
newTodo.value = ''
}
}
const removeTodo = (id) => {
todos.value = todos.value.filter(todo => todo.id !== id)
}
</script>
<template>
<div class="todo-app">
<h1>我的待办事项</h1>
<!-- 添加新任务 -->
<form @submit.prevent="addTodo">
<input
v-model="newTodo"
placeholder="输入新任务..."
@keyup.enter="addTodo"
>
<button type="submit">添加</button>
</form>
<!-- 任务列表 -->
<ul>
<TodoItem
v-for="todo in todos"
:key="todo.id"
:todo="todo"
@remove="removeTodo(todo.id)"
/>
</ul>
<p>剩余: {{ todos.filter(t => !t.done).length }} 项</p>
</div>
</template>
3. TodoItem.vue(子组件)
xml
<template>
<li class="todo-item">
<input
type="checkbox"
v-model="todo.done"
>
<span :class="{ done: todo.done }">{{ todo.text }}</span>
<button @click="$emit('remove')">删除</button>
</li>
</template>
<script setup>
defineProps({
todo: Object
})
defineEmits(['remove'])
</script>
<style scoped>
.done {
text-decoration: line-through;
color: #999;
}
</style>
✅ 功能包含:
- 添加任务(回车/按钮)
- 完成/取消任务
- 删除任务
- 统计剩余数量
六、调试技巧
1. 浏览器 DevTools
安装 Vue Devtools 扩展:
- 查看组件树
- 实时修改响应式数据
- 检查事件监听器
2. 控制台日志
arduino
// 在 setup() 中
console.log('当前状态:', reactiveData)
3. 常见错误排查
| 错误现象 | 解决方案 |
|---|---|
| 数据不更新 | 检查是否用 ref/reactive 包裹 |
| 事件不触发 | 检查 @click 是否拼写正确 |
| 组件不显示 | 检查是否正确 import 和注册 |
| 样式失效 | 检查 <style scoped> 是否冲突 |
七、下一步学习路线
- 路由管理 :学习 Vue Router 实现多页面跳转
- 状态管理 :掌握 Pinia 管理全局状态
- TypeScript:为 Vue 项目添加类型安全
- 构建工具:深入理解 Vite 配置
- UI 库:集成 Element Plus / Naive UI 快速开发
八、总结:Vue 3 核心要点
| 概念 | 关键语法 | 用途 |
|---|---|---|
| 响应式 | ref(), reactive() |
数据驱动视图 |
| 模板指令 | v-if, v-for, v-model |
声明式渲染 |
| 事件处理 | @click, .prevent |
用户交互 |
| 组件通信 | props, emit, slots |
模块化开发 |
| 组合式 API | setup(), script setup |
逻辑复用 |
💬 记住 :
"Vue 的核心思想是:数据变,视图自动更新。"掌握这一点,你就已经入门了!
资源推荐:
作者 :前端工程师
更新日期 :2026 年 2 月
版权声明:本文可自由转载,但请保留出处。
如果你希望我提供 完整的 Todo List 项目代码仓库 或 Vue 3 + TypeScript 版本示例,欢迎继续提问!