(1)vue的基础语法
Vue基本语法
插值操作
- Mustache
表示:{{}}
用法:见下图
- v-once
说明:该指令表示元素和组件(组件后面才会学习)叧渲染一次,不会随着数据的改变而改变。当数据改变时,插值处的内容不会更新。
用法:<span v-once>{{ msg }}</span>
- v-html
说明:我们从服务器请求到的数据本身就是一个HTML代码,我们可能希望的是按照HTML格式进行解析,并且显示对应的内容,输出真正的HTML。
用法:见图
-
v-text
说明: v-text作用和Mustache一致,插入文本,不够灵活,会自动覆盖标签内的值
用法:<span v-text="msg"></span>
-
v-pre
说明:不解析{{}}的值
用法:<span v-pre>{{ msg }}</span>
渲染的结果仍是{{msg}} -
v-cloak
说明:可以用来隐藏未编译的Mustache标签直到实例准备完成。
<style>
[v-cloak]{
display: none;
}
</style>
<div id="app">
<h1 v-cloak>{{message}}</h1>
</div>
<script>
// 在vue解析之前,div中有一个属性v-cloak
// 在vue解析之后,会自动删除v-cloak
setTimeout(function(){
const app = new Vue({
el: "#app",
data: {
message: "Hello 小哀酱",
}
});
}, 3000)
</script>
v-bind 属性绑定(class,style)
说明:动态绑定属性。 v-bind用于绑定一个或多个属性值,或者向另一个组件传递props值。比如图片的链接src、网站的链接href、动态绑定一些类、样式等等
语法糖::
用法:<a v-bind:href="url">vue官网</a>
v-bind绑定class属性(绑定class有两种方式:对象语法,数组语法)
- 对象语法
用法:<div :class="{ 属性名: 变量 }"></div>
,变量的值为true或false
<div class="static" :class="{ active: isActive}">
Hello Vue
</div>
data: {
isActive: true,
}
还可以把数据对象放到计算属性上
<div :class="classObject"></div>
data: {
isActive: true,
},
computed: {
classObject: function () {
return {
active: this.isActive && !this.error,
}
}
}
- 数组语法
<div :class="[active, error]"></div>
data: {
active: 'active',
error: 'text-danger'
}
可以在数组中使用三元表达式
<div :class="[isActive ? 'active' : '', error]"></div>
在数组中加上引号就是字符串,不加引号就是变量,数组和对象可以混合使用
v-bind绑定style属性(绑定style有两种方式:对象语法,数组语法)
- 对象方法
key
:值为属性名称,驼峰式(fontSize)或短横线分隔(font-size引号括起来)value
:值为变量
<div :style="{ color: color, fontSize: fontSize }"></div>
data: {
color: 'red',
fontSize: '30px'
}
也可以直接绑定一个样式对象
<div :style="styleObject"></div>
data: {
styleObject: {
color: 'red',
fontSize: '13px'
}
}
- 数组语法
style后面跟的是一个数组类型。多个值以,分割即可
<div :style="[baseStyles,overridingStyles ]"></div>
计算属性
- 基本使用
当一个变量改变时另一个变量可以发生改变,或者模板中插值操作的表达式太过复杂时,都可以把变量拿出来放到computed内。
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>index</title>
<script src="../vue.js"></script>
</head>
<body>
<div id="app">
<h1>{{msg}}</h1>
<h1>{{reverseMsg}}</h1>
</div>
</body>
<script>
const app = new Vue({
el: "#app",
data: {
msg: "Hello Vue",
},
computed: {
reverseMsg: function () {
return this.msg.split("").reverse().join('')
}
}
});
</script>
</html>
- 和方法比较
通过方法也能实现相同效果:
<h1>{{reverseMsg()}}</h1>
methods: {
reverseMsg: function () {
return this.msg.split('').reverse().join('')
}
}
methods和computed看起来都可以实现我们的功能,那么为什么还要多一个计算属性这个东西呢?
原因:计算属性会进行缓存,如果多次使用时,计算属性只会调用一次。
不同点:计算属性是基于它们的响应式依赖进行缓存的,只用相关响应式依赖发生改变时它们才会重新求值,这就意味着只要 message 还没有发生改变,多次访问 reversedMsg 计算属性会立即返回之前的计算结果,而不必再次执行函数;而每当触发重新渲染时,对于方法渲染,将总会再次执行函数。
- 和侦听属性比较
侦听属性watch,当用数据改变时,调用watch,如下:
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>index</title>
<script src="../vue.js"></script>
</head>
<body>
<div id="app">
<h1>{{fullname}}</h1>
</div>
</body>
<script>
const app = new Vue({
el: "#app",
data: {
firstName: "Foo",
lastName: "Bar",
fullname: "Foo Bar"
},
watch: {
firstName: function(newVal, oldVal){
this.fullname = newVal + " " + this.lastName
},
lastName: function(newVal, oldVal){
this.fullname = this.firstName + " " + newVal
}
}
});
</script>
</html>
使用计算属性
computed: {
fullname: function () {
return this.firstName + " " + this.lastName
}
},
虽然计算属性在大多数情况下更合适,但当需要在数据变化时执行异步或开销较大的操作时,watch方式是最有用的。
- 计算属性的setter
计算属性默认只有getter,不过在需要时也提供一个setter:
computed: {
fullName: {
// getter
get: function () {
return this.firstName + ' ' + this.lastName
},
// setter
set: function (newVal) {
let names = newVal.split(' ')
this.firstName = names[0]
this.lastName = names[names.length - 1]
}
}
}
事件监听
指令:v-on
作用:绑定事件监听,监听用户发生的时间,比如点击、拖拽、键盘事件等等
语法糖:@
预期:Function | Inline Statement | Object
参数:event
简单示例,点击按钮实现数字加减
<div id="app">
<h3>{{count}}</h3>
<button @click="increment">+</button>
<button @click="decrement">-</button>
</div>
<script>
const app = new Vue({
el: "#app",
data: {
count: 0
},
methods: {
increment () {
this.count++
},
decrement () {
this.count--
},
}
});
</script>
事件监听也可以传参数
- 1.当不需要传参数时,模板中可以省略()
- 2.模板有(),但是没传参数,方法的参数值为
undefined
- 3.模板中事件传参数,方法得到相对应的值
- 4.当模板中省略(),但是方法内有形参,得到的结果时监听事件(下面的代码演示的是第4种情况)
<div id="app">
<button @click="btn1">按钮1</button>
</div>
<script>
const app = new Vue({
el: "#app",
methods: {
btn1 (event) {
console.log(event);
}
}
});
</script>
- 当方法内既想得到普通参数,又想得到监听事件,使用
$event
<div id="app">
<button @click="btn(123, "abc", $event)">按钮</button>
</div>
<script>
const app = new Vue({
el: "#app",
methods: {
btn (num, chr, event) {
console.log(num, chr, event);
}
}
});
</script>
v-on的修饰符:
- .stop,调用event.stopPropagation(),当父、子标签上都有事件时,阻止事件冒泡,加在子标签上
- .prevent,调用event.preventDefault(),阻止默认事件
- .(keyCode | keyAlias),只有当事件是从特定键触发时才能触发回调,如:(此时只监听enter键)
@keyup.enter=funcName
- .native,监听组件根元素的原生事件
- .once,只能触发一个回调
条件判断指令
指令:v-if, v-else-if, v-else
使用方式:
<div id="app">
<h2 v-if="score>100">S</h2>
<h2 v-else-if="score>80">A</h2>
<h2 v-else-if="score>60">B</h2>
<h2 v-else>C</h2>
</div>
<script>
const app = new Vue({
el: "#app",
data: {
score: 0
},
});
</script>
案例:切换登录方式
<div id="app">
<span v-if="loginStyle">
<label for="username">账号</label>
<input type="text" id="username" placeholder="用户账号">
</span>
<span v-else>
<label for="email">邮箱</label>
<input type="text" id="email" placeholder="用户邮箱">
</span>
<button @click="loginStyle = !loginStyle">切换类型</button>
</div>
<script src="../js/vue.js"></script>
<script>
const app = new Vue({
el: '#app',
data: {
loginStyle: true
}
})
</script>
问题:容易出现input复用问题,当一个输入框内有用户输入,切换登录方式时,用户输入的内容还在
原因:因为Vue使用虚拟DOM渲染,出于性能考虑,会尽可能地复用已经存在地元素,而不是重新创建新的元素
解决:给每个input加上不同地key属性
<span v-if="loginStyle">
<label for="username">账号</label>
<input type="text" id="username" placeholder="用户账号" key="username">
</span>
<span v-else>
<label for="email">邮箱</label>
<input type="text" id="email" placeholder="用户邮箱" key="email">
</span>
类似可以隐藏标签的指令还有v-show
。
v-show和v-if一样,都是决定标签是否被渲染
不同点时,v-if为false时,标签就根本不会存在;而v-show的实质是样式为
display: none
,适用于需要频繁切换显示和隐藏的标签开发中如何选择呢?当需要在显示不隐藏之间切片很频繁时,使用v-show。当叧有一次切换时,通过使用v-if
循环指令
指令:v-for
使用:
<div id="app">
<ul>
<li v-for="movie in movies">{{movie}}</li>
</ul>
</div>
<script>
const app = new Vue({
el: "#app",
data: {
movies: ['无名之辈', "流浪地球", '寄生虫', '魔童降世', "战狼2"]
},
});
</script>
在遍历时可以获得索引值v-for="(movie, index) in movies"
,如果遍历对象时,也可以获得key、value和index值v-for="value, key, index in object"
官方推荐使用v-for时,使用key属性,但要保证key的唯一性,不建议使用索引值。原因是当数组插入数据时,index发生变化,就不能利用key的特性
为什么使用key属性?这个Vue的虚拟DOM的Diff算法有关。
参考React's diff algorithm
一般来讲,在5个组件数组中插入一个组件,得到新的数组,两个组件数组形成映射关系是非常难的,
默认的,diff算法是把两个数组按顺序形成映射。但是如果你加入key属性,就可以帮助diff快速形成映射。
哪些数组方法是响应式的?
push(); pop(); shift(); unshift(); splice(); sort(); reverse()
用法参考:数组方法的使用
注意:通过索引值修改数组中的元素不是响应式 ,如果要修改元素可以通过splice(),或者使用Vue.set(要修改的对象, 索引值, 修改后的值)
表单绑定
指令:v-model
作用:实现表单元素与数据的双向绑定
基本使用:
<div id="app">
<input type="text" v-model="message">
<h3>{{message}}</h3>
</div>
<script>
const app = new Vue({
el: "#app",
data: {
message: "hello"
},
});
</script>
<!--这里的v-model绑定的就是input的value值-->
相当于:v-bind
和v-on
搭配使用
<div id="app">
<input type="text" :value="message" @input="valueChange">
<h3>{{message}}</h3>
<!--另外写法-->
<input type="text" :value="message" @input="message=$event.target.value">
</div>
<script>
const app = new Vue({
el: "#app",
data: {
message: "hello"
},
methods: {
valueChange (event) {
this.message = event.target.value;
}
}
});
</script>
其他使用:
- radio,单选框,当有 v-model 时,可以省略 name 属性
<div id="app">
<input type="radio" value="男" v-model="sex">男
<input type="radio" value="女" v-model="sex">女
<h3>性别:{{sex}}</h3>
</div>
<script>
const app = new Vue({
el: "#app",
data: {
sex: "男" // 默认值
},
});
</script>
- checkbox,复选框
<!--单选框-->
<div id="app">
<label for="agreement">
<input type="checkbox" id="agreement" v-model="isAgree">用户协议
</label>
<p><button :disabled="!isAgree">Next</button></p>
</div>
<script>
const app = new Vue({
el: "#app",
data: {
isAgree: false
},
});
<!--多选框使用-->
<div id="app">
<input type="checkbox" value="篮球" v-model="hobby">篮球
<input type="checkbox" value="足球" v-model="hobby">足球
<input type="checkbox" value="羽毛球" v-model="hobby">羽毛球
<h2>{{hobby}}</h2>
</div>
<script>
const app = new Vue({
el: "#app",
data: {
hobby: ['篮球']
},
});
</script>
- select
<!--单选-->
<div id="app">
<select name="province" id="" v-model="province">
<option value="安徽">安徽</option>
<option value="江苏">江苏</option>
<option value="上海">上海</option>
</select>
<h2>{{provice}}</h2>
</div>
<script>
const app = new Vue({
el: "#app",
data: {
province: "上海"
},
});
</script>
<!--多选-->
<div id="app">
<select name="province" id="" v-model="provinces" multiple>
<option value="安徽">安徽</option>
<option value="江苏">江苏</option>
<option value="上海">上海</option>
</select>
<h2>{{provice}}</h2>
</div>
<script>
const app = new Vue({
el: "#app",
data: {
provinces: ["上海"]
},
});
</script>
修饰符:
- lazy:可以让数据失去焦点或者回车时才会更新
- number:把输入的内容自动转换成数字类型,和type="number"(只能输入数字)配合使用
- trim:可以过滤内容左右两边的空格
Vue的options之过滤器
<div>{{price|showPrice}}</div>
<script>
const app = new Vue({
el: "#app",
data: {
price: 56.00
},
filters: {
showPrice (price) {
return "¥" + price.toFixed(2) // 显示小数点后2位
}
}
});
</script>
【推荐】FlashTable:表单开发界的极速跑车,让你的开发效率一路狂飙
【推荐】Flutter适配HarmonyOS 5知识地图,实战解析+高频避坑指南
【推荐】博客园的心动:当一群程序员决定开源共建一个真诚相亲平台
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步