返回一个reactive或readonly包裹的proxy对象
其实就是将一个proxy对象转化成普通对象
<template> <div> </div> </template> <script> import {ref,reactive,toRaw,readonly,shallowReactive,shallowReadonly,toRefs} from 'vue' export default { name: 'App', setup (props,context) { //这是一个普通对象 const obj={ a:1, b:2 } const proxyObj=reactive(obj)//转换成代理对象 console.log(proxyObj)//打印成一个proxy对象 const newObj=toRaw(proxyObj)//转换成普通对象 console.log(newObj)//打印成一个普通对象 //包装前和转换后其实是相等的 console.log(newObj===obj)//true return { } } } </script> <style> </style>
返回包裹对象的本身,和原对象是相等的
这种包含是浅度(shallow)的不是深度(deep)的
<template> <div> </div> </template> <script> import {ref,reactive,toRaw,markRaw,readonly,shallowReactive,shallowReadonly,toRefs} from 'vue' export default { name: 'App', setup (props,context) { //这是一个普通对象 const obj={ a:1, b:2 } const rawObj=markRaw(obj)//包裹成普通对象 console.log(obj)//打印一个普通对象 console.log(rawObj)//依然打印一个普通对象 console.log(obj===rawObj)//true const proxyObj=reactive(rawObj)//包装成proxy对象 console.log(proxyObj)//但打印的依然还是普通对象 return { } } } </script> <style> </style>
钩子参看前篇,略
父组件作为数据的提供方:provider
Son.vue
<template> <h1>{{sonName}} i am son component</h1> <h1>{{directsonname}} directly provider name</h1> </template> <script> export default { name: 'Son', inject:['sonName','directsonname'], setup(){ return { } }, } </script> <style scoped> </style>
Father.vue
<template> <h1>{{fathername}} i am fahter component</h1> <hr/> <Son></Son> </template> <script> import Son from './Son.vue' export default { name: 'Father', setup(){ const sonName='sonname' return { sonName } }, provide:{ sonName: 'sonName' }, inject:['fathername'], components:{ Son } } </script> <style scoped> </style>
App.vue
<template> <div> <Father ></Father> </div> </template> <script> import {ref,reactive} from 'vue' import Father from './components/Father.vue' export default { name: 'App', setup (props,context) { const myname=ref('Fathername') return { myname } }, provide:{ fathername:'Fathername', directsonname:'directSonName' }, components:{ Father, } } </script> <style> </style>
Fther.vue
<template> <h1>{{name}}</h1> <hr/> <h1>{{age}}</h1> <hr/> <h1>{{hobby}}</h1> <hr/> <h1>{{career}}</h1> <hr/> <Son></Son> </template> <script> import Son from './Son.vue' export default { name: 'Father', inject:['name','age','hobby','career'], setup(){ return { } }, components:{ Son } } </script> <style scoped> </style>
App.vue
<template> <div> <Father ></Father> </div> </template> <script> import {ref,reactive,provide} from 'vue' import Father from './components/Father.vue' export default { name: 'App', setup (props,context) { provide('name','zhangsan') provide('age',30) provide('hobby','sing') provide('career','programmer') return { } }, components:{ Father, } } </script> <style> </style>
推荐用法(inject也携程组合式的):
Father.vue
<template> <h1>{{name}}</h1> <hr/> <h1>{{age}}</h1> <hr/> <h1>{{hobby}}</h1> <hr/> <h1>{{career}}</h1> <hr/> <Son></Son> </template> <script> import Son from './Son.vue' import {inject } from 'vue' export default { name: 'Father', // inject:['name','age','hobby','career'], setup(){ const name=inject('name','国泰民安') const age=inject('age','100') const hobby=inject('hobby','daqiu') const career=inject('career','dadouduo') return { name, age, hobby, career } }, components:{ Son } } </script> <style scoped> </style>
app.vue
<template> <div> <Father ></Father> </div> </template> <script> import {ref,reactive,provide} from 'vue' import Father from './components/Father.vue' export default { name: 'App', setup (props,context) { provide('name','zhangsan') provide('age',30) provide('hobby','sing') provide('career','programmer') return { } }, components:{ Father, } } </script> <style> </style>
使用ref或reactive包裹
Father.vue
<template> <h1>{{name}}</h1> <hr/> <h1>{{age}}</h1> <hr/> <h1>{{hobby}}</h1> <hr/> <h1>{{career}}</h1> <hr/> <Son></Son> </template> <script> import Son from './Son.vue' import {inject } from 'vue' export default { name: 'Father', // inject:['name','age','hobby','career'], setup(){ const name=inject('name','国泰民安') const age=inject('age','100') const hobby=inject('hobby','daqiu') const career=inject('career','dadouduo') return { name, age, hobby, career } }, components:{ Son } } </script> <style scoped> </style>
App.vue
<template> <div> <Father ></Father> <button @click="changeNumber">改变</button> </div> </template> <script> import {ref,reactive,provide} from 'vue' import Father from './components/Father.vue' export default { name: 'App', setup (props,context) { const myname=ref('张小三') provide('name',myname) provide('age',30) provide('hobby','sing') provide('career','programmer') setTimeout(()=>{ myname.value='王大拿' },2000) const changeNumber=()=>{ myname.value='郭晶晶' } return { changeNumber } }, components:{ Father, } } </script> <style> </style>
<template> <h1>{{name}}</h1> <hr/> <h1>{{age}}</h1> <hr/> <h1>{{hobby}}</h1> <hr/> <h1>{{career}}</h1> <hr/> <button @click="changeName">改变姓名</button> <Son></Son> </template> <script> import Son from './Son.vue' import {inject } from 'vue' export default { name: 'Father', // inject:['name','age','hobby','career'], setup(){ const name=inject('name','国泰民安') const age=inject('age','100') const hobby=inject('hobby','daqiu') const career=inject('career','dadouduo') const changeName=inject('changeName') return { name, age, hobby, career, changeName } }, components:{ Son } } </script> <style scoped> </style>
App.vue
<template> <div> <Father ></Father> </div> </template> <script> import {ref,reactive,provide,readonly} from 'vue' import Father from './components/Father.vue' export default { name: 'App', setup (props,context) { const myname=ref('张小三') provide('name',readonly(myname)) provide('age',30) provide('hobby','sing') provide('career','programmer') const changeName=()=>{ myname.value='郭小晶' } provide('changeName',changeName) return { } }, components:{ Father, } } </script> <style> </style>
Father.vue
<template> <h1>{{name}}</h1> <Son></Son> </template> <script> import Son from './Son.vue' import {ref,inject } from 'vue' export default { name: 'Father', data(){ return{ name:'zhangan' } }, methods:{ changeName(){ this.name='lisi' } }, // inject:['name','age','hobby','career'], setup(){ return { } }, components:{ Son } } </script> <style scoped> </style>
App.vue
<template> <div> <Father ref="father"></Father> <hr/> <button @click="changename">改变名称</button> </div> </template> <script> import {ref,reactive,provide,readonly} from 'vue' import Father from './components/Father.vue' export default { name: 'App', setup (props,context) { return { } }, methods:{ changename(){ this.$refs.father.changeName() } }, components:{ Father, } } </script> <style> </style>
Father.vue
<template> <h1>{{name}}</h1> <!-- 这里的ref的名字要和setup里面的名字一致--> <h1 ref="mychild">张三</h1> <button @click="changeMyName">改变名字</button> <Son></Son> </template> <script> import Son from './Son.vue' import {ref,inject } from 'vue' export default { name: 'Father', setup(){ //默认必须要ref一个null值,注意这里的child要和组件上的ref的名字一致 const mychild=ref(null) const changeMyName=()=>{ //通过mychild拿到子组件节点,并进行dom操作 mychild.value.innerText='lisi' } return { mychild, changeMyName } }, components:{ Son } } </script> <style scoped> </style>
App.vue
<template> <div> <Father ref="father"></Father> </div> </template> <script> import {ref,reactive,provide,readonly} from 'vue' import Father from './components/Father.vue' export default { name: 'App', setup (props,context) { return { } }, methods:{ }, components:{ Father, } } </script> <style> </style>
另外一例
Father.vue
<template> <!-- 这里的ref的名字要和setup里面的名字一致--> <h1 >{{name}}</h1> <button @click="changeMyName">改变名字</button> <Son></Son> </template> <script> import Son from './Son.vue' import {ref,inject } from 'vue' export default { name: 'Father', setup(){ const name=ref('zhangsan') const changeMyName=()=>{ name.value='lilaosi' } return { name, changeMyName } }, components:{ Son } } </script> <style scoped> </style>
App.vue
<template> <div> <Father ref="father"></Father> <button @click="setname">设置名字</button> </div> </template> <script> import {ref,reactive,provide,readonly} from 'vue' import Father from './components/Father.vue' export default { name: 'App', setup (props,context) { const father=ref(null) const setname=()=>{ father.value.changeMyName() } return { father, setname } }, methods:{ }, components:{ Father, } } </script> <style> </style>