1.defineProps:传递props (子组件接收数据

如果我们正在构建一个博客,我们可能需要一个表示博客文章的组件。我们希望所有的博客文章分享相同的视觉布局,但有不同的内容。要实现这样的效果自然必须向组件中传递数据,例如每篇文章标题和内容,这就会使用到 props。

defineProps:子组建把属性暴露给父组件父组件向子组件传值,子组件通过defineProps接收

案例一:

子组件:Comp.vue

子组件接收父组件传过来的title,然后渲染到页面

<template>
  <h4 style='color:red'>{{ title }}</h4>
</template>
<script setup>
defineProps(['title'])
</script>

//或者写成
<template>
  <h4 style='color:red'>{{ props.title }}</h4>
</template>
<script setup>
const props = defineProps(['title'])
</script>

父组件:

<template>
  <Comp :title=mss></Comp>
</template>
<script setup>
  import {ref} from 'vue'
  import Comp from './Comp.vue'
  const mss=ref(111)
</script>

案例二:

子组件:Comp.vue

子组件还可以加上类型的定义

<template>
  <p>拿到父组件传过来的:{{ son2 }}</p>
</template>
<script setup>
  //接收父组件传过来的
    defineProps({
      son2:String
    })
</script>

 父组件:

父组件传的值必须是string类型,否则会警告

<template>
  <Comp :son2=son2></Comp>
</template>

<script setup>
    import {ref} from 'vue'
    import Comp from './Comp.vue'
    const son2=ref('111')
</script>

案例三:

在实际应用中,我们可能在父组件中会有如下的一个博客文章数组

const posts = ref([
  { id: 1, title: 'My journey with Vue' },
  { id: 2, title: 'Blogging with Vue' },
  { id: 3, title: 'Why Vue is so fun' }
])

子组件:BlogPost.vue

<script setup>
 defineProps(['title'])
</script>

<template>
  <h4>{{ title }}</h4>
</template>

父组件:

<template>
	<BlogPost
  	v-for="item in titleData"
	  :key="item.id"
  	:title="item.title"
	></BlogPost>
</template>
<script setup>
import { ref } from 'vue'
import BlogPost from './BlogPost.vue'
  
const titleData = ref([
  { id: 1, title: 'My journey with Vue' },
  { id: 2, title: 'Blogging with Vue' },
  { id: 3, title: 'Why Vue is so fun' }
])
</script>


 shopadmin:

 到时候父组件可能会用到这些属性,用的时候传值给子组件

其实elementui自带的不是这种动态的,只不过封装起来方便使用,所以采用这种动态封装的方法

这些属性可以去翻阅elementui查看是干嘛的,是ui自带的,改成动态的了


2.defineExpose (子传父 

使用 <script setup> 的组件是默认关闭的——即通过模板引用或者 $parent 链获取到的组件的公开实例,不会暴露任何在 <script setup> 中声明的绑定。所以需要把子组建的属性暴露出去。

defineExpose:把子组建的属性暴露出去(我的理解是方法

案例一:

子组件定义自己的属性

<template>
  <div>子组件helloword.vue</div>
</template>

<script setup>
import { ref } from 'vue'
const count = ref(123456)
defineExpose({
  count
})
</script>

父组件接收:

在子组件上绑定ref(ref叫什么不重要,自定义的),然后初始值一般都传一个null,调用的时候调用子组件的value.属性就可以了

<template>
  <div @click="helloClick">父组件</div>
  <helloword ref="hello"></helloword>
</template>

<script setup>
import { ref } from 'vue'
import helloword from './components/HelloWorld.vue'
const hello = ref(null)
const helloClick = () => {
  console.log(hello.value.count) // 123456
}
</script>

案例二:

 子组件:MyComponent.vue

<template>
  <div>
  	<slot name="a" :text="sonText" :count="5"></slot>
	</div>
</template>
<script setup>
  import {ref} from 'vue';
  const sonText = ref('hello');
  const ran=ref(0);
  setInterval(()=>{
    sonText.value="oh"+ran.value;
    ran.value++;
  },1000)
  //给父组件传递
  defineExpose({
    sonText
  })
</script>

 这里补充一下slot,slot没有什么实质性意义,就是充当组件,接收模板片段。具有更多的属性,能够接收任意类型的 JavaScript 值作为 props。

组件的最大特性就是 重用 ,而用好插槽能大大提高组件的可重用能力
插槽的作用:父组件向子组件传递内容。

通俗的来讲,插槽无非就是在 子组件 中挖个坑,坑里面放什么东西由 父组件 决定

比如这里的name,text,count都是自定义的,写上slot就具有这个属性了。

 


 defineEmits:子组件向父组件传递事件

子组件去绑定事件:

 <el-button @click="$emit('edit')" />

//暴露出去
defineEmits(["edit"])

父组件调用:

<template>
    <AsideList :active="activetab == item.id" v-for="(item, index) in tabList"
             :key="index" @edit="handleEdit(item)">
//这里是edit是因为暴露出来的事件就叫edit,然后传进去item,这样点击之后能拿到item
                {{ item.name }}
    </AsideList>
</template>

<script setup>
import AsideList from './AsideList.vue';

//这样就能点击到子组件了
const handleEdit=(row)=>{
    console.log(row)
    console.log('点击')
}

Logo

旨在为数千万中国开发者提供一个无缝且高效的云端环境,以支持学习、使用和贡献开源项目。

更多推荐