学习Vue第一章Vue核心

一:Vue核心:

多个单词用-分开 在Vue中 用’'引用起来

1.初始化vue

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
        
    <script src="../js/vue.js"></script>   
    <title>初步学习Vue</title>
</head>

<!-- 总结
            1.想让Vue工作,就要配置一个Vue实例,且要传入一个对象
            2.html只是混入了一些  Vue特殊字符
            3.root容器里的代码被称为  模板 

            4一个容器 只对应一个vue实例

            5.{{}}里面 可以写 js表达式  
            js表达式(属于js代码) :一个表达式可以生成一个值,可以放在生成值的任何地方
                    1.a
                    2.a+b
                    3.x === y ? 'a' : 'b'
            js代码
                    1.if(){}
            6.data一旦发生改变那么  模板中用到数据的地方也会发生改变更新
            7.真实开发中只会有一个Vue实例,并且会含着组件一起使用
-->

<body>
    <div id="root">
        <!-- {{参数名}}Vue的特殊字符串  使用参数名让Vue知道替换为哪个值 -->
        <h1>hello {{name}},{{address.toUpperCase()}}</h1>   
    </div>

    <script type="text/javascript">
        Vue.config.productionTip = false;   // 关闭开发环境   生产环境少了很多提示
        new Vue({     // 创建Vue对象 需要传递对象参数
            el: "#root",   // el表示  需要Vue为哪一个容器服务  值为css选择器
            data:{name:"上海",
            address: "gggg"  // data用于存储数据,给容器使用  现在我们使用对象存储
        }
        })

    </script>
    <!-- 1.下载vue.js
        2.在页面中引入js
        3.在浏览器上下载扩展Vue4.关闭开发环境提示
        
        shift + 刷新   为强制刷新

        favicon为网站的页签图标   拿一个图标放在根路径上就可以了
    -->
</body>
</html>

2.Vue模板语法

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>模板语法</title>

    <script type="text/javascript" src="../js/vue.js"></script>
</head>
<body>
    <!--   使用了指令语法的属性的值 都可以使用js表达式 -->
    <div id="root">     
        <a :href="url.toUpperCase()" v-bind:x="name"> 点我1 </a>
        <hr/>
        <a href="xxx"> 点我2来上 {{school.name}}{{school.age}} </a>
    </div>
<!-- Vue中的指令语法都是用v- 开头的
    给一个标签中的属性值绑定表达式  用 v-bind:  可以简写为:  

    1.插值语法:
        用于解析标签体内容  {{}}   可以直接读取到data中所有的属性
    2.指令语法
        用于解析标签 (包括:标签属性、标签体内容、绑定时间)
        v-
        v-bind:  ====> :    :href='xxx'  xxx也要是js表达式   xxx.toUpperCase()
-->
    <script type="text/javascript">
        Vue.config.productionTip = false;  // 关闭开发环境提示错误
        
        new Vue({
            el:"#root",
            data:{
                name:'张三',
                hello:'nihao',
                url:'xxx.com',
                school:{   // 嵌套对象
                    name:'小学',
                    age:'20'
                }
            }
        })
    </script>
</body>
</html>

3.Vue数据绑定

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>数据绑定</title>

    <script type="text/javascript" src="../js/vue.js"></script>
</head>
<body>
    <!-- v-bind: 是单向绑定,data中的数据改变,页面的数据会变,但是页面的数据改变,data中的不会改变
        v-model: 是双向绑定  
        model是只能用在表单类组件上(输入类组件)用户交互   都要都value值
    
        v-model:value  默认收集的就是value的值 所以可以简写为  v-model-->
    <div id="root">                   
        单向数据绑定:<input type="text" v-bind:value="name">
        双向数据绑定:<input type="text" v-model:value="age">
        <br/>
        单向数据绑定简写:<input type="text" :value="name">
        双向数据绑定简写:<input type="text" v-model="age">
    </div>

    <script type="text/javascript">
        Vue.config.productionTip = false; // 关闭开发者模式提醒
        new Vue({
            el:'#root',
            data:{name:'华南',
                age:'20'}
        })
    </script>
</body>
</html>

4.el与data的两种写法

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>el   data 的两种写法</title>
    <!-- 1.引入js依赖 -->
    <script type="text/javascript" src="../js/vue.js"></script>
</head>

<!-- 总结:
        1.el选择元素的两种写法
                1.new Vue的时候  用el: 选择器
                2.使用一个const变量接收Vue   使用v.$mount("#root")  挂仔
        2.data
                1.使用对象的形式{}
                2.使用函数的形式    在组件的地方一定要用 函数形式
                    data:function(){return{数据}}
                    简写  data(){return{数据}}
                注意不要使用箭头函数  ()=>  使用了的话 里面的this就不是Vue-->
<body>
    <!-- 2.给定一个容器 -->
    <div id="root">
        <h1>{{name}}</h1>
    </div>
    <div id="root2">
        <h1>{{name}}</h1>
    </div>

    <script type="text/javascript">
        Vue.config.productionTip = false; // 3.关闭生产环境提示
        // 4.使用Vue操作这个容器
        const v =   new Vue({
         //   el:'#root',
            data:{
                name:'zengli'
            }
        })
        setTimeout(()=>{  //  setTimeout 定时任务
            v.$mount('#root')  // 这个mount(组织、登上)更加灵活 
        },1000)
        
        // data的两种写法
        const v1= new Vue({
            // data:function(){
            //     return{
            //         name:"jjjjj"
            //     }
            // }
            data(){
                return{
                    name:"张三"
                }
            }
        })
        v1.$mount("#root2")

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

5.MVVM模型

M:模型(Model):对应data的数据
V:视图(View):模板
VM: 视图模型(ViewModel):Vue实例对象

模型和视图通过MV 实例对象连接起来
通过data bindings 和 DOM listeners

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>el   data 的两种写法</title>
    <!-- 1.引入js依赖 -->
    <script type="text/javascript" src="../js/vue.js"></script>
</head>
<!-- 总结
        1.M 是Model   就是data里面的数据
        2.V 是View    就是页面模型
        3.Vm 是ViewModel  就是Vue实例对象

        模型和视图通过MV 实例对象连接起来    
        通过data bindings  和 DOM listeners

        插值语句是{{可以方Vue实例对象中有的东西}}
        VM身上所有的属性  及 Vue原型上的所有属性,在Vue模板中都可以使用
    -->
<body>
    <!-- 2.给定一个容器 -->
    <div id="root">
        <h1>{{name}}</h1>

        <h1>{{$emit}}</h1>
    </div>

    <script type="text/javascript">
        Vue.config.productionTip = false; // 3.关闭生产环境提示
        // 4.使用Vue操作这个容器
        const vm =  new Vue({
            data(){
                return {
                    name:"张三"
                }
            }
        })
        console.log(vm)
        vm.$mount("#root")
    </script>
</body>
</html>


6.数据代理defineproperty 定义属性

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>,.....</title>
    <!-- 1.引入js依赖 -->
    <script type="text/javascript" src="../js/vue.js"></script>
</head>
<body>
    <!-- 2.给定一个容器 -->
    <div id="root">

    </div>

    <script type="text/javascript">
//         1.使用var声明的变量,其作用域为该语句所在的函数内,且存在变量提升现象;
// 2.使用let声明的变量,其作用域为该语句所在的代码块内,不存在变量提升;
        Vue.config.productionTip = false; // 3.关闭生产环境提示
        // 4.使用Vue操作这个容器

        let v = 18;
        let perten = {
            name: '张三',
            sex: '男'
        }
        // defineproperty 给一个变量添加属性值   
        Object.defineProperty(perten,'age',{
            // value: 20,   // 添加属性的值
            // enumerable: true,   // 控制属性是否可以被枚举  默认是false
            // writable: true,     // 控制属性是否可以被修改  默认值是false
            // configurable:true    // 控制属性是否可以被删除  默认值是false
            
            //当有人读取perten的age属性的时候 就会触发get函数  返回值 作为age的值 
            get(){
                return v;
            },
            //当有人读取perten的age属性的时候 就会触发set函数  会收到具体的值
            set(value){
                v = value
            }
        })
        for (let key in perten) {
            console.log([key])
        }

        console.log(perten)
    </script>
</body>
</html>

7.数据代理的定义

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>el   data 的两种写法</title>
    <!-- 1.引入js依赖 -->
    <script type="text/javascript" src="../js/vue.js"></script>
</head>
<body>
    <script type="text/javascript">
        Vue.config.productionTip = false; // 3.关闭生产环境提示
        // 数据代理就是   通过一个对象去操作另一个对象的属性值
        let obj1 = {x:100}
        let obj2 = {y:200}
        // 通过 obj2操作obj1的x
        Object.defineProperty(obj2,'x',{
            get(){
                return obj1.x
            },
            set(value){
                obj1.x = value
            }
        })
        console.log(obj1)
    </script>
</body>
</html>

8.数据代理的解释

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>el   data 的两种写法</title>
    <!-- 1.引入js依赖 -->
    <script type="text/javascript" src="../js/vue.js"></script>
</head>
<body>
    <!-- 2.给定一个容器 -->
    <div id="root">
        <h2>{{name}} </h2>
        <h2>{{age}}</h2>
    </div>
    <!-- 数据代理
    Vue中通过VM对象来代理数据data中的数据
        2. 数据代理的好处
            更加方便的操作data中的数据   (不然要用_data.来操作)
        3.基本原理
            通过Object.defineporperty()来把data中的每一个属性 添加到Vm中
            并且通过getter setter 方法来操作 _data的数据   
            data的数据就会放在VM对象的_data中

            data中的数据一改变,页面就会改变
-->

    <script type="text/javascript">
        Vue.config.productionTip = false; // 3.关闭生产环境提示
        // 4.使用Vue操作这个容器
        const vm= new Vue({
            el: '#root',
            data:{
                name: '曾黎',
                age: '20'
            }            
        })
       console.log(vm)
    </script>
</body>
</html>

9.事件处理

2.Vue中绑定事件 用 v-on:事件名=''  或者 @事件名  事件的函数写在 methods中
<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>Document</title>
    <script type="text/javascript" src="../js/vue.js"></script>
</head>
<body>
    <div id='root'>
        <h1>{{name}}</h1>
        <button v-on:click="function1">点我看详情</button>
        <!-- <button @click="function2">点我查看详情2</button> -->
        <button @click="function3($event,22)"></button>
    </div>

    <!-- 总结
    1.Vm实例中使用  尽量都是使用不同函数,不要使用箭头函数  使用不同函数中的this就是VM  而箭头函数的this是window

    2.Vue中绑定事件 用 v-on:事件名=''  或者 @事件名  事件的函数写在 methods中

    3.传递参数  默认会有 event事件源   使用在方法名后面用($event,参数) 来传递参数  $event 是事件源参数的占位符

		4.data中的数据都会有数据代理
    -->
    <script type="text/javascript">
        Vue.config.productionTip = false; // 关闭生产环境提示
        const vm = new Vue({
            data:{
                name:'张三'
            },
            methods:{
                function1:function(){
                    alert(1111)
                },
                function2(event){
                    console.log(event)
                    alert(2222)
                },
                function3(event,number){
                    console.log(event)
                    alert(number)
                }
            }
        })
        vm.$mount('#root')
    </script>
</body>
</html>

10.事件修饰符

    1.事件冒泡  : 多个嵌套组件中, 触发内嵌的内层组件,会一次触发外层事件  (先从外往让内层捕获  再冒泡)

事件修饰符可以连着写 @keyup.stop.prevent 先停止冒泡再停止默认行为
常用:
1. prevent(阻止) 阻止默认事件的发生
2.stop 停止冒泡行为
3.once 让事件只发生一次
不常用
4.capture 捕获时先执行 回调函数
5.self 只有当event.target是当前操作元素的时候,才会执行回调函数
6.passive 立即执行默认行为,无需等待事件函数执行完
scroll是滚动事件
wheel 是滚轮滚动事件

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>el   data 的两种写法</title>
    <!-- 1.引入js依赖 -->
    <script type="text/javascript" src="../js/vue.js"></script>
</head>
        <!-- 总结
        1.事件冒泡  : 多个嵌套组件中, 触发内嵌的内层组件,会一次触发外层事件  (先从外往让内层捕获  再冒泡)

        常用:
        1. prevent(阻止)  阻止默认事件的发生
        2.stop   停止冒泡行为
        3.once   让事件只发生一次
        不常用
        4.capture  捕获时先执行 回调函数
        5.self     只有当event.target是当前操作元素的时候,才会执行回调函数
        6.passive  立即执行默认行为,无需等待事件函数执行完  
        -->
<body>
    <!-- 2.给定一个容器 -->
    <div id="root">
        <!-- a 标签触发点击事件之后就会有默认行为  跳转  prevent可以阻止 -->
        <a href="xxx.com" @click.prevent="fun">点我</a>  
        <!-- once修饰符  只让事件触发一次 -->
        <button @click.once="fun">次次次</button> 
    </div>

    <div id="x1" @click="fun1">
        <!-- 事件冒泡  : 多个嵌套组件中, 触发内嵌的内层组件,会一次触发外层事件 
          stop  阻止事件冒泡-->
        <button @click.stop="fun1">点我</button>
    </div>

    <!--事件冒泡需要先捕获在 冒泡  使用capture 就可以在捕获的时候执行事件函数  -->
    <div id="ceshi" @click.capture="fun(1)">
        <button @click="fun(2)">kankan</button>
    </div>

    <!-- self事件修饰符  只有当 event.target是当前操作元素的时候才会调用事件函数 -->
    <div id="ceshi2" @click.self="fun">
        <button @click="fun">kankan</button>
    </div>

    <!-- passive (消极的,被动的) 事件默认行为立即执行  无需等待事件回调执行完毕 -->
    <script type="text/javascript">
        Vue.config.productionTip = false; // 3.关闭生产环境提示
        // 4.使用Vue操作这个容器
        new Vue({
            el:'#root',
            methods:{
                fun(){
                    alert(111)
                }
            }
        })

        const vm=new Vue({
            methods:{
                fun1(){
                    alert("111")
                }
            }
        })
        vm.$mount("#x1")

        const vm1=new Vue({
            methods:{
                fun(number){
                    console.log(number)
                    alert("111")
                }
            }
        })
        vm1.$mount("#ceshi")

        const vm2=new Vue({
            methods:{
                fun(number){
                    console.log(number)
                    alert("111")
                }
            }
        })
        vm2.$mount("#ceshi2")
    </script>
</body>
</html>

11.Vue中的键盘事件

3.系统按键 ctrl\alt\shift\mete(win键) 配合其他键 要指定固定的键的话可以 @keyup.alt.y 指定配合y才触发
1)配合keyup使用: 需要配合其他键使用 加上其他键
2)配合keydown的话 可以直接使用

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>el   data 的两种写法</title>
    <script type="text/javascript" src="../js/vue.js"></script>
</head>
<body>

    <!-- 键盘事件总结
    keyup 键盘弹起事件   keydown 键盘落下事件

    常用别名
    enter  
    delete
    esc 退出
    space 空格
    tab 换行  (特殊  只能用在键盘按下事件  因为tab本身会切换元素
    up上  down  left  right 

    2.Vue未提供的别名 可以用键盘原始key值去绑定  多个单词的话  用 小写加-符号分开

    3.系统按键  ctrl\alt\shift\mete(win键)
        1)配合keyup使用: 需要配合其他键使用  加上其他键
        2)配合keydown的话 可以直接使用

    4.Vue.config.keycodes.自定义键名 = 键码  可以定制
    -->

    <div id="root">
        <!-- <input type="text" @keyup.shift="fun"> -->
        <!-- <input type="text" @keyup.caps-lock="fun"> -->
        <input type="text" @keyup.jingru="fun">
    </div>

    <script type="text/javascript">
        Vue.config.productionTip = false;

        Vue.config.keyCodes.jingru = 20   // 定义一个别名按键  

        new Vue({
            el:"#root",
            methods:{
                fun(e){
                    console.log(e.target.value)
                    console.log(e.keyCode,e.key)
                }
            }
        })
    </script>
</body>
</html>

12.计算属性 computed

1.这里通过插值语法调用函数 一定要加() 返回值作为显示值
2.data数据中的属性一旦发生改变,Vue就会重新加载模板 加载数据

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>el   data 的两种写法</title>
    <!-- 1.引入js依赖 -->
    <script type="text/javascript" src="../js/vue.js"></script>
</head>
<body>
    <!-- 2.给定一个容器 -->
    <div id="root">:<input type="text" v-model="firstName"> </input> 
        <br/>:<input type="text" v-model="lastName">
        <br/>
        <!-- 这里通过插值语法调用函数  一定要加() 返回值作为显示值     不加()就是直接显示方法 -->
        全名:<h1>{{fullName()}}</h1> 
    </div>

<!-- data数据中的属性一旦发生改变,Vue就会重新加载模板  加载数据 -->

    <script type="text/javascript">
        Vue.config.productionTip = false; // 3.关闭生产环境提示
        // 4.使用Vue操作这个容器
        new Vue({
            el:'#root',
            data:{
                firstName:'曾',
                lastName:'黎'
            },
            methods:{
                fullName(){
                    return this.firstName+'-'+this.lastName;
                }
            }
        })
    </script>
</body>
</html>

computed:

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>el   data 的两种写法</title>
    <!-- 1.引入js依赖 -->
    <script type="text/javascript" src="../js/vue.js"></script>
</head>

    <!-- 总结
    计算属性:原来不存在,是通过属性(data中的)动态计算而来的  底层借用了object.defineproperty的setter和getter方法

    get()方法  1.在第一次获取的时候调用 2.计算属性所依赖的属性发生改变时
            计算属性的get方法是由缓存的  他的返回值可以作为计算属性的值

    set()方法   当计算属性被修改是 这个set方法会被调用  在这个里面要对 依赖属性做出修改

    计算属性直接在VM实例对象中
    -->

<body>
    <!-- 2.给定一个容器 -->
    <div id="root">:<input type="text" v-model="firstname"><br/><input type="text" v-model="lastname"><br/>
        全名:<span>{{fullname}}</span>
        全名:<span>{{fullname}}</span>
        全名:<span>{{fullname}}</span>
    </div>

    <script type="text/javascript">
        Vue.config.productionTip = false; // 3.关闭生产环境提示
        // 4.使用Vue操作这个容器
       const vm= new Vue({
            el:'#root',
            data:{
                firstname:'曾',
                lastname:'黎'
            },
            computed:{
                fullname:{
                    // 计算属性的get方法是由缓存的  他的返回值可以作为计算属性的值
                    // 调用时机:1.在第一次获取的时候调用 2.计算属性所依赖的属性发生改变时
                    // 计算属性直接在VM实例对象中
                    get(){
                        console.log(1111)
                        return this.firstname+'-'+this.lastname;
                    },
                    // 当计算属性被修改是 这个set方法会被调用  在这个里面要对 依赖属性做出修改
                    set(value){
                        const str = value.split("-");
                        this.firstname=str[0]
                        this.lastname=str[1]
                    }
                }
            }
        })
    </script>
</body>
</html>

计算属性简写:
只用到get方法的时候

   computed:{
     sproperty:function(){
       return this.lastname
      			}
      再简写
   sproperty(){
       return this.lastname
         }
      }

13.监视属性watch 两种 watch vm.$watch

监视一个已经存在了的属性,也可以是计算属性,当他发生变化时,handler就会执行

被Vue修饰的标签中 可以写简单的VM对象中含有的语法
<button @click=“ishot = !ishot”>点我切换天气

            // watch:{
            //     //监视一个已经存在的属性 计算属性也可以 
            //     ishot:{
            //         handler(newvalue,oldvalue){  // 当这个属性发生变化时  会调用handler函数
            //             console.log("ishot的值改变了",newvalue,oldvalue)
            //         }
            //     }
            // }
        })
        vm.$watch('ishot',{
            immediate:true,  // 初始化就调用一次handler
            handler(newvalue,oldvalue){
                console.log("ishot的值改变了",newvalue,oldvalue)
            }
        })
<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>el   data 的两种写法</title>
    <!-- 1.引入js依赖 -->
    <script type="text/javascript" src="../js/vue.js"></script>
</head>
<body>
    <!-- 2.给定一个容器 -->
    <div id="root">
        <h1>今天的天气很{{info}}</h1>
        <!-- <button @click="changeweather()">点我切换天气</button> -->
        <!--Vue修饰的标签中 可以写简单的VM对象中含有的语法 -->
        <button @click="ishot = !ishot">点我切换天气</button>
    </div>

    <script type="text/javascript">
        Vue.config.productionTip = false; // 3.关闭生产环境提示
        // 4.使用Vue操作这个容器
        const vm=new Vue({
            el:'#root',
            data:{
                ishot:true
            },
            computed:{
                info(){
                    return this.ishot ? '炎热' : '凉爽';
                }
            },
            methods:{
                changeweather(){
                    this.ishot = !this.ishot
                }
            },
            // watch:{
            //     //监视一个已经存在的属性 计算属性也可以 
            //     ishot:{
            //         handler(newvalue,oldvalue){  // 当这个属性发生变化时  会调用handler函数
            //             console.log("ishot的值改变了",newvalue,oldvalue)
            //         }
            //     }
            // }
        })
        vm.$watch('ishot',{
            immediate:true,  // 初始化就调用一次handler
            handler(newvalue,oldvalue){
                console.log("ishot的值改变了",newvalue,oldvalue)
            }
        })
    </script>
</body>
</html>

14.watch的深度监视 deep 及一些注意事项

1、Vue的watch默认不检测对象的对象内部值的改变(一层)
配置deep:true 就可以监测(多层)
备注:
vue自身是可以监测对象内部值的改变,只是watch不可以

                // 'number.a':{  // '属性名'是一种原始写法  这样就可以点到具体的属性
                //     handler(){
                //         console.log("a改变了")
                //     }

            watch:{
                number:{   // 监视number 但是number里面还有内嵌对象  内嵌对象的值改变 ,不会触发handler 除非number本身改变
                   deep:true,  // 开启深度监测  这个number里面的值发生改变就可以监测到了
                    handler(){
                        console.log("number改变了")
                    }
                }
                            }
监视属性的简写

1.在VM中写好的watch属性简写

            watch:{   
                // immediate:true,  handler函数初始化时立即执行
                // deep:true,          开启深度监视
                ishot(newvlue,oldvalue){  // 只有这个handler函数的时候可以简写  监听属性名(newvalue,oldvalue)
                    console.log(newvlue+'-' +oldvalue)
                }
            }

2.使用VM对象调用写
不要传递对象了 直接就写函数,代替handler 只要配置handler方法的时候

        vm.$watch('ishot',function(newvalue,oldvalue){
            console.log(newvalue,oldvalue)
        })

15.监视属性和计算属性的对比

1.computed可以做的事情,watch属性都可以做
2.有一些要用到异步回调的处理,只能watch做,而不能computed做

被Vue所管理的函数,都要写成不同函数,这样this就是VM或者组件
不被Vue所管理的函数,(定时器的回调函数、ajax的回调函数),最好写成箭头函数()=> ,这样他的this,就会往外找,就会找到VM

                setTimeout(()=>{
定时任务   传递的是箭头函数
                },1000)

16.绑定_class样式的三种写法、字符串、对象、数组

vm.classarr.shift() 删除数组的第一个元素
vm.classarr.push(‘sad’) 推入数组最后一个元素

// floor向下取整 random[0,1) 随机数
const index= Math.floor(Math.random()*2)

        <!-- 点击切换心情    用class的字符串绑定形式  使用于class 类名不确定 需要动态指定 -->
        <div class="basic" :class="a" @click="changmood">{{name}}</div> <br/>
			data中 a:'happy',


        <!-- class绑定  数组形式   适用于class 的类名不确定  个数不确定的情况-->
        <div class="basic" :class="classarr">{{name}}</div><br/>
			data中 classarr:['sad','happy'],


        <!-- 对象的绑定形式   适用于class 类名确定 名字也确定 但是不知道用不用 -->
        <div class="basic" :class="obj">{{name}}</div><br/>
        data中
                        obj:{
                    aa1:true,
                    aa2:true
                }
<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>el   data 的两种写法</title>
    <!-- 1.引入js依赖 -->
    <script type="text/javascript" src="../js/vue.js"></script>
    <style>
        .basic{
            width: 400px;
            height: 100px;
            border: 1px solid black;
        }

        .happy{
            width: 400px;
            height: 100px;
            background-color: aqua;
        }

        .sad{
            width: 400px;
            height: 100px;
            background-color: black;
        }

        .aa1{
            width: 400px;
            height: 200px;
            background-color: blue;
        }
        .aa2{
            width: 400px;
            height: 200px;
            background-color: green; 
        }

    </style>
</head>
<!-- 绑定_class样式的三种写法、字符串、对象、数组 -->
<body>
    <!-- 2.给定一个容器 -->
    <div id="root">
        <!-- 点击切换心情    用class的字符串绑定形式  使用于class 类名不确定 需要动态指定 -->
        <div class="basic" :class="a" @click="changmood">{{name}}</div> <br/>

        <!-- class绑定  数组形式   适用于class 的类名不确定  个数不确定的情况-->
        <div class="basic" :class="classarr">{{name}}</div><br/>

        <!-- 对象的绑定形式   适用于class 类名确定 名字也确定 但是不知道用不用 -->
        <div class="basic" :class="obj">{{name}}</div><br/>
    </div>

    <script type="text/javascript">
        Vue.config.productionTip = false; // 3.关闭生产环境提示
        // 4.使用Vue操作这个容器
        const vm=new Vue({
            el:'#root',
            data:{
                name:'曾黎',
                a:'happy',
                classarr:['sad','happy'],
                obj:{
                    aa1:true,
                    aa2:true
                }
            },
            methods:{
                changmood(){
                    const arr = ['happy','sad']
                    // floor向下取整  random[0,1) 随机数
                   const index= Math.floor(Math.random()*2)
                    this.a = arr[index]
                }
            }
        })
    </script>
</body>
</html>

17.绑定样式_style内联 两种 对象、数组

        <!-- 内联样式的写法  有对象 style里面规定的属性要去掉-除第一个以外的单词边大写  和对象数组两种 -->
        <div :style="obj">{{name}}</div>  <br/>

        <div :style="arr">{{name}}</div>

                obj:{
                    fontSize:'40px'
                },
                arr:[
                    {backgroundColor:'green'},
                    {fontSize:'40px'}
            ]

18.条件渲染

总结 v-if v-show
v-show 更一个布尔表达式 只是会通过 display:none 来隐藏标签 适用于变化频率较高的地方
v-if 更一个布尔表达式 条件为false的话 那么直接就没有显示这个标签了
使用template包住一些元素 在解析的时候就不会有template了

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>el   data 的两种写法</title>
    <!-- 1.引入js依赖 -->
    <script type="text/javascript" src="../js/vue.js"></script>
</head>
        <!--        总结  v-if  v-show 
            v-show  更一个布尔表达式  只是会通过 display:none 来隐藏标签  适用于变化频率较高的地方
            v-if   更一个布尔表达式  条件为false的话  那么直接就没有显示这个标签了
            使用template包住一些元素  在解析的时候就不会有template了
         -->
<body>
    <!-- 2.给定一个容器 -->
    <div id="root">
        <h1>jiajiajia{{n}}</h1>
        <button @click="n++">点我给n++</button>
        <!-- style="display: none;"  v-show 和一个布尔表达式  只是把标签影藏 不会去除标签 -->
        <!-- <h2 v-show="n===1">曾黎</h2>
        <h2 v-show="n===1">湖南长沙</h2> -->

        <!-- v-if  给一个Boolean表达式  不符合会直接删除标签  if else-if else 要写在一起 -->
        <h2 v-if="n===1">曾黎</h2>
        <h2 v-else-if="n===2">张三</h2>
        <h2 v-else>王五</h2>

        <!-- 这样会显示 外层的div  -->
        <div v-if="n===1">
            <h2>djsaf</h2>
            <h2>dasdasf</h2>
            <h2>dsafsa</h2>
        </div>
        <!-- 用template的时候就不用会  显示 template -->
        <template v-if="n===1">
            <h2>djsaf</h2>
            <h2>dasdasf</h2>
            <h2>dsafsa</h2>
        </template>
    </div>

    <script type="text/javascript">
        Vue.config.productionTip = false; // 3.关闭生产环境提示
        // 4.使用Vue操作这个容器
        new Vue({
            el:'#root',
            data:{
                n:0
            }
        })
    </script>
</body>
</html>

19.链表遍历v-for='val in 遍历的对象

总结 v-for 每一个列表都要有一个唯一的key 用:key绑定
1.可以遍历数组 (数组里面的一个对象,索引值) in 数组
2.可以遍历对象 (对象的value,对象的key) in 对象
3.遍历字符串 (字符,index) in str
4.遍历指定次数 (从1开始,从0开始) in number

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>el   data 的两种写法</title>
    <!-- 1.引入js依赖 -->
    <script type="text/javascript" src="../js/vue.js"></script>
</head>
            <!--    总结  v-for   每一个列表都要有一个唯一的key  用:key绑定
                1.可以遍历数组 (数组里面的一个对象,索引值)  in 数组
                2.可以遍历对象   (对象的value,对象的key)  in 对象
                3.遍历字符串   (字符,index) in str
                4.遍历指定次数   (从1开始,从0开始) in number
             -->
<body>
    <!-- 2.给定一个容器 -->
    <div id="root">

        <h1>遍历数组</h1>
        <ul>      
            <li v-for="(p,index) in persons" :key="p.id">
                {{p.name}} - {{p.age}}   {{index}}
            </li>
        </ul>

        <h1>遍历对象</h1>
        <ul>
            <li v-for="(value,k) in obj" :key="k">
                {{value}}--{{k}}
            </li>
        </ul>

        
        <h1>遍历str</h1>
        <ul>
            <li v-for="(char,index) in str" :key="index">
                {{char}}--{{index}}
            </li>
        </ul>

        <h1>遍历指定次数</h1>
        <ul>
            <li v-for="(a,b) in 5" :key="a">
                {{a}}--{{b}}
            </li>
        </ul>
    </div>

    <script type="text/javascript">
        Vue.config.productionTip = false; // 3.关闭生产环境提示
        // 4.使用Vue操作这个容器
        new Vue({
            el:'#root',
            data:{
                persons:[
                    {id:'001',name:'张三',age:10},
                    {id:'002',name:'李四',age:19},
                    {id:'003',name:'王五',age:12}
                ],
                obj:{
                    name:'曾黎',
                    age:20
                },
                str:'dsafsaasg'
            }
        })
    </script>
</body>
</html>

20.key的作用和原理

总结
列表的这个key,它是由vue所管理的,是用来给虚拟DOM做对比的 是虚拟DOM对象的标识
代码----》虚拟DOM----》真实DOM
如果代码出现变动,VUE会把新的虚拟DOM与旧的虚拟DOM做对比 如果有相同的key 那么并且里面的东西也一样,就会复用旧的真实DOM中的数据

使用index
那么如果真实dom中有输入框的数据,那么数据可能被复用的错乱

所以列表中的key,尽量使用唯一标识

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>el   data 的两种写法</title>
    <!-- 1.引入js依赖 -->
    <script type="text/javascript" src="../js/vue.js"></script>
</head>
<!--            总结
    列表的这个key,它是由vue所管理的,是用来给虚拟DOM做对比的  是虚拟DOM对象的标识 
    代码----》虚拟DOM----》真实DOM
    如果代码出现变动,VUE会把新的虚拟DOM与旧的虚拟DOM做对比  如果有相同的key  那么并且里面的东西也一样,就会复用旧的真实DOM中的数据
    
    那么如果真实dom中有输入框的数据,使用index作为key那么可能导致数据可能被复用的错乱

    所以列表中的key,尽量使用唯一标识

 -->

<body>
    <!-- 2.给定一个容器 -->
    <div id="root">

        <h1>遍历数组</h1>
        <button @click.once="add">点击给列表加数据</button>
        <ul>      
            <li v-for="(p,index) in persons" :key="index">
                {{p.name}} - {{p.age}}   {{index}}
                <input type="text">
            </li>
        </ul>
    </div>

    <script type="text/javascript">
        Vue.config.productionTip = false; // 3.关闭生产环境提示
        // 4.使用Vue操作这个容器
        new Vue({
            el:'#root',
            data:{
                persons:[
                    {id:'001',name:'张三',age:10},
                    {id:'002',name:'李四',age:19},
                    {id:'003',name:'王五',age:12}
                ]
            },
            methods:{
                add(){
                const p = {id:'004',name:'曾黎',age:20}
                this.persons.unshift(p)  // 给数组加元素,加载第一个位置上
            }
            }

        })
    </script>
</body>
</html>

21.列表过滤

使用watch(handler)和computed(getter 、 setter)都可以使用在列表过滤中,只不过 computed简单一点

indexof(’ ')匹配一个空字符串的话都可以匹配到

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>el   data 的两种写法</title>
    <!-- 1.引入js依赖 -->
    <script type="text/javascript" src="../js/vue.js"></script>
</head>
<body>
    <!-- 2.给定一个容器 -->
    <div id="root">

        <h1>输入关键字进行模糊匹配</h1>
        <!-- v-model 默认是绑定value 双向绑定   -->
        <input type="text" v-model="keyword">   
        <ul>      
            <li v-for="(p,index) in filpersons" :key="p.id">
                {{p.name}} - {{p.age}}   {{index}}
                <input type="text">
            </li>
        </ul>
    </div>

    <script type="text/javascript">
        Vue.config.productionTip = false; // 3.关闭生产环境提示
        // 4.使用Vue操作这个容器
        new Vue({
            el:'#root',
            data:{
                keyword:'',
                persons:[
                    {id:'001',name:'马冬梅',age:10},
                    {id:'002',name:'周冬雨',age:19},
                    {id:'003',name:'周杰伦',age:12},
                    {id:'003',name:'王亚伦',age:12}
                ],
               // filpersons:[]
            },
            // watch:{
            //     keyword:{
            //         immediate:true,  // 初始化的时候就执行一次
            //         handler(newvalue){
            //            this.filpersons= this.persons.filter((x)=>{
            //             // indexOf()如果没有匹配到  就会返回-1  如果有匹配到就会返回下标
            //                 return x.name.indexOf(newvalue) !== -1
            //             })
            //         }
            //     }
            // }
            computed:{
                filpersons(){    // 计算属性,当第一次获取的时候会 触发get  另外所依赖的属性发生改变的时候也会触发get
                  return  this.persons.filter((x)=>{
                        return x.name.indexOf(this.keyword) !== -1
                    })
                }
            }

        })
    </script>
</body>
</html>

排序升序降序 sort(a,b) a-b 升序
        // 4.使用Vue操作这个容器
        new Vue({
            el:'#root',
            data:{
                keyword:'',
                sortType:0, // 排序初始化是0 1表示降序  2表示升序  
                persons:[
                    {id:'001',name:'马冬梅',age:10},
                    {id:'002',name:'周冬雨',age:19},
                    {id:'003',name:'周杰伦',age:12},
                    {id:'003',name:'王亚伦',age:12}
                ],
               // filpersons:[]
            },
            computed:{
                filpersons(){    // 计算属性,当第一次获取的时候会 触发get  另外所依赖的属性发生改变的时候也会触发get
                    // 用变量接住  之后再进行排序
                  const arr= this.persons.filter((x)=>{
                        return x.name.indexOf(this.keyword) !== -1
                    })
                    if(this.sortType){   // 如果sorttype不是0 就进行排序
                    arr.sort((a,b)=>{ // a代表前一个数据,b代表后一个数据
                        // 如果是1 就进行降序  其他就进行升序
                      return this.sortType ===1 ? b.age-a.age : a.age-b.age;   

                    // 计算属性中的  this.sortType改变了 计算属性就会重新计算

                    })
                    }
                    return arr;
                }
            }

        })

22.Vue数据监测是问题以及数据监测的原理

直接修改这个对象中的一个元素vue监测不到啊啊啊

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>el   data 的两种写法</title>
    <!-- 1.引入js依赖 -->
    <script type="text/javascript" src="../js/vue.js"></script>
</head>
<body>
    <!-- 2.给定一个容器 -->
    <div id="root">
        <button @click="changdata">点我改数据</button>
        <ul>
            <li v-for="p in persons" :key="p.id">
                {{p.name}}-{{p.age}}
            </li>
        </ul>
    </div>

    <script type="text/javascript">
        Vue.config.productionTip = false; // 3.关闭生产环境提示
        // 4.使用Vue操作这个容器
        const vm=new Vue({
            el:'#root',
            data:{
                persons:[
                    {id:'001',name:'马冬梅',age:10},
                    {id:'002',name:'周冬雨',age:19},
                    {id:'003',name:'周杰伦',age:12},
                    {id:'003',name:'王亚伦',age:12}
                ],
               // filpersons:[]
            },
            methods: {
                changdata(){   // 直接修改这个对象中的一个元素vue监测不到啊啊啊
                    this.persons[0] = {id:'001',name:'娜娜',age:10}
                }
            },
        })
    </script>
</body>
</html>

原理:

数据该了之后----》set方法执行----》解析模板----》生成新的虚拟DOM ----》新旧DOM对比—》刷新页面

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>el   data 的两种写法</title>
    <!-- 1.引入js依赖 -->

</head>
<body>
    <!-- 2.给定一个容器 -->


    <script type="text/javascript">
        let data={
            name:'张三',
            age:30
        }
      console.log(data['age'])
        let vm = {}
    // 初始化data中的数据  监测对象监测data
       const o= new observer(data)

       // 把对象返回给vm中的_data
       vm._data = data = o;

       function observer(obj){
            //首先数据会传入这个里面解析
            // 1.先把对象的key转化为数组  是一个字符串形式
           const arr= Object.keys(obj);   
       
           arr.forEach((d)=>{
            //  用defineProperty  给observer对象中加 名为d的属性
            Object.defineProperty(this,d,{
                get(){
                    console.log(d)
                    return obj[d];  // 返回这个原来的数据的值
                },
                set(val){
                    console.log("数据修改完毕 我要去解析了")
                    obj[d] = val
                }
            })
           })
        }
    </script>
</body>
</html>

23.取得对象中属性值的两种方式

 let obj = {
 	name:'小明',
 	age:10
 }

1、点的方式
格式:对象名.属性名

obj.name // 小明

2、中括号的方式
格式:对象名[‘属性名’]或者对象名[“属性名”]

obj['name'] // 小明

24.Vue的set方法 加响应式数据

给Vue加 响应式数据的话 有两种 1.Vue对象的set方法
2.vm实例的* s e t ∗ ∗ 方法注意 S e t 方法不能直接在 v m 实例上加数据,也不能在根数据上加 / / V u e . s e t ( t h i s . s c h o o l , ′ a g e ′ , 20 ) v m . set**方法 注意 Set方法不能直接在vm实例上加数据,也不能在根数据上加 // Vue.set(this.school,'age',20) vm. set方法注意Set方法不能直接在vm实例上加数据,也不能在根数据上加//Vue.set(this.school,age,20)vm.set(this.school,‘age’,21)

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>el   data 的两种写法</title>
    <!-- 1.引入js依赖 -->
    <script type="text/javascript" src="../js/vue.js"></script>
</head>
<body>
    <!-- 2.给定一个容器 -->
    <div id="root">
        <button v-on:click="add">给学校加年龄</button>
        <h1>学校-{{school.name}}</h1>
        <h2>{{school.addrees}}</h2>
        <h2 v-if="school.age">{{school.age}}</h2>
    </div>

    <script type="text/javascript">
        Vue.config.productionTip = false; // 3.关闭生产环境提示
        // 4.使用Vue操作这个容器
        const vm=new Vue({
            el:'#root',
            data:{
                school:{
                    name:'科技大学',
                    addrees:'湖南'
                }
            },
            methods:{
                add(){
                    // 给Vue加 响应式数据的话 有两种  1.Vue对象的set方法  2.vm实例的$set方法
                    //  注意  Set方法不能直接在vm实例上加数据,也不能在根数据上加
                   // Vue.set(this.school,'age',20)
                   vm.$set(this.school,'age',21)
                }
            }
        })
    </script>
</body>
</html>

25.数组的数据监测

对于数组 Vue没有直接给每个数组元素添加getter、setter方法, 所以直接修改数组元素,VUE监听不到。

Vue是把数组常用的方法做了包装 会让他们重新去解析模板

push后入 pop后出 shift前出 unshift前入 splice(要替换的下标,替换几个,内容…)替换 reverse 翻转 sort
还可以使用Vue.set(vm.person.hobby,3,‘吃吃吃’) vm.$set()

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>el   data 的两种写法</title>
    <!-- 1.引入js依赖 -->
    <script type="text/javascript" src="../js/vue.js"></script>
</head>
<body>
    <!-- 2.给定一个容器 -->
    <div id="root">
        <h1>爱好</h1>
        <ul>
            <li v-for="a in person.hobby">
                {{a}}
            </li>
        </ul>
    </div>

    <script type="text/javascript">
        Vue.config.productionTip = false; // 3.关闭生产环境提示
        // 4.使用Vue操作这个容器
        const vm= new Vue({
            el:'#root',
            data:{
                person:{
                    // 对于数组  Vue没有直接给每个数组元素添加getter、setter方法, 所以直接修改数组元素,VUE监听不到
                    // Vue是把数组常用的方法做了包装  会让他们重新去解析模板
                    // push后入  pop后出  shift前出 unshift前入  splice(要替换的下标,替换几个,内容...)替换  reverse 翻转  sort
                    hobby:['抽烟','喝酒','烫头']
                }
               
            }
        })
    </script>
</body>
</html>

26.Vue监视数据总结

Vue会监视所有层次的对象的 通过setter实现

我们写的数据在data中,Vue帮我们做了数据劫持(遍历,defineperporty)在_data中,这样我们的数据修改了就可以被监测到。

1.首先是对象
对象的话,我们要把所有要用的属性都要提前配置好放在data中,如果要后来给Vue加响应数据可以通过:
注意 不可以给vm实例或者vm跟对象加

Vue.set(给哪个对象加,'属性名',)
vm.$set(给哪个对象加,'属性名',)

2.数组 (不要直接用数组下标操作元素,因为Vue没有给setter/getter方法)
要想修改数组元素,可以被Vue监视到的话,Vue是把数组常用的方法做了包装 会让他们重新去解析模板

 push后入  pop后出  shift前出 unshift前入  splice(要替换的下标,替换几个,内容...)替换  reverse 翻转  sort

或者是:

Vue.set(给哪个对象加,索引,)
vm.$set(给哪个对象加,索引,)

27.表单收集总结

/ JSON.Stringify()将对象转化为json格式
console.log(JSON.stringify(this.person))
总结
使用v-model时:
1.如果是input是text 那么默认收集value
2.如果input是radio 那么要自己加上 value属性
3.如果input是checkbox 那么也需要加value 并且要用数组接收才是value 用字符串就是checked的值
没有配置value就是收集checked

        v-model的修饰属性
        1. .number 表示收集的是一个数字类型
        2.  .lazy 光标移开才加载
        3.  .trim 去前后空格
<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>el   data 的两种写法</title>
    <!-- 1.引入js依赖 -->
    <script type="text/javascript" src="../js/vue.js"></script>
</head>
<!--            总结
            使用v-model时:
            1.如果是input是text  那么默认收集value
            2.如果input是radio  那么要自己加上 value属性
            3.如果input是checkbox  那么也需要加value  并且要用数组接收才是value  用字符串就是checked的值
            没有配置value就是收集checked

            v-model的修饰属性
            1. .number 表示收集的是一个数字类型
            2.  .lazy 光标移开才加载
            3.  .trim 去前后空格
-->
<body>
    <!-- 2.给定一个容器 -->
    <div id="root">
            <form @submit.prevent="tijiao">
                <!-- 通过label 绑定这个输入框 而使得点击账户后 光标会到输入框-->
                <label for="zhanghao">账号:</label>  
                <input type="text" id="zhanghao" v-model.trim="person.account">  <br/>
                密码:<input type="password" v-model="person.password">  <br/>
                年龄<input type="number" v-model.number="person.age"> <br/>
                性别:<input type="radio" name="sex" v-model="person.sex" value="man">  
                <!-- 单选的话  name相同  就只会选一个 --><input type="radio" name="sex" v-model="person.sex" value="woman">  <br/>
                爱好:
                吃饭:<input type="checkbox" v-model="person.hobby" value="eat">
                打游戏<input type="checkbox" v-model="person.hobby" value="game">
                睡觉<input type="checkbox" v-model="person.hobby" value="sleep">  <br/>
                所属校区:
                <!--  select 的value 是选中谁谁就是value -->
                <select v-model="person.option">   
                    <option value="">请选择</option>
                    <option value="shanghai">上海</option>
                    <option value="changsha">长沙</option>
                    <option value="wuhan">武汉</option>
                </select>
                <br/>
                其他信息:
                <textarea v-model.lazy="person.other">

                </textarea><br/>
                <input type="checkbox" v-model="person.isop">阅读并且接收<a href="a.com">用户协议</a>
                <br/>
                <button>提交</button>
            </form>
    </div>

    <script type="text/javascript">
        Vue.config.productionTip = false; // 3.关闭生产环境提示
        // 4.使用Vue操作这个容器
        new Vue({
            el:'#root',
            data:{
                person:{
                    account:'',
                    password:'',
                    sex:'',
                    hobby:[],   //  hobby 在checkbox上,如果这个使用字符串来接收  那么就是接收checked的值,使用数组才是value值
                    option:'',
                    other:'',
                    isop:'',
                    age:''
                }
            },
            methods:{
                tijiao(){
                    // JSON.Stringify()将对象转化为json格式
                    console.log(JSON.stringify(this.person))
                }
            }
        })
    </script>
</body>
</html>

28.Vue的过滤器 filter

总结
1.过滤器的作用是 可以对数据进行一些重新的简单的格式化操作
2.过滤器会默认传递 要过滤的数据参数 后面加上你传了的参数
filters:{
过滤器名字(参数,,,){
}
}
Vue.filter(‘allfilter’,function(value){
return ‘我是全局过滤器’+value
})
3.通过Vue.filter可以 增加一个全局过滤器
4.过滤器可以用在差值表达式 和 v-bind的值上面
5.过滤器可以串联过滤 并不会改变原有的数据而是新增数据

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>el   data 的两种写法</title>
    <!-- 1.引入js依赖 -->
    <script type="text/javascript" src="../js/vue.js"></script>
    <script type="text/javascript" src="../js/dayjs.min.js"></script>
</head>
<!--            总结
        1.过滤器的作用是 可以对数据进行一些重新的简单的格式化操作      
        
        2.过滤器会默认传递 要过滤的数据参数  后面加上你传了的参数
        filters:{
            过滤器名字(参数,,,){

            }
        }

        3.通过Vue.filter可以 增加一个全局过滤器

        4.过滤器可以用在差值表达式  和  v-bind的值上面

        5.过滤器可以串联过滤  并不会改变原有的数据而是新增数据
-->
<body>
    <!-- 2.给定一个容器 -->
    <div id="root">
        <h2>未格式化的日期是{{weidate}}</h2>
        <h2>通过计算属性格式化{{formdated}}</h2>
        <h2>通过方法格式化的属性{{formatfun()}}</h2>
        <!-- 过滤器可以多层过滤  只要通过 | 管道符号来实现就好了
        过滤器默认参是 要过滤的数据  可以加参数 -->
        <h2>通过过滤器方法来实现{{weidate | fildate('YYYY-MM-DD') | slicefil}}</h2>
        <h2>通过过滤器方法来实现22{{weidate | fildate}}</h2>

        <h2>全局过滤器{{weidate | allfilter}}</h2>
        <h2 v-bind:x="weidate | allfilter"></h2>
    </div>

    <script type="text/javascript">
       
        Vue.config.productionTip = false; // 3.关闭生产环境提示
        // 4.使用Vue操作这个容器
        Vue.filter('allfilter',function(value){
            return '我是全局过滤器'+value
        })
        new Vue({
            el:'#root',
            data:{
                weidate:1681874109947,
            },
            computed:{
                formdated(){
                  return  dayjs(this.weidate).format('YYYY-MM-DD HH:mm:ss')
                }
            },
            methods:{
                formatfun(){
                    return dayjs(this.weidate).format('YYYY-MM-DD HH:mm:ss')
                }
            },
            filters:{
                //  第一个参数是数据  后面的参数传递参数   参数还可以指定默认值
                fildate(value,str='YYYY'){
                    return dayjs(value).format(str)
                },
                slicefil(value){
                    // 截取数字
                    return value.slice(0,4)
                }
            }    
        })
    </script>
</body>
</html>

29.Vue中的常用指令(内置指令)

1. v-text : 更新元素的 的内容
<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>el   data 的两种写法</title>
    <!-- 1.引入js依赖 -->
    <script type="text/javascript" src="../js/vue.js"></script>
</head>
<!--   t-text  是替换掉标签中的内容 -->
<body>
    <!-- 2.给定一个容器 -->
    <div id="root">
        <h1>{{name}},你好</h1>
        <h1 v-text="name">你好</h1>
    </div>

    <script type="text/javascript">
        Vue.config.productionTip = false; // 3.关闭生产环境提示
        // 4.使用Vue操作这个容器
        new Vue({
            el:'#root',
            data:{
                name:'曾黎'
            }
        })
    </script>
</body>
</html>

2.v-html

v-html个v-text的区别就是
v-html可以把html标签进行解析 显示在页面

但是这样就存在安全隐患
所以严禁在用户输入的地方用v-html

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>el   data 的两种写法</title>
    <!-- 1.引入js依赖 -->
    <script type="text/javascript" src="../js/vue.js"></script>
</head>
<body>
    <!-- 2.给定一个容器 -->
    <div id="root">
        <h1 v-html="da"></h1>
    </div>

    <script type="text/javascript">
        Vue.config.productionTip = false; // 3.关闭生产环境提示
        // 4.使用Vue操作这个容器
        new Vue({
            el:'#root',
            data:{
                da:'<a href="a.com">点我</a>'
            }
        })
    </script>
</body>
</html>

3.v-cloak(披风) 特殊标签 没有值

script不仅可以写在head中 还可以写在 body的最后面

它是用来 标记一些标签 配合css display:none 让一些未经Vue解析的html标签给隐藏(因为网络慢)
一旦Vue接管后 会去除所有的v-cloak属性

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>el   data 的两种写法</title>
    <!-- 1.引入js依赖 -->
    <!-- script不仅可以写在这里  还可以写在 body的最后面 -->
    <script type="text/javascript" src="../js/vue.js"></script>
    
    <style>
        /* 选中 所有的 标签中有v-cloak属性的标签  让他们隐藏 */
        [v-cloak]{
            display:none
        }
    </style>
</head>
<!--        总结
        1.  v-cloak(披风) 这个属性是一个特殊标记
        它是用来 标记一些属性 配合css  让一些未经Vue解析的html标签给隐藏(因为网络慢)

        一旦Vue接管后  会去除所有的v-cloak属性
-->
<body>
    <!-- 2.给定一个容器 -->
    <div id="root">
        <h1 v-cloak>{{name}}</h1>
    </div>

    <script type="text/javascript">
        Vue.config.productionTip = false; // 3.关闭生产环境提示
        // 4.使用Vue操作这个容器
        new Vue({
            el:'#root',
            data:{
                name:'曾黎'
            }
        })
    </script>
</body>
</html>

4.v-once指令

它是放在标签上 让内容只被初始化的时候解析一次 之后数据改变也不会变

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>el   data 的两种写法</title>
    <!-- 1.引入js依赖 -->
    <script type="text/javascript" src="../js/vue.js"></script>
</head>
<!-- 总结
    v-once指令是没有值的
    它是放在标签上 让内容只被初始化的时候解析一次  之后数据改变也不会变了,变为静态的了        
-->
<body>
    <!-- 2.给定一个容器 -->
    <div id="root">
        <h1 v-once>n的初始值{{n}}</h1>
        <h1>{{n}}</h1>
        <button @click="n++"> 点我给n++</button>
    </div>

    <script type="text/javascript">
        Vue.config.productionTip = false; // 3.关闭生产环境提示
        // 4.使用Vue操作这个容器
        new Vue({
            el:'#root',
            data:{
                n:1
            }            
        })
    </script>
</body>
</html>

5.v-pre 跳过编译 直接返回到页面
    v-pre  他也没有值  
    它是可以让标签跳过编译阶段   直接显示在页面
    在那些没有用到指令语法、插值语法的标签中用  会加快整体的编译速度 
<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>el   data 的两种写法</title>
    <!-- 1.引入js依赖 -->
    <script type="text/javascript" src="../js/vue.js"></script>
</head>
<!-- 总结
    v-pre  他也没有值  
    它是可以让标签跳过编译阶段   直接显示在页面
    在那些没有用到指令语法、插值语法的标签中用  会加快整体的编译速度 
-->
<body>
    <!-- 2.给定一个容器 -->
    <div id="root">
        <h1 v-pre>n的初始值</h1>
        <h1>{{n}}</h1>
        <button @click="n++"> 点我给n++</button>
    </div>

    <script type="text/javascript">
        Vue.config.productionTip = false; // 3.关闭生产环境提示
        // 4.使用Vue操作这个容器
        new Vue({
            el:'#root',
            data:{
                n:1
            }            
        })
    </script>
</body>
</html>

6.自定义指令 directives

注意 在指令命名的时候 多个单词要用-分开 并且再写的时候用’ '引用

指令相关的this都是window 并且定义的都是局部指令

要定义全局指令的话,就要用
Vue.directive(‘指令名’,{}/函数)

1.简写 函数的形式

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>el   data 的两种写法</title>
    <!-- 1.引入js依赖 -->
    <script type="text/javascript" src="../js/vue.js"></script>
</head>

<!-- z              总结
            1.自定义属性在Vue中可以用directives写  可以有两个写法 一个函数一个对象
            2.函数的两个参数,一个是整个真实元素  另一个是绑定的一些信息  比如value值
            3.调用时机
                初始化解析绑定关系的时候调用
                每次模板重新解析的时候就会调用
-->

<body>
    <!-- 2.给定一个容器 --> 
    <div id="root">
        <h1>我是n的本值{{n}}</h1>
        <h1 v-big="n">d</h1>
        <button @click="n++">点我加1</button>
    </div>

    <script type="text/javascript">
        Vue.config.productionTip = false; // 3.关闭生产环境提示
        // 4.使用Vue操作这个容器
        new Vue({
            el:'#root',
            data:{
                n:1,
            },
            //  自定义指令可以有两种写法  函数  和对象  对象可以掌握细节
            directives:{
                // 属性名  绑定在哪个元素上 那个元素的真实元素  绑定表达式的值
                big(element,binding){
                    element.innerText = '扩大十倍后的值是'+binding.value*10
                }
            }
        })
    </script>
</body>
</html>

2.对象的形式
元素和指令绑定时
bind(element,binding)、
元素插入到页面时
inserted()、
指令所在模板被重新解析时
update()

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>el   data 的两种写法</title>
    <!-- 1.引入js依赖 -->
    <script type="text/javascript" src="../js/vue.js"></script>
</head>
<body>
    <!-- 2.给定一个容器 -->
    <div id="root">
        <h1 v-text="'我是n的本值'+n"></h1>
        <input v-fbind="n" type="text">
        <button @click="n++">点我加1</button>
    </div>

    <script type="text/javascript">
        Vue.config.productionTip = false; // 3.关闭生产环境提示
        // 4.使用Vue操作这个容器
        new Vue({
            el:'#root',
            data:{
                n:1,
            },
            //  自定义指令对象的写法  可以有三个时机  而函数的简写 只会有两个时机少了一个  当元素插入到页面时这个时机
            directives:{
                fbind:{
                    // 初始化解析绑定关系的时候调用
                    bind(element,binding){
                        element.value = binding.value
                    },
                    // 当元素插入到页面时调用
                    inserted(element,binding){
                        // 有些方法 需要元素 插入到页面才会生效
                        // 比如获取焦点   获取父元素等
                        element.focus()
                    },
                    // 当绑定元素的模板重新解析的时候调用
                    update(element,binding){
                        // 更新逻辑一般和 初始化逻辑一样
                        element.value = binding.value
                    }
                }
            }
        })
    </script>
</body>
</html>

30.Vue的声明周期

setInterval是一个实现定时调用的函数,可按照指定的周期(以毫秒计)来调用函数或计算表达式。setInterval方法会不停地调用函数,直到 clearInterval被调用或窗口被关闭。
由setInterval返回的ID值可用作clearInterval方法的参数。

1.引出Vue的声明周期

Vue的声明周期就是 在Vue执行的时候 会调用一系列的回调函数 又称为钩子函数

mounted函数 它是在Vue初次完成初始化解析并且把真实DOM挂仔到页面时触发

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>el   data 的两种写法</title>
    <!-- 1.引入js依赖 -->
    <script type="text/javascript" src="../js/vue.js"></script>
</head>
<!-- 
                总结
                Vue的声明周期就是 在Vue执行的时候  会调用一系列的回调函数  又称为钩子函数

                mounted函数  它是在Vue初次完成初始化解析并且把真实DOM挂仔到页面时触发
 -->
<body>
    <!-- 2.给定一个容器 -->
    <div id="root">
        <!-- 当对象中的属性名和值同名时  可以简写成 opacity -->
        <h1 :style="{opacity:opacity}">曾黎好好好</h1>
    </div>

    <script type="text/javascript">
        Vue.config.productionTip = false; // 3.关闭生产环境提示
        // 4.使用Vue操作这个容器
       const vm= new Vue({
            el:'#root',
            data:{
                opacity:1
            },
            mounted() {
           setInterval(()=>{
            this.opacity = this.opacity-0.01
            if(this.opacity<=0) this.opacity=1
        },16)
            },
        })


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

2.Vue初始化到挂载

在这里插入图片描述

挂载流程:

<!--                总结
            1.初始化到挂仔的生命周期分为了

            init1    beforecreate  它是会完成vue生命周期和事件 信息   这个时候  数据还没有形成
            init2   created         它是完成数据挂载  数据形成

            数据解析,在内存中生成虚拟DOM
            首先会判断  你写没有写el:  有的话往下   没有的话就只能等待vm.$mount()来挂载再往下
            再  判断有没有 template  
                 有: 那么他就会解析你的template  然后生成虚拟DOM   注意template不会包含外部的一些标签
                 没有: 那么他会解析el选择的标签整体作为模板

            brforeMount    在这个步骤 Vue还是模板没有解析的状态  操作的DOM对象也最终会失效  

            然后Vue会将 内存中的虚拟DOM转化为真实DOM ,并且他会留一份真实DOM在vm中叫做$el  因为到时猴虚拟dom对比的时候要用到

            Mounted  这个时候 已经转化为了真实DOM了 
-->


更新流程
            更新流程-------------------------------------
            beforeupdate 当数据发生改变之后  那么他会执行一个方法  此时 数据已经更新,但是页面还没有更新(解析)

            然后Vue会将新数据生成新的 虚拟DOM做对比(复用) 再将虚拟DOM转化为真实DOM   model---》view

            updated  这个方法中,数据和页面同步了


            beforeUpdate() {
                // 数据改变的时候调用
                console.log('此时数据已经更新,但是 页面还没有解析好,数据不一致')
              
            },
            updated() {
                console.log('数据和页面一致了')
            },
销毁流程
            Vm执行了$destroy方法之后 就会进入销毁流程
            beforedestroy   这个方法中数据还在  可以被调用但是对数据的修改是不奏效的  在这里做一些首尾工作(关闭定时器等)

            destroyed  这个方法中 vm已经被销毁了


            vm虽然被销毁了  但是为他绑定的系统的事件监听还在  vm.$destroy()
<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>el   data 的两种写法</title>
    <!-- 1.引入js依赖 -->
    <script type="text/javascript" src="../js/vue.js"></script>
</head>
<!--                总结
            1.初始化到挂仔的生命周期分为了

            init1    beforecreate  它是会完成vue生命周期和事件 信息   这个时候  数据还没有形成
            init2   created         它是完成数据挂载  数据形成

            数据解析,在内存中生成虚拟DOM
            首先会判断  你写没有写el:  有的话往下   没有的话就只能等待vm.$mount()来挂载再往下
            再  判断有没有 template  
                 有: 那么他就会解析你的template  然后生成虚拟DOM   注意template不会包含外部的一些标签
                 没有: 那么他会解析el选择的标签整体作为模板

            brforeMount    在这个步骤 Vue还是模板没有解析的状态  操作的DOM对象也最终会失效  

            然后Vue会将 内存中的虚拟DOM转化为真实DOM

            Mounted  这个时候 已经转化为了真实DOM了 

            更新流程-------------------------------------
            beforeupdate 当数据发生改变之后  那么他会执行一个方法  此时 数据已经更新,但是页面还没有更新(解析)

            然后Vue会将新数据生成新的 虚拟DOM做对比(复用) 再将虚拟DOM转化为真实DOM   model---》view

            updated  这个方法中,数据和页面同步了

            销毁流程--------------------------------------
            Vm执行了$destroy方法之后 就会进入销毁流程
            beforedestroy   这个方法中数据还在  可以被调用但是对数据的修改是不奏效的  在这里做一些首尾工作(关闭定时器等)

            destroyed  这个方法中 vm已经被销毁了


            vm虽然被销毁了  但是为他绑定的系统的事件监听还在  自定义事件的话就会没有掉   vm.$destroy()
-->

<body>
    <!-- 2.给定一个容器 -->
    <div id="root">
        <h1>{{name}}</h1>
        <h1 @click="n++">{{n}}</h1>
        <button @click="bey">点我销毁vm</button>
    </div>

    <script type="text/javascript">
        Vue.config.productionTip = false; // 3.关闭生产环境提示
        // 4.使用Vue操作这个容器
       const mv= new Vue({
            el:'#root',
            data:{
                name:'曾黎',
                n:0
            },
            methods: {
                bey(){
                    console.log('Baibai')
                    this.$destroy()
                }
            },
            beforeCreate() {
                console.log('我是数据还没有创建号的初始化1状态',this)
                // debugger;
            },
            created() {
                console.log('我数据已经创建好了  数据监测 数据代理完成',this)
            },
            beforeMount() {
                console.log('刚创建完这个虚拟DOM,还没有转化为真实DOM 此时操作DOM最终无效',this)
            },
            mounted() {
                console.log('真实DOM已经解析到页面了 可以操作DOM元素',this)
            },
            beforeUpdate() {
                // 数据改变的时候调用
                console.log('此时数据已经更新,但是 页面还没有解析好,数据不一致')
              
            },
            updated() {
                console.log('数据和页面一致了')
            },
            beforeDestroy() {
                console.log('数据还在但是数据修改不奏效了')
                
            },
            destroyed() {
                console.log('数据已经没有了')
            },
        })
    </script>
</body>
</html>

生命周期总结
<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>el   data 的两种写法</title>
    <!-- 1.引入js依赖 -->
    <script type="text/javascript" src="../js/vue.js"></script>
</head>
<!-- 总结
        1.常用的回调
        mounted  这个时候页面真实DOM转化完成  可以完成发送AJAX请求   自定义事件绑定  开启定时器  开启消息订阅等初始化动作
        beforedestroy   这个时候是销毁之前  可以完成善后工作  比如  关闭定时器  关闭订阅消息

        2.一般来说  Vm是被动销毁的  销毁之后 自定义事件会跟着销毁  但是 原生的DOM不会被销毁
-->


<body>
    <!-- 2.给定一个容器 -->
    <div id="root">
        <h1 :style="{opacity:opacity}">我是{{n}}</h1>
        <button @click="n++">点我n++</button>
        <button @click="bey">点我销毁Vm</button>
    </div>

    <script type="text/javascript">
        Vue.config.productionTip = false; // 3.关闭生产环境提示
        // 4.使用Vue操作这个容器
        new Vue({
            el:'#root',
            data:{
                n:1,
                opacity:1
            },
            methods: {
                bey(){
                    this.$destroy()
                }
            },
            mounted() {
                // 接收定时器的id
            this.timer= setInterval(()=>{
                console.log('11')
            this.opacity = this.opacity-0.01
            if(this.opacity<=0) this.opacity=1
        },16)
            },

            beforeDestroy() {
                // 销毁之前关闭定时器
                clearInterval(this.timer)
            },

        })
    </script>
</body>
</html>

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值