zoukankan      html  css  js  c++  java
  • day83 前端框架--Vue基础&Vue组件

    一,Vue基础补充

      1.获取DOM对象

        给标签加ref属性,ref="xxx"

        this.$refs.xxx

    <body>
    <div id="app">
        <div ref="my_box"></div>
        <button @click="my_click">点击显示文本</button>
    </div>
    <script>
        const app = new Vue({
            el: "#app",
            methods:{
                my_click:function () {
                    // 给div标签加入文本
                    let ele = this.$refs.my_box; // this=>app
                    console.log(ele);
                    ele.innerText = "alex"
                }
            }
        })
    </script>
    </body>

      

      2.Vue对象:计算属性

    <body>
    <div id="app">
        <table>
            <thead>
                <tr>
                    <th>科目</th>
                    <th>成绩</th>
                </tr>
            </thead>
            <tbody>
                <tr>
                    <td>Python</td>
                    <td><input type="text" v-model.number="python"></td>
                </tr>
                <tr>
                    <td>Django</td>
                    <td><input type="text" v-model.number="django"></td>
                </tr>
                <tr>
                    <td>Mysql</td>
                    <td><input type="text" v-model.number="mysql"></td>
                </tr>
                <tr>
                    <td>总分</td>
                    <!--<td>{{python+django+mysql}}</td>-->
                    <td>{{total}}</td>
                </tr>
                <tr>
                    <td>平均分</td>
                    <!--<td>{{(python+django+mysql)/3}}</td>-->
                    <td>{{average}}</td>
                </tr>
    
            </tbody>
        </table>
    </div>
    <script>
        const app = new Vue({
            el: "#app",
            data: {  // 静态属性
                python: "",
                django: "",
                mysql: "",
                // sum: this.python + this.django + this.mysql, // =>sum:nul,不能实时监听数据的变化
            },
            methods: {
    
            },
            computed: {  // 计算属性:将所有数据放入缓存,实时监听数据,当数据改变的时候才会重新渲染,否则一直存在缓存
                total: function () {
                    return this.python + this.django + this.mysql
                },
                average: function () {
                    return this.total()/3
                }
            }
        })
    </script>
    </body>

      3.Vue对象:数据的监听

    watch 监听数据
    
    -- 字符串
        -- 监听到改变新的值和旧的值不同
    
    -- 数组
        -- 只能监听到长度的变化 新旧值相同的
        -- 改变数组的时候监听不到,必须用$set(array,index,value)
            新旧值相同
    
    -- 对象
        -- 只能监听到value的改变 必须深度监听
        -- 增加对象的key 必须用$set(obj,key,value)
        -- 新旧值相同
    <body>
    <div id="app">
        {{name}}
        <br>
        {{hobby}}
        <br>
        {{obj}}
        <button @click="my_click">点我改变数据</button>
    </div>
    <script>
        const app = new Vue({
            el: "#app",
            data: {
                name: "alex",
                hobby: ["抽烟","烫头"],
                obj: {
                    girl: "nezha",
                    age: 36,
                }
            },
            methods: {
                my_click: function () {
                    //修改数据
                    // this.name = "alexdsb";  // 不可变数据类型,重新开辟内存,可以读两块不同的内存
                    // this.hobby.push("腹黑"); // 可变数据类型,会在原内存修改
    
                    // this.hobby[0] = "吸猫";  
                    // console.log(this.hobby);//数据被修改,监听不到数据的变化,深度监听也不行
    
                    app.$set(this.hobby,0,"吸猫"); //修改可变数据类型的专用方法,主动通知浏览器有数据修改,并重新渲染页面
    
                    // this.obj.age = 18; //数据被修改,可以监听到数据的变化
                    // this.obj["sex"] = "女";  //添加数据,监听不到数据的变化,深度监听也不行
                    app.$set(this.obj,"sex","") //修改可变数据类型的专用方法
                }
            },
            watch:{  // 监听器
                name: {
                    handler: function (val,oldval) {  // hander 回调函数
                        console.log(val);
                        console.log(oldval)
                        // 可以做某些操作
                    }
                },
                hobby: { //只能监听数组的长度变化,所有即使值修改了,也不会重新渲染页面
                    handler: function (val,oldval) {
                        // 改变数组的长度的时候新旧值相同
                        console.log(val);
                        console.log(oldval);
                        console.log(this.hobby)
                    },
                    // deep: true  //深度监听
                },
                obj: { //在深度监听的情况,可以监听到value的变化,其他情况监听不了
                    handler: function (val,oldval) {
                        console.log(val);
                        console.log(oldval);
                        console.log(this.obj)
                    },
                    // deep: true
                }
            }
        })
    </script>
    </body>

    二,Vue的组件

      1.组件的全局注册

    Vue.component("组件名称",{
        // 也就是不能同时有两个div
        template:`只识别一个块级作用域`,
        data() {
            return {
                name: xxx
            }
        },
        methods:{},
    })
    -- 任何Vue实例里用<组件名称></组件名称>
    <body>
    <div id="app">
        <my_header></my_header>
    </div>
    <hr>
    <div id="app2">
        <my_header></my_header>
    </div>
    <script>
        //全局注册的组件 可以被在其他根实例的作用域中使用
        Vue.component("my_header",{ // 每一个组件都是vue可复用的实例,但是没有一些根实例的属性
            template:`<div><h1>{{title}}</h1></div>`,
            // template:`<div>{{title}}</div><div>{{title}}</div>`, //只能识别第一个div
    
            data(){ // 对象的单体模式   ==> data function (){}
                return {
                    title:"这是头部",
                }
            },
            methods: {
    
            }
        });
        const app = new Vue({  // 根实例
            el: "#app",
            data: {},
        });
        const app2 = new Vue({
            el: "#app2",
    
        })
    </script>
    </body>

      2.组件的局部注册

    -- let com_config = {......}
    -- const app = new Vue({
        el: "#app",
        components: {
            组件名称: com_fig
        }
    })
    -- <div><组件名称></组件名称></div>
    <body>
    <div id="app">
        <div><my_com></my_com></div>
    
    </div>
    <div id="app2">
        <my_com></my_com>
    </div>
    
    <script>
        let my_com_config = {
            template: `<div><h1>这是局部组件</h1></div>`,
        };
        const app = new Vue({
            el: "#app",
            data: {},
            components: {
                my_com: my_com_config
            },
        });
        const app2 = new Vue({
            el: "#app2",
            data: {},
            components: {
                my_com: my_com_config
            },
        })
    </script>
    </body>

      3.子组件的注册

    -- 在父组件里 components: {
        子组件的名称: 子组件的配置信息
    }
    -- 在父组件的template里展示子组件
        <child></child>
    <body>
    <div id="app">
        <my_com></my_com>
    </div>
    
    <script>
        let child_config = {
            template: `<div><h2>这是一个子组件</h2></div>`
        };
        let my_com_config = {
            template: `<div>
                        <child></child>
                        <h1>这是一个组件</h1>
                        <child></child>
                        </div>`,//子组件只识别一个作用域块
            components: {
                child:child_config
            }
        };
        const app = new Vue({
            el: "#app",
            data: {},
            components: {
                my_com: my_com_config
            }
        });
    
    </script>
    </body>

      4.父子组件的通信

        先给子组件绑定属性

        在子组件通过props:["属性名称"]

    <body>
    <div id="app">
        <my_com></my_com>
    </div>
    <script>
        let child_config = {
            template: `<div>
                        <h2>这是一个子组件</h2>
                        <p>父亲跟你们说~~{{father_say}}}</p>
                        </div>`,
            props: ["father_say",]  //父子通信桥梁
        };
        let my_com_config = {
            template: `<div>
                        <h1>这是一个组件</h1>
                        <child :father_say="f_say"></child>  //子组件值识别一个作用域块
                        </div>`,    // f_say不能直接传字符串
            components: {
                child:child_config
            },
            data(){  //对象的单体模式
                return {
                    f_say: "滚~~~"
                }
            }
        };
        const app = new Vue({
            el: "#app",
            data: {},
            components: {
                my_com: my_com_config
            }
        })
    </script>
    </body>

      

      5.子父组件的通信

        子组件先提交数据:this.$emit("事件名称",data)

        父组件,给子组件绑定事件:自己处理这个事件

    <body>
    <div id="app">
        <my_com></my_com>
    </div>
    <script>
        let child_config = {
            template: `<div>
                        <h2>这是一个子组件</h2>
                        <button @click="my_click">点击向父亲说话</button>
                        </div>`,
            methods: {
                my_click() {
                    //向父亲说话
                    //子组件提交事件
                    this.$emit("son_say","父皇,儿臣有事启奏");
    // 组件就是一个Vue实例,并且this就是指本身这个组件,但是this同时包含Vue根实例的属性
    } }, }; let my_com_config = {//子组件值识别一个作用域块 template: `<div> <h1>这是一个组件</h1> <child @son_say="my_son_say"></child> <p>儿子给我说~~{{s_say}}</p> </div>`, components: { child:child_config }, methods: { my_son_say:function (data) { //这里需要接收参数,标签中可以不接受参数 this.s_say = data; //修改数据 } }, data(){ //对象的单体模式 return { s_say: "" } } }; const app = new Vue({ el: "#app", data: {}, components: { my_com: my_com_config, } }) </script> </body>

      6.非父子组件通信

        定义一个中间调度器:let Event = new Vue();

        其中一个组件向中间调度器提交事件:Event.$emit("事件名称",data)

        另一个组件要监听中间调度器的时间:Event.$on("事件的名称",function(data) { })

    <body>
    <div id="app">
        <com1></com1>
        <com2></com2>
    </div>
    <script>
        let Event = new Vue(); // 充当中间调度器
    
        let com1_config = {
            template: `<div>
                        <h1>这是com1</h1>
                        <button @click="my_click">点击给com2打电话</button>
                        </div>`,
            methods:{
                my_click(){
                    //给com2打电话,今晚等我
                    // 向Event提交事件
                    Event.$emit("call","今晚等我~~")
                }
            }
        };
         let com2_config = {
             template: `<div>
                        <h1>这是com2</h1>
                        <p>com1跟我说~{{com1_say}}</p>
                        </div>`,
             data(){
               return{
                   com1_say: ""
               }
             },
             mounted() {
                 // 组件加载完成后,执行的方法
                 // 监听Event的事件
                 let that = this;
                 Event.$on("call",function (data) {
                     console.log(data);
                     that.com1_say = data
                     // 当前的this => Event
                 })
             }
    
        };
        const app = new Vue({
            el: "#app",
            data: {},
            components: {
                com1: com1_config,
                com2: com2_config,
            }
        })
    </script>
    </body>

      7.混合

        复用共用的代码块:mixins:[base]

    <body>
    <div id="app">
    
    <com1></com1>
    <com2></com2>
    </div>
    <script>
        let base ={
            data() {
                return {
                    is_show: false
                }
            },
            methods:{
                show_text(){
                    this.is_show = true
                },
                hide_text(){
                    this.is_show = false
                }
            }
        };
    
        let com1 = {
            template:`<div>
                    <button @click="show_text">点击显示文本</button>
                    <button @click="hide_text">点击隐藏文本</button>
                    <div v-show="is_show">点我</div>
                    </div>`,
            mixins:[base],
            data() {  //可以重写base的data,以设置is_show的值
                return {
                    is_show: true
                }
            },
        };
    
        let com2 = {
            template:`<div>
                     <button @mouseenter="show_text" @mouseleave="hide_text">提示框</button>
                    <div v-show="is_show">点我</div>
                    </div>`,
            mixins:[base],
        };
        const app = new Vue({
            el: "#app",
            components:{
                com1:com1,
                com2:com2
            },
        })
    </script>
    </body>

      8.插槽 

        实现组件内容的分发:

          slot:

            直接用slot标签

          命名的slot:

            先给slot加name属性

            给标签元素添加slot属性 = name属性值   

    <body>
    <div id="app">
        <com>
            <!--<solt></solt>-->
            <h3 slot="title">python</h3>
            <p slot="brief">从入门到放弃</p>
        </com>
        <com>
            <h3 slot="title">Mysql</h3>
            <p slot="brief">从删库到跑路</p>
        </com>
    </div>
    
    <template id="my_com">
        <div>
            <h1>这是一个组件</h1>
            <hr>
            <!--<slot></slot>-->
            <slot name="title"></slot>
            <slot name="brief"></slot>
        </div>
    </template>
    
    <script>
        let com = {
            template:"#my_com"
        };
        const app = new Vue({
            el: "#app",
            data: {},
            components:{
                com:com,
            }
        })
    </script>
    </body>

            

        

  • 相关阅读:
    【SCOI 2011】 糖果
    【POJ 3159】 Candies
    【POJ 1716】 Integer Intervals
    【POJ 2983】 Is the information reliable?
    【POJ 1364】 King
    【POJ 1201】 Intervals
    【POJ 1804】 Brainman
    6月10日省中提高组题解
    【POJ 3352】 Road Construction
    【POJ 1144】 Network
  • 原文地址:https://www.cnblogs.com/lianyeah/p/10065385.html
Copyright © 2011-2022 走看看