【问题标题】:Use named slots inside grand-child component在孙子组件中使用命名插槽
【发布时间】:2019-02-02 01:14:00
【问题描述】:

我创建了一个全局组件,扩展了 Bootstrap Vue Table 组件,为每个名为 VTable 的表制作了一个自定义模板。

Bootstrap Vue Table 组件可以使用命名槽来自定义数据渲染。

<template>
  <div>
    <b-table
      :items="items"
      :fields="fields"
      ...
    >
    </b-table>
  </div>
</template>

<script>
  import Table from 'bootstrap-vue/es/components/table/table';

  export default {
    name: 'Vtable',
    extends: Table,
    ...
  };
</script>

我在另一个使用新的自定义 HTML 标记的表格组件中使用全局表格组件。

<v-table
  v-if="items"
  :items="items"
  :fields="fields"
  ...
>
  <template
    slot="timestamp"
    slot-scope="data"
  >
    ...
  </template>
  <template
    slot="row-details"
    slot-scope="row"
  >
    ...
  </template>
</v-table>

问题是VTable组件中使用的命名槽没有显示在子组件内部。

我还尝试在全局组件中创建一个自定义命名槽

<template>
  <div>
    <b-table
      ...
    >
      <slot name="customRendering"/>
    </b-table>
  </div>
</template>

并像使用它

<v-table
  ...
>
  <template slot="customRendering">
    <template
      slot="timestamp"
      slot-scope="data"
    >
      ...
    </template>
    <template
      slot="row-details"
      slot-scope="row"
    >
       ...
    </template>
  </template>
</v-table>

没有成功

这可以简单地使用在孙子组件中定义的命名插槽,还是完全不可能? 我还想循环遍历customRendering 槽值以动态重新创建 Bootstrap Vue 表槽。

【问题讨论】:

    标签: javascript vue.js vuejs2 vue-component


    【解决方案1】:

    vtable 组件中,您可以定义要传递的插槽。

    所以如果你有一个组件 my-component 有一个孩子 -> vtable 扩展 -> btable...

    您可以在 vtable 组件中定义要传递的插槽

    <template
      slot="row-details"
      slot-scope="row"
    >
        <slot name="row-details"/>
    </template>
    

    这是https://jsfiddle.net/eywraw8t/308324/的一个简单示例

    您可能需要为每个插槽进行设置。如果你想动态地传递它们(不知道它们的名字),渲染函数会更好,因为你可以遍历父级发送的所有槽,并将它们传递给子级。

    文档:https://vuejs.org/v2/guide/render-function.html#Slots

    具有渲染功能的组件示例,将向下传递作用域插槽

    const Bar = Vue.component('vtable', {
      render(h) {
        const children = Object.keys(this.$slots).map(slot => h('template', { slot }, this.$slots[slot]))
        return h('wrapper', [
          h('foo', {
            attrs: this.$attrs,
            on: this.$listeners,
            scopedSlots: this.$scopedSlots,
          }, children)
        ])
      }
    });
    

    【讨论】:

    • 使用渲染功能,我需要在子 comp 里面做吗?我的渲染函数从未被调用,我无法获得 this.$slot.default
    • 默认用于未命名的插槽,您应该使用this.$slot.timestamp 或者更确切地说this.$slots.map()... 我已经更新了答案以显示示例
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2021-08-25
    • 1970-01-01
    • 2021-02-06
    • 2019-04-25
    • 2022-11-14
    • 2018-11-05
    • 2018-08-19
    相关资源
    最近更新 更多