• Vue2 slot插槽学习笔记


    1. 前言

    回顾VUE 2插槽,插槽在日常开发过程中组件间的交互应用之广,此笔记以官方文档的插槽介绍为顺序进行回顾

    以官方docs为主 —— 链接地址

    • 笔记演示内容文件结构
    view
      slot
        custom
          index.vue //   插槽的 出口 —————— 子组件
        manage
          index.vue // 使用 custom 组件中插槽的 入口 —————— 父级组件
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6

    2. 插槽内容(默认插槽)与 后备内容

    • custom>index.vue 子组件 保持不变
    <template>
      <div class="custom">
        <!-- 定义一个插槽(挖一个坑,等着组件的使用者进行填充) -->
        <slot> 调用组件者,没有让内容进入插槽入口 </slot>
      </div>
    </template>
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    1. 使用custom组件者(父级组件)向插槽内传递具体结构时
    • manage>index.vue
    <template>
      <custom>进入了custom组件插槽入口</custom>
    </template>
    <script>
    import custom from '../custom';
    export default {
      components: {
        custom,
      },
    };
    </script>
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11

    manage>index.vue显示效果如下:(以HTML代码为内容)

    <div class="custom">进入了custom组件插槽入口div>
    
    • 1
    1. 使用custom组件者(父级组件)并未向插槽内传递内容时
    <template>
      <custom />
    </template>
    <script>
    import custom from '../custom';
    export default {
      components: {
        custom,
      },
    };
    </script>
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11

    **注意:**若custom>index.vue没有标签的插槽出口或有标签但不向其传递内容时,在调用它时,的写法都可以,但若要向调用子组件的插槽传递内容时,写法必须是

    manage>index.vue显示效果如下:(以HTML代码为内容)

    <div class="custom"> 调用组件者,没有让内容进入插槽入口 div>
    
    • 1

    可以发现,若使用custom组件者(父级组件)并未向插槽内传递内容时,子组件custom就会使用它的后备内容,即子组件标签包裹的内容

    3. 插槽编译作用域

    • 父组件custom>index.vue
    <template>
      <custom :no="1">
        {{ msg }}<br />
        号码:{{ no }}
      </custom>
    </template>
    <script>
    import custom from '../custom';
    export default {
      components: {
        custom,
      },
      data() {
        return {
          msg: '父组件进入子组件',
        };
      },
    };
    </script>
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 子组件custom>index.vue
    <template>
      <div class="custom">
        <!-- 定义一个插槽(挖一个坑,等着组件的使用者进行填充) -->
        <slot> 调用组件者,没有让内容进入插槽入口 </slot>
      </div>
    </template>
    <script>
    export default {
      data() {
        return {
          no: '2',
        };
      },
    };
    </script>
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15

    该插槽跟模板template的其它地方一样可以访问相同的实例 property (也就是相同的“作用域”),而不能访问 的作用域。

    这里的 no 会是 undefined,因为其 上的no内容是传递给子组件 的而不在 custom子组件内部定义的。

    4. 具名插槽

    具名插槽,根据名称我们大致可以推测出其插槽限定了名字

    在子组件的元素有一个特殊的属性name,以name来限定父组件中传递相同name的结构内容到子组件插槽中

    • 父组件manage>index.uve
    <template>
      <custom>
        <template slot="header"> 头部</template>
    
        没有具名,就传递给默认插槽咯
       <!-- <template slot="default"> 没有具名,就传递给默认插槽咯</template> 默认插槽上下两种写法--> 
    
        <template slot="footer">尾部 </template>
     </custom>
    </template>
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 子组件custom>index.vue
    <template>
      <div class="custom">
        <header>
          <slot name="header"></slot>
        </header>
        <main>
          <slot></slot>
        </main>
        <footer>
          <slot name="footer"></slot>
        </footer>
      </div>
    </template>
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13

    manage>index.vue显示效果如下:(以HTML代码为内容)

    <div class="custom">
        <header> 头部 header>
        <main> 没有具名,就传递给默认插槽咯 main> 
        <footer> 尾部 footer>
    div>
    
    • 1
    • 2
    • 3
    • 4
    • 5

    注意:我们对于header|main|footer,不可能重复写三个组件标签,这样会导致代码冗余度过大,影响解析效率,而Vue也考虑到了这点

    只需在template标签中或者其它标签(如h1|p等)使用slot属性,并赋予想要父组件内容传递到子组件中的插槽名为值,即可将内容插入对应的插槽

    当然,任何没有被包裹在带有 slot