第八节:插槽简介及基本用法、剖析具名插槽、作用域插槽的使用

一. 简介及基本用法

1. 简介

(1). 什么时候使用插槽?

 插槽的使用过程其实是抽取共性、预留不同

 我们会将共同的元素、内容依然在组件内进行封装

 同时会将不同的元素使用slot作为占位,让外部决定到底显示什么样的元素;

(2).  如何定义插槽?

  在封装组件中,使用特殊的元素<slot>就可以为封装组件开启一个插槽;

  该插槽插入什么内容取决于父组件如何使用;

2. 基本使用 (匿名插槽)

(1). 基本用法

(2). 插槽默认内容 

 有时候我们希望在使用插槽时,如果没有插入对应的内容,那么我们需要显示一个默认的内容:当然这个默认的内容只会在没有提供插入的内容时,才会显示。

子组件

<template>
    <div>
        <h4>-------------我是MySlot1开始部分------------</h4>
        <slot>
            <h6 class="h6">我是插槽默认的内容哦,如果不填充,就显示我</h6>
        </slot>            
        <h4>-------------我是MySlot1结束部分------------</h4>    
    </div>
</template>

父组件

<template>
    <div>
        <my-slot1>
        <!--     <h4>我是填充内容1</h4>
            <a href="#">我是填充内容2</a>
            <h4>我是填充内容3</h4> -->
        </my-slot1>
    </div>
</template>

 

二. 具名插槽

1. 背景

 我们希望达到一个插槽对应一块内容的显示,这个时候我们就可以使用 具名插槽。

2. 基本用法

 具名插槽顾名思义就是给插槽起一个名字,<slot> 元素有一个特殊的 attribute:name属性;一个不带 name 的slot,会带有隐含的名字 default

 父组件在调用的时候,可以使用 v-slot 绑定名称从而实现对应,v-slot也可以缩写为 #

子组件

<template>
    <div class="nav-bar">
        <!-- <slot name="default"></slot> -->
        <div class="left">
            <slot name="left1"></slot>
        </div>
        <div class="center">
            <slot name="center1"></slot>
        </div>
        <div class="right">
            <slot name="right1"></slot>
        </div>
    </div>
</template>

父组件

<template>
    <div>
        <my-slot-cpn1>
            <template v-slot:left1>
                <button>左边按钮</button>
            </template>
            <template #center1>
                <button>我是中间按钮</button>
            </template>
            <template #right1>
                <button>右边按钮</button>
            </template>
        </my-slot-cpn1>    
    </div>
</template>

3. 动态插槽名

  可以通过 v-slot:[dynamicSlotName]方式动态绑定一个名称。

子组件

<template>
    <div class="nav-bar">
        <div class="addition">
            <slot :name="name"></slot>
        </div>
    </div>
</template>

<script>
    export default {
        data() {
            return {
                name:'ypf'
            };
        }
    }
</script>

父组件 

<template>
    <div>
        <my-slot-cpn1>
            <template #[name]>
                <button>ypf内容</button>
            </template>
        </my-slot-cpn1>    
    </div>
</template>

<script>
    import MySlotCpn1 from './MySlotCpn1.vue';
    export default {
        components: {
            MySlotCpn1
        },
        data() {
            return {
                name:'ypf'
            };
        }
    }
</script>

 

三. 作用域插槽

1. 背景

 我们希望父组件中 插槽位置 可以访问到子组件中的内容。默认情况下,如下图,是无法访问的。

2. 如何解决?

(1). 插槽 prop (子组件)

 通过绑定在 <slot> 元素上的 attribute 向外传递,这个attribute被称为插槽 prop。

<template>
    <div>
        <template v-for="(item,index) in myList" :key="index">
            <slot :item="item" :index="index">{{index}}</slot>
        </template>
    </div>
</template>

<script>
    export default {
        props: {
            myList: {
                type: Array,
                default: () => []
            }
        },
        data() {
            return {};
        }
    }
</script>

(2). 父组件中,可以使用带值的 v-slot 来定义我们提供的插槽 prop 的名字,从而获取插糟中的属性。 

代码分享:省略部分不关键代码

<template>
    <div>
        <!-- 2. 作用域插槽-->
        <!-- 2.1 通过v-slot:default声明调用 -->
        <show-names2 :myList="myList">
            <template v-slot:default="myInfo">
                <button>{{myInfo.item}}----{{myInfo.index}}</button>
            </template>
        </show-names2>
        <!-- 2.2 独占默认插槽的缩写语法  省略template -->
        <show-names2 :myList="myList">
            <template v-slot="myInfo">
                <button>{{myInfo.item}}----{{myInfo.index}}</button>
            </template>
        </show-names2>
        <!-- 2.3 可以直接加在组件上 -->
        <show-names2 :myList="myList" v-slot="myInfo">
            <button>{{myInfo.item}}----{{myInfo.index}}</button>
        </show-names2>
    </div>
</template>

<script>
    export default {
        data() {
            return {
                myList: ["ypf1", "ypf2", "ypf3", "ypf4"],
            };
        }
    }
</script>

3. 独占默认插槽缩写

(1). 如果我们的插槽是默认插槽default,那么在使用的时候 v-slot:default="myInfo"可以简写为v-slot="myInfo":

(2). 并且如果我们的插槽只有默认插槽时,组件的标签可以被当做插槽的模板来使用,这样,我们就可以将 v-slot 直接用在组件上:

<template>
    <div>
        <!-- 2. 作用域插槽-->
        <!-- 2.2 独占默认插槽的缩写语法  省略template -->
        <show-names2 :myList="myList">
            <template v-slot="myInfo">
                <button>{{myInfo.item}}----{{myInfo.index}}</button>
            </template>
        </show-names2>
        <!-- 2.3 可以直接加在组件上 -->
        <show-names2 :myList="myList" v-slot="myInfo">
            <button>{{myInfo.item}}----{{myInfo.index}}</button>
        </show-names2>
    </div>
</template>

<script>
    export default {
        data() {
            return {
                myList: ["ypf1", "ypf2", "ypf3", "ypf4"],
            };
        }
    }
</script>

4. 默认插槽和具名插槽混合

 如果我们有默认插槽和具名插槽,那么按照完整的template来编写。

子组件:

<template>
    <div>
        <template v-for="(item,index) in myList" :key="index">
            <!-- 插槽prop -->
            <slot :item="item" :index="index">{{index}}</slot>
            <!-- 具名插糟 -->
            <slot name="ypf"></slot>
        </template>
    </div>
</template>

父组件:

    <!-- 3. 多个插槽需要使用完整的template-->
        <show-names3  :myList="myList">
            <template v-slot="myInfo">
                <button>{{myInfo.item}}-{{myInfo.index}}</button>
            </template>
            <!-- 具名插糟 -->
            <template v-slot:ypf>
                <h2>我是ypf的插入内容</h2>
            </template>
        </show-names3>

 

 

 

 

 

 

!

  • 作       者 : Yaopengfei(姚鹏飞)
  • 博客地址 : http://www.cnblogs.com/yaopengfei/
  • 声     明1 : 如有错误,欢迎讨论,请勿谩骂^_^。
  • 声     明2 : 原创博客请在转载时保留原文链接或在文章开头加上本人博客地址,否则保留追究法律责任的权利。
 
posted @ 2021-09-26 16:27  Yaopengfei  阅读(1312)  评论(1编辑  收藏  举报