深入浅出篇 — Vue

1,510 阅读9分钟

前言

本篇作为vue的知识梳理,包括:
- vue的创建
- vue的指令
- vue的插值
- vue的生命周期
- vue的组件
- vue的计算属性
- vue的组件
- 扩展——Es6模块化

vue的特点:

  • 渐进式(vue的侵入性很少)
  • 组件化
  • 数据响应式 -> 其会监控数据的变化,当数据发生变化时,自动重新渲染页面

创建vue工程

  • 直接在页面上引入vue.js
  • 使用脚手架(vue-cli)搭建工程

正课开始

一. 创建vue实例

<div id="app"></div>        //被挂载的元素,
<script>
    // 在这里无论是挂载,还是模板等都有多种写法,后面会慢慢接触
    const vm = new Vue({    // 创建一个vue实例
        el: "#app",          // 挂载 :  用来控制我们想控制的元素
        template: '',       // 模板 :  可用来书写代码,模板里只能有一个根元素 否则报错
        data: {},           // 数据 :  可能用到的数据
        methods: {}         // 方法 :  可能用到的函数  注意this指向,后面会提到
    })
</script>
知识点:
    当创建vue实例时,Vue会将下面配置成员提升到vue实例中
    1. data配置中的所有成员
    2. methods配置中的所有成员
    3. ...还有后面会介绍

二. 模板语法 - 插值

  • 当要插入数据时可在模板中使用插值
  • 在模板的元素内部使用 {{ js表达式 }}
例:
{{ num + 1 }}
{{ ok ? 'yes' : 'no' }}
{{ '123'.split('').reverse().join('') }}
...

三. $watch - 用于监控数据前后的改变

<div id="app">{{a}}</div>       // {{}}这个就是插值表达式 

<script>
    var data = {a : 1}
    
    var vm = new Vue ({ 
        el:'#app',
        
        data :data              // 注:这两个data不是一个
        // 前面的代表此对象的属性,而后面的代表新定义的变量
    })
    
    vm.$watch ('a',function (newval,oldval) {
        //第一个参数为观察的变量,第二个参数为回调函数
        console.log(newval,oldval)
    })
    vm.$data.a = 2
    //改变的数据要写在 vm.$watch 后
</script>
小知识点:
    上一节说过data配置中的所有成员,会提升到vue实例中
    - 所以 data.a == vm.a == vm.$data.a
    - 即 vm.$data == data

四. 模板语法 - 指令

  • 指令是带有v-前缀的特殊特性 ,通常作为元素的属性存在,名称上以 v- 开头
常用指令:
v-once  当添加上此指令时,会进行一次性的插值,当数据改变时插值处的内容不会更新
v-html  双大括号语法会将数据解释为普通的文本。而当添加上此指令时,会输出真正的html代码。 v-html = "xxx"
v-bind  Mustache语法不能作用到html特性上。当添加上此指令时,就可以作用在html特性上。 v-bind:属性="xxx"
v-if    根据值的真假来插入或移除该元素  v-if='xxx' , 当xxx取值为true时,该元素会被渲染
v-on    用于注册事件,[语法糖 @]。  @click = 'xxx' 
v-show  根据值的真假来插入或移除该元素  v-show ='xxx'
v-for   基于一个数组渲染一个列表,循环生成元素  v-for = '(item,index) in items'  :key = index  ,可用key属性来确定唯一值
v-model 双向数据绑定,是一个语法糖。指令在表单 <input> , <textarea> 及<select>元素上创建 
指令用法详解:
  • v-on

         在@click = 'xxx'中, 当xxx为函数时,这就用到了前面提到的methods属性
    
         <div id="app3">
             // 第二个实参 $event 为原始的dom事件
             <button  @click="click1('abc',$event)">提交</button>
             
         </div>
         
         <script>
             var vm = new Vue({
                 el: "#app3",
                 methods: {
                     click1: function (str, e) {
                         console.log(str, e)
                     }
                 }
             })
         </script>
    
  • v-bind 与class和style的特殊用法

         当v-bind 用于class和style时,vue.js做了专门的强化,表达式结果的类型除了字符串之外,还可以是对象或数组
         
         1. 当作用在class身上时
         
         <div id="app3">
             <div  :class='{active:isActive}'>2313</div>
                 //  active这个class是否存在 取决于数据属性isActive的取值
                 //  其可以和普通的class共存
                 //  也可以传入多个属性来动态切换多个class  {green:isGreen , red: "isRed"}
                 //  也可用数组的方式 : ['green','red']  这样就直接添加了这两个类名
                 //  可配合三元运算来获取动态样式    [isGreen?'green':'',isRed?'red':'']
         </div>
         
         <script>
             var vm = new Vue({
                 el: "#app3",
                 data :{
                     isActive : 'ture'  // 在这里只举了一个例子,其他同理
                 }
             })
         </script>
         
         
         2. 当作用在style身上时
         
         <div id="app3">
             <div :style='{color:color,fontSize:size}'>2313</div>
             
             //  同样此处也可以用三元运算 来动态绑定数据
             //  <div :style = '{background : isgreen ? 'green' : ""}'>2313</div>
         
         </div>
         
         <script>
             var vm = new Vue({
                 el: "#app3",
                 data :{
                     color:'red',
                     size:'20px',
                     isgreen : true
                 }
             })
      </script>
    
  • v-show 与 v-if 的区别

     v-if 是真正的渲染
     v-show 是通过控制css样式来改变元素的显示和隐藏,其元素会被渲染并保留在dom中 
    
  • v-model

      <div id="app3">
          <input type="text" v-model='val'>       // 这样就实现了input的双向数据绑定
              // 当input中的内容改变时,下方sapn标签内的内容也会改变
              
          <span>姓名:{{val}}</span>              //将val数据显示在页面中
      </div>
      <script>
          
          var vm = new Vue({
              el: "#app3",
              data: {
                  val: "土行孙"                           // 设置input中的初始值
              }
              methods:{
                  hand:function(){
                      this.val                 //  可通过this对象获取到data中的值
                  }
          })
      </script>
    

五. 模板的配置

  • 页面中直接书写

  • 在template配置中书写(常见)

  • 在render中手动用函数创建,render函数的参数是创建虚拟dom对象的方法

  • render的优先级> template > 在页面中书写

  •      <script>
          
          var vm = new Vue({
              el: "#app3",
              template:'<h1>商品和库存管理</h1>' ,  // 模板
              render(createElement){
                  return createElement('h1','hello')
              }
          })
      </script>
    

六. 小结:

  1. 配置对象中
  • el : 配置控制的元素 , css选择器
  • data : 管理的数据,该数据是响应式的
  • methods : 配置方法 方法中的this指向vue实例, 所以不能使用箭头函数, 会干扰
  1. 挂载的配置
  • 通过el进行配置
  • 使用vue实例中的$mount函数进行配置

七. 计算属性 computed

  • 计算属性,其中的配置也会提升到vue实例中
  • 通常情况下,计算属性是用户通过data或其他计算属性得到的数据
例:
1. 普通篇
    <div id="app">
        <h1>名字:{{name}}</h1>
        <h1>qq:{{qqNumber}}</h1>
        <h5>合计信息:{{full}}</h5>   // 计算属性会自动的帮你带调用这个函数来得到这个结果,所以不用这么些full()
    </div>
<script>
    var vm = new Vue({
        el: "#app",
        data: {
            name: '战士',
            qqNumber: 123456789
        },
        //这就是计算属性,当然这个功能也能用其他方式完成,比如methods方法,后面会介绍他们的不同
        computed: {
            full() {   // 这样写是只读的,改变数据也没用
                return this.name + this.qqNumber
            }
        }

    })
</script>

 2. 进阶篇
    <script>
    var vm = new Vue({
        el: "#app3",
        data: {
            name: '战士',
            qqNumber: 123456789
        },
        // 只看这里
        computed: {
            full: { // 这样配置就既能读取值 又能设置值了
                get() {
                    return this.name + this.qqNumber
                },
                set(newVal) {
                    //比如再用到双向数据绑定的时候,就能监控到改变的值了
                    console.log(newVal)
                }

            }
        }

    })
</script>
计算属性与方法的区别:
  • 计算属性会检查计算属性的依赖,当依赖没有发生变化时,vue会直接使用之前缓存的结果,而不会重新计算
  • 计算属性可以配置get和set,分别用于读取时和设置时
  • 计算属性的读取函数,不可以有参数,有参数无意义

八. 组件的创建和注册

  • 组件是页面中可重复使用的功能单元
  • 组件的创建 : 组件对于开发者,是一个普通的配置对象,该配置对象几乎和之前的vue配置对象一样
  • 组件的注册分为两种: 全局注册和局部注册
  • 组件可以嵌套重复使用,因此会形成一个组件树,树的根叫做根组件
组件的使用:
    <div id="app3">
        <vue></vue>   // 组件的名称
    </div>
    <script>
    // 定义全局组件  第一个参数为组件的名字 , 第二个参数为一个配置对象
    Vue.component('vue', {template: '<h1>看到你,很开心!!!</h1>'})

    var vm = new Vue({
        el: "#app3",
        data: qq = 123,

        // 局部注册组件
        components: {
            vue: {
                // 在这里接收了属性并赋值
                template: '<h1 :title = 1>看到你{{str}},很开心{{title}}!!!</h1>',
                // 组件中也可以有数据和方法
                data: function () {
                    return {
                        str: "的时候"
                    }
                },
                // 通过props为组件定义属性
                props: ['title']
            },
            //这里的属性名为 组件名称, 属性值为一个配置对象
        }
    })

九. vue的生命周期

new Vue() 从创建vue实例开始

  • beforeCreate:组件实例刚刚创建好之后,此时,组件实例中还没有提升任何的成员

  • created:组件实例中已经提升了所有成员,但是,此时还没有渲染页面的任何内容

  • beforeMount: 组件即将进行渲染,但是还没有进行渲染,此时已经编译好模板,渲染的所有条件已经满足

  • mounted : 组件已经完成了渲染 (页面可见)[重要!!!!]

  • 此时,等待组件更新(当一个组件的属性或状态发生变化的时候,会自动重新渲染)

  • beforeUpdate:组件即将更新,但还没有更新,此时得到的数据是新的,但界面是旧的

  • updated:组件已经完成更新,此时数据和界面都是新的

  • beforeDestroy:当组件即将被销毁时

  • destroyed: 组件已经被销毁后

十. 扩展 - 初识模块化

模块化简介
  • 历史上,JavaScript一直没有模块(module)体系,无法将一个大程序拆分成互相依赖的小文件,再用简单的方法拼起来。而其他语言都有此功能
  • 在ES6之前,社区制定过一些模块加载方案,最主要的有CommonJS和AMD两种。前者用于服务器,后者用于浏览器。ES6在语言规格的层面上,实现了模块功能,而且实现得相当简单,完全可以取代现有的CommonJS和AMD规范,成为浏览器和服务器通用的模块解决方案。
  • ES6模块的设计思想,是尽量的静态化,使得编译时就能确定模块的依赖关系(这种加载称为'编译时加载'),以及输入和输出的变量。而CommonJS和AMD模块,都只能在运行时确定这些东西
实现模块化的方式 :
  • CommonJs
  • AMD
  • CMD
  • ES6官方规范
Es6模块化 :
  • 模块中的所有变量,全部是局部的,只能在模块内部使用
  • 模块导出 : export default 导出的数据
  • 模块导入(要在所有代码之前) : import 变量名 from "模块路径"