vue之事件处理、双向绑定、表单控制、v-model进阶、购物车案例
目录
事件处理
事件 | 释义 |
---|---|
input | 当输入框进行输入的时候 触发的事件 |
change | 当元素的值发生改变时 触发的事件 |
blur | 当输入框失去焦点的时候 触发的事件 |
change 和 blur 最本质的区别:
如果输入框为空,失去焦点后,change不会触发,但是blur会触发
过滤案例
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>过滤案例</title>
<script src="https://cdn.bootcdn.net/ajax/libs/vue/2.6.12/vue.min.js"></script>
</head>
<body>
<div id="box">
<p><input type="text" v-model="myText" @input="handleInput" placeholder="请输入要筛选的内容:"></p>
<ul>
<li v-for="data in newList">{{data}}</li>
</ul>
</div>
</body>
<script>
var vm = new Vue({
el: '#box',
data: {
myText: '',
dataList: ['a', 'at', 'atom', 'be', 'beyond', 'cs', 'csrf'],
newList: ['a', 'at', 'atom', 'be', 'beyond', 'cs', 'csrf'],
},
methods: {
handleInput() {
this.newList = this.dataList.filter(item => {
// item.indexOf(this.myText):输入框中输入的字符串在筛选元素中的索引
return item.indexOf(this.myText) > -1 // 返回索引大于1的元素:>-1 就表示包含在其中
})
},
},
})
</script>
</html>
事件修饰符
事件修饰符 | 释义 |
---|---|
.stop | 只处理自己的事件,父控件冒泡的事件不处理(阻止事件冒泡) |
.self | 只处理自己的事件,子控件冒泡的事件不处理 |
.prevent | 阻止a链接的跳转 |
.once | 事件只会触发一次(适用于抽奖页面) |
使用修饰符时,顺序很重要;相应的代码会以同样的顺序产生
用 v-on:click.prevent.self 会阻止所有的点击
而 v-on:click.self.prevent 只会阻止对元素自身的点击
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>第二天</title>
<script src="js/vue.js"></script>
</head>
<body>
<div id="div_id">
<div @click.self="divFunc" style="background-color: red;height: 100px">
<hr>
<p @click="pFunc" style="background-color: green;height: 50px"></p>
</div>
<p><a href="https://www.baidu.com" @click.prevent="aFunc">点我有你好看</a></p>
<p><button @click.once="onceFunc">秒杀速来!!!</button></p>
</div>
<script>
let vm = new Vue({
el:'#div_id',
data:{},
methods:{
pFunc(){
alert('p标签的冒泡')
},
divFunc(){
alert('div标签的冒泡')
},
aFunc(){
// 最后跳的是这个页面而不是a标签内的百度页面
location.href = 'https://www.sougou.com'
},
// 点击事件只能触发一次
onceFunc(){
alert(111)
}
}
})
</script>
</body>
</html>
按键修饰符
就是按对应的按键松开时会触发事件。例如按enter键触发事件,按q键触发事件。
注意: 在事件触发时会自动把按键对象当作参数传入
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>第二天</title>
<!-- <script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.4.1/jquery.min.js"></script>-->
<!-- <link href="https://cdn.bootcdn.net/ajax/libs/twitter-bootstrap/3.4.1/css/bootstrap.min.css" rel="stylesheet">-->
<!-- <script src="https://cdn.bootcdn.net/ajax/libs/twitter-bootstrap/3.4.1/js/bootstrap.min.js"></script>-->
<script src="js/vue.js"></script>
</head>
<body>
<div id="div_id">
<input type="text" @keyup="keyFunc($event)">
<p><input type="text" @keyup.enter="keyEnter($event)"></p>
</div>
<script>
let vm = new Vue({
el:'#div_id',
methods:{
keyFunc(event){
alert(event.key)
},
keyEnter(event){
alert(event.key)
}
}
})
</script>
</body>
</html>
数据双向绑定
v-model的使用
实现在input框输入内容实时传给v-model绑定的变量名的值,这样就能实时获取用户输入的内容
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Title</title>
<script src="https://cdn.bootcdn.net/ajax/libs/vue/2.6.12/vue.min.js"></script>
</head>
<body>
<div id="box">
<input type="text" v-model="myText" placeholder="请输入内容">
您输入的内容是:{{myText}}
</div>
</body>
<script>
var vm = new Vue({
el: '#box',
data: {
myText: '',
},
})
</script>
</html>
表单控制
属性 | 结果 |
---|---|
checkbox | 单选时是true或false,多选时是数组 |
radio | 结果是对应的value值 |
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>第二天</title>
<script src="js/vue.js"></script>
</head>
<body>
<div id="div_id">
<p>username: <input type="text" v-model="username">----->{{username}}</p>
<p>password: <input type="password" v-model="password">----->{{password}}</p>
<p>记住密码: <input type="checkbox" v-model="remember">----->{{remember}}</p>
<p>单选: <input type="radio" v-model="choice_one" value="男">男
<input type="radio" v-model="choice_one" value="女">女
<input type="radio" v-model="choice_one" value="其他">其他----->{{choice_one}}
</p>
<p>多选: <input type="checkbox" v-model="choice_many" value="篮球">篮球
<input type="checkbox" v-model="choice_many" value="足球">足球
<input type="checkbox" v-model="choice_many" value="排球">排球----->{{choice_many}}
</p>
</div>
<script>
let vm = new Vue({
el:'#div_id',
data:{
username:'',
password:'',
remember:true,
choice_one:'',
choice_many:[],
},
})
</script>
</body>
</html>
v-model进阶
v-model 之 lazy、number、trim
lazy:等待input框的数据绑定时区焦点之后再变化
number:数字开头,只保留数字,后面的字母不保留;字母开头,都保留
trim:去除首位的空格
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>第二天</title>
<script src="js/vue.js"></script>
</head>
<body>
<div id="div_id">
<p><input type="text" v-model="normal" placeholder="normal">--->{{normal}}</p>
<p><input type="text" v-model.lazy="lazy" placeholder="lazy">--->{{lazy}}</p>
<p><input type="text" v-model.number="number" placeholder="number">--->{{number}}</p>
<p><input type="text" v-model.trim="trim" placeholder="trim">--->{{trim}}</p>
</div>
<script>
let vm = new Vue({
el:'#div_id',
data:{
normal:'',
lazy:'',
number:'',
trim:'',
}
})
</script>
</body>
</html>
购物车案例
购物车案例 - 结算
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>购物车结算</title>
<script src="https://cdn.bootcdn.net/ajax/libs/vue/2.6.12/vue.min.js"></script>
<style>
table, td {
border: 1px solid black;
text-align: center;
}
</style>
</head>
<body>
<div id="box">
<table>
<tr>
<td>商品名称</td>
<td>价格</td>
<td>数量</td>
<td>选择</td>
</tr>
<tr v-for="item in dataList">
<td>{{item.name}}</td>
<td>{{item.price}}</td>
<td>{{item.number}}</td>
<td><input type="checkbox" :value="item" v-model="checkGroup"></td>
</tr>
</table>
<br>已选商品:{{checkGroup}}
<br>总价:{{getPrice()}}
</div>
</body>
<script>
var vm = new Vue({
el: '#box',
data: {
dataList: [
{name: '今瓶没', price: 99, number: 2},
{name: '西柚记', price: 59, number: 1},
{name: '水壶转', price: 89, number: 5},
],
checkGroup: [],
},
methods: {
getPrice() {
let sum_price = 0
for (i in this.checkGroup) { // 这里的 i 是索引
sum_price += this.checkGroup[i]['number'] * this.checkGroup[i]['price']
}
return sum_price
}
}
})
</script>
</html>
购物车案例 - 全选/全不选
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>全选/全不选</title>
<script src="https://cdn.bootcdn.net/ajax/libs/vue/2.6.12/vue.min.js"></script>
<style>
table, td {
border: 1px solid black;
text-align: center;
}
</style>
</head>
<body>
<div id="box">
<table>
<tr>
<td>商品名称</td>
<td>价格</td>
<td>数量</td>
<td>全选/全不选<input type="checkbox" v-model="allChecked" @change="checkAll"></td>
</tr>
<tr v-for="item in dataList">
<td>{{item.name}}</td>
<td>{{item.price}}</td>
<td>{{item.number}}</td>
<td><input type="checkbox" :value="item" v-model="checkGroup" @change="checkOne"></td>
</tr>
</table>
<br>已选商品:{{checkGroup}}
<br>总价:{{getPrice()}}
</div>
</body>
<script>
var vm = new Vue({
el: '#box',
data: {
dataList: [
{name: '今瓶没', price: 99, number: 2},
{name: '西柚记', price: 59, number: 1},
{name: '水壶转', price: 89, number: 5},
],
checkGroup: [],
allChecked: false,
},
methods: {
getPrice() {
let sum_price = 0
for (i in this.checkGroup) { // 这里的 i 是索引
sum_price += this.checkGroup[i]['number'] * this.checkGroup[i]['price']
}
return sum_price
},
checkAll() {
if (this.checkGroup.length > 0) {
this.checkGroup = []
} else {
this.checkGroup = this.dataList
}
},
checkOne() {
if (this.checkGroup.length === this.dataList.length) {
this.allChecked = true
} else {
this.allChecked = false
}
}
}
})
</script>
</html>
购物车案例 - 数量加减
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>控制加减</title>
<script src="https://cdn.bootcdn.net/ajax/libs/vue/2.6.12/vue.min.js"></script>
<link href="https://cdn.bootcdn.net/ajax/libs/twitter-bootstrap/4.5.3/css/bootstrap.min.css" rel="stylesheet">
</head>
<body>
<div class="row">
<div id="box" class="col-md-4 offset-md-1 text-center mt-5 ">
<table class="table table-bordered">
<thead>
<tr>
<th scope="col">商品名称</th>
<th scope="col">单价</th>
<th scope="col">数量</th>
<th scope="col">全选/全不选 <input type="checkbox" v-model="allChecked" @change="checkAll"></th>
</tr>
</thead>
<tbody>
<tr v-for="item in dataList">
<td>{{item.name}}</td>
<td>{{item.price}}</td>
<td>
<button class="btn link btn-sm" @click="reduceNum(item)">-</button>
{{item.number}}
<button class="btn link btn-sm" @click="item.number++">+</button>
</td>
<td><input type="checkbox" :value="item" v-model="checkGroup" @change="checkOne"></td>
</tr>
<tr class="text-left">
<td colspan="4">总价:{{getPrice()}}
</tr>
</tbody>
</table>
</div>
</div>
</body>
<script>
var vm = new Vue({
el: '#box',
data: {
dataList: [
{name: '今瓶没', price: 99, number: 1},
{name: '西柚记', price: 59, number: 1},
{name: '水壶转', price: 89, number: 1},
],
checkGroup: [],
allChecked: false,
},
methods: {
getPrice() {
let sum_price = 0
for (i in this.checkGroup) {
sum_price += this.checkGroup[i]['number'] * this.checkGroup[i]['price']
}
return sum_price
},
checkAll() {
if (this.checkGroup.length > 0) {
this.checkGroup = []
} else {
this.checkGroup = this.dataList
}
},
checkOne() {
// if (this.checkGroup.length === this.dataList.length) {
// this.allChecked = true
// } else {
// this.allChecked = false
// }
this.allChecked = this.checkGroup.length === this.dataList.length;
},
reduceNum(item) {
if (item.number === 1) {
item.number = 1
} else {
item.number--
}
}
}
})
</script>
</html>