VUE3入门很简单(4)---组件通信(props)

🧩 Props 是啥?一句话说清楚

Props(属性)是父组件向子组件传递数据的单向通道。

你可以把它想象成:爸爸(父组件)给孩子(子组件)塞零花钱(数据),但孩子不能反过来改爸爸钱包里的钱(单向数据流)。这是 Vue 的"家规"!


✨ 基本用法:三步走,轻松上手

第一步:子组件声明接收哪些 props

在子组件中,使用 defineProps(组合式 API)或 props 选项(选项式 API)来声明它期望接收的数据。

html 复制代码
<!-- ChildComponent.vue -->
<script setup>
// 组合式 API 写法(推荐)
const props = defineProps({
  title: {
    type: String,
    required: true
  },
  count: {
    type: Number,
    default: 0
  }
})
</script>

<template>
  <div>
    <h2>{{ title }}</h2>
    <p>当前计数:{{ count }}</p>
  </div>
</template>

💡 小贴士:defineProps 是 Vue 3 宏(macro),不需要 import!

第二步:父组件传递数据

在父组件中,像 HTML 属性一样给子组件"赋值"。

vue 复制代码
<!-- ParentComponent.vue -->
<template>
  <ChildComponent title="欢迎来到 Vue 世界!" :count="userScore" />
</template>

<script setup>
import ChildComponent from './ChildComponent.vue'
const userScore = 99
</script>

注意:title 是字符串字面量,直接写;而 count 是变量,要用 :(即 v-bind)绑定。

第三步:跑起来!看看效果

页面会显示:

复制代码
欢迎来到 Vue 世界!
当前计数:99

搞定!是不是比点外卖还简单?


⚠️ 注意事项:这些坑我替你踩过了

1. 不要直接修改 props!

Vue 严格遵守单向数据流。如果你在子组件里尝试:

js 复制代码
// ❌ 千万别这么干!
props.count++ // 控制台会警告你!

2. 类型校验很重要

虽然可以只写 defineProps(['title', 'count']),但强烈建议加上类型和默认值。这样:

  • 防止传错类型(比如把数字当字符串传)
  • 团队协作时别人一看就知道要传什么
  • 减少 bug,提升代码健壮性

3. 对象/数组的默认值要用函数返回

因为对象和数组是引用类型,如果直接写 default: [],所有组件实例会共享同一个数组!

js 复制代码
// ✅ 正确写法
items: {
  type: Array,
  default: () => []
}

4. 命名规范:camelCase vs kebab-case

在 JS 中用驼峰(myProp),在模板中用短横线(my-prop):

vue 复制代码
<!-- 父组件模板 -->
<ChildComponent my-prop="hello" />

<!-- 子组件中 -->
defineProps({ myProp: String })

Vue 会自动帮你转换,但别搞混!


🎯 使用场景:什么时候该用 Props?

场景 是否适合用 Props
父组件控制子组件显示内容(如标题、列表数据) ✅ 非常适合
子组件需要配置(如按钮大小、主题色) ✅ 用 props 传配置项
多个层级嵌套传递数据(祖传 props) ⚠️ 可以,但超过 3 层建议用 provide/inject 或状态管理
子组件想改父组件的数据 ❌ 用 emit + 父组件响应

🛠️ 实战示例:一个可配置的卡片组件

html 复制代码
<!-- Card.vue -->
<script setup>
const props = defineProps({
  title: { type: String, required: true },
  content: { type: String, default: '' },
  theme: { 
    type: String, 
    validator: (value) => ['light', 'dark'].includes(value),
    default: 'light'
  }
})
</script>

<template>
  <div :class="`card card--${theme}`">
    <h3>{{ title }}</h3>
    <p>{{ content }}</p>
  </div>
</template>

<style scoped>
.card--dark { background: #333; color: white; }
.card--light { background: #f5f5f5; }
</style>

父组件使用:

vue 复制代码
<Card 
  title="今日任务" 
  content="学会 Props!" 
  theme="dark" 
/>

看,一个灵活又安全的组件就诞生了!


✅ 总结:Props 的黄金法则

  1. 单向流动:父传子,子不能改。
  2. 明确声明:类型、默认值、是否必填,一个都不能少。
  3. 命名规范:JS 驼峰,模板短横线。
  4. 复杂数据用函数默认值:避免引用共享。
相关推荐
Wenzar_5 分钟前
# D3.js实战进阶:从基础图表到交互式数据仪表盘的全流程构建在现代前端开发中,**数据可视化已成为提升用户体验的核心能力之一
java·javascript·python·信息可视化·ux
燐妤7 分钟前
前端HTML编程2:深入学习表单与表格
前端·学习·html5
菜鸟小码8 分钟前
MapReduce 编程模型详解:Mapper、Reducer、Driver 三大核心组件
大数据·javascript·mapreduce
朝阳3912 分钟前
react【实战】首页 -- 响应式导航栏(含带联动动画的搜索框)
前端·react.js·前端框架
贾铭26 分钟前
如何实现一个网页版的剪映(五)如何跳转到视频某一帧
前端·后端
Ruihong28 分钟前
手写 React 对比 VuReact 编译:真正省下来的是维护成本
vue.js·react.js·面试
林恒smileZAZ29 分钟前
CSS 滚动驱动动画(scroll-timeline):无 JS 实现滚动特效
前端·javascript·css
俺不会敲代码啊啊啊30 分钟前
el-table实现行拖拽(包含展开项)
前端·vue.js·typescript
LIO30 分钟前
React Router 极简指南(v6+)
前端·react.js
明月_清风32 分钟前
从 AST 视角看透前端工程化:一条编译管线如何串联起所有工具
前端