Ⅰ响应数据用法和父子通信
父组件:
<templete>
<!-- vue3 可以不用,单个盒子包裹起来 -->
<Children :fatherName="fatherName" @handle="fun" />
<div>{{name}}</div>
</templete>
<script>
import {ref,toRefs} from 'vue'
export default {
setup() {
const name=ref('张xx')
const fatherName=ref('pather')
function fun(num) {
console.log('接受子组件传递过来的值' + num)
}
const fun1=(num)=>{
console.log('接受子组件传递过来的值' + num)
}
return {
fun,
fun1,
fatherName,
...toRefs(name)
}
}
}
</script>
子组件
<templete>
<!-- vue3 可以不用,单个盒子包裹起来 -->
<span> {{ name }} </span>
<span> {{ age }} </span>
<span> {{ fatherName }} </span>
</templete>
<script>
import { reactive, toRefs } from 'vue'
export default {
props: {
fatherName: { type: String }
},
setup(props, { emit }) {
console.log(props.fatherName) // => 获取父组件 传递 子组件的参数
emit('handle', 123) // => 子组件 委托 父组件 调用方法接受参数
const state = reactive({ name: '张三', age: 18 })
return {
//...state => 会失去响应
...toRefs(state), // => 解构,正确写法,能获取到响应式数据
...toRefs(props)
}
}
}
</script>
3.在script标签上的setup的使用
<templete>
<span> {{ state.name }} </span>
<span> {{ state.age }} </span>
<span> {{ fatherName }} </span>
</templete>
<script setup>
import { reactive,defineProps,defineEmits } from 'vue'
const state = reactive({ name: '李四', age: 20 })
const fatherName = defineProps(['fatherName']) // => 获取父组件 传递 子组件的参数
const emit = defineEmits(['handle','delete'])
const change=()=>{
emit('handle', '子调用方法时传给父') // => 子组件 委托 父组件 调用方法接受参数
}
const delet=()=>{
emit('delete', '删除') // => 子组件 委托 父组件 调用方法接受参数
}
</script>
Ⅱ组件之间的通信
- 除了 【1】中 提到的嵌入 setup(props, { emit }) {} 形参 的 props 和 emit。
- 还有 :proxy.$parent【直接获取,或调用父组件方法】和 ref 【直接获取、或调用子组件方法】;
<templete>
<div>
<Children ref="children" />
</div>
</templete>
<script>
import { getCurrentInstance, ref } from 'vue'
export default {
setup() {
const { proxy } = getCurrentInstance()
console.log(proxy.$parent) // => 获取父组件的 return 中的所有对象 .
const children = ref(null)
// 变量名要和组件的ref值 对应 , 赋值必须为 ref(null) .
console.log(children.value) //=> 获取父组件的 return 中的所有对象 .
}
}
</script>
3.还有也可以通过 provide 、inject 传递方法和参数
provide 、inject一个接收一个传递,只能从父 => 子 => 孙 => (只能从上往下单向传递)
<script>
// ①父组件:
import { provide } from 'vue'
export default {
setup(){
const name = '张三'
provide('name ', name ) //向下传递
return { name }
}
}
// ②子组件:
import { inject } from 'vue'
export default {
setup(){
const getName = inject( 'name'); //接收父传递下来的
return { getName }
}
}
</script>
4、mitt 可以跨组件传值
4.1 npm安装 npm install --save mitt
4.2 注册挂载使用
在main.js里进行全局注册挂载
import mitt from 'mitt'
// vue3挂载到全局
app.config.globalProperties.$mitt = mitt();
1.在组件里使用
import {getCurrentInstance,onMounted } from "vue";
setup(){
const emitter1= ()=>{
const internalInstance = getCurrentInstance()
const emitter = internalInstance.appContext.config.globalProperties.emitter
return emitter
}
let bused=emitter1()
onMounted(()=>{
bused.emit("方法",'传值')
})
return{bused}
},
this.bused.emit("方法",'传值')
2.另一个组件
setup(){
const emitter1= ()=>{
const internalInstance = getCurrentInstance()
const emitter = internalInstance.appContext.config.globalProperties.emitter
return emitter
}
let bused=emitter1()
onMounted(()=>{
bused.on("方法",(值value)=>{
setTimeout(() => {
cur.value=value
}, 100);
})
})
return{bused}
},
this.bused.on("方法",(值value)=>{
setTimeout(() => {
this.cur=value
}, 100);
})