Vue 组件:$emitting 不适用于父子组件。我做错了什么?

Vue components: $emitting not working for parent-child components. What I'm doing wrong?

我有一个登录组件,我在 App.vue 主 vue 组件中调用它。 在登录 vue 中,当我单击任何必须在 vue js 路由器的帮助下激活另一个 vue 组件的按钮时,登录页面必须替换为该新的 vue 组件。所以我搜索了解决方案,但没有找到任何有效的解决方案。有趣的是...存在解决方案,但不知何故它们对我不起作用。我想我错过了什么,但究竟是什么?这是我试图找出不对的地方的第二天。有一件事有效但作为野蛮方法 - v-on:click.native 在登录 vue 中单击任何按钮后隐藏登录 vue,但这不是我想要的。

重要!我在一个 laravel 项目中使用 vue js。 Laravel 版本 8 和 vue js 版本 2

这是我的代码

Login.vue

<template>
<div id="login">
    <header-nav></header-nav>
    ...
                    <form>
                       ...
                            <label>
                                <input type="email" v-model="email" name="email" class="form-control" placeholder="email">
                            </label>
                        ...
                            <label>
                                <input type="password" v-model = "password" name="password" class="form-control" placeholder="password">
                            </label>
                        ...
                            <label>
                                <input type="checkbox">
                            </label>Remember Me
                        ...
                            <input type="submit" v-on:click.prevent="login" value="Login" class="btn float-right login_btn">
                       ...
                    </form>
                <div class="card-footer">
                    <div class="d-flex justify-content-center links">
                        Don't have an account?
                        <router-link to="register" v-on:click.prevent='hideLogin'>Sign Up</router-link>
                    </div>
                    <div class="d-flex justify-content-center">
                        <a href="#">Forgot your password?</a>
                    </div>
                </div>
</div>
</template>

<script>

import HeaderNav from "../layout/HeaderNav";

export default {
    name: "Login",
    components: {HeaderNav},
    data: () => {
        return {
            email: '',
            password: ''
        }
    },

    methods:{
        login(){
            this.$store.dispatch('users/login', {email: this.email, password: this.password})
        },

        hideLogin(){
            this.$emit('hideLogin');
            console.log('Hide login');
        }
    },

    template: HeaderNav
}

</script>  

App.vue

<template>
    <div>
        <login v-if="!isHidden" v-on:hideLogin="isHidden = true"></login>
        <router-view></router-view>
    </div>
</template>

<script>
    import Login from "./auth/Login";

    export default {
        name: "App",
        components: {
            Login
        },
        data () {
            return {
                isHidden: false
            }
        },
    }
</script> 

this post 中所述,您需要使用 click.native 才能使用 router-link 侦听 onclick 事件,例如

<router-link to="register" v-on:click.native='hideLogin'>Sign Up</router-link>

也就是说,另一个常见的选择是监听路由器本身的变化并在路由变化时关闭模型:

一种方法是更新 Login.vue 文件中的 hideLogin 逻辑:

router-link 中删除点击监听器并为 $route

添加一个监听器
export default {
    name: "Login",
    components: {HeaderNav},
    data: () => {
        return {
            email: '',
            password: ''
        }
    },

    methods: {
        login() {
            this.$store.dispatch('users/login', {email: this.email, password: this.password})
        },

        hideLogin() {
            this.$emit('hideLogin');
            console.log('Hide login');
        }
    },

    template: HeaderNav,
    
    watch: {
        $route() {
            this.hideLogin();
        }
    }
}

这样,当您导航到 register 路线(或任何其他路线)时,将调用 hideLogin 方法。


仅供参考,您可以将 v-on: 替换为 @,例如@click.native.