这是笔者在学习过程中为了增强对相关知识的掌握而记录的笔记,如果有幸帮到您笔者将十分开心。

笔者将子组件向父组件传值分为了两种情况:

  1. 子组件主动向父组件发送数据;
  2. 父组件主动获取子组件的数据。

区别是前者的触发条件在子组件内,而后者的触发条件在父组件里。

展示页面的效果如下所示:

情景一、子组件主动向父组件发送数据

$emit

在子组件内可以通过$emit('function', param)将数据发送出去。

$emit一共接收两个参数,其中function为定义在父组件中、由子组件触发的函数;param为子组件发送的数据。

子组件的代码如下:

<!-- 子组件 -->
<template>
    <div class="childArea">
        <div class="childTitle">This is child component</div>
        <el-button 
            type="warning"
            size="small" 
            plain 
            @click="sendMessage">
                子组件中的按钮
        </el-button>
    </div>
</template>

<script>
    export default {
        data() {
            return {
                game: '启动!!!'
            }
        },

        methods: {
            sendMessage() {
                // transmit为父组件定义的监听器
                // this.game为发送的数据
                this.$emit('transmit', this.game)
            }
        }
    }
</script>

<style lang="scss" scoped>
    .childArea {
        width: 200px;
        height: 200px;
        background-color: #fffef9;
        border-radius: 20px ;
        box-shadow: rgb(204, 219, 232) 3px 3px 6px 0px inset,
                    rgba(255, 255, 255, 0.5) -3px -3px 6px 1px inset;
        .childTitle {
            padding: 10px 0 30px 0;
            color: #fcaf17;
        }
    }
</style>

笔者给el-button绑定了一个点击事件sendMessage()。当按钮被点击时,子组件将会通过$emit向父组件发送function: 'transmit'param: 'this.data'两个参数。

父组件的代码如下:

<!-- 父组件 -->
<template>
    <div class="parentArea">
        <div class="title">This is parent component</div>
        <div class="content">原神 {{ message }}</div>
        <el-button type="danger" size="small" plain>父组件中的按钮</el-button>
        <!-- 通过v-on/@监听从子组件传入的数据 -->
        <childComponent class="child" @transmit="getMessage"/>
    </div>
</template>

<script>
    import childComponent from '@/views/test4.vue'

    export default {
        components: {
            childComponent
        },

        data() {
            return {
                message: '······'
            }
        },

        methods: {
            getMessage(data) {
                this.message = data; //data即为子组件发送的数据
            }
        }
    }
</script>

<style lang="scss" scoped>
    .parentArea {
        background-color: #feeeed;
        height: 400px;
        .title {
            font-size: 22px;
            color: #f15b6c;
        }
        .content {
            margin: 15px 0;
            font-size: 20px;
        }
        .child {
            margin: auto;
            margin-top: 30px;
        }
    }
</style>

在父组件导入的子组件中通过@transmit监听子组件传入的数据(transmit就是子组件$emit定义的参数function)。transmit对应的函数getMessage(data)的参数data即为子组件传入的数据。

点击“子组件中的按钮”后的效果如下所示:

(原始人认为,宇宙万法的那个源头,它是什么?它是原~原~对吧,所以,原神--启动!🚀) 

除了将$emit写在methods里,还可以像<el-button @click='$emit('transmit', game)'></el-button>这样将$emit直接写在组件模板表达式里。

并且,虽然在示例中传入了两个参数,但$emit也可以只传function这一个参数。如果需要在触发事件时附带一个特定的值,便需要再传入一个额外的参数param

情景二、父组件主动获取子组件的数据

有些时候可能我们需要点击父组件的按钮来获取子组件的数据,因此便有了情景二。

$refs

在父组件中,可以通过给子组件绑定ref来获取子组件的数据。

父组件代码(省略了css):

<!-- 父组件 -->
<template>
    <div class="parentArea">
        <div class="title">This is parent component</div>
        <div class="content">原神 {{ message }}</div>
        <el-button 
            type="danger" 
            size="small"
            plain 
            @click="showMessage">
                父组件中的按钮
        </el-button>
        <!-- 通过给子组件绑定ref属性获取子组件的数据 -->
        <childComponent class="child" ref="childRef"/>
    </div>
</template>

<script>
    import childComponent from '@/views/test4.vue'

    export default {
        components: {
            childComponent
        },

        data() {
            return {
                message: '······'
            }
        },

        methods: {
            showMessage() {
                this.message = this.$refs.childRef.game; //获取子组件的game变量
            }
        }
    }
</script>

首先给el-button绑定点击事件showMessage(),给子组件绑定ref='childRef'。当点击“父组件中的按钮”时,子组件的game被赋值给父组件的message。实现的效果与情景一一样,便不展示了。

$refs除了可以获取子组件的数据,还可以获取子组件的方法。先在子组件中定义如下方法:

然后在父组件的点击事件中通过$refs调用:this.$refs.childRef.notice()。效果如下所示:

当然,如果子组件的方法return了返回值,也能通过$refs获取到。还是notice方法里,返回了字符串'oo',然后在父组件里console.log(this.$refs.childRef.notice())。可以在右侧的控制台上看到已经打印出'oo'。因此,父组件也可以采取此方式获取子组件的数据。

其实也能通过$refs调用子组件的$emit来获取数据(父组件让子组件给自己发送数据),核心思路就是this.$refs.child.function,子组件childfunction里包含$emit。笔者就不展示啦。

最后,如果这边文章帮到您,不妨点一个小小的赞💖如果文章有误也恳请指正,阿里嘎多~

GitHub 加速计划 / vu / vue
80
16
下载
vuejs/vue: 是一个用于构建用户界面的 JavaScript 框架,具有简洁的语法和丰富的组件库,可以用于开发单页面应用程序和多页面应用程序。
最近提交(Master分支:4 个月前 )
73486cb5 * chore: fix link broken Signed-off-by: snoppy <michaleli@foxmail.com> * Update packages/template-compiler/README.md [skip ci] --------- Signed-off-by: snoppy <michaleli@foxmail.com> Co-authored-by: Eduardo San Martin Morote <posva@users.noreply.github.com> 6 个月前
e428d891 Updated Browser Compatibility reference. The previous currently returns HTTP 404. 6 个月前
Logo

旨在为数千万中国开发者提供一个无缝且高效的云端环境,以支持学习、使用和贡献开源项目。

更多推荐