vue-父子组件通信

父组件向子组件传值-props

定义父组件app,定义子组件product-com,当子组件需要使用父组件的值—子组件中使用props接收父组件传递的值

  • 只接收使用数组接收多个值 props:[‘name’]
  • 可以定义需要的格式props:{name:String}
  • 可以限制类型、限制必要性、指定默认值
props:{
	name:{
        type:String, //类型
        required:true, //必要性
        default:'老王' //默认值
	}
}

备注:props是只读的,Vue底层会监测你对props的修改,如果进行了修改,就会发出警告,若业务需求确实需要修改,那么请复制props的内容到data中一份,然后去修改data中的数据。

案例

 <div id="app">
        <ul>
            
            <product-com v-for="(item,index) in protList" :product="item">product-com>
        ul>
    div>
<script>
    // 定义子组件---产品组件
    Vue.component('product-com',{
    	// 接收从父组件传递过来的变量
        // product就相当于父元素中数据对象item,所以item.title对应product.title
        props:['product'],
        template:`
  • 产品名称:{{product.title}}

    产品描述:{{product.des}}

    产品价格:{{product.price}}

  • `
    , }) //定义父组件---拥有产品数据 let app=new Vue({ el:"#app", data:{ // 假设有三个产品,将要显示在产品列表中 protList:[ { title:"产品一", price:"10", des:"产品描述一" }, { title:"产品二", price:"20", des:"产品描述二" }, { title:"产品三", price:"30", des:"产品描述三" } ] } })
    script>

    子组件向父组件传值-自定义事件

    定义父组件app,定义子组件school-com,在子组件列表中选择一个学校,在父组件中显示选中的学校,将子元素的数据传递给父元素—需要自定义触发事件实现数据传递。案例中使用@chiden-parent=schoolChange,change-parent为自定义事件,在子组件中使用this.$emit(‘chiden-parent’,schoolName)触发。当chiden-parent被触发时,会调用定义在父组件中的schoolChange事件。

    • 第一个参数—触发事件名
    • 第二个参数—子组件传递给父组件的参数

    案例

     <div id="app">
            <ul>
               <school-com @chiden-parent="schoolChange" v-for="(item,index) in schoolList" :school-name="item" :index="index" :key="index">school-com>
            ul>
            <h2>选中的学校是{{school}}h2>
        div>
    
    <script>
        //子组件
        Vue.component('school-com',{
            props:['index','schoolName'],
            template:`
  • {{index+1}}---学校名称:{{schoolName}}

  • `
    , methods:{ choose:function(schoolName){ // $emit传入事件名称,触发事件名称叫chiden-parent this.$emit('chiden-parent',schoolName) } } }) //父组件 let app=new Vue({ el:"#app", data:{ schoolList:["北大","清华","浙大","川大"], school:'' }, methods:{ // 触发父组件---school改变事件 schoolChange:function(data){ // 可以理解为因为$emit为自定义事件,第二个参数就会作为这个方法的第一个参数 this.school=data; } } })
    script>

    子组件向父组件传值-ref

    • 被用来给元素或子组件注册引用信息(id的替代者)
    • 应用在html标签上获取的是真实DOM元素,应用在组件标签上是组件实例对象(vc)

    在父组件中使用ref给子组件标识xxx


    在父组件中使用this.$refs.xxx获取组件

    父组件中绑定自定义事件到子组件,使用 this.$refs.xxx.$on() 这样写起来更灵活,比如可以加定时器。和中自定义事件是一样的用法,只是定义自定义事件时,不是在组件上直接写。触发子组件中atguigu事件事件,就是触发父组件中getStudentName事件

    案例

    Student子组件

    <template>
    	<div class="student">
    		<button @click="sendStudentlName">把学生名给Appbutton>
    	div>
    template>
    
    <script>
    	export default {
    		name:'Student',
    		data() {
    			return {
    				name:'张三',
    			}
    		},
    		methods: {
    			sendStudentlName(){
    				//触发Student组件实例身上的atguigu事件
    				this.$emit('atguigu',this.name,666,888,900)
    			}
    		},
    	}
    script>
    

    App父组件

    <template>
    	<div class="app">
    		
    		<Student ref="student"/>
    	div>
    template>
    
    <script>
    	import Student from './components/Student'
    
    	export default {
    		name:'App',
    		components:{Student},
    		data() {
    			return {
    				studentName:''
    			}
    		},
    		methods: {
    			getStudentName(name,...params){
    				console.log('App收到了学生名:',name,params)
    				this.studentName = name
    			},
    		},
    		mounted() {
    			this.$refs.student.$on('atguigu',this.getStudentName) //绑定自定义事件
    			// this.$refs.student.$once('atguigu',this.getStudentName) //绑定自定义事件(一次性)
    		},
    	}
    script>
    

    若想让自定义事件只能触发一次,可以使用once修饰符,或$once方法。
    触发自定义事件:this.$emit('atguigu',数据)
    绑定自定义事件使用this. r e f s . x x x . refs.xxx. refs.xxx.on()
    解绑自定义事件使用this.$off

    • 解绑一个自定义事件 this.$off(‘事件名称’)//字符串形式
    • 解绑多个自定义事件 this .$off([ ’ 事件1’, ‘事件2’]) //数组形式
    • 解绑所有自定义事件 this.$off() //无参
    mounted() {   
          console.log(this.$refs.student.$on('atguigu',this.getStudentName));  
      },
     
    beforeDestroy() {     
         this.$off("atguigu"); 
    }
    

    子组件向父组件传值-$parent(不利于维护)

    vue中有定义的$parent可以拿到子组件中的父组件,父组件要获取到子组件的数据,可以在子组件中获取到父组件,在调用父组件的函数,用函数传递参数

    案例

     <div id="app">
            <ul>
                <school-com v-for="(item,index) in schoolList" :school-name="item" :index="index" :key="index">school-com>
            ul>
            <h2>选中的学校是{{school}}h2>
        div>
      
      <script>
        // 子组件
        Vue.component('school-com', {
            props: ['index', 'schoolName', 'action'],
            template: `
  • {{index+1}}--学校名称:{{schoolName}}

  • `
    , // 这里可以看出是通过点击子组件来触发方法用来调用父组件的方法 methods: { choose: function (schoolName) { console.log(this.$parent) this.$parent.schoolChange(schoolName); } } }) //父组件 let app = new Vue({ el: "#app", data: { schoolList: ["北大", "清华", "浙大", "川大"], school: '' }, methods: { schoolChange: function (data) { this.school = data; } } })
    script>

    你可能感兴趣的:(Vue,vue.js,javascript,前端)