实现组件传值的流程
1-定义组件
2-注册组件
3-使用组件
定义组件
组件template内容和template选项之间连接的选择器 一定用id选择器,用其他选择器不起作用
注册组件
局部注册
components
全局注册
vue.component
使用组件
使用组件时单标记与双标记的区别:
单标记后的内容不被渲染,注意用多个组件时使用双标记
父组件向给子组件传递信息–组件的通信(props传值–翻译为属性传值)
props: property属性
思路:父组件中给子组件添加属性和值,子组件通过props选项接收属性,子组件使用即可
子组件校验props
将props改写为对象,对象中有各个选项(type/required/validator函数/default默认值),限制对应属性的校验内容
···//警告,prop不合法--msg属性校验失败,期待一个可以转换为数字的内容,目前得到的是字符串“hello my-child” [Vue warn]: Invalid prop: type check failed for prop "msg". Expected Number with value NaN, got String with value "hello my-child".
2.4 组件之间的事件传值(没有关系限制-父子之间,兄弟之间都可以)
emit 派发
思路:组件A给组件B传递一个函数,组件B触发这个函数,组件A收到来自组件B的内容
<!--父组件要做2件事情:
1.定义一个方法,用来让子组件派发,并接收子组件传来的值
2.给子组件传递一个事件:@自定义事件名="父组件定义的methods事件" 这样子组件可以拿到名字为my-event的事件-->
<my-child @my-event="getData"></my-child>
//子组件要做2件事情:
//1.通过emits选项接收来自父组件的事件
emits: ['父组件传来的事件名']
//2.派发来自父组件的事件(所谓的派发就是告知父组件根据自己的参数去执行对应的函数)
//在对应的方法体内:(实际参数要和父组件函数定义时的形参对应起来)
this.$emit('来自父组件的事件名',实际参数)
父向子传值 通过props传值
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Props传值</title>
</head>
<body>
<div id="app">
<!-- 使用组件在这里写 -->
<!-- 父组件 -->
<my-parent></my-parent>
</div>
<!-- 组件的视图层的定义 -->
<!-- 父组件 -->
<template id="parent">
<!-- 这个div是内容的根标签,在vue2中必须要加,vue3中可以不加 -->
<div>
<h2>我是父组件</h2>
<hr>
<!--flag msg是自定义属性,:flag="flag"右边的flag是父组件的数据 -->
<my-child msg="666" :flag="flag"></my-child>
</div>
</template>
<!-- 子组件的视图 -->
<template id="child">
<div>
<h3>我是子组件</h3>
<p>Parent给子组件的msg数据:{{msg}}</p>
<p>Parent给子组件的flag数据:{{flag?"flag为true":"flag为false"}}</p>
</div>
</template>
<script src="./lib/vue.global.js"></script>
<script>
// 子组件的定义
const Child ={
template:'#child',
//接收-props选项,表示接收的属性,属性名是字符串---多个属性用数组
//接收后就可以将"msg","flag"作为data中数据使用
props:["msg","flag"]
}
// 父组件的定义
const Parent ={
template:'#parent',
data(){
return{
flag:false
}
},
// 注册
components:{
//组件别名(帕斯卡命名法):组件名
MyChild:Child
}
}
const {createApp} = Vue;
const app =createApp({
data(){
return {
}
},
components:{
// 将Parent注册为布局组件
MyParent:Parent
}
})
app.mount("#app");
</script>
</body>
</html>
接受值设置
props:{
//msg是属性名,根据父组件传来的属性确定
//type表示数据类型,required:true表示必须传值
//default为默认值
msg:{
type:String,
required:true,
//父组件没有传递msg属性时
default:'默认值',
//添加校验函数,val是形参,自命名,表示msg的值
validator(val){
// if(val.length<=5){
// alert("父元素的msg属性传值位数少");
// }
//加return
return val.length>5;
}
},
flag:Boolean
},
父子组件互相传值 props emits
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>事件传值</title>
<style>
.child{
color:red;
border:2px dashed lightcoral;
}
</style>
</head>
<body>
<div id="app">
<!-- 使用组件在这里写 -->
<counter-container></counter-container>
</div>
<!-- 组件的视图层的定义 -->
<template id="counter">
<div class="child">
<!-- 点击时让count加上父组件传来的数 -->
<button @click="clickHandler">
{{title}}--步长为{{step}}
</button>
<p>
当前计数器的值为:{{count}}
</p>
</div>
</template>
<script src="./lib/vue.global.js"></script>
<script>
//定义组件Counter
const Counter ={
// 内容写在template选项内,省略<template></template>
template:'#counter',
//通过props选项接收父组件传来的属性名
props:["title","step"],
//通过emits选项接收父组件传来的事件名
emits:["plus"],
data(){
return{count:1}
},
methods:{
clickHandler(){
//this.step中的step是父组件传来的
this.count+=this.step;
//触发父组件传来的plus
//第一个参数为父组件传来的plus事件名,后面是参数,参数个数不限
this.$emit("plus",this.count)
}
}
}
//定义组件CounterContainer
//父组件给子组件传递1个函数,@自定义事件名 = "父组件的事件"
const CounterContainer ={
template:`<div class="parent">
<h2>这是计数器的父组件</h2>
<h2>接收来自子组件的值为:{{fromChild}}</h2>
<hr>
<p>以下是子组件的内容:</p>
<Counter :step="1" title="计数器1" @plus="plusHandler"></Counter>
</div>`,
components:{
Counter
},
data(){
return{
fromChild:1
}
},
methods:{
//val表示子组件传递1个值
plusHandler(val){
console.log("来自子组件的参数:"+val);
//将fromChild改为来自子组件的参数的值
this.fromChild =val;
}
}
}
const {createApp} = Vue;
const app =createApp({
data(){
return {
}
},
components:{
//注册
CounterContainer
}
})
app.mount("#app");
</script>
</body>
</html>
兄弟组件之间的传值
兄弟之间的传值 需要借助父组件作为桥梁