-1

我是我的 VueJS 项目,我想在子导航菜单中添加自定义按钮。按钮列表应该是每个视图可定义的。我的第一次尝试是向主数据元素添加一个简单的属性,但这不起作用。比我找到了 mixins 的概念,但这也不起作用。这是我的概念:

// main.js
new Vue({
    //...
    mixins: [{
        data() {
            return {
                customHeaderButtons: [],
                test: '123'
            };
        }
    }],
})
<!-- TheHeader.vue -->
<template>
    <CHeader>
        <CSubheader class="px-3">
            <CBreadcrumbRouter class="border-0" />
            <CHeaderNav v-if="$root.customHeaderButtons" class="ml-auto" style="min-height: 0">
                <CHeaderNavLink v-for="item in $root.customHeaderButtons">
                    <CIcon :name="item.iconName" />
                </CHeaderNavLink>
                {{$root.customHeaderButtons}}
            </CHeaderNav>
            {{$root.test}} --> 123
        </CSubheader>
    </CHeader>
</template>

<!-- MyView.vue -->
<template>
    {{test}} --> ABC
</template>
<script>
export default {
    data() {
        return {
            customHeaderButtons: [{
                iconName: 'cil-save'
            }],
            test: 'ABC'
        }
    },
    // ...
}
</script>

你能告诉我,为什么值的变化MyView.vue没有应用于标题?在我的想象中,一旦用户导航到MyView.vue,标题栏中的文本应该切换到 ABC。

PS:TheHeader 是我模板的一部分。它不包含在视图本身中!

<!-- TheContainer.vue -->
<template>
  <div class="c-app">
    <TheSidebar/>
    <div class="c-wrapper">
      <TheHeader/> <-- The data from any child view should be sent here <---+
      <div class="c-body">                                                  |
        <main class="c-main">                                               |
          <CContainer fluid>                                                |
            <transition name="fade">                                        |   
              <router-view></router-view> <-- This is where MyView goes ----+
            </transition>
          </CContainer>
        </main>
      </div>
      <TheFooter/>
    </div>
  </div>
</template>
4

1 回答 1

0

我现在找到了一个受本教程启发的可行解决方案。但我不得不承认,这很复杂,这可能不是理想的灵魂。以下是它的工作原理:

首先,修改容器 vuew (您放置<router-view>标签的位置:将属性绑定添加到您的标题元素/组件(如 Boussadjra 所述)。然后,将事件侦听器添加到router-view,就像这样:

<template>
    <div class="c-app">
        <TheSidebar />
        <div class="c-wrapper">
            <TheHeader :customHeaderButtons="customHeaderButtons" />
            <div class="c-body">
                <main class="c-main">
                    <CContainer fluid>
                        <transition name="fade">
                            <router-view @setCustomHeaderButtons="setButtons"></router-view>
                        </transition>
                    </CContainer>
                </main>
            </div>
            <TheFooter />
        </div>
    </div>
</template>

在代码的 javascript 部分中,您必须实现该事件侦听器,并且您必须确保在每次页面更改后重置按钮:

export default {
    name: 'TheContainer',
    components: {
        TheSidebar,
        TheHeader,
        TheFooter
    },
    data() {
        return {
            customHeaderButtons: []
        }
    },
    methods: {
        setButtons(buttons) {
            this.customHeaderButtons = buttons;
        }
    },
    beforeRouteUpdate (to, from, next) {
        this.customHeaderButtons = [];
        next();
    }
}

现在,在您看来,您必须在事件中发出此created事件:

export default {
   data() {
       return {
           customHeaderButtons: [{
               iconName: 'cil-save'
           }],
       }
   },
    created() {
        this.$emit('setCustomHeaderButtons', this.customHeaderButtons);
    }
}

确保this.customHeaderButtons您事先在视图模型中定义。

还要确保,在您将多个视图相互嵌套的情况下,您必须重新发出事件。它不会自动冒泡!或者,您可以使用this.$parent.$emit()绕过嵌套级别。

如果您有更好、更简单的方法,请随时发布。

于 2020-03-30T16:18:47.073 回答