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>

image

事件修饰符

事件修饰符 释义
.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>

image

按键修饰符

就是按对应的按键松开时会触发事件。例如按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>

image

数据双向绑定

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>

image

表单控制

属性 结果
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>

image

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>

image

购物车案例

购物车案例 - 结算

<!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>

image

购物车案例 - 全选/全不选

<!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>

image

购物车案例 - 数量加减

<!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>

image

posted @ 2022-05-03 14:47  zong涵  阅读(68)  评论(0编辑  收藏  举报