Vue.js组件通信之自定义事件详解


Posted in Javascript onOctober 19, 2019

组件通信

从父组件向子组件通信,通过props传递数据就可以了,但Vue组件通信的场景不止有这一种,归纳起来,组件之间的通信可以用下图来表示:

Vue.js组件通信之自定义事件详解

自定义事件

当子组件需要向父组件传递数据时,就要用到自定义事件。子组件用**$ emit()来触发事件**,父组件用**$ on()**来监听子组件的事件。

父组件也可以直接在子组件的自定义标签上使用v-on来监听子组件触发的事件。

<!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">
  <script src="https://unpkg.com/vue/dist/vue.js"></script>
  <title>自定义事件</title>
</head>
<body>
  <div id="app">
    <p>总数:{{total}}</p>
    <my-component
      @increase="handleGetTotal"
      @reduce="handleGetTotal"></my-component>
  </div>
  <script>
    Vue.component('my-component',{
      template: '\
        <div>\
          <button @click="handleIncrease">+1</button>\
          <button @click="handleReduce">-1</button>\
        </div>',
      data: function () {
        return {
          counter: 0
        }
      },
      methods: {
        handleIncrease: function () {
          this.counter++;
          this.$emit('increase', this.counter);
        },
        handleReduce: function () {
          this.counter--;
          this.$emit('reduce', this.counter);
        }
      }
    });

    var app = new Vue({
      el: '#app',
      data: {
        total: 0
      },
      methods: {
        handleGetTotal: function (total) {
          this.total = total;
        }
      }
    });
  </script>
</body>
</html>

Vue.js组件通信之自定义事件详解

子组件有两个按钮,分别实现+1和-1的效果,在改变组件的data “counter”后,通过$emit()在把它传递给父组件,父组件使用v-on:increase和v-on:reduce监听事件。

$emit()方法的第一个参数是自定义事件的名称,后面的参数是要传递的数据,可以不填或者填写多个。

注意:除了用v-on在组件上监听自定义事件外,也可以监听DOM事件,这时候可以用 .native修饰符表示监听的是一个原生事件,监听的是该组件的根元素:

<my-component v-on:click.native="handleClick"></my-component>

使用v-model

Vue 2.x 可以在自定义组件上使用v-model指令。

<!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">
  <script src="https://unpkg.com/vue/dist/vue.js"></script>
  <title>使用v-model</title>
</head>
<body>
  <div id="app">
    <p>总数:{{total}}</p>
    <my-component v-model="total"></my-component>
  </div>
  <script>
    Vue.component('my-component',{
      template: '<button @click="handleClick">+1</button>',
      data: function () {
        return {
          counter: 0
        }
      },
      methods: {
        handleClick: function () {
          this.counter++;
          this.$emit('input',this.counter);
        }
      }
    });

    var app = new Vue({
      el: '#app',
      data: {
        total: 0
      }
    });
  </script>
</body>
</html>

仍然是点击按钮+1的效果,不过这次组件$emit()的事件是特殊的input,在使用组件的父级,并没有在<my-component>上使用@input=“handler”,而是使用了v-model板顶的一个数据total。这也可以称作是一个语法糖,因为上面的示例可以间接地用自定义事件来实现:

<div id="myApp">
  <p>总数:{{total}}</p>
  <my-component1 @input="handlegetTotal"></my-component1>
</div>
<script>
  Vue.component('my-component1',{
    template: '<button @click="handleClick">+1</button>',
    data: function () {
      return {
        counter: 0
      }
    },
    methods: {
      handleClick: function () {
        this.counter++;
        this.$emit('input',this.counter);
      }
    }
  });

  var myApp = new Vue({
    el: '#myApp',
    data: {
      total: 0
    },
    methods: {
      handlegetTotal: function (value) {
        this.total = value;
      }
    }
  });
</script>

v-model还可以用来创建自定义的表单输入组件,进行数据双向绑定:

<!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">
  <script src="https://unpkg.com/vue/dist/vue.js"></script>
  <title>自定义表单输入组件</title>
</head>
<body>
  <div id="app">
    <p>总数:{{total}}</p>
    <my-component v-model="total"></my-component>
    <button @click="handleReduce">-1</button>
  </div>
  <script>
    Vue.component('my-component',{
      props: ['value'],
      template: '<input :value="value" @input="updateValue">',
      methods: {
        updateValue: function (event) {
          this.$emit('input', event.target.value);
        }
      }
    });

    var app = new Vue({
      el: '#app',
      data: {
        total: 0
      },
      methods: {
        handleReduce: function () {
          this.total--;
        }
      }
    });
  </script>
</body>
</html>

Vue.js组件通信之自定义事件详解

注意:实现这样一个具有双向绑定的v-model组件要满足下面的两个要求:

  • 接受一个value属性
  • 在有新的value时触发input事件

更多教程点击《Vue.js前端组件学习教程》,欢迎大家学习阅读。

关于vue.js组件的教程,请大家点击专题vue.js组件学习教程进行学习。

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持三水点靠木。

Javascript 相关文章推荐
Ext JS Grid在IE6 下宽度的问题解决方法
Feb 15 Javascript
JavaScript 权威指南(第四版) 读书笔记
Aug 11 Javascript
同时使用n个window onload加载实例介绍
Apr 25 Javascript
javascript删除option选项的多种方法总结
Nov 22 Javascript
JavaScript基础——使用Canvas绘图
Nov 02 Javascript
JS实现二叉查找树的建立以及一些遍历方法实现
Apr 17 Javascript
js 发布订阅模式的实例讲解
Sep 10 Javascript
浅谈JavaScript find 方法不支持IE的问题
Sep 28 Javascript
vue2.0路由切换后页面滚动位置不变BUG的解决方法
Mar 14 Javascript
使用vue-router完成简单导航功能【推荐】
Jun 28 Javascript
JavaScript字符串处理常见操作方法小结
Nov 15 Javascript
JS+CSS实现动态时钟
Feb 19 Javascript
Vue.js自定义指令学习使用详解
Oct 19 #Javascript
Vue.js标签页组件使用方法详解
Oct 19 #Javascript
基于JavaScript获取base64图片大小
Oct 18 #Javascript
react MPA 多页配置详解
Oct 18 #Javascript
vue滚动插件better-scroll使用详解
Oct 18 #Javascript
VUE实现密码验证与提示功能
Oct 18 #Javascript
VUE实现图片验证码功能
Nov 18 #Javascript
You might like
PHP Memcached应用实现代码
2010/02/08 PHP
php 短链接算法收集与分析
2011/12/30 PHP
关于php程序报date()警告的处理(date_default_timezone_set)
2013/10/22 PHP
输入值/表单提交参数过滤有效防止sql注入的方法
2013/12/25 PHP
PHP的cookie与session原理及用法详解
2019/09/27 PHP
php实现的数组转xml案例分析
2019/09/28 PHP
对联广告js flash激活
2006/10/19 Javascript
JavaScript对象创建及继承原理实例解剖
2013/02/28 Javascript
利用javascript实现禁用网页上所有文本框,下拉菜单,多行文本域
2013/12/14 Javascript
java、javascript实现附件下载示例
2014/08/14 Javascript
angularjs中的e2e测试实例
2014/12/06 Javascript
原生javascript实现隔行换色
2015/01/04 Javascript
jQuery实现可展开合拢的手风琴面板菜单
2015/09/15 Javascript
Jquery attr()方法 属性赋值和属性获取详解
2016/04/15 Javascript
BootStrap智能表单实战系列(九)表单图片上传的支持
2016/06/13 Javascript
NodeJS远程代码执行
2016/08/28 NodeJs
jsonp跨域请求实现示例
2017/03/13 Javascript
[js高手之路]单例模式实现模态框的示例
2017/09/01 Javascript
jquery写出PC端轮播图实例
2018/01/26 jQuery
Angular6 用户自定义标签开发的实现方法
2019/01/08 Javascript
jQuery实现带3D切割效果的轮播图功能示例【附源码下载】
2019/04/04 jQuery
详解50行代码,Node爬虫练手项目
2019/04/22 Javascript
vue 搭建后台系统模块化开发详解
2019/05/01 Javascript
Vue中使用better-scroll实现轮播图组件
2020/03/07 Javascript
在Apache服务器上同时运行多个Django程序的方法
2015/07/22 Python
关于python中密码加盐的学习体会小结
2019/07/15 Python
Django实现WebSSH操作物理机或虚拟机的方法
2019/11/06 Python
python实现图片素描效果
2020/09/26 Python
为什么在使用动态 SQL 语句时必须为低层数据库对象授予权限
2012/12/13 面试题
个人找工作的自我评价
2013/10/17 职场文书
英文自我鉴定
2013/12/10 职场文书
大学生村官承诺书
2014/03/28 职场文书
小学假期安全广播稿
2014/09/28 职场文书
2014年学生会工作总结范文
2014/11/07 职场文书
优秀员工事迹材料
2014/12/20 职场文书
Vue2.0搭建脚手架
2022/03/13 Vue.js