Vue | 组件化 | 组件通信

通信问题就是如何沟通,如何唠嗑的问题。

在前后端分离时数据传输的流向是这样子的:

  • 父组件向服务器接口请求数据
  • 子组件向父组件请求本组件数据
  • 父组件监听子组件发生的事情并做响应的处理

不如来看以下细胞信号传输:细胞如何相互沟通。

传送和接收这些信息所需的网络很复杂。这是由一支信使分子军队组成,跨细胞和在细胞之间传输信号(传讯分子)。它们寻找接收信号的目标(受体),最后,信使和受体相互作用,使细胞产生了最终的结果(细胞对原始信号做出回应)。
https://askthescientists.com/zh-hans/qa/what-is-cell-signaling/

也就是说,通信是需要两方共同参与,谁发出?传给谁?


瞎掰结束,来看 Vue 中的组件通信。

最上层的组件从服务器请求数据,每个子组件向父组件请求自己所需的数据。

不要跨级请求数据,浪费数据请求。

关键指令:

  • 父传子 props
  • 子传父 自定义事件 $emit

来个 DNA 检测确认父子关系,传信息前肯定是要确定对方身份的,将信息传给敌方就尴尬了。

陈佩斯:(从台侧上)队长——别开抢!是我!(然后像电线竿立着)
朱时茂:哦——你小子。说话!是你把敌人引到这儿来的?(陈佩斯不做声)
朱时茂:你说话呀!
陈佩斯:你们家电线杆子能说话吗!
朱时茂:你这个……台词还是要说的嘛!
陈佩斯:让说就说呗。
朱时茂:你千万记得啊!只要我掏出枪来一抬手——
陈佩斯:怎么着?
朱时茂:你就倒下。
陈佩斯:为什么?
朱时茂:这表示我的枪法准啊!

来理一理下面的组件关系:

<template id="cpn">
    <div>
        {{goods}}
    </div>
</template>
//----data----
const cpn = {
    template: "#cpn"
}
const app = new Vue({
    el: "#app",
    data: {
        goods: ['腊肉', "肥肠", "咸鸭蛋"]
    },
    components: {
        cpn
    }
})

app 是 cpn 的父组件,现在的需求是儿子 cpn 向爸爸 app 要物资,即 goods 列表。

怎么要?打电话还是发短信。

怎么传,电报?

传递信息需要双发的共同努力,父组件发送,子组件接收。

<div id="app">
    <cpn v-bind:cgoods="goods"></cpn>
</div>
<template id="cpn">
    <div>
        <h1>{{cgoods}}</h1>
    </div>
</template>
<script>
    const cpn = {
        template: "#cpn",
        props: ["cgoods"],
    }
    const app = new Vue({
        el: "#app",
        data: {
            goods: ['腊肉', "肥肠", "咸鸭蛋"]
        },
        components: {
            cpn
        }
    })
</script>

通过 <cpn v-bind:cgoods="goods"></cpn> 将父子组件连接,子组件通过 props 接收父组件传来的数据。

下面来理智分析(瞎掰)一波。

过年回家,家里 准备了很多的过年的物资data·,儿子回到了老父亲的家里 app 过年,
临走时父亲从自己的背包 goods 中拿出很多儿子想吃的塞到了儿子的背包 cgoods里。

父子分别,儿子到自己的家 cpn 后,从背包里拿出老父亲给自己塞的腊肉咸鸭蛋,开始准备今天的晚饭 {{cgoods}}

这真是一个温情的故事。

父子传递信息大概就是这么个意思。

至于如何处理数据(腊肉啥的)这里就不搞了。


逻辑理通后来看一波零碎的知识。

这里有点 TypeScript 的影子,类型限制和默认值,来波 TypeScript 代码,TypeScript 搞起来。

props: {
    cgoods: {
        type: String,
        default: "烤肠",
        required: true
        // 必须传值
    }
}

也就是说可以对 props 的接收数据可以进行类型限制,确定默认值等。


反过来看一下子传父的过程。

子组件发生事件,父组件要知道,比如人生大事结婚订婚等。

家人是坚强后盾。

先让自己知道自己发生了什么事情???

<div id="app">
    <cpn></cpn>
</div>

<template id="cpn">
    <div>
        <button 
        v-for="item in categories"
        @click="btnClick(item)">{{item.name}}</button> 
    </div>
</template>

<script>
  const cpn = {
      template: "#cpn",
      data() {
          return {
              categories: [
                  {id: 001, name: "评论"},
                  {id: 002, name: "简信"},
                  {id: 003, name: "投稿请求"},
                  {id: 004, name: "喜欢和赞"}
              ]
          }
      },
      methods: {
          btnClick(item) {
              console.log(item)
          }
      }
  }
  const app = new Vue({
      el: "#app",
      data: {
          
      },
      components: {
          cpn
      }
  })
</script>

首先儿子要先知道自己目前的状况,发生了什么事情。这里就要用到事件监听。要用到 @click && method 一对基友。

问题来了,如何将自己的近况及时告诉自己的父母,父母知道儿子的近况以后做出相应的回应,或放心,或担心,或嘱咐添加衣物按时吃饭,不要累着。

<div id="app">
    <cpn v-on:item-click="cpnClick"></cpn>
    <!-- 4. 得到孩子的近况 -->
</div>

<template id="cpn">
    <div>
        <button 
        v-for="item in categories"
        @click="btnClick(item)">{{item.name}}</button> 
        <!-- 1. 时刻关注自己的状况 -->
    </div>
</template>

<script>
    const cpn = {
        template: "#cpn",
        data() {
            return {
                categories: [
                    {id: 001, name: "饿了"},
                    {id: 002, name: "没钱了"},
                    {id: 003, name: "有女朋友了"},
                    {id: 004, name: "结婚了"}
                ]
            }
        },
        methods: {
            btnClick(item) {
                console.log(item)
                // 2. 我发生了什么事情
                this.$emit('item-click', item)
                // 3. 告诉父母我发生了什么事情
            }
        }
    }
    const app = new Vue({
        el: "#app",
        methods: {
            cpnClick(item) {
                console.log("老子知道你小子的事情了 | ", item.name)
                // 5. 对孩子的近况做出响应
            }
        },
        components: {
            cpn
        }
    })
</script>

将在子组件监听到的事件通过 $emit 传出去,通过 <cpn v-on:item-click="cpnClick"></cpn> 将两者连接,父组件在自己的 methods 中实现对应的响应逻辑。

捋一捋大概是这样:

  • 时刻关注自己的状况
  • 我发生了什么事情
  • 告诉父母我发生了什么事情
  • 得到孩子的近况
  • 对孩子的近况做出相应

来一波总结:

  • 父传子 props
  • 子传父 自定义事件 $emit
最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 213,928评论 6 493
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 91,192评论 3 387
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 159,468评论 0 349
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 57,186评论 1 286
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 66,295评论 6 386
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 50,374评论 1 292
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 39,403评论 3 412
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 38,186评论 0 269
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 44,610评论 1 306
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 36,906评论 2 328
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 39,075评论 1 341
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 34,755评论 4 337
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 40,393评论 3 320
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 31,079评论 0 21
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 32,313评论 1 267
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 46,934评论 2 365
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 43,963评论 2 351

推荐阅读更多精彩内容

  • 前言 组件是 vue.js最强大的功能之一,而组件实例的作用域是相互独立的,这就意味着不同组件之间的数据无法相互引...
    用技术改变世界阅读 2,161评论 1 3
  • 父子组件通信 1、父子组件通过prop传递数据 父组件可以将一条数据传递给子组件,这条数据可以是动态的,父组件的数...
    视觉派Pie阅读 1,263评论 0 18
  •   在前面的章节中小编已经为大家分享了什么是父组件和子组件,接下来小编将为大家分享父组件和子组件之间的通信 一、通...
    外星人_863d阅读 1,185评论 9 47
  • 本文章是我最近在公司的一场内部分享的内容。我有个习惯就是每次分享都会先将要分享的内容写成文章。所以这个文集也是用来...
    Awey阅读 9,437评论 4 67
  • 因为工作需要,我需要经常出差,时间久了,其实我是不喜欢出差的,尤其是一个人的行程,出差前需要考虑很多,装备行李,准...
    香芋与雨阅读 261评论 1 1