零基础学习Vue: 第31课 Vue子组件实现学生管理系统小案例:

效果图如下:

在这里插入图片描述

以下是实现代码:

<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Title</title>
<!-- 引入vue -->
<script src="https://cdn.jsdelivr.net/npm/vue/dist/vue.js"></script>
<!-- 引入bootstrap内定义好的css样式 -->
<link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/[email protected]/dist/css/bootstrap.min.css">
<style>
    *{margin:0;padding:0;}
    #app{
        width:800px;
        margin:50px auto;
    }
    .active {
        background-color: #f5f5f5
    }
    .mask {
        position: fixed;
        left: 0;
        top: 0;
        width: 100%;
        height: 100%;
        background: rgba(0, 0, 0, .35);
    }
    .mask .dialog {
        position: absolute;
        width: 400px;
        height: 200px;
        left: 0;
        right: 0;
        top: 50px;
        margin: auto;
    }
</style>
</head>
<body>

    <!-- vue根组件 -->
<div id="app">
    <add @add="add" @deletes="deletes"></add>
    <!-- :students="students"向子组件传递数据students -->
    <!-- 当students.length数据有长度时显示学生消息列表 -->
    <tablelist :students="students" v-show="students.length" @show="show"></tablelist>
    <!-- 显示弹窗效果 -->
    <hide v-if="isShow" @close="close"></hide>
</div>


<!--添加学生信息add子组件-->
<template id="add">
    <form>
        <div class="form-group">
            <label for="exampleInputEmail1" class='h4'>学生姓名</label>
            <!-- v-model='username':输入的数据与根主件data内的username绑定 -->
            <input type="text" v-model='username' class="form-control" id="exampleInputEmail1" placeholder="请输入学生姓名" v-model='username'>
        </div>
        <div class="form-group">
            <label for="exampleInputPassword1" class='h4'>联系方式</label>
            <!-- v-model='phone':输入的数据与根主件data内的phone绑定 -->
            <input type="text"  v-model='phone' class="form-control" id="exampleInputPassword1" placeholder="请输入联系方式" v-model='phone'>
        </div>
        <!-- @click.prevent阻止默认提交事件 -->
        <button type="submit" class="btn btn-default" @click.prevent="add">添加学生</button>
        <button type="submit" class="btn btn-default" @click.prevent="deletes">删除选中的学生</button>
    </form>
</template>

<!--显示学生信息列表tablelist子组件-->
<template id='tablelist'>
    <div>
        <table class='table table-hover'>
            <caption class='h3'>学生信息表</caption>
            <tr>
                <td>选择</td>
                <td>学生姓名</td>
                <td>联系方式</td>
                <td>删除</td>
            </tr>
            <!-- 遍历父组件传递过来的学生数据students -->
            <tr v-for="(student,index) in students">
                <td>
                    <input type="checkbox" v-model="student.isSelected">
                </td>
                <td>{{student.username}}</td>
                <td>{{student.phone}}</td>
                <td>
                    <!-- 点击删除按钮触发fn     index:点击的学生信息下标 -->
                    <button class='btn btn-danger btn-xs glyphicon glyphicon-trash' @click="fn(index)"></button>
                </td>
            </tr>
        </table>
    </div>
</template>

<!--弹出子组件-->
<template id='hide'>
    <div class='mask'>
        <div class="dialog">
            <div tabindex="-1" role="dialog" aria-labelledby="gridSystemModalLabel">
                <div class="modal-dialog" role="document">
                    <div class="modal-content">
                        <div class="modal-header">
                            <button type="button" class="close" data-dismiss="modal" aria-label="Close"><span
                                    aria-hidden="true">&times;</span></button>
                            <h4 class="modal-title" id="gridSystemModalLabel">你确定要删除吗</h4>
                        </div>

                        <div class="modal-footer">
                            <button type="button" class="btn btn-default" data-dismiss="modal" @click="cancel">取消</button>
                            <button type="button" class="btn btn-primary" @click="confirm">确定</button>
                        </div>
                    </div><!-- /.modal-content -->
                </div><!-- /.modal-dialog -->
            </div><!-- /.modal -->
        </div>
    </div>
</template>

<script>

    //定义学生消息添加子组件
    let add = {
        template:'#add',
        data() {
            return {
                username: '',
                phone: '',
            }
        },
        methods:{
            add(){  //子组件的数据传递给父组件
                //当有一项没有输入值时跳出
                if( !this.username || !this.phone )return;
                //触发事件父组件add事件
                this.$emit('add',this.username,this.phone);

                this.username = '';
                this.phone = '';
            },
            deletes(){
                this.$emit('deletes');
            }
        }
    }

    //定义学生列表子组件
    let tablelist = {
        props:['students'],     //接收父组件传递的数据
        template:'#tablelist',
        methods:{
            fn(index){
                //触发事件show,传递参数index
                this.$emit('show',index)
            }
        }
    }

    let hide = {
        template:'#hide',
        methods:{
            cancel(){       //点击取消按钮
                this.$emit('close',false)
            },
            confirm(){      //点击确认按钮
                this.$emit('close',true)
            }
        }
    }
    let vm = new Vue({
        el:'#app',
        data:{
            students:[],    //使用学生数据储存位置
            isShow:false,   //设置弹窗 显示/隐藏 状态
            num:'', //计入删除的学生下标
        },
        components:{    //注册子组件
            add,
            tablelist,
            hide
        },
        methods:{
            add(username,phone){
                //添加数据
                this.students.push({
                    username,
                    phone,
                    isSelected:false
                })
            },
            deletes(){
                //for循环遍历删除
                for(let i=this.students.length-1; i>=0; i--){
                    if(this.students[i].isSelected){
                        this.students.splice(i,1)
                    }
                }
            },
            show(index){
                this.num = index;   //计入删除的学生下标
                this.isShow = true; //显示弹窗
            },
            close(bool){
                this.isShow = false
                if(bool){       //如果点击确定  那就删除对应的学生信息
                    this.students.splice(this.num,1)
                }
            }
        },
        watch:{ //事件监听
            students:{  //监听data中的students数组
                handler(){  //值改变触发
                    //在本地存储数据
                    console.log('数据改变了  我监控到了')
                    localStorage.setItem('heaven',JSON.stringify(this.students))    //存储缓存
                },
                deep:true,  //深度监视
            }
        },
        created(){  //生命周期函数 获取本地存储的数据
            this.students = JSON.parse(localStorage.getItem('heaven'))||[]; //提取缓存
        }
    })
</script>
</body>
</html>

猜你喜欢

转载自blog.csdn.net/qq_41614928/article/details/89499135
今日推荐