前言:
slot插槽:所谓的插槽意思就是相当于占位符。
作用:把父组件中各种类型的内容展示在子组件中
分类:具名(命名)插槽,作用域插槽,解构插槽等等
总结:
(1)父组件向子组件通信传值—props,$attr(写在子组件中)
(2)父组件调用子组件的方法或属性—ref(写在父组件中的子组件上)
(3)父组件调用子组件的值,即子组件向父组件传值—emit(写在子组件中)
(4)父组件的内容展示在子组件中—slot(写在子组件中)
代码如下:
1.主体插槽slot:slot有默认的名字name=“defalut”,不写的时候则使用默认名字等价于
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width,initial-scale=1.0,maximum-scale=1.0,user-scalable=no" />
<meta name="format-detection" content="telephone=no,email=no,date=no,address=no"/>
<meta http-equiv="X-UA-Compatible" content="IE=edge,chrome=1"/>
<title>slot插槽</title>
</head>
<body>
<div id="app"></div>
<script src="../js/vue.js"></script>
<script>
//子组件
let SlotComponent={
template:`
<button type="button"
<slot></slot>
</button>
`
}
//父组件
let vue = new Vue({
el:"#app",
components:{
SlotComponent
},
template:`
<div>
<SlotComponent>按钮</SlotComponent>
<SlotComponent type="submit">提交</SlotComponent>
</div>
`
});
</script>
</body>
</html>
2.命名插槽(具名插槽):根据位置去替换内容,v-slot:指令可以缩写为#
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width,initial-scale=1.0,maximum-scale=1.0,user-scalable=no" />
<meta name="format-detection" content="telephone=no,email=no,date=no,address=no"/>
<meta http-equiv="X-UA-Compatible" content="IE=edge,chrome=1"/>
<title>命名(具名)插槽</title>
</head>
<body>
<div id="app"></div>
<script src="../js/vue.js"></script>
<script>
//子组件
let BaseLayout={
template:`
<div>
<header>
<slot name="header"></slot>
</header>
<slot></slot>
<footer>
<slot name="footer"></slot>
</footer>
</div>
`
}
//父组件
let vue = new Vue({
el:"#app",
components:{
BaseLayout
},
template:`
<BaseLayout>
<template #header>
<h3>我是页头</h3>
</template>
<div class="main">我是主体内容</div>
<template v-slot:footer>
<h3>我是页尾</h3>
</template>
</BaseLayout>
`
});
</script>
</body>
</html>
效果图:
3.作用域插槽:解决在父级插槽内容中访问子组件的数据,在子组件的上使用v-bind绑定一个属性
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width,initial-scale=1.0,maximum-scale=1.0,user-scalable=no" />
<meta name="format-detection" content="telephone=no,email=no,date=no,address=no"/>
<meta http-equiv="X-UA-Compatible" content="IE=edge,chrome=1"/>
<title>命名(具名)插槽</title>
</head>
<body>
<div id="app"></div>
<script src="../js/vue.js"></script>
<script>
//子组件
let BaseLayout={
template:`
<div>
<header>
<slot name="header" value="我是base-layout的头部"></slot>
</header>
<slot value="我是base-layuout的主体内容"></slot>
<footer>
<slot name="footer" value="我是base-layout的尾部"></slot>
</footer>
</div>
`
}
//父组件
let vue = new Vue({
el:"#app",
components:{
BaseLayout
},
template:`
<BaseLayout>
<template #header="slotProps">
<h3>{{slotProps.value}}</h3>
</template>
<template v-slot:default="slotProps">
<div class="main">{{slotProps.value}}</div>
</template>
<template v-slot:footer="slotProps">
<h3>{{slotProps.value}}</h3>
</template>
</BaseLayout>
`
});
</script>
</body>
</html>
效果图: