《uni-app跨平台开发完全指南》- 03 - Vue.js基础入门
Vue.js 基础
本系列是《uni-app跨平台开发完全指南》系列教程,旨在帮助开发者从零开始掌握uni-app开发。本章将深入讲解Vue.js的核心概念,为你后续的uni-app开发打下坚实基础。
为什么学习Vue.js对uni-app开发如此重要?
很多初学者可能会问:“我直接学uni-app不行吗?为什么要先学Vue.js?”
这里有个很重要的概念需要理解:uni-app的本质是基于Vue.js的跨端实现框架。更形象一点,如果说uni-app是整车制造,那么Vue.js就属于发动机。如果你不懂发动机原理,虽然也能开车,但一旦出现故障,就束手无策了。同样,不掌握Vue.js基础,在uni-app开发中遇到复杂问题时,你会很难找到根本解决方案。
一、Vue.js 简介与开发环境搭建
1.1 Vue.js 是什么?
简单来说,Vue.js是一个用于构建用户界面的渐进式JavaScript框架。所谓"渐进式",意味着你可以根据项目需求,逐步采用Vue.js的特性:
- 可以在老项目中局部使用Vue.js增强交互
- 也可以使用Vue.js全家桶开发完整的前端应用
- 还可以用Vue.js开发原生移动应用(如uni-app)
1.2 环境准备:第一个Vue应用
让我们从最简单的HTML页面开始:
<!DOCTYPE html>
<html lang="zh-CN">
<head><meta charset="UTF-8"><meta name="viewport" content="width=device-width, initial-scale=1.0"><title>我的第一个Vue应用</title><!-- 引入Vue.js --><script src="https://cdn.jsdelivr.net/npm/vue@2.6.14/dist/vue.js"></script>
</head>
<body><!-- Vue实例挂载点 --><div id="app"><h1>{{ message }}</h1><button @click="reverseMessage">反转消息</button></div><script>// 创建Vue实例var app = new Vue({el: '#app', // 指定挂载元素data: { // 定义数据message: 'Hello Vue!'},methods: { // 定义方法reverseMessage: function() {this.message = this.message.split('').reverse().join('');}}});</script>
</body>
</html>
代码解析:
el: '#app':告诉Vue这个实例要控制页面中id为app的元素data:定义这个Vue实例的数据,可以在模板中使用{ { message }}:模板语法,将data中的message值渲染到页面@click:事件绑定,点击时执行reverseMessage方法
二、Vue 核心概念
2.1 数据绑定
数据绑定是Vue最核心的特性之一,它建立了数据与DOM之间的自动同步关系。
2.1.1 文本插值:{ { }}
<div id="app"><!-- 基本文本插值 --><p>消息:{{ message }}</p><!-- JS表达式 --><p>计算:{{ number + 1 }}</p><p>三元表达式:{{ isActive ? '激活' : '未激活' }}</p><p>反转:{{ message.split('').reverse().join('') }}</p>
</div><script>
new Vue({el: '#app',data: {message: 'Hello Vue!',number: 10,isActive: true}
});
</script>
重要提示:{ { }}中支持JavaScript表达式,但不支持语句(如if、for等)。
2.1.2 属性绑定:v-bind
<div id="app"><!-- 绑定HTML属性 --><div v-bind:title="tooltip">鼠标悬停查看提示</div><!-- 绑定CSS类 --><div v-bind:class="{ active: isActive, 'text-danger': hasError }">动态类名</div><!-- 绑定样式 --><div v-bind:style="{ color: activeColor, fontSize: fontSize + 'px' }">动态样式</div><!-- 简写 --><img :src="imageSrc" :alt="imageAlt">
</div><script>
new Vue({el: '#app',data: {tooltip: '这是一个提示信息',isActive: true,hasError: false,activeColor: 'red',fontSize: 20,imageSrc: 'path/to/image.jpg',imageAlt: '示例图片'}
});
</script>
v-bind原理:当数据变化时,Vue会自动更新对应的DOM属性。
2.2 指令系统
指令是带有v-前缀的特殊属性,它们为HTML添加了动态行为。
2.2.1 条件渲染:v-if vs v-show
<div id="app"><!-- v-if:条件性地渲染一块内容 --><p v-if="score >= 90">优秀!</p><p v-else-if="score >= 60">及格</p><p v-else>不及格</p><!-- v-show:总是渲染,只是切换display --><p v-show="isVisible">这个元素会显示/隐藏</p><button @click="toggle">切换显示</button><button @click="changeScore">改变分数</button>
</div><script>
new Vue({el: '#app',data: {score: 85,isVisible: true},methods: {toggle: function() {this.isVisible = !this.isVisible;},changeScore: function() {this.score = Math.floor(Math.random() * 100);}}
});
</script>
v-if 与 v-show 的区别:
| 特性 | v-if | v-show |
|---|---|---|
| 渲染方式 | 条件为false时不渲染DOM元素 | 总是渲染,只是切换display属性 |
| 切换开销 | 更高的切换开销(创建/销毁组件) | 更高的初始渲染开销 |
| 适用场景 | 运行时条件很少改变 | 需要非常频繁地切换 |
2.2.2 列表渲染:v-for
<div id="app"><!-- 遍历数组 --><ul><li v-for="(item, index) in items" :key="item.id">{{ index + 1 }}. {{ item.name }} - ¥{{ item.price }}</li></ul><!-- 遍历对象 --><ul><li v-for="(value, key) in userInfo" :key="key">{{ key }}: {{ value }}</li></ul><!-- 遍历数字范围 --><span v-for="n in 5" :key="n">{{ n }} </span>
</div><script>
new Vue({el: '#app',data: {items: [{ id: 1, name: '苹果', price: 5 },{ id: 2, name: '香蕉', price: 3 },{ id: 3, name: '橙子', price: 4 }],userInfo: {name: '张三',age: 25,city: '北京'}}
});
</script>
关键点:
- :key的重要性:为每个节点提供唯一标识,优化列表渲染性能
- 可以使用
(item, index)或(value, key, index)语法
2.2.3 事件处理:v-on
<div id="app"><!-- 基本事件处理 --><button v-on:click="counter += 1">点击次数: {{ counter }}</button><!-- 方法事件处理器 --><button @click="sayHello">打招呼</button><!-- 内联处理器中的方法 --><button @click="say('Hello', $event)">带参数的事件</button><!-- 事件修饰符 --><form @submit.prevent="onSubmit"><input type="text"><button type="submit">提交</button></form><!-- 按键修饰符 --><input @keyup.enter="onEnter" placeholder="按回车键触发">
</div><script>
new Vue({el: '#app',data: {counter: 0},methods: {sayHello: function(event) {alert('Hello!');console.log(event); // 原生事件对象},say: function(message, event) {alert(message);if (event) {event.preventDefault();}},onSubmit: function() {alert('表单提交被阻止了!');},onEnter: function() {alert('你按了回车键!');}}
});
</script>
常用事件修饰符:
.stop:阻止事件冒泡.prevent:阻止默认行为.capture:使用事件捕获模式.self:只当事件是从侦听器绑定的元素本身触发时才触发回调.once:只触发一次.passive:告诉浏览器你不想阻止事件的默认行为
2.2.4 双向数据绑定:v-model
<div id="app"><!-- 文本输入 --><input v-model="message" placeholder="编辑我"><p>消息是: {{ message }}</p><!-- 多行文本 --><textarea v-model="multilineText"></textarea><p style="white-space: pre-line;">{{ multilineText }}</p><!-- 复选框 --><input type="checkbox" id="checkbox" v-model="checked"><label for="checkbox">{{ checked ? '已选中' : '未选中' }}</label><!-- 多个复选框 --><div><input type="checkbox" id="jack" value="Jack" v-model="checkedNames"><label for="jack">Jack</label><input type="checkbox" id="john" value="John" v-model="checkedNames"><label for="john">John</label><input type="checkbox" id="mike" value="Mike" v-model="checkedNames"><label for="mike">Mike</label><br><span>选中的名字: {{ checkedNames }}</span></div><!-- 单选按钮 --><div><input type="radio" id="one" value="One" v-model="picked"><label for="one">One</label><input type="radio" id="two" value="Two" v-model="picked"><label for="two">Two</label><br><span>选中的值: {{ picked }}</span></div><!-- 选择框 --><select v-model="selected"><option disabled value="">请选择</option><option>A</option><option>B</option><option>C</option></select><span>选中的值: {{ selected }}</span>
</div><script>
new Vue({el: '#app',data: {message: ''