IT数码 购物 网址 头条 软件 日历 阅读 图书馆
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
图片批量下载器
↓批量下载图片,美女图库↓
图片自动播放器
↓图片自动播放器↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁
 
   -> JavaScript知识库 -> 【vue】vue双向数据绑定的原理解析及代码实现_04 -> 正文阅读

[JavaScript知识库]【vue】vue双向数据绑定的原理解析及代码实现_04

目录

?? 双向绑定

1. 问题

2. 原因

3. 何时使用双向绑定

4. 如何使用双向绑定: (普通文本框)

5. 结果

6. 示例: 文本框输入搜索关键词,点按钮执行搜索

7. 双向绑定的原理

8. 示例: 使用事件模拟v-model的原理

9. 实现按回车搜索,边输入边搜索

10. 不同表单元素,绑定原理不同

11. v-model简写

💥 扩展:this判断—8种指向

?? 总结:知识点提炼


?【前文回顾】👉 vue的常用指令及用法总结(续)_03?


?? 双向绑定

1. 问题

用传统的:绑定表单元素的value属性,无法自动获得界面上用户输入的新内容。

2. 原因

其实在vue中有两种绑定方式:

???????? (1). 单向绑定:

???????? a. 可自动将程序中的变化,更新到界面上显示(Model->View)

???????? b. 但是,如果界面中用户修改了内容,则无法将新内容自动更新到程序中的变量中(View ×-> Model)

???????? (2). 双向绑定:

???????? a. 即可以自动将程序中的变化,更新到界面上显示(Model->View)

???????? b. 又可以自动将界面上用户修改的新内容自动更新回程序中的变量中(View -> Model)

3. 何时使用双向绑定

今后,只要在vue中,想获得表单元素的新内容,都用双向绑定

4. 如何使用双向绑定: (普通文本框)

???????? <input v-model:value="变量">

???????? ?? View<-Model

? ? ? ? ? ? View->Model

5. 结果

???????? (1). 程序中变量值发生了变化,则自动将程序中的变量值更新到界面上显示

???????? (2). 用户在界面中输入了新内容,则自动将界面上的新内容,更新回data中的变量里保存。

6. 示例: 文本框输入搜索关键词,点按钮执行搜索

6_v-model.html

<!DOCTYPE html>
<html lang="en">
<head>
  <meta charset="UTF-8">
  <meta name="viewport" content="width=device-width, initial-scale=1.0">
  <title>Document</title>
  <script src="js/vue.js"></script>
</head>
<body>
  <!--1. 做界面-->
  <div id="app">
    <!--1.1 找可能发生变化的位置
      本例中: 文本框的内容可能发生变化-->
    <input type="text" v-model:value="keywords">
    <!--1.2 找触发事件的元素
      本例中: button触发事件-->
    <button @click="search">百度一下</button>
  </div>
  <script>
    //2. 创建new Vue()对象
    var vm=new Vue({
      el:"#app",
      //3. 创建模型对象
      //3.1 因为界面上只需要一个变量,所以
      data:{
        keywords:"" //保存用户在文本框中输入的内容,开局,用户什么都没输入,默认""
      },
      //3.2 因为界面上需要一个函数
      methods:{
        search(){
          console.log(`查找 ${this.keywords} 相关的内容...`);
        }
      }
    })
  </script>
</body>
</html>
<!-- 事到如今呀。。。有些事儿,你也该知道了。孩子大了,瞒不住了。
其实,v-model后的“:value”和“:checkex”都可以省略。v-model很聪明,可以根据自己所在何种元素,自动判断应该绑定哪个属性。
比如,在文本框就自动绑定value属性,在radio就自动绑定checked属性。
虽然可以简写,但是,简写后更看不出原理,所以,一定要先把学习到的这四种不同情况,做熟练,再享受简写带来的便利。虽然简写,但是原理不变。 -->

?运行结果:

??

7. 双向绑定的原理

v-model会自动为当前表单元素绑定: @input或@change。当当前表单元素的value值发生变化时,自动触发事件,调用事件处理函数,自动修改data中的变量。

🏿 分析:双向数据绑定原理的实现
?

?? vue数据的双向绑定是通过数据劫持结合发布者-订阅者模式的方式来实现的。其核心就是通过Object.defineProperty()方法设置set和get函数来实现数据的劫持(监听),在数据变化时发布消息给订阅者,触发相应的监听回调。也就是说数据和视图同步,数据发生变化,视图跟着变化,视图变化,数据也随之发生改变;


总结起来,大致过实现过程就是:首先是对数据进行监听,然后当监听的属性发生变化时则告诉订阅者是否要更新,若更新就会执行对应的更新函数从而更新视图。


注:创建访问器属性,使用Object.defineProperty或Object.defineProperties添加,详情可参考我之后会发布的JS高级篇——关于保护对象知识点里的创建访问器属性,这里稍作解释:

👉 只要希望利用自定义规则保护对象属性值时,都要用访问器属性

👉 什么是访问器属性: 自己不保存属性值,而是只提供对另一个数据属性的保护!——保镖


?

?? MVVM模式就是Model–View–ViewModel模式。它实现了View的变动,自动反映在 ViewModel,反之亦然。对于双向绑定的理解,就是用户更新了View,Model的数据也自动被更新了,这种情况就是双向绑定。再说细点,就是在单向绑定的基础上给可输入元素input、textare等添加了change(input)事件,(change事件触发,View的状态就被更新了)来动态修改model。

8. 示例: 使用事件模拟v-model的原理

7_v-model2.html

<!DOCTYPE html>
<html lang="en">
<head>
  <meta charset="UTF-8">
  <meta name="viewport" content="width=device-width, initial-scale=1.0">
  <title>双向绑定原理:使用@input事件模拟实现双向绑定</title>
  <script src="js/vue.js"></script>
</head>
<body>
  <!--1. 做界面-->
  <div id="app">
    <!--1.1 找可能发生变化的位置
      本例中: 文本框的内容可能发生变化-->
    <input type="text" @input="myInput" :value="keywords">
    <!--1.2 找触发事件的元素
      本例中: button触发事件-->
    <button @click="search">百度一下</button>
  </div>
  <script>
    //2. 创建new Vue()对象
    var vm=new Vue({
      el:"#app",
      //3. 创建模型对象
      //3.1 因为界面上只需要一个变量,所以
      data:{
        keywords:"" //保存用户在文本框中输入的内容,开局,用户什么都没输入,默认""
      },
      //3.2 因为界面上需要一个函数
      methods:{
        search(){
          console.log(`查找 ${this.keywords} 相关的内容...`);
        },
        myInput(e){
          //this不指当前触发事件的元素了
          //vue中所有的this都指向当前new Vue()对象本身!
          //获得当前文本框的内容
          var value=e.target.value;
          //        当前文本框 内容
          //将文本框的内容自动修改到data中的keywords变量上
          this.keywords=value;
        }
      }
    })
  </script>
</body>
</html>
<!-- 事到如今呀。。。有些事儿,你也该知道了。孩子大了,瞒不住了。
其实,v-model后的“:value”和“:checkex”都可以省略。v-model很聪明,可以根据自己所在何种元素,自动判断应该绑定哪个属性。
比如,在文本框就自动绑定value属性,在radio就自动绑定checked属性。
虽然可以简写,但是,简写后更看不出原理,所以,一定要先把学习到的这四种不同情况,做熟练,再享受简写带来的便利。虽然简写,但是原理不变。 -->

运行结果:

9. 实现按回车搜索,边输入边搜索

???????? (1). 按回车搜索:

???????? a. <input @keyup="事件处理函数">

???????? b. 问题: 虽然可以实现边输入边搜索,但是,按任意键都执行搜索,不是我们想要的。我们希望只有按回车才执行搜索

???????? c. 解决: vue中提供了一套事件修饰符:

????????????????? 1). 什么是: 对触发事件的条件或默认行为加以限制

????????????????? 2). 比如: @keyup.13,表示只有13号回车键才能触发事件

???????? d. 问题: 如果只有13号键可以触发事件,那么,如何实现边输入边搜索呢?

???????? e. 解决: 利用vue提供的"监听函数"

???????? (2). 实现边输入边搜索:

???????? a. 什么是"监听函数": 当data中某个变量一改变,就会立刻自动触发的特殊函数。

????????b. 何时: 今后,只要希望data中的一个变量一变,立刻自动执行一个操作时,都要用监听函数!——个变量都可以有一个监听函数

???????? c. 如何:

????????????????? new Vue({
????????????????????????? el:"#app",

????????????????????????? data:{ ... 变量: 值, ... },

????????????????????????? methods:{

?????????????????????????????????? 事件处理函数(){

?????????????????????????????????? }

????????????????????????? },

????????????????????????? watch:{ //专门包含所有监听函数的区域

?????????????????????????????????? 变量名(){

??????????????????????????????????????????? //只有data中同名变量的值发生变化时自动触发!

?????????????????????????????????? }

????????????????????????? }
????????????????? })

???????? (3). 示例: 实现边输入边搜索,按回车也能搜索

???????? 8_v-model3.html

<!DOCTYPE html>
<html lang="en">
<head>
  <meta charset="UTF-8">
  <meta name="viewport" content="width=device-width, initial-scale=1.0">
  <title>Document</title>
  <script src="js/vue.js"></script>
</head>
<body>
  <!--1. 做界面-->
  <div id="app">
    <!--1.1 找可能发生变化的位置
      本例中: 文本框的内容可能发生变化-->
    <!--1.2 找触发事件的元素
      本例中: 
      button触发单击事件
      input还可触发键盘抬起事件,但是,只允许13号键触发事件-->
    <input type="text" v-model:value="keywords" @keyup.13="search">
    <button @click="search">百度一下</button>
  </div>
  <script>
    //2. 创建new Vue()对象
    var vm=new Vue({
      el:"#app",
      //3. 创建模型对象
      //3.1 因为界面上只需要一个变量,所以
      data:{
        keywords:"" //保存用户在文本框中输入的内容,开局,用户什么都没输入,默认""
      },
      //3.2 因为界面上需要一个函数
      methods:{
        search(){
          console.log(`查找 ${this.keywords} 相关的内容...`);
        }
      },
      watch:{//专门保存所有监听函数的区域
        keywords(){//专门监听data中keywords变量的函数
          //希望只要keywords变量发生改变,就自动搜索
          this.search();
        }
      }
    })
  </script>
</body>
</html>
<!-- 事到如今呀。。。有些事儿,你也该知道了。孩子大了,瞒不住了。
其实,v-model后的“:value”和“:checkex”都可以省略。v-model很聪明,可以根据自己所在何种元素,自动判断应该绑定哪个属性。
比如,在文本框就自动绑定value属性,在radio就自动绑定checked属性。
虽然可以简写,但是,简写后更看不出原理,所以,一定要先把学习到的这四种不同情况,做熟练,再享受简写带来的便利。虽然简写,但是原理不变。 -->

运行结果:?

?? 分析:本例是一个全方位的多个方式实现搜索的功能,这也是我们以后做网站需要集成的搜索功能:

1. 一边输入一边搜索(输入和搜索同步)的搜索功能,这是watch的功劳:watch:{...}

watch:{

????????keywords(){

??????????this.search();

????????}

}

2. 输入内容后,按回车实现,这是keyup.13的功劳:@keyup.13="search"

<input?type="text"?v-model:value="keywords"?@keyup.13="search">

3. 默认保留的点击按钮,实现搜索:@click="search"

<button?@click="search">百度一下</button>
?

👇 前3次是边输入边搜索功能的实现;第四次是回车实现;第五次是点击按钮触发 👇

10. 不同表单元素,绑定原理不同

??一般情况下我们默认用户提交的信息为绑定v-mode指令的表单元素的value属性的值;当然这只是一般情况下,实际上用户提交的信息与不同表单类型有关。 ?

???????? (1). radio:

???????? 对应小程序视频: 小程序->在线->VUE->day02 4. 双向绑定 v-mode radio ...

???????? a. 特点:

????????????????? 1). 提前准备好一批写死的value,让用户多选一。

???????? ???????? 2). 选中哪个radio或不选中哪个radio改变的是checked

???????? b. 如何: 所以v-model应该绑定在checked属性上:

???????? <input type="radio" value="1" name="sex" v-model:checked="变量">男
???????? <input type="radio" value="0" name="sex" v-model:checked="变量">女

???????? c. 原理:

????????????????1). Model变->View跟着变: v-model会拿变量的新值和当前的radio写死的value值做比较。如果变量的新值==当前radio的value值,则当前radio选中。否则如果变量的新值!=当前radio的value值,则当前radio不选中

????????????????? 2). View变->Model跟着变: v-model会将当前选中的radio的value自动更新到变量中。

???????? d. 示例: 选择性别:

???????? 9_v-model_radio.html

<!DOCTYPE html>
<html lang="en">
<head>
  <meta charset="UTF-8">
  <meta name="viewport" content="width=device-width, initial-scale=1.0">
  <title>Document</title>
  <script src="js/vue.js"></script>
</head>
<body>
  <div id="app">
    <!-- 把表单元素写在label里,可以扩大选中区域 -->
    <label><input type="radio" value="1" name="sex" v-model:checked="sex">男</label>
    <label><input type="radio" value="0" name="sex" v-model:checked="sex">女</label>
    <h3>我是{{sex==1?"男生♂":"女生♀"}}</h3>
  </div>
  <script>
    new Vue({
      el:"#app",
      data:{
        sex:1
      }
    })
  </script>
</body>
</html>
<!-- 事到如今呀。。。有些事儿,你也该知道了。孩子大了,瞒不住了。
其实,v-model后的“:value”和“:checkex”都可以省略。v-model很聪明,可以根据自己所在何种元素,自动判断应该绑定哪个属性。
比如,在文本框就自动绑定value属性,在radio就自动绑定checked属性。
虽然可以简写,但是,简写后更看不出原理,所以,一定要先把学习到的这四种不同情况,做熟练,再享受简写带来的便利。虽然简写,但是原理不变。 -->

运行结果:?

???

???????? (2). select:

???????? a. 特点:

????????????????? 1). 先准备好一批写死的option和value值,备选

????????????????? 2). 用户每选择一个option,就会将当前选中的option的value值交给整个select的value属性

????????????????? 3). 所以,应该将v-model绑定在每次都会被改变的select的value属性上

???????? b. 如何:

????????????????? <select v-model:value="变量">
????????????????????????? <option value="值1">文本</option>

????????????????????????? ... ...

???????? c. 原理:

????????????????? 1). Model变->View跟着变: v-model会用=右边的变量值和select下每个option的value值做比较。哪个option的value值==变量值,这个option就被选中

????????????????? 2). View变->Model跟着变: 用户选择了哪个option。select就会把选中的option的value交给select的value。然后v-model就将select的新value,自动更新到=右边的变量中保存

???????? d. 示例: 选择订单状态:

???????? 10_v-model_select.html

<!DOCTYPE html>
<html lang="en">
<head>
  <meta charset="UTF-8">
  <meta name="viewport" content="width=device-width, initial-scale=1.0">
  <title>Document</title>
  <script src="js/vue.js"></script>
</head>
<body>
  <div id="app">
    <select v-model:value="orderStatus">
      <option value="0">未付款</option>
      <option value="10">已付款</option>
      <option value="20">已发货</option>
      <option value="30">已签收</option>
    </select>
    <h3>当前订单状态为: {{orderStatus==0?"未付款":orderStatus==10?"已付款":orderStatus==20?"已发货":"已签收"}}</h3>
  </div>
  <script>
    new Vue({
      el:"#app",
      data:{
        orderStatus:0 //保存当前订单状态,开局是未付款
      }
    })
  </script>
</body>
</html>
<!-- 事到如今呀。。。有些事儿,你也该知道了。孩子大了,瞒不住了。
其实,v-model后的“:value”和“:checkex”都可以省略。v-model很聪明,可以根据自己所在何种元素,自动判断应该绑定哪个属性。
比如,在文本框就自动绑定value属性,在radio就自动绑定checked属性。
虽然可以简写,但是,简写后更看不出原理,所以,一定要先把学习到的这四种不同情况,做熟练,再享受简写带来的便利。虽然简写,但是原理不变。 -->

运行结果:

?????

???????? (3). checkbox: 单独使用

???????? 对应小程序视频列表: 小程序->在线->VUE->day02 6. 双向绑定 v-model checkbox ...

???????? a. 特点: 不需要value属性,单纯修改checked属性,就可切换两种状态,所以,v-model应该绑定在checked属性上。且绑定的变量只有两种值: true或false.

???????? b. 如何: <input type="checkbox" v-model:checked="变量">

????????????????? 且变量值为bool值

???????? c. 原理:

????????????????? 1). Model变->View跟着变: 变量值为true,则选中;变量值为false,则未选中。

????????????????? 2). View变->Model跟着变: 将当前checkbox的选中状态(checked属性值)自动更新回程序中的变量里。

???????? d. 示例: 点同意,启用元素; 不同意,禁用元素

???????? 11_v-model_checkbox.html

<!DOCTYPE html>
<html lang="en">
<head>
  <meta charset="UTF-8">
  <meta name="viewport" content="width=device-width, initial-scale=1.0">
  <title>Document</title>
  <script src="js/vue.js"></script>
</head>
<body>
  <!--1. 先做界面-->
  <div id="app">
    <!--1.1 找可能发生变化的位置: 
      两个文本框+按钮的disabled只需要一个变量控制即可——是否同意——isAgree
      用户选中checkbox修改isAgree的同意状态-->
    用户名:<input :disabled="isAgree==false"><br/>
    密码:<input type="password"  :disabled="isAgree==false"><br/>
    <input type="checkbox" v-model:checked="isAgree">同意<br/>
    <button  :disabled="isAgree==false">注册</button>
  </div>
  <script>
    new Vue({
      el:"#app",
      data:{
        isAgree:false //保存是否同意的状态,开局,默认不同意。
      }
    })
  </script>
</body>
</html>
<!-- 事到如今呀。。。有些事儿,你也该知道了。孩子大了,瞒不住了。
其实,v-model后的“:value”和“:checkex”都可以省略。v-model很聪明,可以根据自己所在何种元素,自动判断应该绑定哪个属性。
比如,在文本框就自动绑定value属性,在radio就自动绑定checked属性。
虽然可以简写,但是,简写后更看不出原理,所以,一定要先把学习到的这四种不同情况,做熟练,再享受简写带来的便利。虽然简写,但是原理不变。 -->

运行结果:?

?????

11. v-model简写

以上案例中, v-model后的":value"或":checked",都可省略。v-model可自动根据自己所在的元素判断绑定哪种元素。但是,虽然简写,原理是不变的!

???????? <表单元素 v-model="变量">

💥 扩展:this判断—8种指向

this ?8种指向: 判断this,一定不要看定义在哪儿!只看调用时!

?? 1. obj.fun()?? this->obj

?? 2. fun() 或 (function(){ ... })() 或 多数回调函数 或 定时器函数?? this->window

?? 3. new Fun()?? this->new正在创建的新对象

?? 4. 类型名.prototype.共有方法=function(){ ... }?? this->将来谁调用指谁,同第一种情况

?? 5. DOM或jq中事件处理函数中的this->当前正在触发事件的DOM元素对象

? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ?如果需要使用简化版函数,必须$(this)

?? 6. 箭头函数中的this->箭头函数外部作用域中的this

?? 7. jQuery.fn.自定义函数=function(){ ... }?? this->将来调用这个自定义函数的.前的jQuery子对象,不用再$(this)

?? 8. new Vue()中methods中的函数中的this->当前new Vue()对象?

?? 总结:知识点提炼

1. MVVM: 界面View+模型Model+视图模型ViewModel

2. Vue绑定原理: 访问器属性+虚拟DOM树

???????? 变量被修改时: 访问器属性发出通知,虚拟DOM树扫描并仅更新受影响的元素

3. 虚拟DOM树优点:

(1). 小: 只包含可能变化的元素。

(2). 遍历查找快

(3). 修改效率高: 只修改受影响的元素。

(4). 避免重复编码: 已封装DOM增删改查代码

4. Vue功能3步:

(1). 先创建增强版的界面:

? a. 整个界面必须包含在一个唯一的父元素下:

? ??通常是<div id="app">
? b. 可能变化的元素内容用{{自定义变量名}}标记

? c. 触发事件的元素用@click="自定义处理函数名"标记

(2). 再创建new Vue()对象,其中el:指向new Vue()要监控的页面区域

(3). 在new Vue()对象内定义模型对象data和methods

? a.界面所需的所有变量都放在data中

? b.界面所需的所有事件处理函数都放在methods中

5. 总结: 绑定语法+13种指令

(1). 如果元素的内容需要随变量自动变化: ?{{}}

(2). 如果元素的属性值需要随变量自动变化: ?:

(3). 控制一个元素显示隐藏: v-show //使用display:none隐藏元素

(4). 控制两个元素二选一显示: ?v-if? v-else //使用删除元素方式隐藏元素

(5). 多个元素多选一显示: v-if? v-else-if?? v-else

(6). 只要反复生成多个相同结构的元素组成列表时: v-for ?:key="唯一标识"

强调: 为什么必须加:key="i"?给每个元素副本添加唯一标识。修改数组中某个元素值时,避免重建整个列表,只需要修改一个DOM元素副本即可!提高修改效率。

(7). 只要绑定事件: @? $event

(8). 防止用户短暂看到{{}}: v-cloak和v-text

(9). 只要绑定原始HTML代码片段内容: v-html

(10). 如果元素的内容只在首次加载时绑定一次,之后都不会改变: v-once

???????? 优化: 减少虚拟DOM树中元素个数。

(11). 保护内容中的{{}}不被编译: v-pre

(12). 今后只要想获得表单元素的值或状态: v-model


?【后文传送门】👉??vue动态样式绑定详解_05?


???

如果这篇【文章】有帮助到你,希望可以给【青春木鱼】点个👍,创作不易,相比官方的陈述,我更喜欢用【通俗易懂】的文笔去讲解每一个知识点,如果有对【前端技术】感兴趣的小可爱,也欢迎关注??????青春木鱼??????,我将会给你带来巨大的【收获与惊喜】💕💕!

  JavaScript知识库 最新文章
ES6的相关知识点
react 函数式组件 & react其他一些总结
Vue基础超详细
前端JS也可以连点成线(Vue中运用 AntVG6)
Vue事件处理的基本使用
Vue后台项目的记录 (一)
前后端分离vue跨域,devServer配置proxy代理
TypeScript
初识vuex
vue项目安装包指令收集
上一篇文章      下一篇文章      查看所有文章
加:2022-06-14 22:29:05  更:2022-06-14 22:29:52 
 
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁

360图书馆 购物 三丰科技 阅读网 日历 万年历 2024年11日历 -2024/11/23 16:49:32-

图片自动播放器
↓图片自动播放器↓
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
图片批量下载器
↓批量下载图片,美女图库↓
  网站联系: qq:121756557 email:121756557@qq.com  IT数码