Vue 2.0 知识点总结

Vue 2.0 知识点总结

  • Vue 2.0 知识点总结
    • 1. vue 简介
      • 1.1 框架的概念
      • 1.2 Vue的概念
      • 1.3 vue 的特性
        • 数据驱动视图
        • 双向数据绑定
        • MVVM
        • MVVM 的工作原理
    • 2. vue 的基本使用
      • 2.1 初步导入和配置
      • 2.2 定义和使用数据
    • 3. vue 的调试工具
      • 3.1 安装 vue-devtools 调试工具
      • 3.2 配置 Chrome 浏览器中的 vue-devtools
      • 3.3 使用 vue-devtools 调试 vue 页面
    • 4. vue 的指令
      • 4.1 指令的概念
      • 4.2 六大类指令
        • 1. **内容渲染**指令
        • 2. **属性绑定**指令
        • 3. **事件绑定**指令
        • 4. **双向绑定**指令
        • 5. **条件渲染**指令
        • 6. **列表渲染**指令
      • 4.3 自定义指令
        • 1. 什么是自定义指令
        • 2. 自定义指令的分类
        • 3. 私有自定义指令
        • 4. 使用自定义指令
        • 5. 为自定义指令动态绑定参数值
        • 6. 通过 binding 获取指令的参数值
        • 7. update 函数
        • 8. 函数简写
        • 9. 全局自定义指令
    • 5.过滤器
      • 5.1 过滤器概念
      • 5.2 定义过滤器
      • 5.3 私有过滤器和全局过滤器
      • 5.4 连续调用多个过滤器
      • 5.5 过滤器传参
      • 5.6 过滤器的兼容性
    • 6. watch 侦听器
      • 6.1 什么是 watch 侦听器
      • 6.2 使用 watch 检测用户名是否可用
      • 6.3 immediate 选项
      • 6.4 deep 选项
      • 6.5 监听对象单个属性的变化
    • 7. 计算属性
      • 7.1 什么是计算属性
      • 7.2 计算属性的特点
      • 7.3 计算属性-案例
    • 8. vue-cli
      • 8.1 单页面应用程序
      • 8.2 什么是 vue-cli
      • 8.3 安装和使用
      • 8.4 vue 项目的运行流程
      • 8.5 Vue 组件库
        • 1. vue-cli 手动选择要安装的功能
        • 2. ESLint 基本语法
          • 2.1 什么是 ESLint?
          • 2.2 常见的 ESLint 规则
          • 2.3 修改 vue-cli 项目的语法规则
    • 9. vue 组件
      • 9.1 什么是组件化开发
      • 9.2 vue 中的组件化开发
      • 9.3 vue 组件的三个组成部分
        • 1. template
        • 2. script
        • 3. style
      • 9.4 组件之间的父子关系
        • 1. 使用组件的三个步骤
        • 2. 通过 components 注册的是私有子组件
        • 3. 注册全局组件
      • 9.5 组件的 props
        • 1. props 是只读的
        • 2. props 的 default 默认值
        • 3. props 的 type 值类型
        • 4. props 的 required 必填项
        • 5. 组件之间的样式冲突问题
      • 9.6 组件的基本使用
        • 1. 思考:如何解决组件样式冲突的问题
        • 2. style 节点的 scoped 属性
        • 3. /deep/ 样式穿透
      • 9.7 动态组件
        • 1. 什么是动态组件
        • 2. 如何实现动态组件渲染
        • 3. 使用 keep-alive 保持状态
        • 4. keep-alive 对应的生命周期函数
        • 5. keep-alive 的 include 属性
    • 10. 组件之间的数据共享
      • 10.1 组件之间的关系
      • 10.2 父子组件之间的数据共享
        • 1. 父组件向子组件共享数据
        • 2. 子组件向父组件共享数据
      • 10.3 兄弟组件之间的数据共享
    • 11. vuex
      • 11.1 Vuex 起步
        • 1. Vuex 是什么
        • 2. 使用 Vuex 的好处
        • 3. 在项目中安装和**配置 Vuex**
          • 3.1 安装 Vuex 的依赖包
          • 3.2 封装 Store 模块
          • 3.3 把 Store 实例挂载到 Vue 实例上
      • 11.2 State 的基本使用
        • 1. 什么是 State
        • 2. 组件访问 State 数据
          • 2.1 第一种方式
          • 2.2 第二种方式
          • 2.3 拓展:mapState 辅助函数的原理
      • 11.3 Mutation 的基本使用
        • 1. 怎样修改 State 中的数据
        • 2. Mutation 是什么
        • 3. State、组件、Mutation 之间的关系
        • 4. Mutation 的使用步骤
          • 4.1 载荷(Payload)
          • 4.2 提交载荷(Payload)
        • 5. mapMutations 辅助函数
      • 11.4 Action 的基本使用
        • 1. Mutation 必须是同步函数
        • 2. Action 是什么
        • 3. 定义 Action 方法
        • 4. 调用 Action 方法
          • 4.1 第一种方式
          • 4.2 第二种方式
      • 11.5 Getter 的基本使用
        • 1. 组件中计算属性的局限性
        • 2. Getter 是什么
        • 3. 定义 Getter 方法
        • 4. 访问 Getter
          • 4.1 第一种方式
          • 4.2 第二种方式
      • 11.6 Module 的基本使用
        • 1. 思考:当前遇到的问题
        • 2. Module 是什么
        • 3. 定义模块
        • 4. 注册模块
        • 5. namespaced(命名空间)
        • 6. 访问Module
          • 6.1 通过模块的注册名称访问模块下的成员
          • 6.2 访问命名空间下的 state 数据
          • 6.3 访问命名空间下的 mutation 方法
          • 6.4 访问命名空间下的 action 和 getter
    • 12.组件的生命周期
      • 12.1 生命周期 & 生命周期函数
      • 12.2 组件生命周期函数的分类
      • 12.3 生命周期图示
    • 13. ref 引用
      • 13.1 什么是 ref 引用
      • 13.2 使用 ref 引用 DOM 元素
      • 13.3 使用 ref 引用组件实例
      • 13.4 控制文本框和按钮的按需切换
      • 13.5 让文本框自动获得焦点
      • 13.6 this.$nextTick(cb) 方法
    • 14. 路由
      • 14.1 路由的基本概念与原理
        • 1. 后端路由
        • 2. 前端路由
      • 14.2 vue-router的基本使用
        • 1. 基本使用步骤
        • 2. 路由重定向
        • 3. Vue路由-404页面
      • 14.3 vue-router嵌套路由
        • 1. 嵌套路由功能分析
        • 2. 父路由组件模板
        • 3. 子级路由模板
        • 4. 嵌套路由配置
      • 14.4 vue-router动态路由匹配
        • 1. 思考:
        • 2. 应用场景:通过动态路由参数的模式进行路由匹配
        • 3. 路由组件传递参数
          • 3.1 props的值为布尔类型
          • 3.2 props的值为对象类型
          • 3.3 props的值为函数类型
      • 14.5 vue-router命名路由
        • 1. 命名路由的配置规则
      • 14.6 vue-router编程式导航
        • 1. 页面导航的两种方式
        • 2. 编程式导航基本用法
        • 3. 编程式导航参数规则
      • 14.5 HTML5 History 模式
    • 15. 插槽
      • 15.1 什么是插槽
      • 15.2 插槽的基础用法
      • 15.3 默认插槽
      • 15.4 具名插槽
        • 1. 为具名插槽提供内容
        • 2. 具名插槽的简写形式
      • 15.5 作用域插槽
        • 1. 使用作用域插槽
        • 2. 解构插槽 Prop


Vue 2.0 知识点总结

1. vue 简介

1.1 框架的概念

  • 概念:框架指的就是程序员必须遵守的规则或约束。
  • 例如:
    1. 想要驾驶汽车,就必须遵守交通规则;
    2. 想要使用 vue 开发前端项目,就必须掌握 vue 的使用规则

1.2 Vue的概念

  • vue 的官方文档(使用说明书):https://cn.vuejs.org/v2/guide/

  • 官方给出的概念:vue (读音 /vjuː/,类似于 view) 是一套用于构建用户界面的渐进式框架

  • vue 不强求程序员一次性接受并使用它的全部功能特性。

Vue 2.0 知识点总结_第1张图片

1.3 vue 的特性

  • vue 框架的特性,主要体现在如下两方面:
    1. 数据驱动视图
    2. 双向数据绑定
数据驱动视图

在使用了 vue 的页面中,data 数据的变化,会导致页面结构的重新渲染。示意图如下:

Vue 2.0 知识点总结_第2张图片

双向数据绑定
  1. data 数据的变化,会导致页面的重新渲染
  2. 表单数据的变化,会被自动更新到 data 数据中

Vue 2.0 知识点总结_第3张图片

MVVM
  • MVVM 是 vue 实现数据驱动视图和双向数据绑定的核心原理
  • MVVM 指的是 ModelViewViewModel
  • 它把每个 HTML 页面都拆分成了这三个部分,如图所示:

Vue 2.0 知识点总结_第4张图片

MVVM 的工作原理
  • ViewModel 作为 MVVM 的核心,是它把当前页面的数据源(Model)和页面的结构(View)连接在了一起。

Vue 2.0 知识点总结_第5张图片

  • 数据源发生变化时,会被 ViewModel 监听到,VM 会根据最新的数据源自动更新页面的结构
  • 表单元素的值发生变化时,也会被 VM 监听到,VM 会把变化过后最新的值自动同步到 Model 数据源中

2. vue 的基本使用

2.1 初步导入和配置

  • 步骤1:导入 Vue 的 JS 文件,window 全局挂载名为 Vue 的构造函数
  • 步骤2:new 构造函数,创建 Vue 的实例对象,用 vm 来表示
  • 步骤3:通过 el 选项,指定当前的 Vue 实例要控制页面上哪个区域的渲染
  • 步骤4:创建需要被 Vue 实例控制的 DOM 区域。

Vue 2.0 知识点总结_第6张图片
注意:选择器一定要和 el 选项的值匹配

2.2 定义和使用数据

  • vue 提供了 data 选项,专门用来定义数据,供页面渲染时使用。

Vue 2.0 知识点总结_第7张图片

3. vue 的调试工具

3.1 安装 vue-devtools 调试工具

  • vue 官方提供的 vue-devtools 调试工具,能够方便开发者对 vue 项目进行调试与开发。
  1. Chrome 浏览器在线安装 vue-devtools

  2. FireFox 浏览器在线安装 vue-devtools

3.2 配置 Chrome 浏览器中的 vue-devtools

  • 点击 Chrome 浏览器右上角的 按钮,选择更多工具 -> 扩展程序 -> Vue.js devtools 详细信息,并勾选如下的两个选项:

Vue 2.0 知识点总结_第8张图片

3.3 使用 vue-devtools 调试 vue 页面

  • 在浏览器中访问一个使用了 vue 的页面,打开浏览器的开发者工具,切换到 Vue 面板,即可使用 vue-devtools调试当前的页面。

Vue 2.0 知识点总结_第9张图片

4. vue 的指令

4.1 指令的概念

  • 概念:指令(Directives)是 vue 为开发者提供的一套特殊语法。
  • 为啥要学:提高程序员渲染 DOM 的效率。
  • vue 中的指令按照不同的用途可以分为如下 6 大类
    1. 内容渲染指令
    2. 属性绑定指令
    3. 事件绑定指令
    4. 双向绑定指令
    5. 条件渲染指令
    6. 列表渲染指令
  • 注意:指令是 vue 开发中最基础、最常用、最简单的知识点。

4.2 六大类指令

1. 内容渲染指令
  • 内容渲染指令用来辅助开发者渲染 DOM 元素的文本内容。
  • 常用的内容渲染指令有如下 3 个:
    1. v-text 填充纯文本
    • 不解析标签
    • 相比插值表达式更加简洁
    1. 插值表达式
    • 表达式:{{}}
    • 优点:大家都遵循同样的规则写代码,代码可读性明显提高了,方便后期的维护。
    • 缺点:没有专门提供事件机制。
    1. v-html 填充HTML片段
    • v-text 指令和插值表达式只能渲染纯文本内容。如果要把包含 HTML 标签的字符串渲染为页面的 HTML 元素,则需要用到 v-html 这个指令
    1. 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>Documenttitle>
    head>
    
    <body>
      <div id="app">
        <p>------------ v-text ---------------p>
        
        <p v-text="username">名字是:p>
        <p v-text="gender">性别:p>
    
        <p>------------ { { } } ---------------p>
        
        
        <p>名字是:{{ username }}p>
        <p>性别是:{{ gender }}p>
        <p>{{ username + '~~~' }}p>
        <p>{{ username + gender }}p>
        <p>{{ 123 }}p>
        <p>{{ true }}p>
        <p>{{ 1>3 ? '成立' : '不成立' }}p>
        <p>{{ username.length }}p>
        
        
        <p>{{ username.split('').reverse().join('') }}p>
    
        <p>--------------- v-html ---------------p>
        <div v-text="info">div>
        <div>{{info}}div>
        <div v-html="info">div>
      div>
    
      <script src="./lib/vue-2.6.12.js">script>
      <script>
        const vm = new Vue({
          el: '#app',
          // 声明数据
          data: {
            username: '汤哥1234',
            gender: '男',
            info: '

    这是一个h3标签

    '
    } })
    script> body> html>
2. 属性绑定指令
  • 语法:v-bind:属性名=“表达式”
  • 简写::属性名=“表达式”
  • 作用:标签的属性与vue表达式动态绑定
  • 注意:在实际开发中,v-bind: 指令特别常用,因此,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>Documenttitle>
    head>
    
    <body>
      <div id="app">
        
        
        
        <input type="text" :placeholder="info">
        <img :src="url" alt="">
        <h3 :title="txt + '~~~~'">xxxxxxxxxxxh3>
        <input :type="password" placeholder="v-bind: 是属性绑定指令">
      div>
    
      <script src="./lib/vue-2.6.12.js">script>
      <script>
        const vm = new Vue({
          el: '#app',
          data: {
            info: 'abcdefg',
            // 图片的 url 地址
            url: 'https://img0.baidu.com/it/u=3280618160,1318135601&fm=253&fmt=auto&app=138&f=JPEG?w=800&h=500',
            txt: '这是h3的标题',
            password: 'password'
          }
        })
      script>
    body>
    
    html>
    
3. 事件绑定指令
  • 语法:

    1. v-on:事件名="methods中的函数(实参)"
    2. v-on:事件名="methods中的函数"
  • 简写: @事件名="methods中的函数"

  • 作用:给DOM元素绑定事件

  • 事件对象

    1. 无参数,直接用形参接收
    2. 有参数,手动传入 $event 对象
  • $event:$event 是 vue 提供的特殊变量,用来表示原生的事件参数对象 event。$event 可以解决事件参数对象event被覆盖的问题。

    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>Documenttitle>
    head>
    
    <body>
      <div id="app">
        <h3>count是:{{ count }}h3>
        
        
        
        <button @click="add(2, $event)">+Nbutton>
      div>
    
      <script src="./lib/vue-2.6.12.js">script>
      <script>
        const vm = new Vue({
          el: '#app',
          data: {
            count: 0
          },
          methods: {
            // 绑定事件,必然会有事件对象 event
            add (n, e) {
              console.log(n, e.target);
              // e.target 是事件的触发源
              // 记住:e.target 是原生的 DOM 对象
              e.target.style.backgroundColor = 'red'
    
              this.count += n
    
              // 在 add 函数中,调用 show 函数
              this.show()
            },
            show () {
              console.log('触发了 methods 中的 show 函数')
            }
          },
        })
      script>
    body>
    
    html>
    
  • 事件修饰符

    • 语法:@事件名.修饰符名
    • 常用的 5 个事件修饰符如下:
      Vue 2.0 知识点总结_第10张图片
    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>Documenttitle>
      <style>
        .outer {
          padding: 100px 50px;
          background-color: orange;
        }
    
        .inner {
          padding: 50px;
          background-color: cyan;
        }
      style>
    head>
    
    <body>
      <div id="app">
        
        <a href="https://juejin.cn/editor/drafts/7075957234605244447" @click.prevent="show">去掘金网站a>
    
        <div class="outer" @click="handler2">
          
          <div class="inner" @click.stop="handler1">内部的 divdiv>
        div>
      div>
    
      <script src="./lib/vue-2.6.12.js">script>
      <script>
        const vm = new Vue({
          el: '#app',
          methods: {
            show () {
              console.log('点击了 a 链接')
            },
            handler1 () {
              console.log('点击了内部的盒子')
            },
            handler2 () {
              console.log('点击了外部的盒子')
            }
          },
        })
      script>
    body>
    
    html>
    
  • 按键修饰符

    • 在监听键盘事件时,我们经常需要判断详细的按键。此时,可以为键盘相关的事件添加按键修饰符
    • 回车键触发 @keyup.enter
    • 取消键触发 @keyup.esc
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>Documenttitle>
head>

<body>
  <div id="app">
    
    
    
    
    
    <input type="text" @keyup.enter="submit" @keyup.esc="clear">
  div>

  <script src="./lib/vue-2.6.12.js">script>
  <script>
    const vm = new Vue({
      el: '#app',
      methods: {
        submit (e) {
          console.log('触发了 submit 函数')
          console.log(e.target.value)
        },
        clear (e) {
          console.log('触发了 esc 函数')
          e.target.value = ''
        }
      },
    })
  script>
body>

html>
4. 双向绑定指令
  • vue 提供了 v-model 双向数据绑定指令,用来辅助开发者在不操作 DOM 的前提下,快速获取表单的数据

  • 语法: v-model="vue数据变量"

  • 作用:把标签的 value 属性 与 vue变量 双向绑定

  • v-model 指令的修饰符

    • 为了方便对用户输入的内容进行处理,vue 为 v-model 指令提供了 3 个修饰符,分别是:

    Vue 2.0 知识点总结_第11张图片

    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>Documenttitle>
    head>
    
    <body>
      <div id="app">
        <h3>count是:{{count}}h3>
        <button @click="count += 1">+1button>
    
        <hr>
    
        
        
        
        
        
        
        <input type="text" :value="count" @input="getValue">
    
        <hr>
    
        
        
        
        <input type="text" v-model.number="count">
    
        <hr>
        
        
        <input type="text" v-model.lazy.trim="msg">
    
        <hr>
        
        
        
        
        
      div>
    
      <script src="./lib/vue-2.6.12.js">script>
      <script>
        // 3. vm 实例就是 ViewModel
        const vm = new Vue({
          // 2. el 所指定的区域,就是 View 视图
          el: '#app',
          // 1. Model 数据源
          data: {
            count: 0,
            msg: 'abc'
          },
          methods: {
            getValue(e) {
              // console.log(typeof e.target.value)
              this.count = parseInt(e.target.value)
            }
          },
        })
      script>
    body>
    
    html>
    
5. 条件渲染指令
  • 条件渲染指令用来辅助开发者按需控制 DOM 的显示与隐藏。条件渲染指令有如下两个,分别是:

    • v-if
    • v-show
  • 语法:

    • v-show="vue变量"
    • v-if="vue变量"
  • 原理:

    • v-show 用的display:none隐藏 (频繁切换使用)
    • v-if(不频繁): 动态创建和移除元素插入或移除节点
  • v-if 和 v-show 的区别

    1. 实现原理不同:
    • v-if 指令会动态地创建或移除 DOM 元素,从而控制元素在页面上的显示与隐藏;
    • v-show 指令会动态为元素添加或移除 style=“display: none;” 样式,从而控制元素的显示与隐藏;
    1. 性能消耗不同:
    • v-if 有更高的切换开销,而 v-show 有更高的初始渲染开销。
    • 如果需要非常频繁地切换,则使用 v-show 较好
    • 如果在运行时条件很少改变,则使用 v-if 较好
    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>Documenttitle>
    head>
    
    <body>
      <div id="app">
        <button @click="flag = !flag">Togglebutton>
        <p v-if="!flag">这是被 v-if 控制的元素p>
        <p v-show="flag">这是被 v-show 控制的元素p>
      div>
    
      <script src="./lib/vue-2.6.12.js">script>
      <script>
        const vm = new Vue({
          el: '#app',
          data: {
            // 如果 falg 为 true,则展示被控制的元素
            // 如果 falg 为 false,则隐藏被控制的元素
            flag: false
          }
        })
      script>
    body>
    
    html>
    
    
  • v-else

    • v-if 可以单独使用,或配合 v-else 指令一起使用:
    • 注意:v-else 指令必须配合 v-if 指令一起使用,否则它将不会被识别!
  • v-else-if

    • v-else-if 指令,顾名思义,充当 v-if 的“else-if 块”,可以连续使用:
    • 注意:v-else-if 指令必须配合 v-if 指令一起使用,否则它将不会被识别!
    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>Documenttitle>
    head>
    
    <body>
      <div id="app">
        
        
        <p v-if="flag">条件成立p>
        <p v-else>条件不成立p>
    
        <hr>
        <h3 v-if="age>=18">成年人,可以抽烟喝酒烫头h3>
        <h1 v-else>未成年,漫画 + 娃哈哈h1>
    
        <hr>
    
        <p v-if="score === 'A'">优秀p>
        <p v-else-if="score === 'B'">良好p>
        <p v-else-if="score === 'C'">一般p>
        <p v-else>p>
    
    
      div>
    
      <script src="./lib/vue-2.6.12.js">script>
      <script>
        const vm = new Vue({
          el: '#app',
          data: {
            flag: true,
            age: 18,
            // A -> 优秀
            // B -> 良好
            // C -> 一般
            // D -> 差
            score: 'A'
          }
        })
    
      script>
    body>
    
    html>
    
6. 列表渲染指令
  • vue 提供了 v-for 列表渲染指令,用来辅助开发者基于一个数组来循环渲染一个列表结构。v-for 指令需要使

  • 用 item in list 形式的特殊语法,其中:

    • list 是待循环的数组
    • item 是被循环的每一项
  • v-for 中的索引

  • v-for 指令还支持一个可选的第二个参数,即当前项的索引。

    • 语法格式为 (item, index) in list
    • 注意:v-for 指令中的 item 项和 index 索引都是形参,可以根据需要进行重命名。例如 (user, i) in userlist
    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>Documenttitle>
      <style>
        table {
          width: 600px;
          border-collapse: collapse;
        }
    
        td,
        th {
          border: 1px solid #efefef;
          line-height: 35px;
          font-size: 12px;
          text-align: center;
        }
      style>
    head>
    
    <body>
      <div id="app">
        <table>
          <thead>
            <tr>
              <th>idth>
              <th>nameth>
              <th>ageth>
              <th>indexth>
            tr>
          thead>
          <tbody>
            
            
            
            
            
            
            
    
            
            
    
            
            
            
            <tr v-for="(item, index) in list" :key="item.id">
              <td>{{ item.id }}td>
              <td>{{ item.name }}td>
              <td>{{ item.age }}td>
              <td>索引是:{{ index }}td>
            tr>
          tbody>
        table>
      div>
     
      <script src="./lib/vue-2.6.12.js">script>
      <script>
        const vm = new Vue({
          el: '#app',
          data: {
            // 用户的数组
            list: [
              { id: 1, name: '老汤', age: 35 },
              { id: 2, name: '狗哥', age: 34 },
              { id: 3, name: '小彬彬', age: 18 },
              { id: 4, name: '杨耀', age: 20 }
            ]
          }
        })
      script>
    body>
    
    html>
    
  • 使用 key 维护列表的状态

    • 当列表的数据变化时,默认情况下,vue 会尽可能的复用已存在的 DOM 元素,从而提升渲染的性能。但这种默认的性能优化策略,会导致有状态的列表无法被正确更新。
    • 为了给 vue 一个提示,以便它能跟踪每个节点的身份,从而在保证有状态的列表被正确更新的前提下,提升渲染的性能。此时,需要为每项提供一个唯一的 key 属性:
  • key 的注意事项

    1. key 的值只能是字符串或数字类型
    2. key 的值必须具有唯一性(即:key 的值不能重复)
    3. 建议把数据项 id 属性的值作为 key 的值(因为 id 属性的值具有唯一性)
    4. 使用 index 的值当作 key 的值没有任何意义(因为 index 的值不具有唯一性)
    5. 建议使用 v-for 指令时一定要指定 key 的值(既提升性能、又防止列表状态紊乱)
    DOCTYPE html>
    <html lang="en">
    
    <head>
      <meta charset="UTF-8">
      <meta name="viewport" content="width=device-width, initial-scale=1.0">
      <title>Documenttitle>
    head>
    
    <style>
      li {
        list-style: none;
      }
    style>
    
    <body>
      
      <div id="app">
    
        
        <div>
          <input type="text" v-model="name">
          <button @click="addNewUser">添加button>
        div>
    
        
        <ul>
          
          
          
          
          
          <li v-for="(user, index) in userlist" :key="user.id">
            <input type="checkbox" />
            姓名:{{user.name}}
          li>
        ul>
      div>
    
      <script src="./lib/vue-2.6.12.js">script>
      <script>
        const vm = new Vue({
          el: '#app',
          data: {
            // 用户列表
            userlist: [
              { id: 1, name: '张三疯' },
              { id: 2, name: '桑三炮' },
              { id: 3, name: '倪大野' }
            ],
            // 输入的用户名
            name: '',
            // 下一个可用的 id 值
            nextId: 4
          },
          methods: {
            // 点击了添加按钮
            addNewUser () {
              if (this.name === '') {
                this.userlist.unshift({ id: this.nextId, name: '禽兽' })
                this.name = ''
                this.nextId++
              } else {
                this.userlist.unshift({ id: this.nextId, name: this.name })
                this.name = ''
                this.nextId++
              }
    
            }
          },
        })
      script>
    body>
    
    html>
    

4.3 自定义指令

Vue 2.0 知识点总结_第12张图片

1. 什么是自定义指令
  • vue 官方提供了 v-text、v-for、v-model、v-if 等常用的指令。
  • 除此之外 vue 还允许开发者自定义指令。
2. 自定义指令的分类
  • vue 中的自定义指令分为两类,分别是:
    • 私有自定义指令
    • 全局自定义指令
3. 私有自定义指令
  • 在每个 vue 组件中,可以在 directives 节点下声明私有自定义指令。示例代码如下:

Vue 2.0 知识点总结_第13张图片

directives: {
focus: {
// 指令的定义
inserted: function (el) {
el.focus()
} }
}
4. 使用自定义指令
  • 在使用自定义指令时,需要加上 v- 前缀。示例代码如下:

Vue 2.0 知识点总结_第14张图片

5. 为自定义指令动态绑定参数值
  • 在 template 结构中使用自定义指令时,可以通过等号(=)的方式,为当前指令动态绑定参数值

Vue 2.0 知识点总结_第15张图片

6. 通过 binding 获取指令的参数值
  • 在声明自定义指令时,可以通过形参中的第二个参数,来接收指令的参数值:

Vue 2.0 知识点总结_第16张图片

7. update 函数
  • bind 函数只调用 1 次:当指令第一次绑定到元素时调用,当 DOM 更新时 bind 函数不会被触发。
  • update 函数会在每次 DOM 更新时被调用。示例代码如下:

Vue 2.0 知识点总结_第17张图片

8. 函数简写
  • 如果 bind 和update 函数中的逻辑完全相同,则对象格式的自定义指令可以简写成函数格式:

Vue 2.0 知识点总结_第18张图片

9. 全局自定义指令
  • 全局共享的自定义指令需要通过“Vue.directive()”进行声明,示例代码如下:

Vue 2.0 知识点总结_第19张图片

5.过滤器

5.1 过滤器概念

  • 过滤器(Filters)是 vue 为开发者提供的功能,常用于文本的格式化
  • 过滤器可以用在两个地方:
    1. 插值表达式
    2. v-bind 属性绑定。
  • 过滤器应该被添加在 JavaScript 表达式的尾部,由“管道符”进行调用

5.2 定义过滤器

  • 在创建 vue 实例期间,可以在 filters 节点中定义过滤器
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>Documenttitle>
head>

<body>
  <div id="app">
    
    
    
    <p>{{ message | capt }}p>
    <p>{{ info | capt }}p>
  div>

  <script src="./lib/vue-2.6.12.js">script>
  <script>
    // 声明过滤器的语法:
    // Vue.filter('过滤器的名字', 过滤器的fucntion函数)
    // 过滤器的本质:就是一个 function 函数
    // 过滤器的 function 函数,第一个形参,永远都是 | 前面那个值
    Vue.filter('capt', function (val) {
      // 注意:过滤器函数,必须 return 一个处理的结果,
      // 如果没有 return 任何结果,就是一个无效的过滤器

      // 1. 把 val 的首字母转为大写
      const result = val.charAt(0).toUpperCase() + val.slice(1)
      // 2. 把转化的结果,return 出去
      return result
    })

    const vm = new Vue({
      el: '#app',
      data: {
        message: 'hello vue.js',
        info: 'my name is xxx'
      }
    })
  script>
body>

html>

5.3 私有过滤器和全局过滤器

  • 在 filters 节点下定义的过滤器,称为私有过滤器,因为它只能在当前 vm 实例所控制的 el 区域内使用。
  • 如果希望在多个 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>Documenttitle>
head>

<body>
  <div id="app">
    
    
    
    <p>{{ message | capt }}p>
    <p>{{ info | capt }}p>
    <p>{{ message | test }}p>
    <p>--------------p>
    <p>{{ message | capt | test }}p>
  div>

  <hr>

  <div id="app2">
    <h3>{{ msg | capt }}h3>
    
  div>

  <script src="./lib/vue-2.6.12.js">script>
  <script>
    // 声明过滤器的语法:
    // Vue.filter('过滤器的名字', 过滤器的fucntion函数)
    // 过滤器的本质:就是一个 function 函数
    // 过滤器的 function 函数,第一个形参,永远都是 | 前面那个值
    Vue.filter('capt', function (val) {
      // 注意:过滤器函数,必须 return 一个处理的结果,
      // 如果没有 return 任何结果,就是一个无效的过滤器

      // 1. 把 val 的首字母转为大写
      const result = val.charAt(0).toUpperCase() + val.slice(1)
      // 2. 把转化的结果,return 出去
      return result
    })

    const vm = new Vue({
      el: '#app',
      data: {
        message: 'hello vue.js',
        info: 'my name is xxx'
      },
      // 私有过滤器节点
      filters: {
        // 形参中的 val 就是调用过滤器时候, | 前面那个值
        test(val) {
          return val + '~~'
        }
      }
    })

    const vm2 = new Vue({
      el: '#app2',
      data: {
        msg: 'welcome xxx'
      }
    })
  script>
body>

html>

5.4 连续调用多个过滤器

  • 过滤器可以串联地进行调用
 <p>{{ message | capt | test }}p>

5.5 过滤器传参

  • 过滤器的本质是 JavaScript 函数,因此可以接收参数
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>Documenttitle>
head>

<body>
  <div id="app">
    <p>{{ msg | maxLength(3) }}p>
    <p>{{ maxLength2(msg, 5) }}p>
  div>

  <script src="./lib/vue-2.6.12.js">script>
  <script>
    Vue.filter('maxLength', function (val, endIndex = 3) {
      if (val.length <= endIndex) {
        return val
      }
      // 字符串的 slice 函数,接收俩参数:
      // 开始的下标(包含)
      // 结束的下标(不包含)
      // slice/substr/substring
      return val.slice(0, endIndex) + '...'
    })

    const vm = new Vue({
      el: '#app',
      data: {
        msg: '1234567890'
      },
      methods: {
        maxLength2(val, endIndex = 3) {
          if (val.length <= endIndex) {
            return val
          }
          // 字符串的 slice 函数,接收俩参数:
          // 开始的下标(包含)
          // 结束的下标(不包含)
          // slice/substr/substring
          return val.slice(0, endIndex) + '...'
        }
      },
    })
  script>
body>

html>

5.6 过滤器的兼容性

  • 过滤器仅在 vue 2.x 和 1.x 中受支持,在 vue 3.x 的版本中剔除了过滤器相关的功能。

  • 在企业级项目开发中:

    • 如果使用的是 2.x 版本的 vue,则依然可以使用过滤器相关的功能
    • 如果项目已经升级到了 3.x 版本的 vue,官方建议使用计算属性或方法代替被剔除的过滤器功能

6. watch 侦听器

6.1 什么是 watch 侦听器

  • watch 侦听器允许开发者监视数据的变化,从而针对数据的变化做特定的操作。

6.2 使用 watch 检测用户名是否可用

  • 监听 username 值的变化,并使用 axios 发起 Ajax 请求,检测当前输入的用户名是否可用
// 侦听器
      watch: {
        async username (newName, oldName) {
          console.log('监视到了 username 值的变化。', newName, oldName)

          // 如果用户名为空,则 return,防止调用接口报错
          if (newName === '') return

          // 注意:如果调用某个函数,返回值是 Promise 实例,
          // 则可以使用 async/await 简化 Promise 的使用。
          const result = await axios.get('https://www.escook.cn/api/finduser/' + newName)
          console.log(result.data)
        }
      }

6.3 immediate 选项

  • 默认情况下,组件在初次加载完毕后不会调用 watch 侦听器。如果想让 watch 侦听器立即被调用,则需要使用 immediate 选项

示例代码如下:

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>Documenttitle>
head>

<body>
  <div id="app">
    请输入值:<input type="text" v-model="username" placeholder="请输入值">
  div>

  <script src="./lib/vue-2.6.12.js">script>
  <script src="./lib/axios.js">script>
  <script>
    const vm = new Vue({
      el: '#app',
      data: {
        username: ''
      },
      // 侦听器
      watch: {
        async username (newName, oldName) {
          console.log('监视到了 username 值的变化。', newName, oldName)

          // 如果用户名为空,则 return,防止调用接口报错
          if (newName === '') return

          // 注意:如果调用某个函数,返回值是 Promise 实例,
          // 则可以使用 async/await 简化 Promise 的使用。
          const result = await axios.get('https://www.escook.cn/api/finduser/' + newName)
          console.log(result.data)
        },
        // 表示页面初次渲染好之后,就立即触发当前的 watch 侦听器
        immediate: true
      }
    })
  script>
body>

html>

6.4 deep 选项

  • 如果 watch 侦听的是一个对象,如果对象中的属性值发生了变化,则无法被监听到。此时需要使用 deep 选项

代码示例如下:

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>Documenttitle>
head>

<body>
  <div id="app">
    <input type="text" v-model="goods.title">

    <button @click="updateGoods">修改 goodsbutton>
  div>

  <script src="./lib/vue-2.6.12.js">script>
  <script>
    const vm = new Vue({
      el: '#app',
      data: {
        // 商品的信息对象
        goods: {
          title: '娃哈哈酸奶',
          price: 3,
          count: 200
        }
      },
      watch: {
        goods: {
          handler: function (newVal) {
            console.log(newVal)
          },
          // 如果监听的对象上的属性发生了变化,可以能够触发侦听器
          // 深度监听
          deep: true
        }
      },
      methods: {
        updateGoods () {
          this.goods = {
            title: '牛奶',
            price: 5,
            count: 100
          }
        }
      },
    })
  script>
body>

html>

6.5 监听对象单个属性的变化

  • 如果只想监听对象中单个属性的变化,则可以按照如下的方式定义 watch 侦听器:
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>Documenttitle>
head>

<body>
  <div id="app">
    <input type="text" v-model="goods.title">
  div>

  <script src="./lib/vue-2.6.12.js">script>
  <script>
    const vm = new Vue({
      el: '#app',
      data: {
        // 商品的信息对象
        goods: {
          title: '娃哈哈酸奶',
          price: 3,
          count: 200
        }
      },
      watch: {
        /* 'goods.title': {
          handler: function (newVal, oldVal) {
            console.log(newVal, oldVal)
          }
        } */

        // 如果在定义侦听器的时候,必须要添加 immediate 或 deep 选项,需要把侦听器定义为【对象格式】
        // 否则,直接把侦听器定义为【函数格式】即可
        'goods.title'(newVal, oldVal) {
          console.log(newVal, oldVal)
        }
      }
    })
  script>
body>

html>

7. 计算属性

7.1 什么是计算属性

  • 计算属性指的是通过一系列运算之后,最终得到一个属性值。
  • 这个动态计算出来的属性值可以被模板结构或 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>Documenttitle>
head>

<body>
  <div id="app">
    <h3>count 的值是:{{ count }}h3>

    
    

    
    
    <p>count * count 的值是:{{ num }}p>
    <p>count * count 的值是:{{ num }}p>
    <p>count * count 的值是:{{ num }}p>
  div>

  <script src="./lib/vue-2.6.12.js">script>
  <script>
    const vm = new Vue({
      el: '#app',
      data: {
        count: 2
      },
      // 计算属性
      computed: {
        // 1. 计算属性在定义的时候,需要被定义成函数
        // 4. 注意:计算属性,会缓存上一次计算的结果
        // 5. 只有计算属性中依赖的数据项发生变化的时候,才会重新对计算属性求值
        num() {
          console.log('执行了 num 这个计算属性')
          // 2. 计算属性,必须 return 一个计算的结果,否则,就是无效的计算属性
          return this.count * this.count
        }
      }
    })
  script>
body>

html>

7.2 计算属性的特点

  • 虽然计算属性在声明的时候被定义为方法,但是计算属性的本质是一个属性
  • 计算属性会缓存计算的结果,只有计算属性依赖的数据变化时,才会重新进行运算

7.3 计算属性-案例

效果图:
Vue 2.0 知识点总结_第20张图片

DOCTYPE html>
<html lang="en">

<head>
  <meta charset="UTF-8">
  <meta name="viewport" content="width=device-width, initial-scale=1.0">
  <meta http-equiv="X-UA-Compatible" content="ie=edge">
  <title>Documenttitle>
  <script src="./lib/vue-2.6.12.js">script>
  <style>
    .box {
      width: 200px;
      height: 200px;
      border: 1px solid #ccc;
    }
  style>
head>

<body>
  <div id="app">
    <div>
      <span>R:span>
      <input type="text" v-model.number="r">
    div>
    <div>
      <span>G:span>
      <input type="text" v-model.number="g">
    div>
    <div>
      <span>B:span>
      <input type="text" v-model.number="b">
    div>
    <hr>

    
    
    
    
    <div class="box" :style="{ 'background-color': rgb }">
    div>
    
    <p>{{ rgb }}p>
    <button @click="show">按钮button>
  div>

  <script>
    // 创建 Vue 实例,得到 ViewModel
    var vm = new Vue({
      el: '#app',
      data: {
        // 红色
        r: 0,
        // 绿色
        g: 0,
        // 蓝色
        b: 0
      },
      // 计算属性
      computed: {
        // 1. 计算属性,在定义的时候,要定义成函数
        // 注意:只要计算属性中,用到的 data 数据发生了变化,就会重新对计算属性求值
        rgb() {
          // 2. 必须 return 一个结果
          return `rgb(${this.r}, ${this.g}, ${this.b})`
        }
      },
      methods: {
        // 点击按钮,在终端显示最新的颜色
        show() {
          // 在 methods 函数中,要访问计算属性的值,要通过 this.计算属性 来访问
          console.log(this.rgb)
        }
      },
    });
  script>
body>

html>

8. vue-cli

8.1 单页面应用程序

  • 单页面应用程序(英文名:Single Page Application)简称 SPA,顾名思义,指的是一个 Web 网站中只有唯一的一个 HTML 页面,所有的功能与交互都在这唯一的一个页面内完成。

8.2 什么是 vue-cli

  • vue-cli 是 Vue.js 开发的标准工具。它简化了程序员基于 webpack 创建工程化的 Vue 项目的过程。
  • 引用自 vue-cli 官网上的一句话:
  • 程序员可以专注在撰写应用上,而不必花好几天去纠结 webpack 配置的问题。
  • 中文官网:https://cli.vuejs.org/zh/

8.3 安装和使用

  • vue-cli 是 npm 上的一个全局包,使用 npm install 命令,即可方便的把它安装到自己的电脑上:npm install -g @vue/cli

  • 基于 vue-cli 快速生成工程化的 Vue 项目:vue create 项目的名称

8.4 vue 项目的运行流程

  • 在工程化的项目中,vue 要做的事情很单纯:通过 main.js 把 App.vue 渲染到 index.html 的指定区域中。
  • 其中:
    • App.vue 用来编写待渲染的模板结构
    • index.html 中需要预留一个 el 区域
    • main.js 把 App.vue 渲染到了 index.html 所预留的区域中

8.5 Vue 组件库

1. vue-cli 手动选择要安装的功能
  • 目标:在使用 vue-cli 创建项目的时候,能够手动选择要安装的功能
  • 回顾之前使用 vue-cli 创建项目的步骤:
    1. 运行 vue create 项目名称
    2. 选择 Default([vue 2] babel, eslint)

image.png

  • 存在的问题:

    1. 只包含特定的 3 个功能(vue2 + babel + eslint)
    2. 不包含 vue-router、vuex 等其它功能
  • 推荐的方式:选择 Manually select features

  • 好处:在项目创建期间,能够选择并安装更多的功能

    Vue 2.0 知识点总结_第21张图片

  • 手动选择要安装的功能(1/10)

    1. 运行 vue create 项目名称
    2. 选择 Manually select features

Vue 2.0 知识点总结_第22张图片

  • 手动选择要安装的功能(2/10)

    • 推荐选择并安装以下的 6 个功能:

    Vue 2.0 知识点总结_第23张图片

    1. ↑↓箭头切换选中项
    2. 空格切换选中状态
    3. *号表示安装选中的功能
  • 手动选择要安装的功能(3/10)

    • 选择要安装的 vue 版本(建议选择 2.x):

    Vue 2.0 知识点总结_第24张图片

  • 手动选择要安装的功能(4/10)

    • 是否使用 history 模式的路由(建议输入 n):

    Vue 2.0 知识点总结_第25张图片

  • 手动选择要安装的功能(5/10)

    • 选择要使用的 CSS 预处理器(建议选择 Less):

    Vue 2.0 知识点总结_第26张图片

  • 手动选择要安装的功能(6/10)

    • 选择要使用的 ESLint 语法规则(建议选择 ESLint + Standard config):

    Vue 2.0 知识点总结_第27张图片

  • 手动选择要安装的功能(7/10)

    • 选择额外的 lint 功能(建议选择 Lint on save,在 Ctrl + S 的时候检测代码是否符合规范):

    Vue 2.0 知识点总结_第28张图片

  • 手动选择要安装的功能(8/10)

    • 把第三方插件的配置选项放到哪个配置文件中(建议选择 In dedicated config files,表示:独立的配置文件):

    Vue 2.0 知识点总结_第29张图片

  • 手动选择要安装的功能(9/10)

    • 是否把刚才所有的操作保存为预设,方便下次直接基于预设,一键生成项目(建议输入 y):

    Vue 2.0 知识点总结_第30张图片

  • 手动选择要安装的功能(10/10)

    • 为预设提供一个好记的名字(建议输入英文的预设名称):

    Vue 2.0 知识点总结_第31张图片

2. ESLint 基本语法

目标:能够知道 ESLint 常见的语法规则,并在实际开发中遵守这些规则

2.1 什么是 ESLint?
  • 官方概念:ESLint 是可组装的 JavaScript 和 JSX 检查工具。
  • 通俗理解:一个工具,用来约束团队成员的代码风格。
  • 好处:保证团队协作开发时,编写出来的代码风格保持一致。
  • 例如:
    1. JS 中的字符串,统一使用单引号表示
    2. 代码缩进,统一使用两个空格
    3. 不允许出现 ≥2 个的连续空行
2.2 常见的 ESLint 规则

Vue 2.0 知识点总结_第32张图片

  • 更多的 ESLint 规则,请查阅官方文档 https://eslint.bootcss.com/docs/rules/
2.3 修改 vue-cli 项目的语法规则
  1. 找到项目根目录下的 .eslintrc.js 配置文件
  2. 在 rules 配置选项中,修改默认的语法规则

Vue 2.0 知识点总结_第33张图片

9. vue 组件

9.1 什么是组件化开发

  • 组件化开发指的是:根据封装的思想,把页面上可重用的 UI 结构封装为组件,从而方便项目的开发和维护。

9.2 vue 中的组件化开发

  • vue 是一个支持组件化开发的前端框架。
  • vue 中规定:组件的后缀名是 .vue。之前接触到的 App.vue 文件本质上就是一个 vue 的组件。

9.3 vue 组件的三个组成部分

  • 每个 .vue 组件都由 3 部分构成,分别是:
    • template -> 组件的模板结构
    • script -> 组件的 JavaScript 行为
    • style -> 组件的样式
  • 其中,每个组件中必须包含 template 模板结构,而 script 行为和 style 样式是可选的组成部分。
1. template
  • vue 规定:每个组件对应的模板结构,需要定义到