# 插槽
Vue 实现了一套内容分发的 API,将 <slot></slot>
元素作为承载分发内容的出口。
插槽(Slot)是 Vue 提出来的一个概念,正如名字一样,插槽用于决定将所携带的内容,插入到指定的某个位置,从而使模板分块,具有模块化的特质和更大的重用性。
插槽显不显示、怎样显示是由父组件来控制的,而插槽在哪里显示就由子组件来进行控制
插槽就是 Vue 实现的一套内容分发的 API,将元素作为承载分发内容的出口。
# 插槽slot
插槽内可以是任意内容。
<div id="app">
<child-component></child-component>
</div>
<script>
Vue.component("child-component", {
template: `
<div>
Hello,World!
<slot></slot>
</div>
`,
});
let vm = new Vue({
el: "#app",
data: {},
});
</script>
# 具名插槽
具名插槽,用于标记往哪个具名插槽中插入子组件内容。简单理解就是 给每一个 slot
一个name
属性,父组件中 使用子组件标签时用的v-slot:name
要跟子组件的name
匹配上,才会渲染出来,就是 默认插槽 !!
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<meta http-equiv="X-UA-Compatible" content="ie=edge" />
<title>Document</title>
<script src="lib/vue.js"></script>
</head>
<body>
<div id="app">
<com>
<template v-slot:header>
<h1>标题</h1>
</template>
<template v-slot:main>
<h2>内容</h2>
</template>
<template v-slot:footer>
<h3>底部内容</h3>
</template>
</com>
</div>
<script>
var vm = new Vue({
el: "#app",
data() {
return {
info: 1,
};
},
components: {
com: {
template: `
<div class="container">
<header>
<slot name="header"></slot>
</header>
<main>
<slot name="main"></slot>
</main>
<footer>
<slot name="footer"></slot>
</footer>
</div>
`,
},
},
});
</script>
</body>
</html>
# 编译作用域
父级模板里的所有内容都是在父级作用域中编译的;子模板里的所有内容都是在子作用域中编译的。
<div id="app">
{{ red }}
<com1></com1>
</div>
<script>
var vm = new Vue({
el: "#app",
data() {
return {
isActive: true,
red: "red",
};
},
components: {
com1: {
data() {
return {
info: "子组件内容",
};
},
template: "<h2>我是子组件{{ info }} {{ red }}</h2>", // Property or method "red" is not defined on the instance but referenced during render. Make sure that this property is reactive, either in the data option, or for class-based components, by initializing the property.
},
},
});
</script>
# 后备内容 当在组件里面没有写内容时在 slot 里面默认渲染的内容
<div id="app">
{{ red }}
<com1></com1>
</div>
<script>
var vm = new Vue({
el: "#app",
data() {
return {
isActive: true,
red: "red",
};
},
components: {
com1: {
data() {
return {
info: "子组件内容",
};
},
template: "<h2>我是子组件{{ info }}<slot>我是插槽的默认内容</slot></h2>",
},
},
});
</script>
# 作用域插槽
用作访问我们组件里面的属性
template 内可以通过临时变量 props 来访问来自子组件插槽的数据 msg
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<meta http-equiv="X-UA-Compatible" content="ie=edge" />
<title>Document</title>
<script src="lib/vue.js"></script>
</head>
<body>
<div id="app">
<com :list="list">
<template v-slot:default="slotProps">
<li @click="slotProps.item.age++">{{slotProps.item.name}}{{slotProps.item.age}}</li>
</template>
</com>
</div>
<script>
var vm = new Vue({
el: "#app",
data() {
return {
list: [
{
name: "张三",
age: 40,
},
{
name: "李四",
age: 40,
},
],
};
},
components: {
com: {
props: ["list"],
data() {
return {};
},
template: `
<ul><slot v-for="item in list" :item = "item"></slot></ul>
`,
},
},
});
</script>
</body>
</html>