JackCin's blog JackCin's blog
首页
  • 页面

    • Html
    • CSS
  • 核心

    • JavaScript基础
    • JavaScript高级
  • 框架

    • Vue
  • jQuery
  • Node
  • Ajax
Linux
  • 操作系统
  • 数据结构与算法
  • 51单片机
  • CC2530
  • 网站
  • 分类
  • 标签
  • 归档
GitHub (opens new window)

JackCin

前端小菜鸡(✪ω✪)
首页
  • 页面

    • Html
    • CSS
  • 核心

    • JavaScript基础
    • JavaScript高级
  • 框架

    • Vue
  • jQuery
  • Node
  • Ajax
Linux
  • 操作系统
  • 数据结构与算法
  • 51单片机
  • CC2530
  • 网站
  • 分类
  • 标签
  • 归档
GitHub (opens new window)
  • 页面

  • 核心

  • 框架

    • Vue

      • 初识 Vue
      • Vue 基础语法
        • 一、插值操作
          • 1、Mustaceh
          • 2、v-once
          • 3、v-html
          • 4、v-text
          • 5、v-pre
          • 6、v-cloak
        • 二、绑定属性(v-bind)
          • 1、 v-bind介绍
          • 2、 v-bind基础
          • 3、 v-bind动态绑定class
          • 3.1 v-bind绑定class--(对象语法)
          • 3.2 v-bind绑定class--(数组语法)
          • 4、 v-bind绑定style
          • 4.1 v-bind绑定style(对象)
          • 4.2 v-bind绑定style(数组)
        • 三、计算属性
          • 1、 什么是计算属性?计算属性的基本使用
          • 2、 计算属性的复杂操作
          • 3、 计算属性的setter 和getter
          • 4、 计算属性的缓存(计算属性和methods的对比)
        • 四、事件监听 v-on
          • 1、 事件监听
          • 2、 v-on 基础
          • 3、 v-on参数
          • 4、 v-on修饰符
        • 五、条件判断 v-if、v-else-if、v-else
          • 5.1 v-if、v-else-if、v-else
          • 5.2 条件渲染案例--登录切换
          • 5.3 案例小问题--登录切换input的复用
          • 5.4 v-show的使用以及和v-if的区别
        • 六、 遍历循环 v-for
          • 6.1 v-for遍历数组
          • 6.2 v-for 遍历对象
          • 6.3 组件的 key 属性
          • 6.4 数组中哪些方法是响应式的?
          • 6.5 案例 - 图书购物车
        • 七、表单绑定v-model
          • 7.1 表单绑定v-model
          • 7.2 v-model 原理
          • 7.3 v-model结合radio类型使用
          • 7.4 v-model结合checkbox类型使用
          • 7.5 v-model结合select类型使用
          • 7.6 v-model 修饰符的使用
      • 组件化开发
      • 前端模块化
      • Vue CLI 脚手架
      • vue-route
      • Promise
      • Vuex
      • 网络模块封装
  • 前端
  • 框架
  • Vue
JackCin
2022-11-12
目录

Vue 基础语法

# 一、插值操作

# 1、Mustaceh

  • 如何将data中的文本数据,插入到HTML中呢?
    • 我们已经学习过了,可以通过Mustache语法(也就是双大括号)。
    • Mustache: 胡子/胡须.
  • 我们可以像下面这样来使用,并且数据是响应式的
 
<div id="app">
  <h2>{{message}}</h2>
  <h2>{{message}}, 李银河!</h2>
<!-- Mustache: 胡子/胡须 -->
  <!--mustache语法中,不仅仅可以直接写变量,也可以写简单的表达式-->
  <h2>{{firstName + lastName}}</h2>
  <h2>{{firstName + ' ' + lastName}}</h2>
  <h2>{{firstName}} {{lastName}}</h2>
  <h2>{{counter * 2}}</h2>
</div>
 
<script src="../js/vue.js"></script>
<script>
  const app = new Vue({
    el: '#app',
    data: {
      message: '你好啊',
      firstName: 'kobe',
      lastName: 'bryant',
      counter: 100
    },
  })
 
  // 模板语法指的就是:写代码时,按照规定好的方式来
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25

# 2、v-once

  • 但是,在某些情况下,我们可能不希望界面随意的跟随改变
    • 这个时候,我们就可以使用一个Vue的指令
  • v-once:
    • 该指令后面不需要跟任何表达式(比如v-for后面是由跟表达式的)
    • 该指令表示元素和组件(组件后面才会学习)只渲染一次,不会随着数据的改变而改变。
    • 代码如下:

img

 
<div id="app">
  <h2>{{message}}</h2>
  <h2 v-once>{{message}}</h2>
</div>
<!-- v-once: 
该指令后面不需要跟任何表达式(比如之前的v-for后面是由跟表达式的)
该指令表示元素和组件(组件后面才会学习)只渲染一次,不会随着数据的改变而改变 -->
<script src="../js/vue.js"></script>
<script>
  const app = new Vue({
    el: '#app',
    data: {
      message: '你好啊'
    }
  })
  // 指令的本质就是自定义属性
</script>
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18

# 3、v-html

  • 某些情况下,我们从服务器请求到的数据本身就是一个HTML代码
    • 如果我们直接通过{{}}来输出,会将HTML代码也一起输出。
    • 但是我们可能希望的是按照HTML格式进行解析,并且显示对应的内容。
  • 如果我们希望解析出HTML展示
    • 可以使用v-html指令
    • 该指令后面往往会跟上一个string类型
    • 会将string的html解析出来并且进行渲染
 
<div id="app">
  <h2>{{url}}</h2>
  <h2 v-html="url"></h2>
</div>
<!-- v-html指令
该指令后面往往会跟上一个string类型
会将string的html解析出来并且进行渲染 -->
<script src="../js/vue.js"></script>
<script>
  const app = new Vue({
    el: '#app',
    data: {
      message: '你好啊',
      url: '<a href="http://www.baidu.com">百度一下</a>'
    }
  })
</script>
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18

# 4、v-text

  • v-text作用和Mustache比较相似:都是用于将数据显示在界面中
  • v-text通常情况下,接受一个string类型
  • v-text 会覆盖标签内的其他文本
<div id="app">
        <h1>{{message}} ,'World'</h1>
        <!-- v-text 会覆盖标签内的其他文本 -->
        <h1 v-text="message">World</h1>
    </div>

    <script src="../js/vue.js"></script>

    <script>
        const app = new Vue({
            el: '#app',
            data: {
                message: "Hello!",
            }
        })
    </script>
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16

# 5、v-pre

  • v-pre用于跳过这个元素和它子元素的编译过程,用于显示原本的Mustache语法。
  • 比如下面的代码:
    • 第一个h2元素中的内容会被编译解析出来对应的内容
    • 第二个h2元素中会直接显示
 
<div id="app">
  <h2>{{message}}</h2>         //你好啊
  <h2 v-pre>{{message}}</h2>   // {{message}}
</div>
<!-- 
  v-pre用于跳过这个元素和它子元素的编译过程,用于显示原本的Mustache语法。
 -->
<script src="../js/vue.js"></script>
<script>
  const app = new Vue({
    el: '#app',
    data: {
      message: '你好啊'
    }
  })
</script>
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17

# 6、v-cloak

  • 在某些情况下,我们浏览器可能会直接显然出未编译的Mustache标签。
  • cloak: 斗篷
  • v-cloak,相当于一个属性在vue 解析前存在,解析后删除
<style>
    [v-cloak] {
      display: none;
    }
</style>
 
  <div id="app" v-cloak>
    <h2>{{message}}</h2>
  </div>
  <!-- 
  在某些情况下,我们浏览器可能会直接显示出未编译的Mustache标签。
cloak: 斗篷
需要和css一起搭配使用
v-cloak 指令用法
(1)插值表达式存在的问题:“闪动”
(2)如何解决该问题:使用v-cloak指令
(3)解决该问题的原理:先隐藏,替换好值之后再显示最终的值
 -->
  <script src="../js/vue.js"></script>
  <script>
    // 在vue解析之前, div中有一个属性v-cloak
    // 在vue解析之后, div中没有一个属性v-cloak
    setTimeout(function () {
      const app = new Vue({
        el: '#app',
        data: {
          message: '你好啊'
        }
      })
    }, 1000)
  </script>
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31

# 二、绑定属性(v-bind)

# 1、 v-bind介绍

  • 前面我们学习的指令主要作用是将值插入到我们模板的内容当中。
  • 但是,除了内容需要动态来决定外,某些属性我们也希望动态来绑定。
    • 比如动态绑定a元素的href属性
    • 比如动态绑定img元素的src属性
  • 这个时候,我们可以使用v-bind指令:
    • 作用:动态绑定属性
    • 缩写::
    • 预期:any (with argument) | Object (without argument)
    • 参数:attrOrProp (optional)

# 2、 v-bind基础

  • v-bind用于绑定一个或多个属性值,或者向另一个组件传递props值(这个学到组件时再介绍)
  • 在开发中,有哪些属性需要动态进行绑定呢?
    • 还是有很多的,比如图片的链接src、网站的链接href、动态绑定一些类、样式等等
  • 比如通过Vue实例中的data绑定元素的src和href,代码如下:
 
  <!-- 
    v-bind用于绑定一个或多个属性值,或者向另一个组件传递props值
   -->
 
<div id="app">
  <!-- 错误的做法: 这里不可以使用mustache语法-->
  <!--<img src="{{imgURL}}" alt="">-->
  
  <!-- 正确的做法: 使用v-bind指令 -->
  <img v-bind:src="imgURL" alt="">
  <a v-bind:href="aHref">百度一下</a>
  <!--<h2>{{}}</h2>-->
 
  <!--语法糖的写法-->
  <img :src="imgURL" alt="">
  <a :href="aHref">百度一下</a>
</div>
 
<script src="../js/vue.js"></script>
<script>
  const app = new Vue({
    el: '#app',
    data: {
      message: '你好啊',
      imgURL: 'https://img11.360buyimg.com/mobilecms/s350x250_jfs/t1/20559/1/1424/73138/5c125595E3cbaa3c8/74fc2f84e53a9c23.jpg!q90!cc_350x250.webp',
      aHref: 'http://www.baidu.com'
    }
  })
</script>
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
  • v-bind语法糖

    • v-bind有一个对应的语法糖,也就是简写方式
    • 在开发中,我们通常会使用语法糖的形式,因为这样更加简洁。
    • 简写方式如下**:**
    <div id=" app">
    	<a :href="link" >Vueis官网</a>
    	<img :src="logoURL" alt=""">
    </div>
    
    1
    2
    3
    4

# 3、 v-bind动态绑定class

  • 很多时候,我们希望动态的来切换class,比如:
    • 当数据为某个状态时,字体显示红色。
    • 当数据另一个状态时,字体显示黑色
  • 绑定class有两种方式:
    • 对象语法
    • 数组语法

# 3.1 v-bind绑定class--(对象语法)

  • 绑定方式:对象语法
  • 对象语法的含义是:class后面跟的是一个对象。
  • 对象语法里的键要加引号,不加就不加就成了变量,而不是类名(除了key中包含特殊字符外可以不加引号)
    • 对象语法有下面这些用法:
用法一:直接通过{}绑定一个类
<h2 :class="{'active': isActive}">Hello World</h2>
 
用法二:也可以通过判断,传入多个值
<h2 :class="{'active': isActive, 'line': isLine}">Hello World</h2>
 
用法三:和普通的类同时存在,并不冲突
注:如果isActive和isLine都为true,那么会有title/active/line三个类
<h2 class="title" :class="{'active': isActive, 'line': isLine}">Hello World</h2>
 
用法四:如果过于复杂,可以放在一个methods或者computed中
注:classes是一个计算属性
<h2 class="title" :class="classes">Hello World</h2>
1
2
3
4
5
6
7
8
9
10
11
12
13

代码:

  • 注:当key中包含特殊字符如横线“-”(不是下划线), 空格等js不支持的变量时需要用引号。 因为vue会将"{}"中的内容应用到js中处理!
<!-- 
  绑定class有两种方式:->和普通的类同时存在,并不冲突
     对象语法 
     数组语法
    都对象.数组内的属性不用加引号
 -->
 
  <div id="app">
    <!--<h2 class="active">{{message}}</h2>-->
 <!-- 普通用法:这种属于多此一举 -->
    <!--<h2 :class="active">{{message}}</h2>-->
 
 <!-- 对象语法 -->
    <!--<h2 v-bind:class="{key1: value1, key2: value2}">{{message}}</h2>-->
    <!--<h2 v-bind:class="{类名1: true, 类名2: boolean}">{{message}}</h2>-->
    <h2 class="title" v-bind:class="{active: isActive, line: isLine}">{{message}}</h2>
    <h2 class="title" v-bind:class="getClasses()">{{message}}</h2>
    <button v-on:click="btnClick">按钮</button>
  </div>
 
  <script src="../js/vue.js"></script>
  <script>
    const app = new Vue({
      el: '#app',
      data: {
        message: '你好啊',
        isActive: true,
        isLine: true
      },
      methods: {
        btnClick: function () {
          this.isActive = !this.isActive
        },
        getClasses: function () {
          return {
            active: this.isActive,
            line: this.isLine
          }
        }
      }
    })
  </script>
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42

# 3.2 v-bind绑定class--(数组语法)

  • 绑定方式:数组语法
    • 数组语法的含义是:class后面跟的是一个数组。
    • 数组写法里面的元素要加引号,不加就成了变量,而不是类名
  • 数组语法有下面这些用法:
<!-- 数组语法 -->
用法一:直接通过[]绑定一个类
<h1 v-bind:class="['active']">{{message}}</h1>

用法二:也可以传入多个值
<h1 v-bind:class="['active','line']">{{message}}</h1>

 <!-- 可以与普通类同时存在,如果数组里的元素没有加引号,则相当于一个变量,而不是字符串 -->
<h1 class="title" :class="['active',line]">{{message}}</h1>
<!-- 如果过于复杂,可以放到一个 methods 或 computed 中 -->
<h1 :class="getArrClass()">{{message}}</h1>
1
2
3
4
5
6
7
8
9
10
11

# 4、 v-bind绑定style

  • 我们可以利用v-bind:style来绑定一些CSS内联样式。

  • 在写CSS属性名的时候,比如font-size

    • 我们可以使用驼峰式 (camelCase) fontSize
    • 或短横线分隔 (kebab-case,记得用单引号括起来) ‘font-size’
  • 绑定style有两种方式:

    • 对象语法
    • 数组语法

# 4.1 v-bind绑定style(对象)

:style="{color: currentColor, fontSize: fontSize + 'px'}"
1
  • style后面跟的是一个对象类型
    • 对象的key是CSS属性名称
    • 对象的value是具体赋的值,值可以来自于data中的属性
<div id="app">
    <p v-bind:style="{fontSize:'50' +'px'}">{{message}}</p>
    <p v-bind:style="{fontSize:'50px',backgroundColor: finalColor}">{{message}}</p>
    <p :style="getStyle()">{{message}}</p>
</div>
<script src="../js/vue.js"></script>
<script>
    const app = new Vue({
        el: "#app",
        data: {
            message: "你好!",
            finalColor: "yellow"
        },
        methods: {
            getStyle() {
                return { fontSize: '50px', backgroundColor: this.finalColor}
            }
        }
    })
</script>
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20

# 4.2 v-bind绑定style(数组)

​

<div v-bind:style="[baseStyles, overridingStyles]"></div>
1
  • style后面跟的是一个数组类型
  • 多个值以 , 分割即可
<div id="app">
    <p v-bind:style="{fontSize:'50' +'px'}">{{message}}</p>
    <p v-bind:style="[finalStyle]">{{message}}</p>
    <!-- 多个用逗号(,)隔开 -->
    <p v-bind:style="[finalStyle,finalStyle2]">{{message}}</p>
</div>
<script src="../js/vue.js"></script>
<script>
    const app = new Vue({
        el: "#app",
        data: {
            message: "你好!",
            finalStyle: { fontSize: '50px', backgroundColor: 'red' },
            finalStyle2: { color: "blue" }
        },
    })
</script>
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17

# 三、计算属性

# 1、 什么是计算属性?计算属性的基本使用

  • 我们知道,在模板中可以直接通过插值语法显示一些data中的数据。
  • 但是在某些情况,我们可能需要对数据进行一些转化后再显示,或者需要将多个数据结合起来进行显示
    • 比如我们有firstName和lastName两个变量,我们需要显示完整的名称。
    • 但是如果多个地方都需要显示完整的名称,我们就需要写多个
  • 我们可以将上面的代码换成计算属性: OK,我们发现计算属性是写在实例的computed选项中的。
 
  <div id="app">
    <h2>{{firstName + ' ' + lastName}}</h2>
    <h2>{{firstName}} {{lastName}}</h2>
    <!-- {{}} 里面也可以调用方法,需要加() -->
    <h2>{{getFullName()}}</h2>
 
    <!-- {{}} 里面一般用的是变量名,方法有个() 可能有点别扭,这时候就能使用计算属性 -->
    <!-- !!计算属性不用加括号 -->
    <h2>{{fullName}}</h2>
  </div>
 
  <script src="../js/vue.js"></script>
  <script>
    const app = new Vue({
      el: '#app',
      data: {
        firstName: 'Lebron',
        lastName: 'James'
      },
      // computed: 计算属性()
      computed: {
         // computed里面定义的也是函数,但是函数名一般不加类似于get的动词 
        //  但是它叫计算属性,所以一般起类似于属性的名字
 
        fullName: function () { 
            // 这样写其实也是一个语法糖 里面有setter和getter 这个是getter
          return this.firstName + ' ' + this.lastName
        }
      },
      methods: {
        getFullName() {
          return this.firstName + ' ' + this.lastName
        }
      }
    })
  </script>
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37

# 2、 计算属性的复杂操作

  • 计算属性中也可以进行一些更加复杂的操作,比如下面的例子:
 
<div id="app">
  <h2>总价格: {{totalPrice}}</h2>
</div>
 
<script src="../js/vue.js"></script>
<script>
  const app = new Vue({
    el: '#app',
    data: {
      books: [
        {id: 110, name: 'Unix编程艺术', price: 119},
        {id: 111, name: '代码大全', price: 105},
        {id: 112, name: '深入理解计算机原理', price: 98},
        {id: 113, name: '现代操作系统', price: 87},
      ]
    },
    computed: {
      totalPrice: function () {
        let result = 0;
        for (let i=0; i < this.books.length; i++) {
          result += this.books[i].price
        }
        return result;
 
        // 1.第一种方式
        /*
        let total = 0
        this.books.forEach(book => {
          total += book.price * book.count
        })
        return total
        */
 
        // 2.第二种方式
        // let total = 0
        // for (let i in this.books) {
        //   const book = this.books[i]
        //   total += book.price * book.count
        // }
        // return total
 
        // 3.第三种方式
        // 高阶函数 filter/reduce/map
        return this.books.reduce((preValue, book) => {
          return preValue + book.price * book.count
        }, 0)
 
        // reduce的补充
        // https://www.cnblogs.com/amujoe/p/11376940.html
      }
    }
  })
</script>
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54

# 3、 计算属性的setter 和getter

  • 每个计算属性都包含一个getter和一个setter
    • 在上面的例子中,我们只是使用getter来读取。
    • 在某些情况下,你也可以提供一个setter方法(不常用)。
    • 在需要写setter的时候,代码如下:
 
<div id="app">
  <h2>{{fullName}}</h2>
</div>
 
<script src="../js/vue.js"></script>
<script>
  const app = new Vue({
    el: '#app',
    data: {
      firstName: 'Kobe',
      lastName: 'Bryant'
    },
    computed: {
      // computed本质是一个对象 里面可以有属性,里面的属性又是一个对象,里面又可以写方法
      // 简写
      // fullName: function () { 
      //   return this.firstName + ' ' + this.lastName
      // }
      // name: 'coderwhy'
 
 
      // 完整写法
      // 计算属性一般是没有set方法, 只读属性.
      // 计算属性一般实现get方法,没有实现set方法,一般不希望别人给计算属性设置值,一般直接删除set
      // 所以调用计算属性不需要加() 本质是调用属性fullname 里面的get
      fullName: { // 对象
        set: function(newValue) { // 如果想实现set方法,这里是有一个参数的
          // 可以在控制台试试 app.fullName="yang yanyan" 就会调用set
          console.log('-----', newValue);
          const names = newValue.split(' ');
          this.firstName = names[0];// 赋值
          this.lastName = names[1];
        },
        get: function () {
          return this.firstName + ' ' + this.lastName
        }
      },
 
      // fullName: function () { // 这个函数就是get方法
      //   return this.firstName + ' ' + this.lastName
      // }
    }
  })
</script>
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45

# 4、 计算属性的缓存(计算属性和methods的对比)

  • 我们可能会考虑这样的一个问题:
    • methods和computed看起来都可以实现我们的功能,
    • 那么为什么还要多一个计算属性这个东西呢?
    • 原因:计算属性会进行缓存,如果多次使用时,计算属性只会调用一次。
  • 我们来看下面的代码:
 
<div id="app">
  <!--1.直接拼接: 语法过于繁琐-->
  <h2>{{firstName}} {{lastName}}</h2>
 
  <!--2.通过定义methods-->
  <h2>{{getFullName()}}</h2>
  <h2>{{getFullName()}}</h2>
  <h2>{{getFullName()}}</h2>
  <h2>{{getFullName()}}</h2>
 
  <!--3.通过computed-->
  <h2>{{fullName}}</h2>
  <h2>{{fullName}}</h2>
  <h2>{{fullName}}</h2>
  <h2>{{fullName}}</h2>
</div>
 
<script src="../js/vue.js"></script>
<script>
  // angular -> google
  // TypeScript(microsoft) -> ts(类型检测)
  // flow(facebook) ->
  const app = new Vue({
    el: '#app',
    data: {
      firstName: 'Kobe',
      lastName: 'Bryant'
    },
    methods: {
      getFullName: function () {
        console.log('getFullName');
        return this.firstName + ' ' + this.lastName
      }
    },
    computed: {
      fullName: function () {
        console.log('fullName');
       // 会观察有没有变化 没有变化就直接返回原来结果 而不是重新计算 有变化就重新调用一次
       // 浏览器控制台 app.fullName='why' 会再调用一次
        return this.firstName + ' ' + this.lastName
      }
    }
  })
 
</script>
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46

# 四、事件监听 v-on

# 1、 事件监听

  • 在前端开发中,我们需要经常和用于交互。
    • 这个时候,我们就必须监听用户发生的事件,比如点击、拖拽、键盘事件等等
    • 在Vue中如何监听事件呢?使用v-on指令
  • v-on介绍
    • 作用:绑定事件监听器
    • 缩写:@
    • 预期:Function | Inline Statement | Object
    • 参数:event

# 2、 v-on 基础

  • 这里,我们用一个监听按钮的点击事件,来简单看看v-on的使用
    • 下面的代码中,我们使用了v-on:click="counter++”
    • 另外,我们可以将事件指向一个在methods中定义的函数

img

  • 注:v-on也有对应的语法糖:
    • **v-on:click **可以写成 @click

img

img

# 3、 v-on参数

  • 当通过methods中定义方法,以供@click调用时,需要注意参数问题:
  • 情况一:如果该方法不需要额外参数,那么方法后的()可以不添加。
    • 但是注意:如果方法本身中有一个参数,那么会默认将原生事件event参数传递进去
  • 情况二:如果需要同时传入某个参数,同时需要event时,可以通过**$event**传入事件。
<div id="app">
    <!-- 如果不需要传入参数,则方法名后不用加() -->
    <button v-on:click="btn1Click">按钮1</button>
    <!-- 传入数字,则为参数,传入字符则要看加没加 "",有是字符串,没有则是变量名 -->
    <button @click="btn2Click(123,'abc',temp)">按钮2</button>
    <!-- 不省略(),同时方法本身需要接受参数,那么参数为undefined -->
    <button @click="btn3Click()">按钮3</button>
    <!-- 在事件调用时省略了(),但方法本身要接收一个参数,则默认参数为event -->
    <button v-on:click="btn3Click">按钮4</button>
    <!-- 可以用 $event 手动获取 event -->
    <button @click="btn3Click($event)">按钮5</button>
</div>
<script src="../js/vue.js"></script>
<script>
    const app = new Vue({
        el: '#app',
        data: {
            temp: "lllll"
        },
        methods: {
            btn1Click() {
                console.log("btn1")
            },
            btn2Click(item1, item2, item3) {
                console.log(item1)
                console.log(item2)
                console.log(item3)
            },
            btn3Click(item) {
                console.log(item)
            }
        }
    })
</script>
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34

# 4、 v-on修饰符

  • 在某些情况下,我们拿到event的目的可能是进行一些事件处理。
  • Vue提供了修饰符来帮助我们方便的处理一些事件:
    • .stop - 调用 event.stopPropagation()。
    • .prevent - 调用 event.preventDefault()。
    • .{keyCode | keyAlias} - 只当事件是从特定键触发时才触发回调。
    • .native - 监听组件根元素的原生事件。
    • .once - 只触发一次回调。

img

<div id="app">
    <!-- 阻止冒泡 .stop  -->
    <div @click="divInput">
        11111111
        <button @click="btnInput">不阻止</button>
        <button @click.stop="btnInput">阻止</button>
    </div>
    <!-- 阻止默认行为 .prevent  -->
    <div>
        <a href="https://www.baidu.com/">不阻止</a>
        <a href="https://www.baidu.com/" @click.prevent>阻止</a>
    </div>
    <!-- 监听键盘事件 -->
    <div>
        <!-- <input type="text" @keyup="keyUp"> -->
        <!-- 监听键盘的某个键帽 这里以回车键为例-->
        <!-- 键修饰符,键别名写法 -->
        <!-- <input type="text" @keyup.enter="keyUp"> -->
        <!-- 键修饰符,键代码写法 -->
        <input type="text" @keyup.13="keyUp">
    </div>
    <!-- 点击回调只能触发一次 -->
    <button @click="abc">点击</button>
    <button @click.once="abc">once</button>
</div>
<script src="../js/vue.js"></script>
<script>
    const app = new Vue({
        el: '#app',
        data: {
        },
        methods: {
            divInput() {
                console.log("div")
            },
            btnInput() {
                console.log("btn")
            },
            keyUp() {
                console.log("keyUp")
            },
            abc() {
                console.log("abc")
            }
        }
    })
</script>
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47

# 五、条件判断 v-if、v-else-if、v-else

# 5.1 v-if、v-else-if、v-else

  • v-if、v-else-if、v-else
    • 这三个指令与JavaScript的条件语句if、else、else if类似。
    • Vue的条件指令可以根据表达式的值在DOM中渲染或销毁元素或组件
    • v-if后面的条件为false时,对应的元素以及其子元素不会渲染。
    • 也就是根本没有对应的标签出现在DOM中。
<div id="app">
    <div v-if="score>=90">优秀</div>
    <div v-else-if="score>=80">良好</div>
    <div v-else-if="score>=60">及格</div>
    <div v-else>不及格</div>
</div>
<script src="../js/vue.js"></script>
<script>
    const app = new Vue({
        el: '#app',
        data: {
            message: 'Hello World!',
            score: 78,
        },
    })
</script>
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16

# 5.2 条件渲染案例--登录切换

  • 做一个简单的小案例:

    • 用户再登录时,可以切换使用用户账号登录还是邮箱地址登录。

    • 类似如下情景:

 
  <div id="app">
    <span v-if="isUser">
      <label for="username">用户账号</label>
      <input type="text" id="username" placeholder="用户账号">
    </span>
 
    <span v-else>
      <label for="email">用户邮箱</label>
      <input type="text" id="email" placeholder="用户邮箱">
    </span>
    <button @click="isUser = !isUser">切换类型</button>
  </div>
 
  <script src="../js/vue.js"></script>
  <script>
    const app = new Vue({
      el: '#app',
      data: {
        isUser: true
      }
    })
  </script>
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23

# 5.3 案例小问题--登录切换input的复用

  • 小问题:

    • 如果我们在有输入内容的情况下,切换了类型,我们会发现文字依然显示之前的输入的内容。
    • 但是按道理讲,我们应该切换到另外一个input元素中了。
    • 在另一个input元素中,我们并没有输入内容。
    • 为什么会出现这个问题呢?
  • 问题解答

    • 这是因为Vue在进行DOM渲染时,出于性能考虑,会尽可能的复用已经存在的元素,而不是重新创建新的元素。
    • 在上面的案例中,Vue内部会发现原来的input元素不再使用,直接作为else中的input来使用了
  • 解决方案

    • 如果我们不希望Vue出现类似重复利用的问题,可以给对应的input添加key
    • 并且我们需要保证key的不同
 
<div id="app">
  <span v-if="isUser">
    <label for="username">用户账号</label>
    <input type="text" id="username" placeholder="用户账号" key="username">
  </span>
  <span v-else>
    <label for="email">用户邮箱</label>
    <input type="text" id="email" placeholder="用户邮箱" key="email">
  </span>
  <button @click="isUser = !isUser">切换类型</button>
</div>
 
<script src="../js/vue.js"></script>
<script>
  const app = new Vue({
    el: '#app',
    data: {
      isUser: true
    }
  })
</script>
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22

# 5.4 v-show的使用以及和v-if的区别

  • v-show的用法和v-if非常相似,也用于决定一个元素是否渲染:
  • v-if和v-show对比
  • v-if和v-show都可以决定一个元素是否渲染,那么开发中我们如何选择呢?
    • v-if当条件为false时,压根不会有对应的元素在DOM中。
    • v-show当条件为false时,仅仅是将元素的display属性设置为none而已。
  • 开发中如何选择呢?
    • 当需要在显示与隐藏之间切换很频繁时,使用v-show
    • 当只有一次切换时,通过使用v-if
 
<div id="app">
  <!--v-if: 当条件为false时, 包含v-if指令的元素, 根本就不会存在dom中-->
  <h2 v-if="isShow" id="aaa">{{message}}</h2>
 
  <!--v-show: 当条件为false时, v-show只是给我们的元素添加一个行内样式: display: none-->
  <h2 v-show="isShow" id="bbb">{{message}}</h2>
</div>
<!-- 
  当需要在显示与隐藏之间切片很频繁时,使用v-show
当只有一次切换时,通过使用v-if
 -->
 
<script src="../js/vue.js"></script>
<script>
  const app = new Vue({   
    el: '#app',
    data: {
      message: '你好啊',
      isShow: true
    }
  })
</script>
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23

# 六、 遍历循环 v-for

# 6.1 v-for遍历数组

  • 当我们有一组数据需要进行渲染时,我们就可以使用v-for来完成。
    • v-for的语法类似于JavaScript中的for循环。
    • 格式如下:item in items的形式。
  • 我们来看一个简单的案例:
  • 如果在遍历的过程中不需要使用索引值
    • v-for="movie in movies"
    • 依次从movies中取出movie,并且在元素的内容中,我们可以使用Mustache语法,来使用movie
  • 如果在遍历的过程中,我们需要拿到元素在数组中的索引值呢?
  • 语法格式:v-for="(item, index) in items"
  • 其中的index就代表了取出的item在原数组的索引值。
 
<div id="app">
  <!--1.在遍历的过程中,没有使用索引值(下标值)-->
  <ul>
    <li v-for="item in names">{{item}}</li>
  </ul>
 
  <!--2.在遍历的过程中, 获取索引值-->
  <ul>
    <li v-for="(item, index) in names">
      {{index+1}}.{{item}}
    </li>
  </ul>
</div>
 
<script src="../js/vue.js"></script>
<script>
  const app = new Vue({
    el: '#app',
    data: {
      names: ['why', 'kobe', 'james', 'curry']
    }
  })
</script>
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24

# 6.2 v-for 遍历对象

  • v-for可以用户遍历对象:
    • 比如某个对象中存储着你的个人信息,我们希望以列表的形式显示出来。
    • 在遍历对象的过程中, 如果只是获取一个值, 那么获取到的是value
 
<div id="app">
  <!--1.在遍历对象的过程中, 如果只是获取一个值, 那么获取到的是value-->
  <ul>
    <li v-for="item in info">{{item}}</li>
  </ul>
 
  <!--2.获取key和value 格式: (value, key) -->
  <ul>
    <li v-for="(value, key) in info">{{value}}-{{key}}</li>
  </ul>
 
  <!--3.获取key和value和index 格式: (value, key, index) -->
  <ul>
    <li v-for="(value, key, index) in info">{{value}}-{{key}}-{{index}}</li>
  </ul>
</div>
 
<script src="../js/vue.js"></script>
<script>
  const app = new Vue({
    el: '#app',
    data: {
      info: {
        name: 'why',
        age: 18,
        height: 1.88
      }
    }
  })
</script>
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31

# 6.3 组件的 key 属性

v-for绑定key和没有绑定key的区别

  • 官方推荐我们在使用v-for时,给对应的元素或组件添加上一个: key属性。
  • 为什么需要这个key属性呢(了解)?
    • 这个其实和Vue的虚拟DOM的Diff算法有关系。
    • 这里我们借用React’s diff algorithm中的一张图来简单说明一下:

v-for-绑定key

  • 当某一层有很多相同的节点时,也就是列表节点时,我们希望插入一个新的节点

    • 我们希望可以在B和C之间加一个F,Diff算法默认执行起来是这样的。
    • 即把C更新成F,D更新成C,E更新成D,最后再插入E,是不是很没有效率?
  • 所以我们需要使用key来给每个节点做一个唯一标识

    • Diff算法就可以正确的识别此节点
    • 找到正确的位置区插入新的节点。
  • 所以一句话,key的作用主要是为了高效的更新虚拟DOM。

# 6.4 数组中哪些方法是响应式的?

  • 因为Vue是响应式的,所以当数据发生变化时,Vue会自动检测数据变化,视图会发生对应的更新。
  • Vue中包含了一组观察数组编译的方法,使用它们改变数组也会触发视图的更新。
    • push()
    • pop()
    • shift()
    • unshift()
    • splice()
    • sort()
    • reverse()
 <div id="app">
    <ul>
     <!-- 这里不使用:key="item" 绑定,因为如果添加元素时出现相同的值,则item再一一对应,会报错 -->
      <li v-for="item in letters">{{item}}</li>
    </ul>
    <button @click="btnClick">按钮</button>
  </div>
 
  <script src="../js/vue.js"></script>
  <script>
    const app = new Vue({
      el: '#app',
      data: {
        letters: ['a', 'b', 'c', 'd']
      },
      methods: {
        btnClick() {
          // 1.push方法 
          // this.letters.push('aaa')
          // this.letters.push('aaaa', 'bbbb', 'cccc')
 
          // 2.pop(): 删除数组中的最后一个元素
          // this.letters.pop();
 
          // 3.shift(): 删除数组中的第一个元素
          // this.letters.shift();
 
          // 4.unshift(): 在数组最前面添加元素
          // this.letters.unshift()
          // this.letters.unshift('aaa', 'bbb', 'ccc')
 
          // 5.splice作用: 删除元素/插入元素/替换元素
          // 删除元素: 第二个参数传入你要删除几个元素(如果没有传,就删除后面所有的元素)
          // 替换元素: 第二个参数, 表示我们要替换几个元素, 后面是用于替换前面的元素
          // 插入元素: 第二个参数, 传入0, 并且后面跟上要插入的元素
          // splice(start)
          // splice(start):
          this.letters.splice(1, 3, 'm', 'n', 'l', 'x')
          // this.letters.splice(1, 0, 'x', 'y', 'z')
 
          // 5.sort() 排序
          // this.letters.sort()
 
          // 6.reverse() 反转
          // this.letters.reverse()
 
          // **注意: 通过索引值修改数组中的元素 
          // Vue内部没有监听这种方式 不是响应式 数组有变化,界面无更新
          // this.letters[0] = 'bbbbbb';
 
          // 用其他方法
          // 法1
          // this.letters.splice(0, 1, 'bbbbbb')
 
          // 法2
          // set(要修改的对象, 索引值, 修改后的值)
          // Vue.set(this.letters, 0, 'bbbbbb')
        }
      }
    })
 
 
    // function sum(num1, num2) {
    //   return num1 + num2
    // }
    //
 
    // function sum(num1, num2, num3) {
    //   return num1 + num2 + num3
    // }
 
    // function sum(...num) { // 可变参数
    //   console.log(num);
    // }
    //
    // sum(20, 30, 40, 50, 601, 111, 122, 33)
  </script>
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77

# 6.5 案例 - 图书购物车

# 七、表单绑定v-model

# 7.1 表单绑定v-model

  • 表单控件在实际开发中是非常常见的。特别是对于用户信息的提交,需要大量的表单。
  • Vue中使用v-model指令来实现表单元素和数据的双向绑定。
  • 案例的解析:
    • 当我们在输入框输入内容时
    • 因为input中的v-model绑定了message,所以会实时将输入的内容传递给message,message发生改变。
    • 当message发生改变时,因为上面我们使用Mustache语法,将message的值插入到DOM中,所以DOM会发生响应的改变。
    • 所以,通过v-model实现了双向的绑定。

img

  • 当然,我们也可以将v-model用于textarea元素
 
<div id="app">
	<textarea v-model="message"></textarea>
	<p>输入的内容是:{{message}}</p>
</div>
 
<script src="../js/vue.js"></script>
<script>
  const app = new Vue({
    el: '#app',
    data: {
      message: '你好啊'
    }
  })
</script>
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15

# 7.2 v-model 原理

  • v-model其实是一个语法糖,它的背后本质上是包含两个操作:
    • 1.v-bind绑定一个value属性
    • 2.v-on指令给当前元素绑定input事件
  • 也就是说下面的代码:
    • <input type="text" v-model="message">
  • 等同于下面的代码:
    • <input type="text" v-bind:value="message" v-on:input="message = $event.target.value">
 
  <div id="app">
    <!--<input type="text" v-model="message">-->
 
    <!-- 上面等同于 -->
    <!--<input type="text" :value="message" @input="valueChange">-->
 
    <!-- 也就是 -->
    <input type="text" :value="message" @input="message = $event.target.value">
    <h2>{{message}}</h2>
  </div>
 
  <script src="../js/vue.js"></script>
  <script>
    const app = new Vue({
      el: '#app',
      data: {
        message: '你好啊'
      },
      methods: {
        valueChange(event) {
          this.message = event.target.value;
        }
      }
    })
  </script>
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26

# 7.3 v-model结合radio类型使用

  • 当存在多个单选框时
  • 单选按钮radio的value会影响v-model的值(input得有value属性,value是什么获取到的就是什么)
  • 一旦v-model绑定的是同一个变量,name可以不用写
 
  <div id="app">
    <label for="male">
      <!-- 需要加相同的name 否则可以多选 -->
      <!-- <input type="radio" id="male" value="男" name="sex">男 -->
      <!-- 一旦v-moddel绑定的是同一个变量,name可以不用写 -->
      <input type="radio" id="male" value="男" v-model="sex">男
    </label>
    <label for="female">
      <input type="radio" id="female" value="女" v-model="sex">女
    </label>
    <label for="other">
      <input type="radio" id="other" value="其他" v-model="sex">其他
    </label>
    <h2>您选择的性别是: {{sex}}</h2>
  </div>
 
  <script src="../js/vue.js"></script>
  <script>
    const app = new Vue({
      el: '#app',
      data: {
        message: '你好啊',
        sex: '女' // 可以给radio默认值
      }
    })
  </script>
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27

# 7.4 v-model结合checkbox类型使用

  • 复选框分为两种情况:单个勾选框和多个勾选框
  • 单个勾选框:
    • v-model即为布尔值。
    • 此时input的value并不影响v-model的值。
  • 多个复选框:
    • 当是多个复选框时,因为可以选中多个,所以对应的data中属性是一个数组。
    • 当选中某一个时,就会将input的value添加到数组中。
 
  <div id="app">
    <!--1.checkbox单选框 -->
    <!-- 
      v-model即为布尔值true/false。
      此时input的value并不影响v-model的值
 -->
    <label for="agree">
      <input type="checkbox" id="agree" v-model="isAgree">同意协议
    </label>
    <h2>您选择的是: {{isAgree}}</h2>
    <button :disabled="!isAgree">下一步</button>
 
    <!--2.checkbox多选框-->
    <!-- 
      当是多个复选框时,因为可以选中多个,所以对应的data中属性是一个数组。
      当选中某一个时,就会将input的value添加到数组中。
   -->
    <input type="checkbox" value="篮球" v-model="hobbies">篮球
    <input type="checkbox" value="足球" v-model="hobbies">足球
    <input type="checkbox" value="乒乓球" v-model="hobbies">乒乓球
    <input type="checkbox" value="羽毛球" v-model="hobbies">羽毛球
    <h2>您的爱好是: {{hobbies}}</h2>
 
     <!-- 值绑定 动态的给value赋值 -->
    <label v-for="item in originHobbies" :for="item">
      <input type="checkbox" :value="item" :id="item" v-model="hobbies">{{item}}
    </label>
  </div>
 
  <script src="../js/vue.js"></script>
  <script>
    const app = new Vue({
      el: '#app',
      data: {
        message: '你好啊',
        isAgree: false, // 单选框
 
        hobbies: [], // 多选框,
        originHobbies: ['篮球', '足球', '乒乓球', '羽毛球', '台球', '高尔夫球']
      }
    })
  </script>
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43

# 7.5 v-model结合select类型使用

  • 和checkbox一样,select也分单选和多选两种情况。
  • 单选:只能选中一个值。
    • v-model绑定的是一个值。
    • 当我们选中option中的一个时,会将它对应的value赋值到mySelect中
  • 多选:可以选中多个值。
    • v-model绑定的是一个数组。
    • 当选中多个值时,就会将选中的option对应的value添加到数组mySelects中
 
  <div id="app">
    <!--1.选择一个-->
    <!-- 
    单选:只能选中一个值。
    v-model绑定的是一个值。
    当我们选中option中的一个时,会将它对应的value赋值到mySelect中
   -->
    <!-- v-model绑定在select标签 -->
    <select name="abc" v-model="fruit">
      <option value="苹果">苹果</option>
      <option value="香蕉">香蕉</option>
      <option value="榴莲">榴莲</option>
      <option value="葡萄">葡萄</option>
    </select>
    <h2>您选择的水果是: {{fruit}}</h2>
 
    <!--2.选择多个-->
    <!-- 
    v-model绑定的是一个数组。
    当选中多个值时,就会将选中的option对应的value添加到数组mySelects中
   -->
    <!-- 加上multiple属性就可以多选 要按ctrl才能多选 -->
    <select name="abc" v-model="fruits" multiple>
      <option value="苹果">苹果</option>
      <option value="香蕉">香蕉</option>
      <option value="榴莲">榴莲</option>
      <option value="葡萄">葡萄</option>
    </select>
    <h2>您选择的水果是: {{fruits}}</h2>
  </div>
 
  <script src="../js/vue.js"></script>
  <script>
    const app = new Vue({
      el: '#app',
      data: {
        message: '你好啊',
        fruit: '香蕉',
        fruits: []
      }
    })
  </script>
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43

# 7.6 v-model 修饰符的使用

  • lazy 修饰符:
    • 默认情况下,v-model 默认是在input事件中同步输入框的数据的。
    • 也就是说,一旦有数据发生改变对应的data中的数据就会自动发生改变。
    • lazy修饰符可以让数据在失去焦点或者回车时才会更新
  • number 修饰符:
    • 默认情况下,在输入框中无论我们输入的是字母还是数字,都会被当做字符串类型进行处理。
    • 但是如果我们希望处理的是数字类型,那么最好直接将内容当做数字处理。
    • number修饰符可以让在输入框中输入的内容自动转成数字类型
  • trim 修饰符:
    • 如果输入的内容首尾有很多空格,通常我们希望将其去除
    • trim修饰符可以过滤内容左右两边的空格

img

 
<div id="app">
  <!--1.修饰符: lazy 让数据在失去焦点或者回车时才会更新-->
  <input type="text" v-model.lazy="message">
  <h2>{{message}}</h2>
 
 
  <!--2.修饰符: number 让在输入框中输入的内容自动转成数字类型-->
	<!-- 或者说是只能输入字符 -->
  <input type="number" v-model.number="age">
  <h2>{{age}}-{{typeof age}}</h2>
 
  <!--3.修饰符: trim 过滤内容左右两边的空格-->
  <input type="text" v-model.trim="name">
  <h2>您输入的名字:{{name}}</h2>
</div>
 
<script src="../js/vue.js"></script>
<script>
  const app = new Vue({
    el: '#app',
    data: {
      message: '你好啊',
      age: 0,
      name: ''
    }
  })
 
  var age = 0
  age = '1111'
  age = '222'
</script>
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32

#

编辑 (opens new window)
上次更新: 2023/09/12, 14:55:44
初识 Vue
组件化开发

← 初识 Vue 组件化开发→

最近更新
01
51单片机及补充知识
09-13
02
独立按键
09-13
03
LCD1602液晶显示器
09-13
更多文章>
Theme by Vdoing | Copyright © 2019-2023 Evan Xu | MIT License
  • 跟随系统
  • 浅色模式
  • 深色模式
  • 阅读模式