【vue3入门】-【21】 组件传递数据

组件传递数据_Props

  • 静态数据传递

组件与组件之间不是完全独立的,而是有交集的,那就是组件与组件之间是可以传递数据的

传递数据的解决方案就是props

app.vue

<template>
  <!--主要要生效Header中的样式,需要删除main.json中默认的main.css样式-->
  <!--不需要再次引入,可以直接使用全局的组件-->
  <!-- <Header />   -->
  <!-- <Main />
  <Aside /> -->
  <parent />
</template>
<script>
// import Header from './pages/header.vue'
// import Main from './pages/main.vue'
// import Aside from './pages/aside.vue'
import parent from './components/parent.vue'

export default {
  components: {
    // Header,
    // Main,
    // Aside
    // 在最上层组件中引用父级组件
    parent
  }
}
</script>
<style></style>

parent.vue

<template>
    <h3>parent</h3>
    <!--在引用子级组件时可以跟上需要传递的参数值对,用以传递参数,而后被子级组件中的props中的数据接收-->
	<!--允许传递多个参数 空格间隔-->
    <child  title="parent数据"/>
</template>
<script>
import child from "./child.vue"


export default {
    data() {
        return {

        }
    },
    // 在父级组件中引用子级组件
    components: {
        child
    }
}
</script>
<style></style>

child.vue

<template>
    <h3>child</h3>
    <p>{{ title }}</p>
</template>
<script>

export default{
    data(){
        return{
            
        }
    },
    // 接收来自父级引用子级组件时传递的参数
    props:["title"] 
}
</script>
<style></style>
  • 动态数据传递

可以通过属性绑定的方式,动态传递数据

<template>
    <h3>parent</h3>
    <!--在引用子级组件时可以跟上需要传递的参数值对,用以传递参数,而后被子级组件中的props中的数据接收-->
    <child title="parent数据" />
    <!--动态传递数据-->
    <child :title="message" />
</template>
<script>
import child from "./child.vue"


export default {
    data() {
        return {
            message: "动态传递的数据"
        }
    },
    components: {
        child
    }
}
</script>
<style></style>

注意事项

props传递数据,只能从父级传递到子级,不能从子级传向父级

组件传递多种数据类型

通过props传递数据,不仅可以传递字符串类型的数据,还可以是其他类型,例如:数字、对象、数组等。

但实际上任何类型的值都可以作为props的值被传递

app.vue

<template>
  <!--主要要生效Header中的样式,需要删除main.json中默认的main.css样式-->
  <!--不需要再次引入,可以直接使用全局的组件-->
  <!-- <Header />   -->
  <!-- <Main />
  <Aside /> -->
  <parent />
</template>
<script>
// import Header from './pages/header.vue'
// import Main from './pages/main.vue'
// import Aside from './pages/aside.vue'
import parent from './components/parent.vue'

export default {
  components: {
    // Header,
    // Main,
    // Aside
    // 在最上层组件中引用父级组件
    parent
  }
}
</script>
<style></style>

parent.vue

<template>
    <h3>parent</h3>
    <!--在引用子级组件时可以跟上需要传递的参数值对,用以传递参数,而后被子级组件中的props中的数据接收-->
    <!--动态传递数据是使用属性绑定的方式-->
    <!--可以传递字符、数字、数组、对象等-->
    <child title="parent数据" :msg="message" :age="age" :names="names" :userInfo="user_info" />
</template>
<script>
import child from "./child.vue"


export default {
    data() {
        return {
            message: "动态传递的数据",
            age: 20,
            names: ["测试1", "测试2", "测试3"],
            user_info: {
                "name": "test1",
                "age": 30
            }
        }
    },
    components: {
        child
    }
}
</script>
<style></style>

child.vue

<template>
    <h3>child</h3>
    <p>{{ title }}</p>
    <p>{{ msg }}</p> <!--字符串类型-->
    <p>{{ age }}</p> <!--数字类型传递-->
    <ul>
        <li v-for="(value, index) of names">{{ value }}</li> <!--数组类型传递-->
    </ul>
    <p>{{ userInfo.name }}</p> <!--对象类型-->
    <p>{{ userInfo.age }}</p>
</template>
<script>

export default{
    data(){
        return{
            
        }
    },
    // 接收来自父级引用子级组件时传递的参数,需要和父级传递参数名同名
    props:["title","msg","age","names","userInfo"] 
}
</script>
<style></style>

组件传递props校验

vue组件可以更细致的声明对传入的props校验要求

  • 参数校验
<template>
    <h3>componentB</h3>
    <p>{{ title }}</p>
</template>
<script>
export default {
    data() {
        return {

        }
    },
    // 不带参数校验的父级参数接收方式
    // props: ["title"]

    // 带参数校验的父级参数接收方式
    props: {
        title: {
            // 传递非规定的类型数据时会存在console报错
            // type: Number
            // 也可以标记多种类型,只要满足其中一种就可以
            type: [String, Number, Array, Object]
        }
    }
}
</script>

参数类型传递错误时,存在console告警

image

  • 默认值校验
<template>
    <h3>componentB</h3>
    <p>{{ title }}</p>
    <p>{{ age }}</p>
    <p v-for="(value, index) of names">{{ value }}</p>
</template>
<script>
export default {
    data() {
        return {

        }
    },
    // 不带参数校验的传递方式
    // props: ["title"]

    // 带参数校验的传递方式
    props: {
        title: {
            // 传递非规定的类型数据时会存在console报错
            // type: String
            // 也可以标记多种类型,只要满足其中一种就可以
            type: [String, Number, Array, Object],
        },
        age: {
            type: Number,
            // 不传时,显示默认值,传递后显示传递的值
            // 注意:数字和字符串可以直接default,但是如果是数字和对象,必须通过工厂函数返回默认值
            default: 20
        },
        names: {
            type: Array,
            // 对于数组和对象类型的值,需要增加函数返回,不能直接返回
            default(){
                return ["空"]
            }

        }
    }
}
</script>
  • 必选项
<template>
    <h3>componentB</h3>
    <p>{{ title }}</p>
</template>
<script>
export default {
    data() {
        return {

        }
    },
    // 不带参数校验的传递方式
    // props: ["title"]

    // 带参数校验的传递方式
    props: {
        title: {
            // 传递非规定的类型数据时会存在console报错
            // type: String
            // 也可以标记多种类型,只要满足其中一种就可以
            type: [String, Number, Array, Object],
            // 必填项,如果父级没有传递对应参数时,console会存在告警
            required: true
        }
        }
    }

image

注意:props接收的数据是只读的,修改时会报错

<template>
    <h3>componentB</h3>
    <p>{{ title }}</p>
    <button @click="updatePropParam">修改props参数</button>
</template>
<script>
export default {
    data() {
        return {
        }
    },
    // 不带参数校验的传递方式
    // props: ["title"]

    // 带参数校验的传递方式
    props: {
        title: {
            // 传递非规定的类型数据时会存在console报错
            // type: String
            // 也可以标记多种类型,只要满足其中一种就可以
            type: [String, Number, Array, Object],
            required: true
        },
    },
    methods: {
        updatePropParam() {
            console.log(this.title);
            // 尝试修改props里面接口的参数数据时会存在异常报错,不允许修改父元素传递过来的数据
            this.title="新数据"
        }
    }
}
</script>

image

组件数据传递

之前讲解过组件之间的数据传递,propes和自定义事件两种方式

  1. props:父传子
  2. 自定义事件$.emit:子传父

除了上述方案,props也可以实现子传父,通过函数执行的方式可以传递子传父

app.vue

<template>
  <componentA />
</template>
<script>
import ComponentEvent from "./components/componentEvent.vue"
import Main from "./components/Main.vue"
import ComponentA from "./components/ComponentA.vue"

export default{
  components:{
    ComponentA
  }
}
</script>

componentEventA.vue

<template>
    <h3>ComponentA</h3>
	<!--使用子组件属性绑定的方式,实现执行函数参数的绑定-->
    <ComponentB title="父级静态参数" :onEvent="childParam" />
    <p>{{ childMessage }}</p>
</template>
<script>
import ComponentB from "./ComponentB.vue"
export default {
    data() {
        return {
            childMessage: ""
        }
    },
    components: {
        ComponentB
    },
    methods: {
        childParam(data) {
            console.log("接收来自子级的参数", data)
            this.childMessage = data
        }
    }
}
</script>

componentEventB.vue

<template>
    <h3>ComponentB</h3>
    <p>{{ title }}</p>
    <!--执行从父级传递过来的参数-->
    <p>{{ onEvent("子级传递的参数信息") }}</p>
</template>
<script>
export default {
    data() {
        return {
        }
    },
    props: {
        "title": String,
        // 接收父级的function函数,主要需要在父级使用绑定方式绑定此参数
        onEvent: Function
    }
}
</script>

image

以上内容出自
【【2023最新版】Vue3从入门到精通,零基础小白也能听得懂,写得出,web前端快速入门教程】 https://www.bilibili.com/video/BV1Rs4y127j8/?share_source=copy_web&vd_source=94c3d5330a46438059359e8dd2494fe9

posted @ 2024-05-07 23:00  PyAj  阅读(13)  评论(0编辑  收藏  举报