作用域插槽是vue中传递上下文数据的唯一方式,需子组件在上绑定属性,父组件通过v-slot参数解构接收,支持重命名、默认值和嵌套解构,但不可在解构中写函数或深层属性。

在 Vue 中,插槽本身不传数据;真正传递上下文数据的是作用域插槽。解构赋值不是用在普通插槽里,而是写在 v-slot(或简写 #)指令的参数中,用来接收子组件通过 <slot></slot> 绑定的响应式对象。
作用域插槽是前提:子组件必须主动“抛出”数据
只有子组件在 <slot></slot> 标签上绑定属性,父组件才能通过作用域插槽拿到数据。普通默认插槽或具名插槽不带数据,无法解构。
- 子组件中这样暴露数据:
<slot :user="userInfo" :loading="isLoading"></slot> - 父组件中才能写:
<template user loading>...</template> - 如果子组件没绑定任何属性,
{ user, loading }就是空对象,解构会失效或报错
解构写法:直接在 v-slot 参数里写对象解构
Vue 2.6+ 和 Vue 3 都支持,语法和 JS 解构一致,无需额外逻辑。
- 基础解构:
v-slot:default="{ user, items }"→ 直接访问user.name、items.length - 重命名字段:
v-slot:default="{ userInfo: user, list: items }"→ 把传入的userInfo改叫user - 设默认值:
v-slot:default="{ user = {}, count = 0 }"→ 防止子组件漏传导致渲染异常 - 嵌套解构:
v-slot:default="{ meta: { title, type } }"→ 适用于传入结构如{ meta: { title: '首页', type: 'home' } }
常见错误提醒:别在解构里写函数或表达式
解构只用于提取属性,不能执行逻辑。以下写法是错的:
- ❌
v-slot:default="{ onClick() { doSomething() } }"—— 这会定义新函数,破坏响应式,也违背插槽设计初衷 - ✅ 正确做法是子组件传方法:
<slot :onclick="handleClick"></slot>,父组件解构:v-slot:default="{ onClick }",然后直接@click="onClick" - ❌
v-slot:default="{ user.name }"—— 不能解构深层属性,只能一层对象解构,深层请用嵌套解构或点号访问
配合 v-for 或 v-if 保持模板干净
解构后,模板内可直接使用变量,配合条件或循环更直观:
<template list emptytext="暂无数据"></template><div v-if="list.length">{{ list.map(i => i.label).join(', ') }}</div><div v-else>{{ emptyText }}</div>
前端入门到VUE实战笔记:立即使用
在学习笔记中,你将探索 前端 的入门与实战技巧!











