目录
- 条件渲染
- v-if
- v-show
- 列表渲染
- 关于:key
- 列表过滤
- watch属性实现
- computed属性
- 列表排序
- 表单数据收集
- input是否配置value属性
- 过滤器
本博客参考尚硅谷官方课程,详细请参考
- 【尚硅谷bilibili官方】
本博客以vue2作为学习目标(请勿混淆v2与v3的代码规范,否则可能出现报错),详细教程请参考
- 【 v2.x 官方文档】
条件渲染
v-if
- v-if=“表达式”
- v-else-if=“表达式”
- v-else=“表达式”
使用示例
<!--html代码-->
<div id="root">
<div>list=[1,2,3],num={{num}}</div>
<button @click="change_num">点我num+1</button>
<div v-if="num === 1">num={{num}}</div>
<div v-else-if="num === 2">num={{num}}</div>
<div v-else-if="num === 3">num={{num}}</div>
<div v-else>num not in list</div>
</div>
<!--js代码-->
<script>
//js代码
const vm = new Vue({
el: "#root",
data: {
name: "数字计算",
num: 0,
},
methods: {
change_num() {
this.num++;
console.log(this.num);
},
},
});
</script>
效果
注意:
- v-if可以和:v-else-if、v-else一起使用,但要求结构不能被“打断”。
- 特点:不展示的DOM元素直接被移除,使用v-if的时,元素可能无法获取到,而使用v-show一定可以获取到。
- 适用于:切换频率较低的场景。
- 常常使用<template></template>标签来包裹DOM元素,这样做可以不影响html结构,但不能与v-show结合使用
v-show
v-show=“表达式”
- 不展示的DOM元素未被移除,仅仅是使用样式隐藏掉
- 切换频率较高的场景。
使用示例
<!--html代码-->
<div id="root">
<!--使用v-show做条件渲染 -->
<button @click="change_num">点我num+1</button>
<h2 v-show="is_show">此时num的值为{{num}},显示</h2>
</div>
<!--js部分代码-->
<script>
const vm = new Vue({
el: "#root",
data: {
name: "条件渲染测试内容",
num: 1,
},
computed: {
//计算num是否能整除2
is_show() {
return this.num % 2 === 0 ? true : false;
},
},
methods: {
//函数每次点击按钮触发,使num值加1
change_num() {
this.num++;
console.log(this.num);
},
},
});
</script>
效果
列表渲染
示例
<!--html代码-->
<div id="root">
<!-- 遍历数组 -->
<h5>数组部分</h5>
<ul>
<li v-for="(info,index) in list1" :key="index">
{{info.id}}--{{info.name}}
</li>
</ul>
<!-- 遍历对象 -->
<h5>对象部分</h5>
<ul>
<li v-for="(value,key) in obj1" :key="key">{{key}}--{{value}}</li>
</ul>
<!-- 遍历字符串 -->
<h5>字符串部分</h5>
<ul>
<li v-for="(char,index) in str1" :key="index">{{char}}--{{index}}</li>
</ul>
</div>
<!--js代码-->
<script>
const vm = new Vue({
el: "#root",
data: {
list1: [
{ id: "001", name: "张三" },
{ id: "002", name: "李四" },
{ id: "003", name: "王五" },
],
obj1: {
name: "车站",
address: "北京",
},
str1: "where is your home?",
},
});
</script>
效果
- v-for指令用于展示列表数据
- 语法:v-for=“(item,index) in list” :key=“”
- 可以进行数组、对象、字符串等遍历
关于:key
- 虚拟DOM中key作为虚拟DOM对象的标识,当对象中的数据发生变化时,Vue根据新数据生成新的虚拟DOM,再由对比算法比较其出与旧的虚拟DOM的差异,最终完成DOM的更新
- vue默认使用index作为key值,但是使用index作为key可能出现下面问题:1. 对数据进行逆序添加、删除等破坏顺序的操作时会产生没有必要的真实DOM更新。2. 若结构中还有输入类DOM将会产生错误的DOM更新
- 应尽量选用每条数据的唯一标识如id、手机号、身份证号等作为key
虚拟DOM对比规则?
- 若新旧虚拟DOM有相同的key。内容不变则直接使用之前的真实DOM,内容改变则生成新的真实DOM随后替换掉页面中之前的真实DOM
- 若在旧的虚拟DOM中没有找到key。创建新的虚拟DOM随后渲染到页面中
列表过滤
效果
html代码
<div id="root">
<h2>人员列表</h2>
<input type="text" v-model="keyWord" />
<ul>
<li v-for="(person,index) in filperson" :key="index">
{{person.name}}--{{person.age}}--{{person.sex}}
</li>
</ul>
</div>
watch属性实现
<script>
new Vue({
el: "#root",
data: {
keyWord: "",
persons: [
{ name: "张三", age: 18, sex: "男" },
{ name: "张四丰", age: 18, sex: "男" },
{ name: "李三", age: 21, sex: "女" },
{ name: "李四水", age: 22, sex: "女" },
],
filperson: [],
},
//watch实现
watch: {
//简写方式:初始进入界面时不会执行,不会显示列表
//关键点:不要修改原数组
// keyWord(val){
// this.filperson = this.persons.filter((p) => {
// return p.name.indexOf(val) !== -1;
// }
keyWord: {
//关键点:indexOf()函数默认空字符串在每个字符串的头部,返回index=0
immediate: true,
handler(val) {
this.filperson = this.persons.filter((p) => {
return p.name.indexOf(val) !== -1;
});
},
},
},
});
</script>
computed属性
<script>
new Vue({
el: "#root",
data: {
keyWord: "",
persons: [
{ name: "张三", age: 18, sex: "男" },
{ name: "张四丰", age: 18, sex: "男" },
{ name: "李三", age: 21, sex: "女" },
{ name: "李四水", age: 22, sex: "女" },
],
},
computed: {
filperson() {
return this.persons.filter((p) => {
return p.name.indexOf(this.keyWord) !== -1;
});
},
},
});
</script>
列表排序
效果
<div id="root">
<h2>人员列表</h2>
<input type="text" v-model="keyWord" />
<button v-on:click="sortKey=2">升序</button>
<button v-on:click="sortKey=1">降序</button>
<button v-on:click="sortKey=0">原顺序</button>
<ul>
<li v-for="(person,index) in filperson" :key="index">
{{person.name}}--{{person.age}}--{{person.sex}}
</li>
</ul>
</div>
<script>
new Vue({
el: "#root",
data: {
keyWord: "",
sortKey: 0,
persons: [
{ name: "张三", age: 18, sex: "男" },
{ name: "张四丰", age: 18, sex: "男" },
{ name: "李三", age: 21, sex: "女" },
{ name: "李四水", age: 22, sex: "女" },
],
},
computed: {
filperson() {
let arr = this.persons.filter((p) => {
return p.name.indexOf(this.keyWord) !== -1;
});
if (this.sortKey) {
arr.sort((p1, p2) => {
return this.sortKey === 1 ? p2.age - p1.age : p1.age - p2.age;
});
}
return arr;
},
},
});
</script>
表单数据收集
<!--html代码-->
<div id="root">
<form @submit.prevent="demo">
账号:<input type="text" v-model.trim="userInfo.account"> <br/><br/>
密码:<input type="password" v-model="userInfo.password"> <br/><br/>
年龄:<input type="number" v-model.number="userInfo.age"> <br/><br/>
性别:
男<input type="radio" name="sex" v-model="userInfo.sex" value="male">
女<input type="radio" name="sex" v-model="userInfo.sex" value="female"> <br/><br/>
爱好:
学习<input type="checkbox" v-model="userInfo.hobby" value="study">
打游戏<input type="checkbox" v-model="userInfo.hobby" value="game">
吃饭<input type="checkbox" v-model="userInfo.hobby" value="eat">
<br/><br/>
所属校区
<select v-model="userInfo.city">
<option value="">请选择校区</option>
<option value="beijing">北京</option>
<option value="shanghai">上海</option>
<option value="shenzhen">深圳</option>
<option value="wuhan">武汉</option>
</select><br/><br/>
其他信息:
<textarea v-model.lazy="userInfo.other"></textarea> <br/><br/>
<input type="checkbox" v-model="userInfo.agree">阅读并接受<a href="http://www.atguigu.com">《用户协议》</a>
<button>提交</button>
</form>
</div>
</body>
v-model的三个修饰符:
- lazy:失去焦点再收集数据
- number:输入字符串转为有效的数字
- trim:输入首尾空格过滤
//js代码
new Vue({
el:'#root',
data:{
userInfo:{
account:'',
password:'',
age:18,
sex:'female',
hobby:[],
city:'beijing',
other:'',
agree:''
}
},
methods: {
demo(){
console.log(JSON.stringify(this.userInfo))
}
}
})
浏览器运行结果
输出值
收集表单数据
标签 | 描述 | |
---|---|---|
文本框 | <input type=“text”/> | v-model将会收集value值,用户输入的就是value值。 |
单选框 | <input type=“radio”/> | v-model将会收集value值,且要给标签配置value值。 |
多选框 | <input type=“checkbox”/> |
input是否配置value属性
否
收集的就是checked(勾选 or 未勾选,是布尔值)
是
(1)当v-model的初始值是非数组时,收集的是checked(勾选 or 未勾选,是布尔值)
(2)当v-model的初始值是数组时,收集的是value组成的数组。
过滤器
- 作用:对数据进行特定的格式化后再进行显示
- 注册:Vue.filter(name,callback)或者new Vue({filter:{}})
- 使用:插值语法或数据绑定
- 注意:过滤器可以接受额外参数,多个过滤器可以进行串联
示例
<!--html代码-->
<div id="root">
<!-- 不带参数 -->
<h5>当前时间:{{time|timeFormatter}}</h5>
<!-- 带有参数 -->
<h5>当前时间:{{time|timeFormatter('YYYY')}}</h5>
<!-- 多个过滤器 -->
<h5>当前时间:{{time|timeFormatter('YYYY-MM-DD HH-mm-ss')|filter2}}</h5>
</div>
<!--js代码-->
<script>
//全局过滤器
Vue.filter("filter2", function (value) {
return value.slice(0, 4);
});
var vm = new Vue({
el: "#root",
data: {
time: Date.now(),
str1: "dangerous",
},
//局部过滤器
filters: {
timeFormatter(value, str = "YYYY-MM-DD") {
return dayjs(value).format(str);
},
},
});
</script>
效果