$slots为空通常是因为子组件未定义插槽出口或父组件未正确提供内容。需检查子组件是否有标签、v-if是否移除了插槽、父组件是否用合法方式传入内容、具名插槽name是否严格匹配,以及作用域插槽数据传递与解构是否一致。

子组件里 $slots 是空对象?先看是否漏定义插槽出口
子组件没写 <slot></slot> 标签,$slots 就一定是空的——它不是“自动收集父组件传的内容”,而是 Vue 根据你写的 <slot></slot> 节点,把对应内容挂载到 $slots 上。没出口,自然没入口。
- 检查子组件模板中是否至少有一个
<slot></slot>或<slot name="xxx"></slot> - 注意:不能只在 JS 里声明 props 或 emit,插槽出口必须显式出现在
<template></template>中 - 如果用了
v-if包裹整个<slot></slot>(比如<slot v-if="show"></slot>),$slots也会为空——因为出口被移除了,不是“不渲染”,是根本没注册
$slots.default 为 undefined?确认父组件写法是否合法
父组件没用合法方式提供默认插槽内容,$slots.default 就不会存在。常见错误是把内容写在自闭合标签里,或误当 prop 传。
- ❌ 错误:
<mycomp title="hello"></mycomp>—— 这里的title是 prop,不是插槽内容 - ❌ 错误:
<mycomp></mycomp>—— 没内容,$slots.default不存在(不是[],是undefined) - ✅ 正确:
<mycomp><p>hi</p><div class="aritcle_card flexRow artxards"> <div class="artcardd flexRow"> <a class="aritcle_card_img" rel="nofollow" href="/ai/1858" title="一键抠图"><img src="https://img.php.cn/upload/ai_manual/000/969/633/68b6c673e1063851.png" alt="一键抠图" onerror="this.onerror='';this.src='/static/lhimages/moren/morentu.png'" ></a> <div class="aritcle_card_info flexColumn"> <a rel="nofollow" href="/ai/1858" title="一键抠图" class="overflowclass">一键抠图</a> <p class="overflowclass">在线一键抠图换背景</p> </div> <a rel="nofollow" href="/ai/1858" title="一键抠图" class="aritcle_card_btn flexRow flexcenter"><b></b><span>下载</span> </a> </div> </div></mycomp>→$slots.default是一个函数数组(Vue 3)或 vnode 数组(Vue 2) - Vue 3 中,即使只传文本,也要包裹在
<template></template>或普通标签里;纯文本节点需用<template>text</template>才能被识别为插槽内容
具名插槽 $slots.header 不存在?name 大小写和拼写必须完全一致
Vue 的插槽匹配是严格字符串比对,name="Header" 和 #header 不匹配,name="head" 和 #header 也不匹配。
- 子组件写
<slot name="header"></slot>,父组件就必须用<template></template>或<template v-slot:header></template> - 注意:空格、连字符、下划线都算不同 name;
name="user-info"≠#userinfo - Vue 3 中,动态插槽名如
v-slot:[slotName],要求slotName不能为null或undefined,否则整个插槽块会被忽略
作用域插槽数据拿不到?检查传递和解构是否闭环
作用域插槽的数据流是「子组件传 → 父组件收」,两边都要对得上。常见断点在子组件没传、父组件解构错、或提前访问未定义字段。
- 子组件必须用
v-bind显式绑定:<slot :row="currentRow" :index="idx"></slot> - 父组件接收时,名字要跟绑定的 key 一致:
<template row index></template>,不是{ data }或props - 如果
row可能为null,别直接写v-if="row.id"——改用v-if="row?.id"(Vue 3)或v-if="row && row.id"(Vue 2) - 子组件中若用
setup()+defineSlots(Vue 3.3+),需确保类型声明与运行时传递一致,否则 TS 提示不准但运行时可能丢失字段
$slots 属性值,再反推哪一环没对上。










