10-Vue核心-监视属性

我们通过实现一个天气案例,引出监视属性

<!DOCTYPE html>
<html lang="en">
  <head>
      <meta charset="UTF-8">
      <title>天气案例</title>
      <!--引入Vue-->
      <script type="text/javascript" src="../js/vue.js"></script>
  </head>
  <body>
    <!--准备好一个容器-->
    <div id="root">
        <!--
            三元表达式
            条件表达式?表达式1:表达式2;
            a) 如果条件表达式为true,则运算后的结果是表达式1;
            b) 如果条件表达式为false,则运算后的结果是表达式2;
        -->

        <!--插值语法实现天气案例-->
        <h2>今天天气很{{isHot ? "炎热" : "凉爽"}}</h2>
        <!--计算属性实现天气案例-->
        <h2>今天天气很{{info}}</h2>
        <button @click="changeWeather">切换天气</button>
    </div>

    <script type="text/javascript">
        // 阻止 vue 在启动时生成生产提示
        Vue.config.productionTip = false;

        new Vue({
            el:"#root",
            data(){
                return{
                    isHot:true
                }
            },
            methods:{
                // 切换天气方法
                changeWeather(){
                    this.isHot = !this.isHot
                }
            },
            computed:{
                //计算属性的简写形式
                info(){
                    return this.isHot ? "炎热" : "凉爽"
                }
            }
        })
    </script>
  </body>
</html>

通过上面的天气案例,我们发现,如果能对普通属性 isHot 或者 计算属性 info 进行监视,当被监视的属性发生变化时,则可以进行相应的操作,这也就是我们即将引出的监视属性。

监视属性watch

1) 当被监视的属性发生变化时,handle()回调函数自动调用

2) 监视的属性必须存在,才能进行监视

3) 当监视的属性发生改变时,调用一次handle(newValue,oldValue)回调函数,其中newValue代表改变后的值,oldValue代表改变前的值

4) 配置项属性immediate默认为false,当immediate为true时,则初始化时调用一下handle()回调函数

监视属性的两种写法

1) new Vue 传入watch配置

const vm = new Vue({
            el:"#root",
            data(){
                return{
                    isHot:true
                }
            },
            
            // 1.监视属性的第一种写法
            watch:{
              
                isHot:{
                    //immediate为true时,初始化时调用一下handler()函数
                    immediate:true,

                    // 当属性isHot发生改变时,调用handler()函数
                    handler(newValue, oldValue){
                        console.log("isHot正在被修改...")
                        console.log("修改后的值:" + newValue + "\t修改前的值:" + oldValue) //第一次初始化时,修改后的值:true    修改前的值:undefined
                    }
                }
            }
        })

2) 通过vm实例对象进行监视,vm.$watch()

const vm = new Vue({
            el:"#root",
            data(){
                return{
                    isHot:true
                }
            },       
        })

        // 2.监视属性的第二种写法
        vm.$watch("isHot",{
            //immediate为true时,初始化时调用一下handler()函数
            immediate:true,

            // 当属性isHot发生改变时,调用handler()函数
            handler(newValue, oldValue){
                console.log("isHot正在被修改...")
                console.log("修改后的值:" + newValue + "\t修改前的值:" + oldValue) //第一次初始化时,修改后的值:true    修改前的值:undefined
            }
        })

使用监视属性,完成对天气案例的一些操作

<!DOCTYPE html>
<html lang="en">
  <head>
      <meta charset="UTF-8">
      <title>天气案例_监视属性</title>
      <!--引入Vue-->
      <script type="text/javascript" src="../js/vue.js"></script>
  </head>
  <body>
    <!--准备好一个容器-->
    <div id="root">
        <!--监视属性实现天气案例-->
        <h2>今天天气很{{info}}</h2>
        <button @click="changeWeather">切换天气</button>
    </div>

    <script type="text/javascript">
        // 阻止 vue 在启动时生成生产提示
        Vue.config.productionTip = false;

        const vm = new Vue({
            el:"#root",
            data(){
                return{
                    isHot:true
                }
            },
            methods:{
                // 切换天气方法
                changeWeather(){
                    this.isHot = !this.isHot
                }
            },
            computed:{
                // 计算属性的简写形式
                info(){
                    return this.isHot ? "炎热" : "凉爽"
                }
            },
            // // 1.监视属性的第一种写法
            // watch:{
            //     // 监视普通属性 isHot
            //     isHot:{
            //         //immediate为true时,初始化时调用一下handler()函数
            //         immediate:true,
            //
            //         // 当属性isHot发生改变时,调用handler()函数
            //         handler(newValue, oldValue){
            //             console.log("isHot正在被修改...")
            //             console.log("修改后的值:" + newValue + "\t修改前的值:" + oldValue) //第一次初始化时,修改后的值:true    修改前的值:undefined
            //         }
            //     },
            //     // 也可以监视计算属性 info
            //     info:{
            //         //immediate为true时,初始化时调用一下handler()函数
            //         immediate:true,
            //
            //         // 当计算属性info发生改变时,调用handler()函数
            //         handler(newValue, oldValue){
            //             console.log("info正在被修改...")
            //             console.log("修改后的值:" + newValue + "\t修改前的值:" + oldValue) //第一次初始化时,修改后的值:炎热    修改前的值:undefined
            //         }
            //     }
            // }
        })

        // 2.监视属性的第二种写法
        vm.$watch("isHot",{
            //immediate为true时,初始化时调用一下handler()函数
            immediate:true,

            // 当属性isHot发生改变时,调用handler()函数
            handler(newValue, oldValue){
                console.log("isHot正在被修改...")
                console.log("修改后的值:" + newValue + "\t修改前的值:" + oldValue) //第一次初始化时,修改后的值:true    修改前的值:undefined
            }
        })
    </script>
  </body>
</html>

 

监视属性中多级结构的写法

1) 监视多级结构中某个属性的变化

"属性.xxx": {}

2) 监视多级结构中所有属性的变化\

属性:{} 或 "属性":{}  

const vm=new Vue( {
    el:"#root",
    data() {
        return {
            numbers: {
                a: 10,
                b:20
            }
        }
    }
    ,
    watch: {

        // 监视多级结构中某个属性的变化,一定要用最原始的方法,"属性.xxx":{}
        // 监视普通属性 numbers 里面的 a
        "numbers.a": {
            // immediate为true时,初始化时调用一下handler()函数
            // immediate:true,

            // 当属性isHot发生改变时,调用handler()函数
            handler(newValue, oldValue) {
                console.log("numbers的a正在被修改...") 
console.log("修改后的值:"+ newValue + "\t修改前的值:"+ oldValue) } } , // 监视多级结构中所有属性的变化,可以使用"属性":{},也可以属性:{} numbers: { // 深度监视,deep默认是false,不监测对象内部值的改变 // 也就是说,当deep=false时,numbers里面a或b发生改变时,是不会调用handler()函数,只有当numbers里面的所有属性发生改变,才会调用handler()函数 // 当deep=true时,只要number中的属性发生变化,就会调用handler()函数 deep:true, // immediate为true时,初始化时调用一下handler()函数 // immediate:true, // 当属性isHot发生改变时,调用handler()函数 handler(newValue, oldValue) { console.log("numbers正在被修改...") console.log("a修改后的值:"+ newValue.a + "\ta修改前的值:"+ oldValue.a)
console.log("b修改后的值:"+ newValue.b + "\tb修改前的值:"+ oldValue.b) } } } })

监视属性watch -- 深度监视

1) Vue中的watch默认不监测对象内部值的改变(一层),也就是默认不开启深度监测,deep的默认值为false。

2) 配置深度监测,deep:true可以监测对象内部值改变(多层)。

备注:

1) Vue自身可以监测对象内部值的改变,但Vue提供的watch默认不可以

2) 使用watch时,根据数据的具体结构,决定是否采用深度监视

 

使用监视属性中的深度监视,完成对天气案例的一些操作

<!DOCTYPE html>
<html lang="en">
    <head>
        <meta charset="UTF-8">
        <title>天气案例_深度监视</title>
        <!--引入Vue-->
        <script type="text/javascript" src="../js/vue.js"></script>
    </head>
    <body>
        <!--准备好一个容器-->
        <div id="root">
            <!--监视属性实现天气案例-->
            <h2>今天天气很{{info}}</h2>
            <button @click="changeWeather">切换天气</button>
            <!--分隔符<hr/>-->
            <hr/>
            <h3>a的值:{{numbers.a}}</h3>
            <button @click="numbers.a++">a自增按钮</button>
            <h3>b的值:{{numbers.b}}</h3>
            <button @click="numbers.b++">b自增按钮</button>
            <button @click="numbers = {a:100,b:200}">彻底替换掉numbers</button>
        </div>

        <script type="text/javascript">
            // 阻止 vue 在启动时生成生产提示
            Vue.config.productionTip = false;

            const vm = new Vue({
                el:"#root",
                data(){
                    return{
                        isHot:true,
                        numbers:{
                            a:10,
                            b:20
                        }
                    }
                },
                methods:{
                    // 切换天气方法
                    changeWeather(){
                        this.isHot = !this.isHot
                    }
                },
                computed:{
                    // 计算属性的简写形式
                    info(){
                        return this.isHot ? "炎热" : "凉爽"
                    }
                },
                watch:{
                    // 监视普通属性 isHot
                    isHot:{
                        // immediate为true时,初始化时调用一下handler()函数
                        // immediate:true,

                        // 当属性isHot发生改变时,调用handler()函数
                        handler(newValue, oldValue){
                            console.log("isHot正在被修改...")
                            console.log("修改后的值:" + newValue + "\t修改前的值:" + oldValue)
                        }
                    },
                    // 监视多级结构中某个属性的变化,一定要用最原始的方法,"属性.xxx":{}
                    // 监视普通属性 numbers 里面的 a
                    "numbers.a":{
                        // immediate为true时,初始化时调用一下handler()函数
                        // immediate:true,

                        // 当属性isHot发生改变时,调用handler()函数
                        handler(newValue, oldValue){
                            console.log("numbers的a正在被修改...")
                            console.log("修改后的值:" + newValue + "\t修改前的值:" + oldValue)
                        }
                    },
                    // 监视多级结构中所有属性的变化,可以使用"属性":{},也可以属性:{}
                    numbers:{
                        // 深度监视,deep默认是false,不监测对象内部值的改变
                        // 也就是说,当deep=false时,numbers里面a或b发生改变时,是不会调用handler()函数,只有当numbers里面的所有属性发生改变,才会调用handler()函数
                        // 当deep=true时,只要number中的属性发生变化,就会调用handler()函数
                        deep:true,

                        // immediate为true时,初始化时调用一下handler()函数
                        // immediate:true,

                        // 当属性isHot发生改变时,调用handler()函数
                        handler(newValue, oldValue){
                            console.log("numbers正在被修改...")
                            console.log("a修改后的值:" + newValue.a + "\ta修改前的值:" + oldValue.a)
                            console.log("b修改后的值:" + newValue.b + "\tb修改前的值:" + oldValue.b)
                        }
                    }
                }
            })

        </script>
    </body>
</html>

 

监视属性的简写

如果监视属性,除了handler之外,没有其他的配置项了,可以进行简写

<!DOCTYPE html>
<html lang="en">
    <head>
        <meta charset="UTF-8">
        <title>天气案例_监视属性_简写</title>
        <!--引入Vue-->
        <script type="text/javascript" src="../js/vue.js"></script>
    </head>
    <body>
        <!--准备好一个容器-->
        <div id="root">
            <!--监视属性实现天气案例-->
            <h2>今天天气很{{info}}</h2>
            <button @click="changeWeather">切换天气</button>
        </div>

        <script type="text/javascript">
            // 阻止 vue 在启动时生成生产提示
            Vue.config.productionTip = false;

            const vm = new Vue({
                el:"#root",
                data(){
                    return{
                        isHot:true
                    }
                },
                methods:{
                    // 切换天气方法
                    changeWeather(){
                        this.isHot = !this.isHot
                    }
                },
                computed:{
                    // 计算属性的简写形式
                    info(){
                        return this.isHot ? "炎热" : "凉爽"
                    }
                },
                // 1.监视属性的第一种写法
                watch:{
                    // 正常写法,监视普通属性 isHot
                    // isHot:{
                    //     // immediate为true时,初始化时调用一下handler()函数
                    //     // immediate:true,
                    //
                    //     // 深度监视,deep默认是false,不监测对象内部值的改变
                    //     // deep:true,
                    //
                    //     // 当属性isHot发生改变时,调用handler()函数
                    //     handler(newValue, oldValue){
                    //         console.log("isHot正在被修改...")
                    //         console.log("修改后的值:" + newValue + "\t修改前的值:" + oldValue) //第一次初始化时,修改后的值:true    修改前的值:undefined
                    //     }
                    // },

                    // 简写写法,监视普通属性 isHot
                    // 如果监视属性,除了handler之外,没有其他的配置项了,则可以进行简写
                    // isHot(newValue, oldValue){
                    //     console.log("isHot正在被修改...")
                    //     console.log("修改后的值:" + newValue + "\t修改前的值:" + oldValue) //第一次初始化时,修改后的值:true    修改前的值:undefined
                    // },

                }
            })

            // 2.监视属性的第二种写法
            // 正常写法
            // vm.$watch("isHot",{
            //     //immediate为true时,初始化时调用一下handler()函数
            //     immediate:true,
            //
            //     // 当属性isHot发生改变时,调用handler()函数
            //     handler(newValue, oldValue){
            //         console.log("isHot正在被修改...")
            //         console.log("修改后的值:" + newValue + "\t修改前的值:" + oldValue) //第一次初始化时,修改后的值:true    修改前的值:undefined
            //     }
            // })

            // 简写
            // 注意,一般不写成箭头函数
            vm.$watch("isHot",function (newValue, oldValue){
                console.log("isHot正在被修改...")
                console.log("修改后的值:" + newValue + "\t修改前的值:" + oldValue) //第一次初始化时,修改后的值:true    修改前的值:undefined
            })
        </script>
    </body>
</html>

 

posted @ 2023-09-12 21:31  马铃薯1  阅读(5)  评论(0编辑  收藏  举报